Ruby on Rails: как отобразить строку в виде HTML?

131

У меня

@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> (без обратных косых черт, которые избегали двойных кавычек). Какой лучший способ "unescape" эти двойные кавычки?

  • 0
    Вы также можете использовать синтаксис% Q [] для экранирования строк. Например, %Q["quotation marks"] => "\"quotation marks\"" Источник: en.wikibooks.org/wiki/Ruby_Programming/Syntax/… Не знаю, поможет ли это.
Теги:
string

9 ответов

272
Лучший ответ

Что происходит, так как в качестве меры безопасности Rails ускользает от вашей строки, потому что в ней может быть встроен вредоносный код. Но если вы сообщите Rails, что ваша строка html_safe, она пройдет через нее.

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

ИЛИ

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

Использование raw отлично работает, но все, что он делает, - это преобразование строки в строку, а затем вызов html_safe. Когда я знаю, что у меня есть строка, я предпочитаю напрямую обращаться к html_safe, потому что он пропускает ненужный шаг и делает более понятным, что происходит. Подробности об экранировании строк и защите XSS находятся в this Asciicast.

  • 0
    Фантастика. Я не мог найти, как это сделать, даже после поиска в течение часа. Спасибо за Ваш ответ.
  • 1
    Я всегда использовал raw . Очень рад узнать об этом!
Показать ещё 2 комментария
15

Используйте raw:

<%=raw @str >

Но, как правильно говорит @jmort253, рассмотрите, где действительно принадлежит HTML.

  • 0
    Привет, это решение работает, за исключением одного предупреждения: см. Отредактированный вопрос
11

Если вы находитесь на rails, который использует Erubis - самый крутой способ сделать это -

<%== @str >

Обратите внимание на знак двойного равенства. См. соответствующий вопрос о SO для получения дополнительной информации.

8

Вы также можете использовать simple_format(@str), который удаляет вредоносный код. Подробнее здесь: http://api.rubyonrails.org/classes/ActionView/Helpers/TextHelper.html#method-i-simple_format

7

Вы смешиваете свою бизнес-логику с вашим контентом. Вместо этого я бы рекомендовал отправить данные на вашу страницу, а затем использовать что-то вроде JQuery для размещения данных, в которых вам это нужно.

Это имеет то преимущество, что вы сохраняете весь свой HTML-код на страницах HTML, где он принадлежит, поэтому ваши веб-дизайнеры могут впоследствии модифицировать HTML-код без необходимости заливать серверный код.

Или, если вы не хотите использовать JavaScript, вы можете попробовать следующее:

@str = "Hi"

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

По крайней мере, ваш HTML-код находится на странице HTML, где он принадлежит.

  • 0
    Проблема в том, что мое приложение берет файл с плохой разметкой и «переводит» его с помощью регулярных выражений в хорошую HTML-разметку для отправки в представление. Поэтому генерируемая HTML-разметка является динамической, поэтому я не могу априори узнать, какие теги должны окружать @str. Где бы я выполнял эту «переводческую» работу, если бы не модели? Я думал, что у нас не должно быть обширного логического кода в представлениях.
  • 1
    Это действительно вопрос мнения. При разработке нового приложения я предпочитаю держать все как можно более чистым. Но часто мы должны работать в рамках того, что оставили нам другие. Если ваш источник данных возвращает разметку HTML, возможно, стоит взглянуть на использование «raw», как описано в решении Майкла Стума.
Показать ещё 6 комментариев
5

Или вы можете попробовать CGI.unescapeHTML.

CGI.unescapeHTML "&lt;p&gt;This is a Paragraph.&lt;/p&gt;"
=> "<p>This is a Paragraph.</p>"
0

Версия html_safe хорошо работает в Rails 4...

<%= "<center style=\"color: green; font-size: 1.1em\" > Administrators only </center>".html_safe if current_user.admin? %
>
0

@str = "<span class=\"classname\">hello</span>"Если, на мой взгляд, я делаю

<%raw @str %>Исходный код HTML <span class=\"classname\">hello</span>, где я действительно хочу, это <span class="classname">hello</span> (без обратных косых черт, которые избегали двойных кавычек). Какой лучший способ "unescape" эти двойные кавычки?

Решение: используйте двойные кавычки внутри одиночных кавычек (или одиночные внутри двойника), чтобы избежать экранирования с обратной косой чертой.

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

так как вы переводите и выбирая свой желаемый код из файла crappy закодированного человека, можете ли вы использовать content_tag в сочетании с вашим регулярным выражением.

Крадуясь из api docs, вы можете интерполировать этот переведенный код на content_tag как:

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

Не зная ваш код, такое мышление будет гарантировать, что ваш переведенный код слишком уступчив.

  • 0
    Я предполагаю, что translation_text - это фактический контент внутри div, верно? т.е. в примере это будет "Hello world!"? Что если в Translate_text больше HTML, то есть вложенных элементов div или span? Должен ли я вызывать content_tag много раз?
  • 0
    да, текст в теге будет translated_text .
Показать ещё 1 комментарий

Ещё вопросы

Сообщество Overcoder
Наверх
Меню