0

In one controller I got a method that I want to refactor to share with other controllers. At the same time, I'm passing it to the callback before_action.

app/models/meal_controller.rb

def check_for_user
  token = request.headers[:token]
  if token.nil?
    render json: "Unathorized", status: 401
  elsif @meal.user.auth_code != token
    render json: "Forbidden", status: 403
  end 
end

So my approach was move check_for_userto the ApplicationController and modify it as follows:

  def check_for_user(item)
    token = request.headers[:token]
    if token.nil?
        render json: "Unathorized", status: 401
    elsif item.user.auth_code != token
        render json: "Forbidden", status: 403
    end 
  end

And back to the MealController, create a other "dummy" method without params and call the check_for_user.

def check_for_user_meal
  check_for_user(@meal)
end

My question is: is there a better way to refactor this code?

Thanks in advance.

tehAnswer
  • 790
  • 1
  • 9
  • 24

2 Answers2

3

I have no problem with your code going in ApplicationController, if it's only a few lines of code.

However, I'd suggest you check the difference between 401 and 403. The main difference is that 401 means there was an error with your authentication attempt, please try again; whereas 403 means you are trying to authenticate in a way that is incorrect so please stop trying.

With a username/password user input, 401 makes sense because its likely the user has mistyped something.

But with tokens, another attempt is only going to get the same result. So both no token and the wrong token should result in a 403 error.

So I'd refactor you code like this:

def request_token
  request.headers[:token]
end

def check_for_user(item)
  if request_token.nil? || item.user.auth_code != request_token
    render json: "Forbidden", status: 403
  end
end 
Community
  • 1
  • 1
ReggieB
  • 7,658
  • 3
  • 35
  • 42
0

You could create a module so the method would be available across the application.

Leon
  • 1,108
  • 2
  • 15
  • 37