class Devise::FailureApp
to the default_url.
page based on current scope and mapping. If no scope is given, redirect
any strategy or hook. Responsible for redirect the user to the sign in
Failure application that will be called every time :warden is thrown from
def self.call(env)
def self.call(env) @respond ||= action(:respond) @respond.call(env) end
def self.default_url_options(*args)
def self.default_url_options(*args) ApplicationController.default_url_options(*args) end
def attempted_path
def attempted_path warden_options[:attempted_path] end
def http_auth
def http_auth self.status = 401 self.headers["WWW-Authenticate"] = %(Basic realm=#{Devise.http_authentication_realm.inspect}) if http_auth_header? self.content_type = request.format.to_s self.response_body = http_auth_body end
def http_auth?
is the same as your public API and uses a format like JSON (so you
handling the errors on their own. This is useful in case your ajax API
on ajax requests in case they want to redirect on failures instead of
This method allows the user to explicitly disable http authentication
including 401 and optional headers.
Choose whether we should respond in a http authentication fashion,
def http_auth? if request.xhr? Devise.http_authenticatable_on_xhr else !(request_format && is_navigational_format?) end end
def http_auth_body
def http_auth_body return i18n_message unless request_format method = "to_#{request_format}" if method == "to_xml" { :error => i18n_message }.to_xml(:root => "errors") elsif {}.respond_to?(method) { :error => i18n_message }.send(method) else i18n_message end end
def http_auth_header?
It does not make sense to send authenticate headers in ajax requests
def http_auth_header? Devise.mappings[scope].to.http_authenticatable && !request.xhr? end
def i18n_message(default = nil)
def i18n_message(default = nil) message = warden.message || warden_options[:message] || default || :unauthenticated if message.is_a?(Symbol) I18n.t(:"#{scope}.#{message}", :resource_name => scope, :scope => "devise.failure", :default => [message, message.to_s]) else message.to_s end end
def recall
def recall env["PATH_INFO"] = attempted_path flash.now[:alert] = i18n_message(:invalid) self.response = recall_app(warden_options[:recall]).call(env) end
def recall_app(app)
def recall_app(app) controller, action = app.split("#") controller_name = ActiveSupport::Inflector.camelize(controller) controller_klass = ActiveSupport::Inflector.constantize("#{controller_name}Controller") controller_klass.action(action) end
def redirect
def redirect store_location! flash[:alert] = i18n_message redirect_to redirect_url end
def redirect_url
def redirect_url opts = {} route = :"new_#{scope}_session_path" opts[:format] = request_format unless skip_format? if respond_to?(route) send(route, opts) else root_path(opts) end end
def respond
def respond if http_auth? http_auth elsif warden_options[:recall] recall else redirect end end
def scope
def scope @scope ||= warden_options[:scope] || Devise.default_scope end
def skip_format?
def skip_format? %w(html */*).include? request_format.to_s end
def store_location!
yet, but we still need to store the uri based on scope, so different scopes
scoped session provided by warden here, since the user is not authenticated
Stores requested uri to redirect the user after signing in. We cannot use
def store_location! session["#{scope}_return_to"] = attempted_path if request.get? && !http_auth? end
def warden
def warden env['warden'] end
def warden_options
def warden_options env['warden.options'] end