假设我有以下字符串
@x = "<a href='#'>Turn me into a link</a>"
在我看来,我希望显示一个链接。也就是说,我不希望 @x 中的所有内容都被转义并显示为字符串。使用和使用有什么区别
<%= raw @x %>
<%= h @x %>
<%= @x.html_safe %>
?
考虑 Rails 3:
html_safe
实际上将字符串“设置”为 HTML 安全(比这要复杂一些,但基本上就是这样)。这样,您可以随意从帮助程序或模型返回 HTML 安全字符串。
h
只能在控制器或视图中使用,因为它来自帮助程序。它将强制输出被转义。它并没有真正被弃用,但您很可能不再使用它:唯一的用途是“还原” html_safe
声明,这很不寻常。
在表达式前面加上 raw
实际上相当于调用 to_s
并在其上链接 html_safe
,但它是在帮助器上声明的,就像 h
一样,因此它只能用于控制器和视图。
“SafeBuffers and Rails 3.0”很好地解释了 SafeBuffer
(执行 html_safe
魔法的类)如何工作。
我认为值得重复:html_safe
not HTML 转义您的字符串。事实上,它会阻止你的字符串被转义。
<%= "<script>alert('Hello!')</script>" %>
将放:
<script>alert('Hello!')</script>
进入您的 HTML 源代码(耶,太安全了!),同时:
<%= "<script>alert('Hello!')</script>".html_safe %>
将弹出警报对话框(您确定这是您想要的吗?)。因此,您可能不想对任何用户输入的字符串调用 html_safe
。
html_safe
不会 转义 也不 转义。虽然将某些内容标记为 not HTML 安全,然后使用 ERB <%= 标记的隐式转义的最终结果可能与取消转义数据然后在输出时重新转义相同,从功能上讲,它两者都没有。有点像 (6 * -1 * -1) 与 6 的区别。
区别在于 Rails 的 html_safe()
和 raw()
。 Yehuda Katz 对此发表了一篇出色的文章,它真的可以归结为:
def raw(stringish)
stringish.to_s.html_safe
end
是的,raw()
是围绕 html_safe()
的包装器,它将输入强制为 String,然后对其调用 html_safe()
。 raw()
也是模块中的帮助程序,而 html_safe()
是 String 类上的一个方法,它创建一个新的 ActiveSupport::SafeBuffer 实例 — 其中有一个 @dirty
标志。
请参阅“Rails’ html_safe vs. raw”。
html_safe :将字符串标记为受信任的安全。它将被插入到 HTML 中,而不会执行额外的转义。 "Hello".html_safe #=> "Hello" nil.html_safe #=> NoMethodError: undefined method `html_safe' for nil:NilClass raw : raw 只是一个包装器html_safe。如果字符串有可能为零,请使用 raw。 raw("Hello") #=> "Hello" raw(nil) #=> "" h html_escape 的别名:转义 HTML 标签字符的实用方法。使用此方法转义任何不安全的内容。在 Rails 3 及更高版本中默认使用它,因此您不需要显式使用此方法
最好的安全方法是:<%= sanitize @x %>
它将避免 XSS!
在简单的 Rails 术语中:
h
将 html 标记删除为数字字符,以便呈现不会破坏您的 html
html_safe
在字符串中设置一个布尔值,以便将该字符串视为 html 保存
raw
将 html_safe 转换为字符串
h
是 html_safe
,这意味着 HTML 按原样呈现。
简短而简单
假设我们不能信任用户输入。
坏的:
user_input.html_safe # asking for trouble
好的:
user_input.html_escape # or
h(user_input) # in some view
我们控制的输入:
trusted_input_only.html_safe
那应该没问题。但要小心你信任的输入是什么。它们只能从您的应用程序中生成。
不定期副业成功案例分享
h
将被弃用。使用"Hi<br/>#{h@ user.name}".html_safe
是很常见且被接受的用法。raw
和html_safe
在实践中存在细微差别:raw(nil)
返回一个空字符串,而nil.html_safe
引发异常。h
不会“还原” html_safe 声明。当字符串为html_safe
时,h
将不执行任何操作。