1

我编写了一个名为 的新中间件,它可以挽救由或RescueAuthTokenFromOmniauth所创建的异常。理想情况下,我想放在堆栈中的 Omniauth 中间件之前。OmniAuth::Strategies::GoogleOauth2OmniAuth::Strategies::FacebookRescueAuthTokenFromOmniauth

我可以RescueAuthTokenFromOmniauth通过使用添加到堆栈中

# application.rb
config.middleware.use RescueAuthTokenFromOmniauth

但是,例如,当我尝试这样做时,

# application.rb
config.middleware.insert_before(OmniAuth::Strategies::GoogleOauth2, RescueAuthTokenFromOmniauth)

运行时出现以下错误rails middleware

No such middleware to insert before: OmniAuth::Strategies::GoogleOauth2

Omniauth::Strategies中间件由 gems omniauth -google-oauth2omniauth-facebook添加。

有没有办法引用OmniAuth::Strategies::GoogleOauth2application.rb以便我可以将我的新中间件放在它之前?

我正在使用导轨(6.0.3.6)。

这是运行 rails 中间件的结果。它已经包含RescueAuthTokenFromOmniauth使用config.middleware.use RescueAuthTokenFromOmniauth

use Webpacker::DevServerProxy
use ActionDispatch::HostAuthorization
use Rack::Sendfile
use ActionDispatch::Static
use ActionDispatch::Executor
use Rack::Rewrite
use ActiveSupport::Cache::Strategy::LocalCache::Middleware
use Rack::Runtime
use Rack::MethodOverride
use ActionDispatch::RequestId
use RequestStore::Middleware
use ActionDispatch::RemoteIp
use Sprockets::Rails::QuietAssets
use Rails::Rack::Logger
use ActionDispatch::ShowExceptions
use WebConsole::Middleware
use ActionDispatch::DebugExceptions
use BetterErrors::Middleware
use Rollbar::Middleware::Rails::RollbarMiddleware
use ActionDispatch::ActionableExceptions
use ActionDispatch::Reloader
use ActionDispatch::Callbacks
use ActiveRecord::Migration::CheckPending
use ActionDispatch::Cookies
use ActionDispatch::Session::CookieStore
use ActionDispatch::Flash
use ActionDispatch::ContentSecurityPolicy::Middleware
use Rack::Head
use Rack::ConditionalGet
use Rack::ETag
use Rack::TempfileReaper
use Warden::Manager
use RescueAuthTokenFromOmniauth
use Rack::Attack
use Bullet::Rack
use OmniAuth::Strategies::GoogleOauth2
use OmniAuth::Strategies::Facebook
run SaverLife::Application.routes

这些都是关于中间件的设置application.rb

require_relative '../lib/rescue_auth_token_from_omniauth'
...
config.middleware.use RescueAuthTokenFromOmniauth

我的新中间件定义在lib/rescue_auth_token_from_omniauth.rb

class RescueAuthTokenFromOmniauth
  def initialize(app)
    @app = app
  end

  def call(env)
    begin
      @app.call env
    rescue ActionController::InvalidAuthenticityToken
      [302, {'Location' => "/users/sign_up", 'Content-Type' => 'text/html'}, ['Invalid Authenticity Token']]
    end
  end
end

我在里面添加了 OmniAuth 中间件devise.rb

  # ==> OmniAuth
  # Add a new OmniAuth provider. Check the wiki for more information on setting
  # up on your models and hooks.
  # config.omniauth :github, 'APP_ID', 'APP_SECRET', scope: 'user,public_repo'
  config.omniauth :google_oauth2,
    Rails.application.credentials.dig(Rails.env.to_sym, :google_client_id),
    Rails.application.credentials.dig(Rails.env.to_sym, :google_client_secret)

  config.omniauth :facebook,
    Rails.application.credentials.dig(Rails.env.to_sym, :facebook_key),
    Rails.application.credentials.dig(Rails.env.to_sym, :facebook_secret),
    scope: "email", info_fields: 'name,email,first_name,last_name'

这就是我的 OmniAuth 初始化程序的样子

# omniauth.rb
OmniAuth.config.logger = Rails.logger

OmniAuth.config.allowed_request_methods = [:post]

注意:我知道现在RescueAuthTokenFromOmniauth是在Omniauth::Strategies中间件之前,所以我的功能有效。但我想明确设置它,insert_before以便清楚它应该放在Omniauth::Strategies中间件之前。

4

2 回答 2

0

你可以在omniauth初始化时做到这一点

# config/initializers/omniauth.rb
require Rails.root.join("lib/rescue_auth_token_from_omniauth")

Rails.application.config.middleware.use OmniAuth::Builder do
  provider :google_oauth2, ENV['GOOGLE_CLIENT_ID'], ENV['GOOGLE_CLIENT_SECRET']
end

Rails.application.config.middleware.insert_before(OmniAuth::Builder, RescueAuthTokenFromOmniauth)

请注意,如果使用上述代码,则不应在 application.rb 上添加中间件,否则会重复。

于 2021-05-17T09:28:27.237 回答
0

我同意Lam Phan 的做法。如果您确实想将初始化程序保存在单独的初始化程序文件中,请确保使用类似的内容引用依赖项初始化程序require_relative './omniauth.rb',否则它将对文件名的字母顺序敏感。

于 2021-05-17T13:51:30.853 回答