仅在root_path上登录后才重定向用户
我的Rails应用程序上有一个root_path
,它不受用户保护,即它是一个简单的门户网站主页,带有登录表单。
用户登录后,我希望它转到dashboard_path
。
我做到了这个:
def signed_in_root_path(scope_or_resource) dashboard_path end
这显然应该在用户登录时使用,并且我不希望它转到root_path
,同时仍然保持用户返回到前一页,如果它尝试到达受限区域并且它要么超时还是没有超时登录。
即:
restricted_page – > login – > restricted_page_but_logged_in
我不想改变这种行为,这就是为什么我没有使用after_sign_in_path
,但是如果它在root_path
,或者想要在不需要用户身份validation的任何路由上重定向它。
我的问题是这不起作用。 登录后,我将被重定向回root_path
,我认为这是因为之前触发了after_sign_in_path
。
有没有办法做到这一点? 谢谢!
编辑:这是我第二次登录时工作,即我转到root_path
,登录,获取闪存消息,说明我已登录,并在root_path
上的表单上再次输入用户名和密码。 我成功地被重定向到dashboard_path
。 不过,不是我想要的行为。
只是一个想法
您可以为登录的URL定义两个根URL,它将指向仪表板,第二个用于非签名用户,这将指向登录页面
根据routes.rb中的一些约束定义不同的根URL
登录用户的根URL
constraints(AuthenticatedUser) do root :to => "dashboard" end
非签名用户的根URL
root :to=>"users/signin"
然后在lib / authenticated_user.rb中创建类AuthenticatedUser
class AuthenticatedUser def self.matches?(request) user_signed_in? end end
现在如果用户登录root_url将指向仪表板,否则它将指向登录页面
你也可以创建两个根(尚未测试)
root :to => "dashboard", :constraints => {user_signed_in?} root :to => "users/signin"
更多关于约束http://edgeguides.rubyonrails.org/routing.html#request-based-constraints
注意
url的优先级基于创建顺序,首先创建 – >最高优先级资源
听起来你的问题太复杂了。 如果你进入覆盖路由变量,它只会导致头痛。 如果你使用的是单独的控制器,我建议使用beforefilter来要求登录并使用except param或在filter之前跳过它。 举个例子:
class ApplicationController < ActionController::Base before_filter :require_login, :except => :root def root # Homepage end protected def require_login redirect_to login_path and return unless logged_in? end end
(确保你已经定义了logged_in?)
如果您使用单独的控制器,它将看起来像这样:
class HomepageController < ApplicationController skip_before_filter :require_login before_filter :route protected def route redirect_to dashboard_path and return if logged_in? end end
关于登录后的正确路由,这将归结为您在创建会话时所执行的操作。 无论如何,此设置应该捕获任何登录尝试访问主页的人,并将它们路由到您的仪表板以及任何尝试访问受限内容的人(除root之外的任何内容)并将其路由到login_path
您可以覆盖after_sign_in_path_for方法,而不会丢失所需的行为。
def after_sign_in_path_for(resource_or_scope) stored_location_for(resource_or_scope) || dashboard_path end
如果current_user存在,我还会在root_path操作中添加一个重定向的条件。
RootController.rb def index if current_user redirect_to dashboard_path else super #or whatever end end
如果要将重定向添加到许多不受保护的操作,也可以使用before_filter。
我正在使用Omniauth,这种方法对我来说效果很好。 如果你正在使用不同的策略,我相信你可以修改它。
登录后,只需将它们重定向到root_path
,它就会将它们带到dashboard_path
或您在下面的路径文件中设置的任何其他默认值。
在app控制器中设置助手和回调方法:
# application_controller.rb class ApplicationController < ActionController::Base protect_from_forgery helper_method :current_user private def current_user @current_user ||= User.find(session[:user_id]) if session[:user_id] end def authenticate_user! unless current_user redirect_to root_url end end end
将before_filter
放入受限制的控制器中以捕获未经授权的人员:
# dashboard_controller.rb class DashboardController < ActionController::Base before_filter :authenticate_user! def index end # rest of controller here end
将这两项添加到路线中。 如果不满足条件,则不会执行第一个。 如果是,则顶部优先,所有root_url
调用将转到仪表板
# routes.rb YourAppName::Application.routes.draw do root :to => 'dashboard#index', :conditions => lambda{ |req| !req.session["user_id"].blank? } root :to => 'static_page#index' # the rest of your routes end
我认为你的解决方案比必要的更复杂。 为什么不在登录表单发布到的操作上执行这样简单的操作:
def login // logic to check whether login credentials authorize user to sign in // say 'user_signed_in?' is boolean to determine whether user has successfully signed in redirect_to(user_signed_in? ? dashboard_path : root_path) end
登录表单是在每个页面(顶部/侧边栏)上还是您有登录页面?
如果在每个页面上,您可以使用request.referrer
来了解用户来自何处。
您可以使用应用程序控制器上的before_filter来控制它。
我不确定你是否在某个地方使用after_filter或before_filter进行重定向,但是你可以在登录控制器中使用skip_filter。 然后将自定义重定向作为该控制器中的filter。
在Rails中跳过before_filter
- 使用设计没有gem,我可以简单地复制文件吗?
- 使用devise进行RESTful登录(Rails 4)
- 设计 – 在开发中删除用户确认
- Devise无法登录Google Chrome
- Rails 4设计3.1.1 ActionController :: Devise中的UnknownFormat :: RegistrationsController #new
- Rails 5 ActionController :: InvalidAuthenticityToken错误
- Ldap没与Devise合作
- TrueClass的未定义方法`model_name’:DeviseConfirmations的类(Rails 4,设计)
- Ruby on Rails:自定义设计注册控制器,请求创建操作