Posted on 2010-02-06 12:36
云自无心水自闲 阅读(3572)
评论(4) 编辑 收藏 所属分类:
Java 、
心得体会 、
Tapestry
在tapestry5中,在页面之间传递基本有3种方法
1、存放在Session中
2、使用@Persist进行持久化
3、使用页面context来传递参数。
其中1和2都需要将数据存放在Session中,相对来说系统的开销比较大。尤其是多用户高并发情况下,对于性能可能会有一定的影响。
使用页面Context来传递则需要在开发时写一些代码,增加了一些开发量,显得没有前两种方法方便。
第3种方法的实现是需要在页面中添加onActivate和onPassivate方法来完成页面参数的传递。
我们先来看一下其背后的故事。
举个例子,比如说我们有两个页面,第一个是查询条件输入页面input,另一个是查询结果输出页面output。input页面中有两个查询条件,起始时间dateFrom和终止时间dateTo
在Input.java中,我们可以很直观地这样写:
@InjectPage
private Output output;
@Property
private String dateFrom;
@Property
private String dateTo;
Object onFormSubmit() {
output.setDateFrom(dateFrom);
output.setDateTo(dateTo);
return output;
}
首先使用注解注入output页面,然后在表单的提交事件中,返回output,这样就在程序中定义了返回页面,而不是使用配置文件的方式。
但是这样的实现却不能正确运行,原因是因为Tapestry5的使用了页面池技术,页面在每次渲染前都是从页面池中随机获取一个页面,而从页面池中取得的页面,所有的属性都是被清空了的。
也就是说在上例中,虽然我们注入了output页面,但是此页面马上就被放入了页面池,而且其中的属性值马上就被清空了。这就是引入onActivate和onPassivate这丙个方法的原因。tapestry5在清空属性前会首先查看是否包含onPassivate方法,如果有,就把其返回值保存起来,然后从页面池中取得页面后,再把刚才保存的值作为参数传递给onActivate方法。
这就是方法3的基本原理,但是无论是在官方的文档或是示例或者网上其他的应用中,可以发现大部分都是使用单个参数的,比如说id。这也很容易理解,因为onPassivate的方法的返回值只能有一个。
在Tapestry5的官方文档中,只有一句非常简要的话介绍了如果传递多个文档的方法: The activation context may consist of a series of values, in which case the return value of the method should be an array or a List. (参见:http://tapestry.apache.org/tapestry5.1/guide/pagenav.html)。
但是这并不是说只要在onPassivate中把参数的值加入到List中,返回一个List,而在onActivate中接受一个List参数,然后就可以得到其中的参数了,因为Tapestry5把参数传给onActivate的方法其实是通过将参数作为HttpRequest中的参数的。如果试图使用上述方法就是得到一个“无法将List转换成String的错误”
所以方法应该是这样的,在Output中:
private List<String> paramList;
public void setParamList(List<String> paramList) {
this.paramList = paramList;
}
public List<String> getParamList() {
return paramList;
}
List<String> onPassivate() {
return paramList;
}
void onActivate(String dateFrom, String dateTo) {
this.dateFrom = dateFrom;
this.dateTo = dateTo;
}
private String dateFrom;
private String dateTo;
在Input页面中,需要把onFormSubmit改一下:
Object onFormSubmit() {
List<String> list = new ArrayList<String>();
output.setParamList(list);
return output;
}
其中,需要注意的是output中的onActivate方法,基参数的顺序必须和List中放入的参数顺序一致。