我有一个名为Feature
的模型,其中包含一个名为body_string
的变量,其中包含我要呈现的HTML标记,而不是转义。
每次我在观看中引用body_string
时,我都需要使用<%=raw
或.html_safe
。这似乎是多余的,而不是那么干。
有没有办法让body_string
变量一劳永逸地建立为html_safe
?
我假设这会发生在app/models/feature.rb
文件中,但我无法弄清楚正确的语法是什么。我想到了这个:
def body_string
return self.body_string.html_safe
end
但是Rails并不喜欢它;它引发stack level too deep
例外。
当然,我可以使用不同的名称定义变量/方法:
def safe_body_string
return self.body_string.html_safe
end
然后只需将视图中的所有引用从body_string
更改为safe_body_string
。但不知何故,这似乎与第一次使用raw
或.html_safe
一样干涸。
有关如何最好地处理此问题的任何见解?我觉得必须有一些非常优雅的东西,我只是没有看到。
答案 0 :(得分:9)
只需使用read_attribute
即可避免对body_string
的递归调用:
def body_string
read_attribute(:body_string).html_safe
end
read_attribute
由write_attribute
补充,用于在模型中设置属性。
关于风格的说明:除非您确实需要,否则不要使用明确的return
。方法中最后一个语句的结果隐式地是从方法返回的值。
答案 1 :(得分:1)
虽然@meager的答案肯定会有效,但我并不认为这个逻辑属于模型。仅仅因为它为模型层添加了视图级别的关注点(HTML安全性),它应该只包含业务逻辑。相反,我建议使用Presenter(请参阅http://nithinbekal.com/posts/rails-presenters/或为此找到一个宝石 - 我个人喜欢Display Case)。您的演示者可以轻松覆盖body_string
方法,并在视图中显示时提供.html_safe
指定。通过这种方式,您可以分离您的疑虑,并可以继续从其他模型中获取body_string
,而不会混淆视图问题。
答案 2 :(得分:0)
也许这个宝石对你有用。当内容完全可信时,我也想停止重复html_safe。
答案 3 :(得分:0)
或者你也可以使用这种方法,
def body_string
super && super.html_safe
end