如何在Ruby On Rails中redirect到上一页?

我有一个页面列出了所有具有可sorting标题和分页的项目。

path: /projects?order=asc&page=3&sort=code 

我select编辑其中一个项目

 path: projects/436/edit 

当我点击该页面上的保存时,它会调用项目控制器/更新方法。 在我更新代码之后,我想要redirect到我之前单击编辑特定项目之前的path。 换句话说,我想在同一个页面上进行相同的sorting。

我看到link_to(:back),并认为:back可能在redirect_to(:back)中工作,但这是不行的。

 puts YAML::dump(:back) yields the following: :back 

任何想法我怎么能得到这个工作。 这似乎是一个容易解决的问题,但我是RoR的新手。

在您的编辑操作中,将请求的URL存储在会话散列中,该散列可在多个请求中使用:

 session[:return_to] ||= request.referer 

然后在更新操作中redirect到它,保存成功后:

 redirect_to session.delete(:return_to) 

为什么redirect_to(:back)不适合你,为什么不行?

redirect_to(:back)对我来说就像一个魅力。 这只是redirect_to(request.env['HTTP_REFERER'])一个捷径

(前导轨3)或http://apidock.com/rails/ActionController/Redirecting/redirect_to(Rails 3)

请注意, redirect_to(:back)在Rails 5中已被弃用。您可以使用

redirect_back(fallback_location: 'something') (请参阅http://blog.bigbinary.com/2016/02/29/rails-5-improves-redirect_to_back-with-redirect-back.html

除了一个例外,我喜欢Jaime的方法,每次重新存储引用者都会更好:

 def edit session[:return_to] = request.referer ... 

原因是如果你编辑多个对象,你总是会被redirect回Jaime的方法中存储在会话中的第一个URL。 例如,假设我有Apple和Orange的对象。 我编辑苹果, session[:return_to]被设置为该行动的引用者。 当我使用相同的代码编辑橘子时, session[:return_to]将不会被设置,因为它已经被定义。 所以当我更新橙色的时候,我会被送到之前Apple#编辑动作的引用者。

这就是我们在应用程序中的做法

 def store_location session[:return_to] = request.fullpath if request.get? and controller_name != "user_sessions" and controller_name != "sessions" end def redirect_back_or_default(default) redirect_to(session[:return_to] || default) end 

这样,您只需将最后一个GET请求存储在:return_to会话参数中,所有表单即使在多次POST时也可以使用:return_to

request.referer由Rack设置,设置如下:

 def referer @env['HTTP_REFERER'] || '/' end 

只要做一个redirect_to request.referer ,它将总是redirect到真正的引用页面,或root_path('/')。 在直接导航到在控制器抛出redirect_to的特定页面的情况下传递失败的testing时,这是非常重要的。

在导轨5中,按照Rails指南中的说明,您可以使用:

 redirect_back(fallback_location: root_path) 

“后退”位置是从HTTP_REFERER头部拉出来的,不保证被浏览器设置。 那就是为什么你应该提供一个'fallback_location'。

对于那些有兴趣的人,这里是我的实现扩展MBO的原始答案(写在轨道4.2.4,ruby2.1.5)。

 class ApplicationController < ActionController::Base after_filter :set_return_to_location REDIRECT_CONTROLLER_BLACKLIST = %w( sessions user_sessions ... etc. ) ... def set_return_to_location return unless request.get? return unless request.format.html? return unless %w(show index edit).include?(params[:action]) return if REDIRECT_CONTROLLER_BLACKLIST.include?(controller_name) session[:return_to] = request.fullpath end def redirect_back_or_default(default_path = root_path) redirect_to( session[:return_to].present? && session[:return_to] != request.fullpath ? session[:return_to] : default_path ) end end