在Rails中向URL添加锚点

时间:2014-08-27 01:37:40

标签: ruby-on-rails url devise routing

我需要在用户更新失败时刷新页面。我发现的问题是,当页面刷新时,我不知道如何在网址中添加片段。下面的代码来自我的注册控制器,基于Devise gem。

  def update
    self.resource = resource_class.to_adapter.get!(send(:"current_#{resource_name}").to_key)
    prev_unconfirmed_email = resource.unconfirmed_email if resource.respond_to?(:unconfirmed_email)

    if resource.update_with_password(account_update_params)
      # If the update went well
      if is_navigational_format?
        flash_key = update_needs_confirmation?(resource, prev_unconfirmed_email) ?
          :update_needs_confirmation : :updated
        set_flash_message :notice, flash_key
      end

      sign_in resource_name, resource, :bypass => true
      # What's crazy is this works
      respond_with resource, location: edit_user_registration_path(anchor: params["tab_selected"])
    else
      # If the update goes horribly wrong
      clean_up_passwords resource
      #  this is where the problem occurs below
      respond_with resource, location: edit_user_registration_path(anchor: params["tab_selected"])
    end
  end

正如您所看到的,我认为添加位置选项可以解决这个问题,但我的网址仍然会以coolsite.com/users的形式返回coolsite.com/users/#profile。我的问题是如何将片段设置为URL?

1 个答案:

答案 0 :(得分:0)

我认为问题是因为您正在使用respond_with。如果更新成功,则respond_with将发出redirect_to,该:location将使用您的respond_with选项。

但是,如果更新未成功,render只需调用edit模板上的:location,这基本上会忽略update选项。它放在那里的路径并不重要,它不会显示在浏览器的地址栏中 - 您已经向location的任何URL发出了请求行动,它所做的就是提供回应。在这种情况下,redirect_to标题仍然在响应中设置,但基本上什么都不做,因为您使用200状态代码进行响应,而不是发出重定向(例如302或类似respond_with的任何内容一样)。

为了获得你的锚,你需要浏览器发出第二个请求(或使用某种JS hackery),即你需要像第一种情况一样发出重定向响应。我认为,为了实现这一点,你无法使用respond_with。它还可能导致显示验证错误和记住您在表单中输入的任何先前值(在您的情况下可能是也可能不是问题)的问题。

这是respond_to的主要问题,它模糊了控制器正在做的事情,所以你需要很好地理解它是如何工作的。 It's being removed from Rails 4.2 and put into a gem无论如何,我的建议是开始使用{{1}}和/或基本的渲染/重定向调用。