我正在使用Omniauth构建一个用于登录服务的Rails应用程序。要验证Google我正在使用OmniAuth Google OAuth2 Strategy。
当用户点击“允许访问”按钮时,一切正常。但是当用户点击“不再感谢”按钮时,会出现以下错误。
OmniAuth::Strategies::OAuth2::CallbackError
我尝试在应用程序控制器中添加以下救援代码。
class ApplicationController < ActionController::Base
rescue_from OmniAuth::Strategies::OAuth2::CallbackError, :with =>
:omniauth_callback_error_handler
protected
def omniauth_callback_error_handler
redirect_to init_sign_in_users_path
end
end
但没有运气。
有什么想法吗?
谢谢:)
答案 0 :(得分:64)
您可以更清晰的方式在omniauth初始化程序中设置on_failure proc:
OmniAuth.config.on_failure = UsersController.action(:oauth_failure)
答案 1 :(得分:34)
这是因为身份验证发生在中间件中,因此控制器不参与其中。这是where the exception is raised,被叫代码是this
我认为你可以通过使用这种代码在Omniauth初始化程序中定义回调来处理这种错误
Omniauth.config do |config|
config.on_failure do
# your handling code invoked in the context of a rack app
end
end
否则三个月前有a commit引入了这种行为
def redirect_to_failure
message_key = env['omniauth.error.type']
new_path = "#{env['SCRIPT_NAME']}#{OmniAuth.config.path_prefix}/failure?message=#{message_key}"
Rack::Response.new(["302 Moved"], 302, 'Location' => new_path).finish
end
指出在出现错误时,您的用户会被重定向到/auth/failure
并显示错误消息,因此您应该能够为该路径定义路径并在应用中处理它。请记住,这不会发生in development mode因此您需要在其他环境中尝试。如果在生产中没有发生这种情况,请尝试将omniauth gem升级到版本1.1.0
答案 2 :(得分:16)
我已经用法比奥的第一个建议解决了这个问题。
OmniAuth.config.on_failure = Proc.new do |env|
UsersController.action(:omniauth_failure).call(env)
#this will invoke the omniauth_failure action in UsersController.
end
在我的UsersController中
class UsersController < ActionController::Base
def omniauth_failure
redirect_to init_sign_in_users_path
#redirect wherever you want.
end
end
答案 3 :(得分:0)
有一种配置可以使用/auth/failure
而不是引发错误。
我使用OmniAuth 1.2.2,当我检查FailureEndpoint时,我发现代码就像this:
def call
raise_out! if OmniAuth.config.failure_raise_out_environments.include?(ENV['RACK_ENV'].to_s)
redirect_to_failure
end
failure_raise_out_environments
定义为here:
def self.defaults
@defaults ||= {
# other configurations
:failure_raise_out_environments => ['development']
}
end
可以配置环境以便解决方案。我使用Rails,所以我将下面的代码放在初始化文件中:
OmniAuth.configure do |config|
# Always use /auth/failure in any environment
config.failure_raise_out_environments = []
end