rxml模板和rhtml模板

[color=red]Builder “模板”[/color]
Builder 是个独立库,它可让你在代码中表达结构化文本(如XML)。一个Builder“模板”
(在扩展名.rxml 文件内)包含使用了Builder 库的Ruby 代码来生成XML。
这儿是个简单的Builder“模板”,它在XML 中输出一个有产品名字和价格的清单。
xml.div(:class => "productlist") do
xml.timestamp(Time.now)
@products.each do |product|
xml.product do
xml.productname(product.title)
xml.price(product.price, :currency => "USD")
end
end
end
用一个适当的产品集合(从“控制器”传入),“模板”会生成下面这些东西
<div class="productlist">
<timestamp>Tue Apr 19 15:54:26 CDT 2005</timestamp>
<product>
<productname>Pragmatic Programmer</productname>
<price currency="USD">39.96</price>
</product>
<product>
<productname>Programming Ruby</productname>
<price currency="USD">44.95</price>
</product>
</div>
注意Builder 是如何接受方法的名字并转换它们到XML 标记的;当我们说xml.price 时,它
创建一个标记叫<price>,它的内容是第一个参数和随后从哈希表设置它的属性。如果你想使
用的标记的名字与一个现有的方法名字冲突,你将需要使用tag!()方法来生成此标记。
xml.tag!("id", product.id)
Builder 可以生成你需要的任何XML;它支持“名字空间”,处理指令,甚至XML 注释。
可在文档中找到Builder 的细节。

17.3 [color=red]RHTML “模板”[/color]

它是最简单的,一个rhtml“模板”只是个正常的HTML 文件。如果一个“模板”不包含
动态内容,它就被简单地发送到用户的浏览器。下面是个完全有效的rhtml“模板”。
<h1>Hello, Dave!</h1>
<p>
How are you, today?
</p>
但是只提交静态“模板”的应用程序很少有用。我们可以使用动态内容。
<h1>Hello, Dave!</h1>
<p>
It's <%= Time.now %>
</p>
如果你是个JSP 程序员,你会知道它是个内联表达式:在<%=和%>之间的任何代码都会被
计算,并使用to_s()将结果转换为一个字符串,那个字符串被替换到结果页面中。在标记内
的表达式可以是任意的代码。
<h1>Hello, Dave!</h1>
<p>
It's <%= require 'date'
DAY_NAMES = %w{ Sunday Monday Tuesday Wednesday
Thursday Friday Saturday }
today = Date.today
DAY_NAMES[today.wday]
%>
</p>
放置很多商业逻辑在一个“模板”内通常被认为是件非常坏的事。我们会在332 页看到
处理此事的更好方式。
有时候你需要在“模板”内直接编写没有任何输出的代码。如果你使用不带有=符号的开
口标记,内容会被执行,但不会有任何东西被插入到“模板”中。我们可重写前个例子
<% require 'date'
DAY_NAMES = %w{ Sunday Monday Tuesday Wednesday
Thursday Friday Saturday }
today = Date.today
%>
<h1>Hello, Dave!</h1>
<p>
It's <%= DAY_NAMES[today.wday] %>.
Tomorrow is <%= DAY_NAMES[(today + 1).wday] %>.
</p>
在JSP 中,这被称为scriptlet。如果有人发现你添加代码到“模板”中,他们会惩罚
你的。放置代码在“模板”中并没有错误。只是不要放置太多代码(特别地不要在“模板”中
放置商业逻辑)。稍后我们会看到,我们如何使用一个帮助方法来把前面的例子做的更好。
你可能认为在文本和代码片断之间的HTML,好像每行都是由一个Ruby 程序写出来。
<%...%>片断被添加同样编程。HTML 被你写的代码交织着。结果,<%和%>之间的代码会影响
“模板”内其余部分的HTML 输出。
<% 3.times do %>
Ho!<br/>
<% end %>
在内部,模板化的代码被转换成下面这样。
3.times do
puts "Ho!<br/>"
end
结果呢?你会看到短语Ho!被写到你浏览器上三次。最后,你可能注意到本书例子代码
使用了由-%>结尾的ERb 块。减号告诉ERb 不要在随后的HTML 结果文件中包括新行。下面例
子中,输出时不会在line one 和line two 之间有间隔。
line one
<% @time = Time.now -%>
line two

[color=red]Escaping Substituted Values[/color]

使用rhtml 有件重要的事情你必须知道。当你使用<%=…%>插入一个值时,它会直接进入
到输出流中。像下面情况。
The value of name is <%= params[:name] %>
通常情况下,这将请求用参数name 的值来替换。但是如果我们输入下面的URL 会怎样呢?
http://x.y.com/myapp?name=Hello%20%3cb%3ethere%3c/b%3e
奇怪的序列%3cb%3ethere%3c/b%3e 是一个HTML<b>there</b>的URL 编码版本。我们“模板”将替换它,并将页面中显示单词there。
这似乎不是个大问题,但是至多它会让你页打开时破损。最坏的情况我们会在427 页的
21 章看到,它的安全漏洞会让你的站点受到功击并丢失数据。
幸运地,解决起来很简单。总是转义任何你要替换进“模板”的文本,以表示这不是HTML。
rhtml“模板”带有一个做这件事的方法。它的长名字是html_escape(),但是大多数人只称
它为h()。
The value of name is <%= h(params[:name]) %>
习惯上是在你输入<%=之后立即输入h(。
如果你需要替换HTML 格式化的文本到一个“模板”中,你就不能使用h()方法,因为HTML
标记会被转义;用户看到的是<em>hello</em>而不是hello。总之,你不应该接受其它创建
的HTML 并显示在你的页面上。在427 页的21 章你会看到,这个错误会让你的应用程序受到
攻击。
sanitize()方法提供了一些保护。它接受一个包含HTML 的字符串并清除危险的部分:
<form>和<script>标记被转义,并且on=属性和javascript:开头的连接都会被删除。
我们的Depot 应用程序中的产品信息被做为HTML 提交(也就是说,它们没有被使用h()
方法转义)。这就允许我们在它们中植入格式化信息。如果我们允许外人进入这些描述,它应
该使用senitize()方法被保护起来以减少站点受到攻击的危险
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值