- 浏览: 249669 次
- 性别:
- 来自: 北京
文章分类
- 全部博客 (192)
- 技术研究学习 (19)
- 工作总结 (4)
- spring3.x (11)
- mail (2)
- jar (2)
- FCKeditor (1)
- quartz (2)
- json (1)
- jdbc (5)
- struts2 (6)
- java基础 (18)
- jboss (3)
- IT名称解析 (1)
- 测试工具 (2)
- 工作趣谈 (1)
- 数据库 (8)
- js (8)
- jquery (1)
- mysql (20)
- Sql (3)
- Oracle (1)
- easyui (0)
- log4j (1)
- 源码研究 (1)
- Jasper Report (0)
- Jbpm4 (4)
- xml (1)
- ireport (0)
- javavm (1)
- sitemesh (5)
- compass (1)
- jvm (1)
- ext (1)
- lucene (0)
- cxf (1)
- Blazeds (0)
- Resteasy (1)
- jaxb (1)
- tomcat (1)
- Rmi (1)
- BoneCP (1)
- velocity (3)
- OSCache (1)
- EHCache (1)
- 高性能开发 (9)
- 设计模式 (0)
- 网络协议应用 (1)
- Ibatis (1)
- powerdesigner (1)
- 架构师之路 (2)
- memcached (4)
- MapReduce (1)
- 测试组 (1)
- 图像处理 (2)
- LoadRunner (2)
- 报表 (1)
- 负载均衡 (1)
- 分布式 (3)
- c# (1)
- java中一些特殊问题 (3)
- java 8 (1)
- Mogodb (1)
- 项目设计与实现 (2)
- Ubuntu (1)
- eclipse (1)
- gradle (1)
- 私有云 (1)
- redis (1)
- 移动前端 (1)
最新评论
你打算结合多种技术来构建一个企业级web站点。比如,你准备采用J2EE技术往你的web站点里添加新内容,而这个系统的其他部分是用CGI或者微软的IIS Server搭建的。
在 这种情况下,怎样让你的应用系统从外观和感受(look and feel)上保持一致呢?一种办案就是采用J2EE技术全部重写,然后选用一种框架,比如Struts-Tiles,但这种办案的开发成本太高,不太现 实。另一种可选方案是在你的应用系统的各个部分采用相同的Look and Feel。但这种方案会使维护站点变成噩梦,因为每当一个应用系统里面的Look and Feel需要改变的时候,你就需要让系统里的其他web应用保持同样的改变。
大多数用于解决这种商务需求的可用框架都有一个共同的缺点, 他们不是平台相关就是框架相关。当你决定采用Tiles作为struts修饰器的时候,需要创建tiles定义文件tiles-defs.xml,然后在 struts-config.xml里面声明forwards,引用这些tiles以修饰原始的JSP。
最简单的一种可能的解决方案是,全部采用纯html方式来生成你的web应用,每一个html页面都不需要知道自己将会被如何修饰,而是在外部采用某种机制来选择合适的修饰器修饰它们。这就是SiteMesh的功能。
SiteMesh是基于Java、J2EE和XML的开源框架,依赖于从Servlet 2.3版本里引入的新功能——过滤器(Filters)
安装和设置
按照以往的经验,学习任何新技术或新框架最好的办法,就是使用它来创建一个简单的应用程序。所以,我们将使用SiteMesh来创建一个简单的Struts应用程序。我们的应用程序包括三个页面:
•一个登录页面
•一个帮助页面,包括页头和页脚
•一个主页面,包括页头、页脚和页边菜单
下面是创建这个简单web应用程序的步骤:
1.SiteMesh基于过滤器,所以我们需要把SiteMesh过滤器通知给我们的web应用程序。在web.xml文件里加入如下几行:
<filter>
<filter-name>sitemesh</filter-name>
<filter-class>
com.opensymphony.module.sitemesh.filter.PageFilter
</filter-class>
<init-param>
<param-name>debug.pagewriter</param-name>
<param-value>true</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>sitemesh</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
这 几行是告诉web容器,所有对web应用的请求都会经由PageFilter“过滤”一下。PageFilter是sitemesh-2.1.jar里的 一个类,你可以从http://www.opensymphony.com/sitemesh/download.html下载该jar包。
2.在WEB-INF目录下生成一个decorators.xml文件,内容如下:
<decorators defaultdir="/decorators">
<!— 给需要页边菜单的页面配置页边菜单修饰器 -->
<decorator name="sidemenu" page="sidemenu.jsp">
<pattern>/home.jsp</pattern>
</decorator>
<!— 给需要页头和页脚的页面配置页头页脚修饰器 -->
<decorator name="headerfooter" page="headerfooter.jsp">
<pattern>/help.jsp</pattern>
</decorator>
</decorators>
decorators.xml 文件用来在你的应用程序里定义修饰器(decorators)。在这个文件里,每个<decorator>元素定义一个修饰器,name指定 修饰器名,page指定修饰器所使用的JSP页面。<pattern>子元素指定这些修饰器如何应用到实际的页面上去。
在我 们的示例web应用里,定义了两个修饰器:追加页头和页脚的headerfooter.jsp和追加页边菜单的sidemenu.jsp。我们想修饰 help页面追加页头和页脚,所以我们追加了一个/help.jsp路径子元素给headerfooter.jsp修饰器。
3.在WebContent/decorators目录下创建headerfooter.jsp:
<%@ taglib uri="http://www.opensymphony.com/sitemesh/decorator" prefix="decorator" %>
<html>
<head>
<title>My Site - <decorator:title default="Welcome!" /></title>
<decorator:head />
</head>
<body>
<table>
<tr>
<td>
<H1>siteMesh Corporation<H1>
</td>
</tr>
<tr>
<td><decorator:body /></td>
</tr>
<tr>
<td> SiteMesh copyright</td>
</tr>
</table>
</body>
</html>
一 个SiteMesh修饰器其实就是一个使用SiteMesh自定义标签的JSP页面。在我们的web应用里,当用户请求help页面的时候, SiteMesh会拦截这个请求,然后再把它发送给web应用。而当应用返回响应的时候,SiteMesh会结合headerfooter.jsp文件解 析这个响应,遇到<decorator:head/>就插入响应文件的<head>,遇到<decorator: body/>就插入响应文件的<body>。最后,被headerfooter.jsp修饰过的文件会被返回给客户端。
4.在WebContent目录下创建help.jsp:
<HTML>
<HEAD>
<%@ page
language="java"
contentType="text/html; charset=ISO-8859-1"
pageEncoding="ISO-8859-1"
%>
<TITLE>Help Page</TITLE>
</HEAD>
<BODY>
Help Page
</BODY>
</HTML>
这是一个在web应用里很常见的help页面。
5.在浏览器里请求help.jsp页面,测试SiteMesh安装是否正常。浏览器将会返回一个包含页头和页脚的help页面。
SiteMesh架构
SiteMesh 架构基于PageFilter——一个Servlet过滤器。容器接收到页面请求时,会把请求传递给PageFilter,PageFilter收集应用 程序的响应细节,生成自定义的响应对象,然后连同请求一起传递给web应用程序。web应用程序把响应资源写入到自定义响应对象里,再返回给 PageFilter。
1.解析阶段
当控制返回给PageFilter的时候,它会检查web应用生成响应的内容类型 (content type),然后基于响应类型,生成不同的解析器来解析响应。比如,如果应用返回text/html类型的内容,SiteMesh会生成一个 FastPageParser实例,并把web应用生成的页面传递给它。FastPageParser会解析这个页面,提取出这个页面的header、 footer、title 等内容。
2.修饰阶段
解析结束后,SiteMesh开始修饰页面。这一阶段分成两部分:
a.决定如何修饰
SiteMesh 有一个概念,叫做修饰器映射,实现这个概念的接口是DecoratorMapper(有init()和getDecorator()方法)。映射器在 sitemesh.xml里声明。在sitemesh.xml文件里,每一个映射器都是它上一个映射器的父映射。当SiteMesh需要一个修饰器来修饰 页面的时候,会在sitemesh.xml里查找映射器,生成找到的第一个映射器的实例并调用getDecorator()方法,在这个方法里尝试查找针 对那个页面的修饰器。如果找到了就返回;否则,调用父映射器的getDecorator()方法,反复进行这个过程,直到找到正确的修饰器。
b.应用修饰
找到修饰器后,SiteMesh会把请求分发给它。修饰器JSP页面会访问在前阶段里解析出来的页面信息。使用各种SiteMesh自定义标签来提取页面信息不同的部分(比如header、footer和title)并把它们插入到输出文件合适的位置上去。
你可以在sitemesh.xml文件里自定义使用哪个页面解析器来解析指定的内容类型或者使用哪种修饰器映射方案,比如:
<?xml version="1.0" encoding="UTF-8"?>
<sitemesh>
<property name="decorators-file" value="/WEB-INF/decorators.xml"/>
<excludes file="${decorators-file}"/>
<page-parsers>
<parser content-type="text/html"
class="com.opensymphony.module.sitemesh.parser.FastPageParser" />
</page-parsers>
<decorator-mappers>
<mapper
class="com.opensymphony.module.sitemesh.mapper.PageDecoratorMapper">
<param name="property.1" value="meta.decorator" />
<param name="property.2" value="decorator" />
</mapper>
<!-- Mapper for localization -->
<mapper
class="com.opensymphony.module.sitemesh.mapper.LanguageDecoratorMapper">
<param name="match.en" value="en" />
<param name="match.zh" value="zh" />
</mapper>
<!-- Mapper for browser compatibility -->
<mapper
class="com.opensymphony.module.sitemesh.mapper.AgentDecoratorMapper">
<param name="match.MSIE" value="ie" />
<param name="match.Mozilla/" value="ns" />
</mapper>
<mapper
class="com.opensymphony.module.sitemesh.mapper.PrintableDecoratorMapper">
<param name="decorator" value="printable" />
<param name="parameter.name" value="printable" />
<param name="parameter.value" value="true" />
</mapper>
<mapper
class="com.opensymphony.module.sitemesh.mapper.ParameterDecoratorMapper">
<param name="decorator.parameter" value="decorator" />
<param name="parameter.name" value="confirm" />
<param name="parameter.value" value="true" />
</mapper>
<mapper
class="com.opensymphony.module.sitemesh.mapper.ConfigDecoratorMapper">
<param name="config" value="${decorators-file}" />
</mapper>
</decorator-mappers>
</sitemesh>
在 这个列表里,<property name="decorators-file">指定了用于定义修饰器的文件。<page-parsers>定义了SiteMesh可 以处理的内容类型。每一个<parser>子元素指定哪一个解析器解析哪一种特定的内容类型。在我们的示例sitemesh.xml文件里, 我们告诉SiteMesh使用FastPageParser解析text/html类型的内容。默认地,SiteMesh只可以处理HTML,但我们可以 创建自己的解析器来处理其他的内容类型。
<decorator-mappers>子元素定义了映射方案,SiteMesh使 用这个映射方案来查找修饰指定页面的修饰器。你可以使用<param>子元素来配置每一个映射器。SiteMesh会把这些配置信息包装成 java.util.Properties对象传递给映射器的init()方法。
区域相关的修饰器
在我们的示例sitemesh.xml文件里,有下面几行标签:
<mapper class="com.opensymphony.module.sitemesh.mapper.LanguageDecoratorMapper">
<param name="match.en" value="en" />
<param name="match.zh" value="zh" />
</mapper>
当 查找一个应用于页面的修饰器时,SiteMesh会首先读取请求头部的Accept-Language信息。如果匹配en区域,SiteMesh会在修饰 器JSP文件名末尾追加-en。在我们的例子里,如果请求定义了修饰器headerfooter.jsp的help.jsp页面,并且使用的是区域是英 国,SiteMesh会首先查找并应用headerfooter-en.jsp修饰器,如果找不到再去应用headerfooter.jsp。
浏览器相关的修饰器
可以使用AgentDecoratorMapper来保证浏览器的兼容性:
<mapper
class="com.opensymphony.module.sitemesh.mapper.AgentDecoratorMapper">
<param name="match.MSIE" value="ie" />
<param name="match.Mozilla/" value="ns" />
</mapper>
这意味着当SiteMesh查找一个修饰器来修饰页面的时候,会首先提取出请求头部的User-Agent信息。如果是IE,就加上-ie到修饰器的文件名末尾,并查找和应用这个修饰器。如果找不到这样的修饰器,则继续应用headerfooter.jsp。
高级SiteMesh
SiteMesh提供映射器,让每一个页面参与到寻找自己修饰器的过程中去。
PrintableDecoratorMapper
大 多数的web站点都提供了一个获得可打印版本页面的功能。所谓可打印版本,一般是指去除了页头、页尾和页边菜单,并使用了另一套样式表的页面。在 SiteMesh里,我们可以使用PrintableDecoratorMapper来提供这个功能。要使用这个映射器,需要在sitemesh.xml 里追加如下几行:
<mapper
class= "com.opensymphony.module.sitemesh.mapper.PrintableDecoratorMapper">
<param name="decorator" value="printable" />
<param name="parameter.name" value="printable" />
<param name="parameter.value" value="true" />
</mapper>
传递给PrintableDecoratorMapper的三个配置参数会被包装成java.util.Properties对象传递给init()方法。
•decorator
用来生成可打印版本页面的修饰器名。
•parameter.name
用来通知SiteMesh我们需要一个可打印版本的请求参数名。比如在我们的例子里,通过在查询字符串里追加printable=true参数传递
•parameter.value
设置可打印参数为何值时SiteMesh提供可打印版本的页面。
PageDecoratorMapper
页面可以通过定义META属性来重载指定修饰自己的修饰器名。
要使用这个映射器,需要在sitemesh.xml文件里加入如下几行:
<mapper
class="com.opensymphony.module.sitemesh.mapper.PageDecoratorMapper">
<param name="property.1" value="meta.decorator" />
</mapper>
PageDecoratorMapper可以获取一个参数列表。在我们的例子里,提供了一个参数名,指定了通过META属性来取得修饰器名。所以如果我们希望使用test修饰器来修饰页面,则在该页头部加入:
<META name="decorator" content="test">
PageDecoratorMapper提供了一种静态的方法来让页面选择自己想要使用的修饰器。另外,页面还可以通过使用ParameterDecoratorMapper在运行时指定要使用的修饰器。
ParameterDecoratorMapper
要使用ParameterDecoratorMapper,在sitemesh.xml里追加如下几行:
<mapper
class= "com.opensymphony.module.sitemesh.mapper.ParameterDecoratorMapper">
<param name="decorator.parameter" value="decorator" />
<param name="parameter.name" value="confirm" />
<param name="parameter.value" value="true" />
</mapper>
三个参数的意义分别如下:
•decorator.parameter
指定修饰器所使用的请求参数名。
•parameter.name
确定使用请求修饰器的确认参数名。
•parameter.value
确定使用请求修饰器的确认参数值。
比如,如果你想使用test修饰器来修饰help.jsp,可以像下面这样访问help.jsp
help.jsp?decorator=test&confirm=true
除了以上这些映射器以外,SiteMesh还提供了更多有用的映射器,比如:
•FrameSetDecoratorMapper
当页面是Frame的时候使用。
•CookieDecoratorMapper
可以通过cookie来指定想要使用的修饰器。
•RobotDecoratorMapper
当请求者被确人为robot的时候使用指定的修饰器。你可以手动的在请求头部追加robot关键字,或者通过修饰器来做。
Velocity 和 Freemarker 修饰器
SiteMesh 并没有限制你只能修饰JSP页面。你可以自由的选择想要修饰的对象,比如Velocity或者Freemarker。Velocity和 Freemarker是一种可被用于生成web页面的模板语言。这些语言比JSP更加的简单易用,但在可编程性方面不如JSP灵活。
SiteMesh通过两个servlet支持这两种模板语言,这两个servlet也被定义在SiteMesh.jar文件里。我们可以像这样在web.xml里声明这两个servlet:
<servlet>
<servlet-name>sitemesh-velocity</servlet-name>
<servlet-class>
com.opensymphony.module.sitemesh.velocity.VelocityDecoratorServlet
</servlet-class>
</servlet>
<!--Declare servlet for handling freemarker requests -->
<servlet>
<servlet-name>sitemesh-freemarker</servlet-name>
<servlet-class>
com.opensymphony.module.sitemesh.freemarker.FreemarkerDecoratorServlet
</servlet-class>
<init-param>
<param-name>TemplatePath</param-name>
<param-value>/</param-value>
</init-param>
<init-param>
<param-name>default_encoding</param-name>
<param-value>ISO-8859-1</param-value>
</init-param>
</servlet>
<!-- Velocity servlet should serve all requests with .vm extension-->
<servlet-mapping>
<servlet-name>sitemesh-velocity</servlet-name>
<url-pattern>*.vm</url-pattern>
</servlet-mapping>
<!-- FreeMarker servlet should serve all requests with .dec extension-->
<servlet-mapping>
<servlet-name>sitemesh-freemarker</servlet-name>
<url-pattern>*.dec</url-pattern>
</servlet-mapping>
当 然,我们还需要在lib文件夹里引入freemarker.jar、velocity-dep.jar和velocity-tools- view.jar。这些jar文件已经包含在SiteMesh的发布包里了。下面让我们修改第一个示例应用,使用Velocity和Freemarker 修饰器来取代JSP。在我们第一个示例应用里定义了两个修饰器:headerfooter和sidemenu。下面我们创建一个 headerfooter.dec:
<html>
<head>
<title>My Site - $Advanced SiteMesh</title>
${head}
</head>
<body>
<table border="1">
<tr>
<td>SiteMesh Corporation</td>
</tr>
<tr>
<td>${body}</td>
</tr>
<tr>
<td>SiteMesh copyright</td>
</tr>
</table>
</body>
</html>
在 这个页面里,我们使用Freemarker模板来请求header、footer和title,而不是使用JSP自定义标签,但页面布局是一样的。当容器 接收到一个.dec扩展名的页面请求时,会把这个请求传递给FreemarkerDecoratorServlet,后者将会调用 FreemarkerDecorator修饰生成的HTML页面。我们使用$Advanced SiteMesh模板来访问应用生成的web页面的title,${head}访问head,${body}访问body。Freemarker提供了非 常丰富的模板,想深入研究的话可以参考http://www.javaworld.com/jw-01-2001/jw-0119- freemarker.html。
相似的,在decorators目录下创建sidemenu.vm文件,这是Velocity修饰器文件:
<html>
<head>
<title>My Site - $title</title>
$head
</head>
<body>
<table border="1">
<tr>
<td> SiteMesh Header </td>
</tr>
<tr>
<td> Sidemenu </td>
<td> $body </td>
</tr>
<tr>
<td> SiteMesh Footer </td>
</tr>
</table>
</body>
</html>
使用$title模板取代<decorator:title/>,使用$head和$body Velocity模板来取代相应的JSP自定义标签。
结论
基 于过滤器的SiteMesh是一个非常灵活和简单易用的修饰器框架。但它还是存在着一些问题。首先,从Servlet 2.3版本才开始支持过滤器,所以一些早期版本的应用服务器无法支持SiteMesh。在使用SiteMesh之前请先检查一下您想使用的应用服务器是否 支持过滤器。
另外,过滤器只有在使用浏览器请求一个页面的时候才能生效。所以,如果你通过浏览器访问home.jsp,它将被修饰,但如 果你使用Servlet的RequestDispatcher.include()或者forward()来控制home.jsp,修饰器就不起作用了。 但是不用担心,从Servlet 2.4版本开始,你可以配置过滤器适用的环境,包括forward和include的情况下都可以使用了。
在 这种情况下,怎样让你的应用系统从外观和感受(look and feel)上保持一致呢?一种办案就是采用J2EE技术全部重写,然后选用一种框架,比如Struts-Tiles,但这种办案的开发成本太高,不太现 实。另一种可选方案是在你的应用系统的各个部分采用相同的Look and Feel。但这种方案会使维护站点变成噩梦,因为每当一个应用系统里面的Look and Feel需要改变的时候,你就需要让系统里的其他web应用保持同样的改变。
大多数用于解决这种商务需求的可用框架都有一个共同的缺点, 他们不是平台相关就是框架相关。当你决定采用Tiles作为struts修饰器的时候,需要创建tiles定义文件tiles-defs.xml,然后在 struts-config.xml里面声明forwards,引用这些tiles以修饰原始的JSP。
最简单的一种可能的解决方案是,全部采用纯html方式来生成你的web应用,每一个html页面都不需要知道自己将会被如何修饰,而是在外部采用某种机制来选择合适的修饰器修饰它们。这就是SiteMesh的功能。
SiteMesh是基于Java、J2EE和XML的开源框架,依赖于从Servlet 2.3版本里引入的新功能——过滤器(Filters)
安装和设置
按照以往的经验,学习任何新技术或新框架最好的办法,就是使用它来创建一个简单的应用程序。所以,我们将使用SiteMesh来创建一个简单的Struts应用程序。我们的应用程序包括三个页面:
•一个登录页面
•一个帮助页面,包括页头和页脚
•一个主页面,包括页头、页脚和页边菜单
下面是创建这个简单web应用程序的步骤:
1.SiteMesh基于过滤器,所以我们需要把SiteMesh过滤器通知给我们的web应用程序。在web.xml文件里加入如下几行:
<filter>
<filter-name>sitemesh</filter-name>
<filter-class>
com.opensymphony.module.sitemesh.filter.PageFilter
</filter-class>
<init-param>
<param-name>debug.pagewriter</param-name>
<param-value>true</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>sitemesh</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
这 几行是告诉web容器,所有对web应用的请求都会经由PageFilter“过滤”一下。PageFilter是sitemesh-2.1.jar里的 一个类,你可以从http://www.opensymphony.com/sitemesh/download.html下载该jar包。
2.在WEB-INF目录下生成一个decorators.xml文件,内容如下:
<decorators defaultdir="/decorators">
<!— 给需要页边菜单的页面配置页边菜单修饰器 -->
<decorator name="sidemenu" page="sidemenu.jsp">
<pattern>/home.jsp</pattern>
</decorator>
<!— 给需要页头和页脚的页面配置页头页脚修饰器 -->
<decorator name="headerfooter" page="headerfooter.jsp">
<pattern>/help.jsp</pattern>
</decorator>
</decorators>
decorators.xml 文件用来在你的应用程序里定义修饰器(decorators)。在这个文件里,每个<decorator>元素定义一个修饰器,name指定 修饰器名,page指定修饰器所使用的JSP页面。<pattern>子元素指定这些修饰器如何应用到实际的页面上去。
在我 们的示例web应用里,定义了两个修饰器:追加页头和页脚的headerfooter.jsp和追加页边菜单的sidemenu.jsp。我们想修饰 help页面追加页头和页脚,所以我们追加了一个/help.jsp路径子元素给headerfooter.jsp修饰器。
3.在WebContent/decorators目录下创建headerfooter.jsp:
<%@ taglib uri="http://www.opensymphony.com/sitemesh/decorator" prefix="decorator" %>
<html>
<head>
<title>My Site - <decorator:title default="Welcome!" /></title>
<decorator:head />
</head>
<body>
<table>
<tr>
<td>
<H1>siteMesh Corporation<H1>
</td>
</tr>
<tr>
<td><decorator:body /></td>
</tr>
<tr>
<td> SiteMesh copyright</td>
</tr>
</table>
</body>
</html>
一 个SiteMesh修饰器其实就是一个使用SiteMesh自定义标签的JSP页面。在我们的web应用里,当用户请求help页面的时候, SiteMesh会拦截这个请求,然后再把它发送给web应用。而当应用返回响应的时候,SiteMesh会结合headerfooter.jsp文件解 析这个响应,遇到<decorator:head/>就插入响应文件的<head>,遇到<decorator: body/>就插入响应文件的<body>。最后,被headerfooter.jsp修饰过的文件会被返回给客户端。
4.在WebContent目录下创建help.jsp:
<HTML>
<HEAD>
<%@ page
language="java"
contentType="text/html; charset=ISO-8859-1"
pageEncoding="ISO-8859-1"
%>
<TITLE>Help Page</TITLE>
</HEAD>
<BODY>
Help Page
</BODY>
</HTML>
这是一个在web应用里很常见的help页面。
5.在浏览器里请求help.jsp页面,测试SiteMesh安装是否正常。浏览器将会返回一个包含页头和页脚的help页面。
SiteMesh架构
SiteMesh 架构基于PageFilter——一个Servlet过滤器。容器接收到页面请求时,会把请求传递给PageFilter,PageFilter收集应用 程序的响应细节,生成自定义的响应对象,然后连同请求一起传递给web应用程序。web应用程序把响应资源写入到自定义响应对象里,再返回给 PageFilter。
1.解析阶段
当控制返回给PageFilter的时候,它会检查web应用生成响应的内容类型 (content type),然后基于响应类型,生成不同的解析器来解析响应。比如,如果应用返回text/html类型的内容,SiteMesh会生成一个 FastPageParser实例,并把web应用生成的页面传递给它。FastPageParser会解析这个页面,提取出这个页面的header、 footer、title 等内容。
2.修饰阶段
解析结束后,SiteMesh开始修饰页面。这一阶段分成两部分:
a.决定如何修饰
SiteMesh 有一个概念,叫做修饰器映射,实现这个概念的接口是DecoratorMapper(有init()和getDecorator()方法)。映射器在 sitemesh.xml里声明。在sitemesh.xml文件里,每一个映射器都是它上一个映射器的父映射。当SiteMesh需要一个修饰器来修饰 页面的时候,会在sitemesh.xml里查找映射器,生成找到的第一个映射器的实例并调用getDecorator()方法,在这个方法里尝试查找针 对那个页面的修饰器。如果找到了就返回;否则,调用父映射器的getDecorator()方法,反复进行这个过程,直到找到正确的修饰器。
b.应用修饰
找到修饰器后,SiteMesh会把请求分发给它。修饰器JSP页面会访问在前阶段里解析出来的页面信息。使用各种SiteMesh自定义标签来提取页面信息不同的部分(比如header、footer和title)并把它们插入到输出文件合适的位置上去。
你可以在sitemesh.xml文件里自定义使用哪个页面解析器来解析指定的内容类型或者使用哪种修饰器映射方案,比如:
<?xml version="1.0" encoding="UTF-8"?>
<sitemesh>
<property name="decorators-file" value="/WEB-INF/decorators.xml"/>
<excludes file="${decorators-file}"/>
<page-parsers>
<parser content-type="text/html"
class="com.opensymphony.module.sitemesh.parser.FastPageParser" />
</page-parsers>
<decorator-mappers>
<mapper
class="com.opensymphony.module.sitemesh.mapper.PageDecoratorMapper">
<param name="property.1" value="meta.decorator" />
<param name="property.2" value="decorator" />
</mapper>
<!-- Mapper for localization -->
<mapper
class="com.opensymphony.module.sitemesh.mapper.LanguageDecoratorMapper">
<param name="match.en" value="en" />
<param name="match.zh" value="zh" />
</mapper>
<!-- Mapper for browser compatibility -->
<mapper
class="com.opensymphony.module.sitemesh.mapper.AgentDecoratorMapper">
<param name="match.MSIE" value="ie" />
<param name="match.Mozilla/" value="ns" />
</mapper>
<mapper
class="com.opensymphony.module.sitemesh.mapper.PrintableDecoratorMapper">
<param name="decorator" value="printable" />
<param name="parameter.name" value="printable" />
<param name="parameter.value" value="true" />
</mapper>
<mapper
class="com.opensymphony.module.sitemesh.mapper.ParameterDecoratorMapper">
<param name="decorator.parameter" value="decorator" />
<param name="parameter.name" value="confirm" />
<param name="parameter.value" value="true" />
</mapper>
<mapper
class="com.opensymphony.module.sitemesh.mapper.ConfigDecoratorMapper">
<param name="config" value="${decorators-file}" />
</mapper>
</decorator-mappers>
</sitemesh>
在 这个列表里,<property name="decorators-file">指定了用于定义修饰器的文件。<page-parsers>定义了SiteMesh可 以处理的内容类型。每一个<parser>子元素指定哪一个解析器解析哪一种特定的内容类型。在我们的示例sitemesh.xml文件里, 我们告诉SiteMesh使用FastPageParser解析text/html类型的内容。默认地,SiteMesh只可以处理HTML,但我们可以 创建自己的解析器来处理其他的内容类型。
<decorator-mappers>子元素定义了映射方案,SiteMesh使 用这个映射方案来查找修饰指定页面的修饰器。你可以使用<param>子元素来配置每一个映射器。SiteMesh会把这些配置信息包装成 java.util.Properties对象传递给映射器的init()方法。
区域相关的修饰器
在我们的示例sitemesh.xml文件里,有下面几行标签:
<mapper class="com.opensymphony.module.sitemesh.mapper.LanguageDecoratorMapper">
<param name="match.en" value="en" />
<param name="match.zh" value="zh" />
</mapper>
当 查找一个应用于页面的修饰器时,SiteMesh会首先读取请求头部的Accept-Language信息。如果匹配en区域,SiteMesh会在修饰 器JSP文件名末尾追加-en。在我们的例子里,如果请求定义了修饰器headerfooter.jsp的help.jsp页面,并且使用的是区域是英 国,SiteMesh会首先查找并应用headerfooter-en.jsp修饰器,如果找不到再去应用headerfooter.jsp。
浏览器相关的修饰器
可以使用AgentDecoratorMapper来保证浏览器的兼容性:
<mapper
class="com.opensymphony.module.sitemesh.mapper.AgentDecoratorMapper">
<param name="match.MSIE" value="ie" />
<param name="match.Mozilla/" value="ns" />
</mapper>
这意味着当SiteMesh查找一个修饰器来修饰页面的时候,会首先提取出请求头部的User-Agent信息。如果是IE,就加上-ie到修饰器的文件名末尾,并查找和应用这个修饰器。如果找不到这样的修饰器,则继续应用headerfooter.jsp。
高级SiteMesh
SiteMesh提供映射器,让每一个页面参与到寻找自己修饰器的过程中去。
PrintableDecoratorMapper
大 多数的web站点都提供了一个获得可打印版本页面的功能。所谓可打印版本,一般是指去除了页头、页尾和页边菜单,并使用了另一套样式表的页面。在 SiteMesh里,我们可以使用PrintableDecoratorMapper来提供这个功能。要使用这个映射器,需要在sitemesh.xml 里追加如下几行:
<mapper
class= "com.opensymphony.module.sitemesh.mapper.PrintableDecoratorMapper">
<param name="decorator" value="printable" />
<param name="parameter.name" value="printable" />
<param name="parameter.value" value="true" />
</mapper>
传递给PrintableDecoratorMapper的三个配置参数会被包装成java.util.Properties对象传递给init()方法。
•decorator
用来生成可打印版本页面的修饰器名。
•parameter.name
用来通知SiteMesh我们需要一个可打印版本的请求参数名。比如在我们的例子里,通过在查询字符串里追加printable=true参数传递
•parameter.value
设置可打印参数为何值时SiteMesh提供可打印版本的页面。
PageDecoratorMapper
页面可以通过定义META属性来重载指定修饰自己的修饰器名。
要使用这个映射器,需要在sitemesh.xml文件里加入如下几行:
<mapper
class="com.opensymphony.module.sitemesh.mapper.PageDecoratorMapper">
<param name="property.1" value="meta.decorator" />
</mapper>
PageDecoratorMapper可以获取一个参数列表。在我们的例子里,提供了一个参数名,指定了通过META属性来取得修饰器名。所以如果我们希望使用test修饰器来修饰页面,则在该页头部加入:
<META name="decorator" content="test">
PageDecoratorMapper提供了一种静态的方法来让页面选择自己想要使用的修饰器。另外,页面还可以通过使用ParameterDecoratorMapper在运行时指定要使用的修饰器。
ParameterDecoratorMapper
要使用ParameterDecoratorMapper,在sitemesh.xml里追加如下几行:
<mapper
class= "com.opensymphony.module.sitemesh.mapper.ParameterDecoratorMapper">
<param name="decorator.parameter" value="decorator" />
<param name="parameter.name" value="confirm" />
<param name="parameter.value" value="true" />
</mapper>
三个参数的意义分别如下:
•decorator.parameter
指定修饰器所使用的请求参数名。
•parameter.name
确定使用请求修饰器的确认参数名。
•parameter.value
确定使用请求修饰器的确认参数值。
比如,如果你想使用test修饰器来修饰help.jsp,可以像下面这样访问help.jsp
help.jsp?decorator=test&confirm=true
除了以上这些映射器以外,SiteMesh还提供了更多有用的映射器,比如:
•FrameSetDecoratorMapper
当页面是Frame的时候使用。
•CookieDecoratorMapper
可以通过cookie来指定想要使用的修饰器。
•RobotDecoratorMapper
当请求者被确人为robot的时候使用指定的修饰器。你可以手动的在请求头部追加robot关键字,或者通过修饰器来做。
Velocity 和 Freemarker 修饰器
SiteMesh 并没有限制你只能修饰JSP页面。你可以自由的选择想要修饰的对象,比如Velocity或者Freemarker。Velocity和 Freemarker是一种可被用于生成web页面的模板语言。这些语言比JSP更加的简单易用,但在可编程性方面不如JSP灵活。
SiteMesh通过两个servlet支持这两种模板语言,这两个servlet也被定义在SiteMesh.jar文件里。我们可以像这样在web.xml里声明这两个servlet:
<servlet>
<servlet-name>sitemesh-velocity</servlet-name>
<servlet-class>
com.opensymphony.module.sitemesh.velocity.VelocityDecoratorServlet
</servlet-class>
</servlet>
<!--Declare servlet for handling freemarker requests -->
<servlet>
<servlet-name>sitemesh-freemarker</servlet-name>
<servlet-class>
com.opensymphony.module.sitemesh.freemarker.FreemarkerDecoratorServlet
</servlet-class>
<init-param>
<param-name>TemplatePath</param-name>
<param-value>/</param-value>
</init-param>
<init-param>
<param-name>default_encoding</param-name>
<param-value>ISO-8859-1</param-value>
</init-param>
</servlet>
<!-- Velocity servlet should serve all requests with .vm extension-->
<servlet-mapping>
<servlet-name>sitemesh-velocity</servlet-name>
<url-pattern>*.vm</url-pattern>
</servlet-mapping>
<!-- FreeMarker servlet should serve all requests with .dec extension-->
<servlet-mapping>
<servlet-name>sitemesh-freemarker</servlet-name>
<url-pattern>*.dec</url-pattern>
</servlet-mapping>
当 然,我们还需要在lib文件夹里引入freemarker.jar、velocity-dep.jar和velocity-tools- view.jar。这些jar文件已经包含在SiteMesh的发布包里了。下面让我们修改第一个示例应用,使用Velocity和Freemarker 修饰器来取代JSP。在我们第一个示例应用里定义了两个修饰器:headerfooter和sidemenu。下面我们创建一个 headerfooter.dec:
<html>
<head>
<title>My Site - $Advanced SiteMesh</title>
${head}
</head>
<body>
<table border="1">
<tr>
<td>SiteMesh Corporation</td>
</tr>
<tr>
<td>${body}</td>
</tr>
<tr>
<td>SiteMesh copyright</td>
</tr>
</table>
</body>
</html>
在 这个页面里,我们使用Freemarker模板来请求header、footer和title,而不是使用JSP自定义标签,但页面布局是一样的。当容器 接收到一个.dec扩展名的页面请求时,会把这个请求传递给FreemarkerDecoratorServlet,后者将会调用 FreemarkerDecorator修饰生成的HTML页面。我们使用$Advanced SiteMesh模板来访问应用生成的web页面的title,${head}访问head,${body}访问body。Freemarker提供了非 常丰富的模板,想深入研究的话可以参考http://www.javaworld.com/jw-01-2001/jw-0119- freemarker.html。
相似的,在decorators目录下创建sidemenu.vm文件,这是Velocity修饰器文件:
<html>
<head>
<title>My Site - $title</title>
$head
</head>
<body>
<table border="1">
<tr>
<td> SiteMesh Header </td>
</tr>
<tr>
<td> Sidemenu </td>
<td> $body </td>
</tr>
<tr>
<td> SiteMesh Footer </td>
</tr>
</table>
</body>
</html>
使用$title模板取代<decorator:title/>,使用$head和$body Velocity模板来取代相应的JSP自定义标签。
结论
基 于过滤器的SiteMesh是一个非常灵活和简单易用的修饰器框架。但它还是存在着一些问题。首先,从Servlet 2.3版本才开始支持过滤器,所以一些早期版本的应用服务器无法支持SiteMesh。在使用SiteMesh之前请先检查一下您想使用的应用服务器是否 支持过滤器。
另外,过滤器只有在使用浏览器请求一个页面的时候才能生效。所以,如果你通过浏览器访问home.jsp,它将被修饰,但如 果你使用Servlet的RequestDispatcher.include()或者forward()来控制home.jsp,修饰器就不起作用了。 但是不用担心,从Servlet 2.4版本开始,你可以配置过滤器适用的环境,包括forward和include的情况下都可以使用了。
相关推荐
sitemesh 使用例子。 <?xml version="1.0" encoding="utf-8"?> <decorators defaultdir="/decorators"> <!-- 此处用来定义不需要过滤的页面 --> <excludes> </excludes> <!-- 用来定义装饰器要过滤的...
如果需要对某些特定页面不应用装饰,或者只对特定部分进行装饰,可以使用 `excludes` 和 `includes` 属性在 `web.xml` 中配置 SiteMesh 过滤器。 9. **优化与性能** SiteMesh 通常对性能的影响很小,但可以通过...
### Sitemesh使用示例 在提供的压缩包文件中,有多个HTML和JSP文件,它们可能是Sitemesh的使用示例: - **index.html**:通常作为网站的主页,可能展示了Sitemesh如何应用全局布局。 - **badsource.html**、**...
接下来是"siteMesh使用文档"。这份文档通常会涵盖以下几个关键知识点: 1. **安装SiteMesh**:这通常包括下载SiteMesh的库文件,将其添加到你的项目构建路径中(例如,如果你使用Maven,可以在pom.xml中添加对应的...
3. **创建装饰模板**:Sitemesh使用HTML文件作为装饰模板,你可以根据需求创建一个基础模板,例如`layout.html`,该模板通常包含页头、页脚、侧边栏等公共部分。 4. **设置页面内容**:对于每个需要装饰的页面,...
3. **创建装饰模板**:Sitemesh 使用一个名为 `decorators` 的目录来存储装饰模板。这些模板定义了页面的通用结构,如头部、底部和侧边栏。例如,你可以创建一个 `default.jsp` 文件,其中包含你的页面布局。 4. **...
- **更强大的过滤器**:在Servlet容器中,Sitemesh 使用过滤器拦截请求和响应,增强了对页面装饰的控制。 - **API改进**:提供了更为简洁、易于使用的API,便于开发者进行定制和扩展。 - **性能优化**:相比之前的...
3. **Sitemesh使用步骤** - **安装与导入**:下载Sitemesh库并将其加入到项目依赖中。 - **配置web.xml**:设置Sitemesh Filter,包括装饰器的配置和默认装饰器的选择。 - **创建装饰器模板**:设计HTML模板,...
通过这个简单的 demo,你可以学习到如何在实际项目中集成和使用 Sitemesh,以提高网站的整体一致性和美观性。同时,Sitemesh 还支持自定义装饰策略、多装饰器应用、动态装饰等功能,可以根据项目需求进行深入研究和...
SiteMesh 是一个开源的 J2EE 页面布局和装饰框架,主要用来解决Web应用程序中的内容与表现层分离的问题。它的设计灵感来源于设计模式中...通过合理地使用SiteMesh,你可以创建出既具有统一风格,又易于维护的Web应用。
3. **使用Spring MVC或Struts2**:如果项目使用了Spring MVC或Struts2等框架,Sitemesh有对应的整合方式,可以更方便地实现页面装饰。 4. **处理Ajax请求**:Sitemesh默认不处理Ajax请求,但可以通过自定义Filter或...
8. **文档和实例**:在提供的资料中,文档将详细介绍如何安装、配置和使用SiteMesh 2.3,实例则可以帮助初学者快速理解和上手实践。 9. **依赖库(Lib)**:SiteMesh 2.3 包含了运行所需的库文件,确保了在各种环境...
Sitemesh使用`<decorator>`标签来定义装饰器,以及`<include>`标签来插入页面内容。 **Struts2 Sitemesh插件** `struts2-sitemesh-plugin-2.2.1.1.jar`是Struts2与Sitemesh集成的关键组件。它使得Struts2应用可以...
- 在需要装饰的页面上,可以使用特殊的注释(例如 `<@sitemesh.page>`)来指定页面内容应插入到布局的哪个部分。 - SiteMesh 提供了一些自定义选项,比如通过 `decorators.xml` 文件来指定哪些页面使用哪种布局,...
在 `sitemesh-2.3.zip` 文件中,包含了该框架的源码、文档、构建文件以及库文件,便于我们了解和使用 Sitemesh。 1. **构建文件** - `build.properties`: 这是一个属性文件,包含了构建过程中的配置参数,如版本...
2. **过滤器机制**:Sitemesh使用Servlet过滤器来拦截HTTP请求,对响应内容进行处理。当用户请求一个页面时,Sitemesh过滤器会捕获这个请求,然后应用装饰模板。 3. **模板语言**:Sitemesh支持多种模板语言,包括...
7. **API 使用**:在 `sitemesh-2.4.1.jar` 文件中,包含了 SiteMesh 的核心 API,开发者可以通过编程方式控制 SiteMesh 的行为,如手动触发装饰过程或获取当前装饰状态。 8. **文档与示例**:通常,完整的 ...
**Sitemesh使用** 1. **标记可装饰页面**:在要装饰的JSP或HTML页面中,使用`<@sitemesh.page>`指令标签来标记页面,让Sitemesh知道这个页面需要被装饰。 2. **自定义装饰规则**:可以通过配置文件(通常为`...
SiteMesh 使用装饰器(Decorator)模式来实现其功能。装饰器模式允许在不修改原有对象的情况下,为对象添加新的行为或属性。在 SiteMesh 中,装饰器页面是包含页面布局和通用元素的模板,比如页头、页脚和侧边栏。当...
通过使用 SiteMesh,可以将页面的头部、底部、侧边栏等公共部分抽取出来,作为模板,然后在每个页面中应用这个模板,从而保持网站的整体风格一致。SiteMesh 使用过滤器(Filter)来拦截HTTP请求和响应,将页面内容与...