配置/ application.rb中
config.middleware.insert_before(Rack::Runtime, Rack::ReverseProxy) do
reverse_proxy_options preserve_host: false
reverse_proxy '/external/app', 'https://runalong.com:64167/app'
end
我使用rack-reverse-proxy将请求转发到另一台服务器(而不是rails服务器),当请求特定网址时,该服务器在另一台主机上运行。现在我想验证用户是否使用devise进行了signed_in,然后仅将请求转发给代理服务器,否则将用户发送回登录页面。
答案 0 :(得分:3)
更新。在一般考虑中,假设目标服务器是公开可用的,您应该考虑身份验证策略,因为仅在临时服务器上检查它是不安全的。
基本上,回答你的问题是 - Devise没有为Rails应用程序添加任何自己的中间件,所以你不能在中间件中使用Devise。您可以使用Warden中间件。
Devise位于Warden之上。在中间件堆栈结束时设计injects Warden::Manager
中间件(它也可以注入omniauth中间件):
# Initialize Warden and copy its configurations.
config.app_middleware.use Warden::Manager do |config|
Devise.warden_config = config
end
除此之外,Devise适用于Rails应用程序级别,即添加sign_in
等助手,类似于控制器。但它不适用于中间件级别本身。
Warden本身就是“懒惰”,描述为here
守望者是懒惰的。也就是说,如果你不使用它,它 没有做任何事情,但是当你使用它时,它会涌入 动作并提供允许身份验证的基础机制 任何基于机架的应用程序。
因此,除非Devise以某种方式与Warden一起操纵,Warden并没有做太多。 Warden所做的是embedding本身可以被其他中间件(以及Rails应用程序)访问的env变量。设计使用此实例。
env['warden'] = Proxy.new(env, self)
Warden还会听取其他中间件(或最终的rails应用程序)可能抛出的特殊warden异常:
result = catch(:warden) do
@app.call(env)
end
为了在中间件中使用Warden,您需要更早地嵌入中间件(在目标中间件之前)。然后你就可以使用Warden(而不是设计助手!)。
在warden source中的每条评论中,它应该嵌入(之前没有)会话构建中间件之后,例如ActionDispatch::Session::CookieStore
:
机架认证的中间件中间件需要 上游会话中间件注入了一个 认证对象进入机架环境哈希
守望者accessor参加会议:
def session
env["rack.session"] || {}
end