Индивидуальный отладчик 401 неавторизованный ответ
Я работаю над JSON-интерфейсом для моего приложения Rails 3.1. Я хотел бы предоставить настраиваемый ответ об ошибке вместо значения по умолчанию:
{"error":"You need to sign in or sign up before continuing."}
Мой API-контроллер включает в себя запрос before_filter на authenticate_user!
, который является тем, что передает этот ответ JSON.
Во время поиска я натолкнулся на qaru.site/info/369735/..., в котором эта запись в викторине. К сожалению, запись в вики не достаточно подробно для меня, чтобы понять, что она говорит мне. В частности, я понятия не имею, где я должен помещать этот код таким образом, чтобы Devise/Warden знал, чтобы вернуть то, что я хочу вернуть.
Из комментариев по другому вопросу SA это звучит так, как будто мне не нужно вызывать custom_failure!
, так как я использую версию Devise выше 1.2 (1.4.2 для конкретной). Однако запись wiki не объясняет, куда должен идти вызов render
, так что authenticate_user!
знает, как использовать это вместо собственного вызова рендеринга.
Где идет этот вызов render
?
Изменить: Я не просто пытаюсь изменить само сообщение (a la the devise en.yml
config); Я пытаюсь изменить фактический формат ответа. В частности, я хочу вернуть это:
render :text => "You must be logged in to do that.", :status => :unauthorized
Ответы
Ответ 1
Для справки в случае, если кто-то еще наткнется на этот вопрос, когда вы ищете, как настроить ответ json-ошибки при неудачной попытке входа в систему с помощью Devise, ключ должен использовать вашу собственную реализацию FailureApp
. (Вы также можете использовать этот подход для переопределения некоторого поведения перенаправления.)
class CustomFailureApp < Devise::FailureApp
def respond
if request.format == :json
json_error_response
else
super
end
end
def json_error_response
self.status = 401
self.content_type = "application/json"
self.response_body = [ { message: i18n_message } ].to_json
end
end
и в devise.rb
найдите раздел config.warden
:
config.warden do |manager|
manager.failure_app = CustomFailureApp
end
Некоторые связанные данные:
Сначала мне показалось, что мне придется переопределить Devise:: SessionsController, возможно, используя параметр recall
, переданный в warden.authenticate!
, но как упоминалось здесь, "отзыв не вызывается для запросов API, только для навигационных. Если вы хотите настроить код статуса http, вы будете иметь лучше удачи сделать это на уровне приложений с ошибкой".
Также https://github.com/plataformatec/devise/wiki/How-To%3a-Redirect-to-a-specific-page-when-the-user-can-not-be-authenticated показывает что-то очень похожее для перенаправления.
Ответ 2
Если вы просто хотите изменить текст, отображаемый с сообщением об ошибке, я считаю, что вы можете просто отредактировать файл локали (/config/locales/devise.en.yml).
RailsCast в этом разделе также может оказаться полезным, если вы хотите получить более подробную информацию. Вы можете найти его на http://railscasts.com/episodes/210-customizing-devise