我正在尝试在 Rails 中的控制器中的更新操作的闪存消息中实现“link_to”,但我无法将其呈现给浏览器

I'm trying to implement `link_to` in a flash message for an update action in a controller in Rails but I cannot get it to render to the browser

我的项目中有这样一个控制器:

class BriefcasesController < ApplicationController
  ...

  def update
    @super_power = SuperPower.find(params[:super_power_id])
    @briefcase.contents.delete(params[:super_power_id].to_s)
    flash[:notice] = "Successfully removed #{view_context.link_to(@super_power.title, super_power_path(@super_power)} from your briefcase."
    redirect_back(fallback_location: '/briefcase'
  end

end

link_to 助手没有向浏览器呈现 link,而是打印 html:Successfully removed <a href=\"/powers/1\>flying</a> from your briefcase. 我也尝试过使用方法 #html_safe 上的 flash 消息无济于事。我想知道是否有使用 view_context 解决此问题的方法,或者是否有更好的方法在 Flash 消息中包含 link。

注意:以下仅适用于Rails相对较旧的版本(4.0及之前确认,可能在4.1)。 Rails用于允许在 flash 消息中传递自定义对象,但后来将其更改为仅允许原始对象(记录在 https://github.com/rails/rails/issues/15522)。

您需要对整个字符串调用 html_safe。使用字符串插值 ("#{some_ruby_code}") 将 "safe" link_to 字符串改回被转义的常规字符串。

您需要在输出即显消息时使用 html_safe - 而不是在存储它们时。

<% flash.each do |key, msg| -%>
  <%= content_tag :div, msg.html_safe, class: name %>
<% end -%>

.html_safe 只是在字符串对象上设置一个标志,它是可信的并且不应被转义。

flash 通过在会话存储中存储 flash 消息来工作 - by default this means a cookie in the browser

所以当你这样做时:

flash[:notice] = "foo"

您将原始字符串 "foo" 存储在 cookie* 中,并在下一次请求时将其解压缩回会话中。但是字符串不是同一个 Ruby 对象 - 因此字符串对象上的 html_safe 标志不是持久的。