Ruby on Rails:如何将字符串呈现为HTML?


154

我有

@str = "<b>Hi</b>"

在我的erb视图中:

<%= @str %>

页面上将显示:<b>Hi</b>当我真正想要的是Hi时。将字符串“解释”为HTML标记的红宝石方法是什么?


编辑:的情况下

@str = "<span class=\"classname\">hello</span>"

如果我认为

<%raw @str %>

HTML源代码是<span class=\"classname\">hello</span>我真正想要的位置<span class="classname">hello</span>(没有转义双引号的反斜杠)。“取消转义”双引号的最佳方法是什么?


您可能还考虑使用%Q []语法进行字符串转义。例如, %Q["quotation marks"] => "\"quotation marks\"" 来源: en.wikibooks.org/wiki/Ruby_Programming/Syntax/… 不知道是否有帮助。
0112年

Answers:


328

更新

出于安全原因,建议使用sanitize代替html_safe链接


发生的事情是,作为一种安全措施,Rails正在为您转义您的字符串,因为其中可能嵌入了恶意代码。但是,如果您告诉Rails您的字符串是html_safe,它将直接通过。

@str = "<b>Hi</b>".html_safe
<%= @str %>

要么

@str = "<b>Hi</b>"
<%= @str.html_safe %>

使用的raw效果很好,但要做的只是将字符串转换为字符串,然后调用html_safe。当我知道我有一个字符串时,我更喜欢直接调用html_safe,因为它跳过了不必要的步骤,使事情更清晰。有关字符串转义和XSS保护的详细信息,请参见此Asciicast


太棒了 搜索一个小时后,我仍然找不到该怎么做。感谢您的回答。
Salil

1
我一直都习惯raw。很高兴知道这一点!
jmcharnes 2013年

向未来致敬=)
卡洛斯·莫拉莱斯


16

使用原始

<%=raw @str >

但是,正如@ jmort253正确说的那样,请考虑HTML真正所属的位置。


嗨,这个解决方案有效,除了一个警告:请参阅编辑过的问题
蒂姆



7

您正在将业务逻辑与内容混合在一起。相反,我建议将数据发送到您的页面,然后使用诸如JQuery之类的数据将数据放置在需要的地方。

这具有将所有HTML保留在它所属的HTML页面中的优势,因此您的Web设计人员可以在以后修改HTML而不用倒入服务器端代码。

或者,如果您不想使用JavaScript,则可以尝试以下操作:

@str = "Hi"

<b><%= @str ></b>

至少以这种方式,您的HTML位于它所属的HTML页面中。


问题是,我的应用程序正在接收标记不良的文件,然后通过正则表达式将其“转换”为良好的HTML标记以发送到视图。因此,正在生成的HTML标记是动态的,因此我不知道哪个标记应该包围@str。如果不在模型中,我将在哪里执行“翻译”工作?我认为我们不应在视图中包含大量的逻辑代码。
蒂姆

1
这确实是一个见解的问题。开发新的应用程序时,我更喜欢保持所有内容的清洁。但是,有时我们必须在别人给我们留下的束缚之内工作。如果您的数据源返回HTML标记,那么可以按照Michael Stum的解决方案中的说明使用“原始”格式。
jmort253 2011年

1
如果您继承了某些代码的支持,并且代码中的区域显示出不良的思维或设计,那么清理它以使其更易于维护确实是您职责的一部分。最好先保留它,然后再保留它,直到需要工作时才保留它。我的部分工作是管理一些旧版应用程序;我喜欢不修复未损坏的东西,但是由于它们的编写方式而无法轻松对其进行增强。我不得不重写大多数函数调用,但是现在使用起来非常容易。
Tin Man'1

如果没有其他理由使用JS,则不应在HTML插值中使用JavaScript。这将打破你的网站的非JS浏览器(是的,有有的)。
Marnen Laibow-Koser 2011年

1
当然,如果您允许非转义的内容,则必须确保由您自己决定非邪恶的标记。
Macario 2012年


0

由于您正在翻译,并且从一个人的s脚的编码文件中选择了想要的代码,您是否可以将content_tag与正则表达式结合使用?

您可以从api文档中窃取此翻译后的代码,content_tag例如:

<%= content_tag translated_tag_type.to_sym, :class => "#{translated_class}" do -%>
<%= translated_text %>
<% end -%>
# => <div class="strong">Hello world!</div>

不知道您的代码,这种想法将确保您翻译的代码过于合规。


我假设translation_text是div中的实际内容,对不对?即在示例中,它将是“ Hello world!”?如果translation_text中包含更多HTML,即嵌套的div或spans,该怎么办?那时我需要多次调用content_tag吗?

和...抱歉,请早点输入...里面的每个嵌套div / span仍然是content_tag,尽管如此,您仍然需要对其进行验证?由于我们看不到您在用花哨的翻译;-)做什么,所以我假设您正在寻找ALL标签,无论regex是否位于html的“父”上……如<ul>。你不会把李所有的东西都当成大屁股打印吗?每个都是自己的content_tag:li,文本正确吗?
pjammer 2011年

0

@str = "<span class=\"classname\">hello</span>" 如果我认为

<%raw @str %> HTML源代码是<span class=\"classname\">hello</span>我真正想要的地方<span class="classname">hello</span>(不带转义双引号>的反斜杠)。“取消转义”双引号的最佳方法是什么?

解决方案:在单引号内使用双引号(或在双引号内使用单引号),以避免使用反斜杠转义。

@str = '<span class="classname">hello</span>'
<%raw @str %>

0

html_safe版本在Rails 4中运作良好...

<%= "<center style=\"color: green; font-size: 1.1em\" > Administrators only </center>".html_safe if current_user.admin? %
>
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.