Оценка строковых шаблонов

У меня есть строковый шаблон как показано ниже

template = '<p class="foo">#{content}</p>'

Я хочу оценить шаблон на основе текущего значения названной переменной content.

html = my_eval(template, "Hello World")

Это - мой текущий подход для этой проблемы:

def my_eval template, content
  "\"#{template.gsub('"', '\"')}\""  # gsub to escape the quotes
end

Существует ли лучший подход к решению этой проблемы?

Править

Я использовал фрагмент HTML в примере кода выше для демонстрации моего сценария. Мой реальный сценарий имеет набор шаблонов XPath в конфигурационном файле. Связывать переменными в шаблоне заменяют для получения допустимой строки XPath.

Я думал об использовании ERB, но отклонил, поскольку это могло бы быть излишество.

8
задан Harish Shetty 3 January 2015 в 06:47
поделиться

2 ответа

Вы можете отобразить строку, как если бы она была шаблоном erb. Видя, что вы используете это в задаче с граблями, вам лучше использовать Erb.new.

template = '<p class="foo"><%=content%></p>'
html = Erb.new(template).result(binding)

Использование первоначально предложенных методов ActionController включает создание экземпляра объекта ActionController :: Base и отправку render или render_to_string.

11
ответ дан 5 December 2019 в 05:03
поделиться

Я не могу сказать, что действительно рекомендую любой из этих подходов. Для этого нужны библиотеки, такие как erb, и они были тщательно протестированы для всех крайних случаев, о которых вы еще не думали. А все, кому придется прикоснуться к вашему коду, будут вам благодарны. Однако, если вы действительно не хотите использовать внешнюю библиотеку, я включил несколько рекомендаций.

Включенный вами метод my_eval у меня не работал. Попробуйте вместо этого что-нибудь вроде этого:

template = '<p class="foo">#{content}</p>'

def my_eval( template, content )
  eval %Q{"#{template.gsub(/"/, '\"')}"}
end

Если вы хотите обобщить это так, чтобы вы могли использовать шаблоны, которые имеют переменные, отличные от содержимого , вы можете расширить его примерно до следующего:

def my_eval( template, locals )
  locals.each_pair{ |var, value| eval "#{var} = #{value.inspect}" }
  eval %Q{"#{template.gsub(/"/, '\"')}"}
end

Этот метод будет называется так

my_eval( '<p class="foo">#{content}</p>', :content => 'value of content' )

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

3
ответ дан 5 December 2019 в 05:03
поделиться
Другие вопросы по тегам:

Похожие вопросы: