`
zuiyanwangyue
  • 浏览: 167160 次
  • 性别: Icon_minigender_1
  • 来自: 河北
社区版块
存档分类
最新评论

由servlet2.3升级到servlet2.4时使用了displaytag的el版本的页面没数据了

阅读更多

背景:

 

    项目需要在web.xml中配置的过滤器不仅能够拦截浏览器向服务器直接发出的request请求,同时也应该能够拦截转发请求,即通过调用request.getRequestDispatcher(forwardURI).forward(request, response)由服务器内部通过转发的方式直接产生的请求,但是这在servlet2.3规范中是做不到的。

 

解决方案:

 

    Servlet2.4规范通过给<filter-mapping>增加子元素<dispatcher>解决了这个问题,<dispatcher>元素有四种可能的取值:REQUEST、FORWARD、INCLUDE和ERROR,分别代表不同的请求类型,其中forward即代表转发。

 

    所以我首先将web.xml从2.3版本升级到2.4,升级过程如下:

    升级前的2.3版本:

<!DOCTYPE web-app PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN" "http://java.sun.com/dtd/web-app_2_3.dtd">
<web-app>
……
</web-app>

     升级后的2.4版本(2.4版本的部署描述符是基于XML Schema定义的):

<web-app xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd" version="2.4">
……
</web-app>

     接下来为要过滤转发请求的<filter-mapping>增加<dispatcher>元素,关键代码如下:

<filter-mapping>
        <filter-name>struts2</filter-name>
        <url-pattern>/*</url-pattern>
        <dispatcher>FORWARD</dispatcher>    
        <dispatcher>REQUEST</dispatcher>
</filter-mapping>

     然后启动应用程序服务器(Tomcat5.5.30),接下来发生了不可思议的“灵异”事件,本来通过使用displaytag标签能够正常显示表格数据的页面突然之间显示“没有数据可供显示”,附页面使用displaytag(标签库是用的EL版本:<%@ taglib uri="http://displaytag.sf.net/el " prefix="display" %>)的主要代码:  

<display:table id="listID" name="${acctList}" partialList="true" size="${actionPagination.recordTotal}" 
		pagesize="${actionPagination.pagesize}" export="true"  requestURI="familyAccountAction.do" class="list">
	<display:column title="选择" media="html" property="familyAccountId" decorator="radio"></display:column>
	<display:column title="发生日期" property="exeDate" sortable="true" headerClass="sortable" decorator="nyrDateColumnDecorator"/>
</display:table>

     接下来就是我解决这个问题的漫漫征途,因为我在这之前并未改动过项目的其它任何文件,所以问题的根源显然在升级web.xml上,但是究竟是为什么呢?

    我首先对出现问题的JSP页面在升级前后tomcat将其编译的servlet源码进行了对比,结果确实发现了有价值的线索。

    使用Servlet2.3版本时tomcat对其编译产生的servlet文件的源码片段:  

    org.displaytag.tags.el.ELTableTag _jspx_th_display_005ftable_005f0 = (org.displaytag.tags.el.ELTableTag) _005fjspx_005ftagPool_005fdisplay_005ftable_0026_005fsize_005frequestURI_005fpartialList_005fpagesize_005fname_005fid_005fexport_005fclass.get(org.displaytag.tags.el.ELTableTag.class);
    _jspx_th_display_005ftable_005f0.setPageContext(_jspx_page_context);
    _jspx_th_display_005ftable_005f0.setParent(null);
    _jspx_th_display_005ftable_005f0.setUid("listID");
    _jspx_th_display_005ftable_005f0.setName("${acctList}");
    _jspx_th_display_005ftable_005f0.setPartialList(true);
    _jspx_th_display_005ftable_005f0.setSize("${actionPagination.recordTotal}");
    _jspx_th_display_005ftable_005f0.setPagesize("${actionPagination.pagesize}");

 

    使用Servlet2.4版本时tomcat对其编译产生的servlet文件的源码片段: 

    org.displaytag.tags.el.ELTableTag _jspx_th_display_005ftable_005f0 = (org.displaytag.tags.el.ELTableTag) _005fjspx_005ftagPool_005fdisplay_005ftable_0026_005fsize_005frequestURI_005fpartialList_005fpagesize_005fname_005fid_005fexport_005fclass.get(org.displaytag.tags.el.ELTableTag.class);
    _jspx_th_display_005ftable_005f0.setPageContext(_jspx_page_context);
    _jspx_th_display_005ftable_005f0.setParent(null);
    _jspx_th_display_005ftable_005f0.setUid("listID");
    _jspx_th_display_005ftable_005f0.setName((java.lang.String) org.apache.jasper.runtime.PageContextImpl.proprietaryEvaluate("${acctList}", java.lang.String.class, (PageContext)_jspx_page_context, null, false));
    _jspx_th_display_005ftable_005f0.setPartialList(true);
    _jspx_th_display_005ftable_005f0.setSize((java.lang.String) org.apache.jasper.runtime.PageContextImpl.proprietaryEvaluate("${actionPagination.recordTotal}", java.lang.String.class, (PageContext)_jspx_page_context, null, false));
    _jspx_th_display_005ftable_005f0.setPagesize((java.lang.String) org.apache.jasper.runtime.PageContextImpl.proprietaryEvaluate("${actionPagination.pagesize}", java.lang.String.class, (PageContext)_jspx_page_context, null, false));

     由此可以看出,在使用Servlet2.4规范之后,tomcat在jsp的编译过程中自动对EL表达式进行解释(注:servlet2.3规范对应jsp1.2而servlet2.4规范对应jsp2.0),因为从jsp2.0规范开始引入了 EL表达式 。如下表述译自jsp2.0规范第22页:

 

    Jsp2.0规范的第22页:

    JSP容器使用web.xml的版本号去检测应该使用jsp1.2规范还是jsp2.0规范,故而一些特性会因为web.xml的版本号不同而表现出不同的行为。下面列举了一个清单,当开发者把web.xml从servelet2.3更新到servlet2.4时应该特别注意它们,其中第一条就提到:

 

    EL表达式在JSP1.2中默认是被忽略的,当把web应用程序更新到jsp2.0时,EL表达式会被自动进行解释。转义序列\$可以被用于禁用EL表达式,这样容器就不会对它进行解释。另外,也可以使用page指令的isELIgnored属性或者<el-ignored>配置元素来禁用EL表达式。使用JSTL1.0的用户有两种选择,一是更新标签库导入jstl1.1的URIS,二是使用这些标签库的RT(请求时属性)版本而不是EL版本(例如使用c_rt代替c、使用fmt_rt代替fmt)。

 

    由此我们就不难解释上面遇到的问题并给出解决方案:

    方案一:由使用Displaytag的EL版本改为使用非EL版本,因为其el版本是为不支持el表达式的实现jsp1.2规范的web容器所定制的,支持jsp2.0规范的web容器同时也会自动支持el,所以就无需再使用专门为jsp1.2规范所定制的el版本的标签库了。

    方案二:升级到jsp2.0之后,仍然使用displaytag的el版本,但是需要在page指令中设置忽略el表达式标志为true,<%@page isELIgnored="true"% >,以便使web容器忽略el表达式。

    方案三:升级到jsp2.0之后,仍然使用displaytag的el版本,但是页面中相应的代码需要改成下面的样子:

<display:table id="listID" name="acctList" partialList="true" size="actionPagination.recordTotal" 
		pagesize="${actionPagination.pagesize}" export="true"  requestURI="familyAccountAction.do" class="list">
	<display:column title="选择" media="html" property="familyAccountId" decorator="radio"></display:column>
	<display:column title="发生日期" property="exeDate" sortable="true" headerClass="sortable" decorator="nyrDateColumnDecorator"/>
</display:table>
    也就是在name和size属性上不再使用el表达式,displaytag标签会调用表达式管理器去进行解释,这与web容器是无关的。

0
0
分享到:
评论

相关推荐

    displaytag标签的使用

    如果你的项目使用的是 Servlet 2.4 之前的版本,需要在 `web.xml` 中手动配置这两个标签库的位置。 要展示数据,DisplayTag 需要在请求或会话范围内获取一个 List 对象。数据可以通过 Hibernate 或其他查询方式获取...

    displayTag使用总结.doc

    - **属性表达式**:可以使用EL(Expression Language)表达式来动态获取数据,例如`${item.property}" /&gt;`。 总的来说,DisplayTag提供了一套完整的表格处理解决方案,使开发者能够更专注于业务逻辑,而不是页面...

    jsp分页经典实例(采用经典分页组建displaytag)

    3. 配置JSP页面,使用DisplayTag标签显示数据和分页导航。 4. 在后台处理HTTP请求,根据用户操作调用相应的数据库操作方法。 5. 实现分页逻辑,计算总页数,获取当前页数据。 6. 异常处理和错误页面设计,确保程序...

    简单时尚无聊通用OA系统源码

    包括JSP、Servlet、JavaBeans、JSTL、EL(Expression Language)、DisplayTag以及EXT库,同时结合了MD5加密算法确保数据安全性,并使用SQL Server 2000作为后端数据库,以及CVS( Concurrent Versions System)进行...

    V512工作室Java web的ppt

    第5章 讲解了JDBC的使用和如何在Tomcat服务器中设置连接池和数据源。还详细讲解了Apache Commons DbUtils组件的使用。 第6章 讲解Cookie技术的如何在Web编程中的运用,以及如何在Servlet中编写操作Cookie的代码。 第...

    java_web_mldn高级篇全套源码完整版

    这份资料包括了从基础到进阶的多个主题,如Servlet、JavaBean、XML、AJAX、Struts框架以及JSP的相关技术。以下是各章节主要内容的详细解释: 1. **第03章:XML简介** - XML(Extensible Markup Language)是一种...

    WEB开发技术 Struts入门 GUI开发

    5. **JSP 视图**:Struts 使用 JSP 作为视图层,可以结合 JSTL、EL(Expression Language)以及自定义标签库来构建动态页面。 6. **Servlet 组件**:虽然 Struts 提供了更高层次的抽象,但其底层仍然依赖于 Servlet...

    java web jsp 常用模块1数据库连接2登陆退出3字符处理4目录处理5分页显示

    Java Web是基于Java技术构建Web应用程序的框架,它包含了Servlet、JSP(JavaServer Pages)以及EL(Expression Language)等核心组件。在这个标题和描述中,我们关注的是五个关键的开发模块,它们对于构建功能丰富的...

    struts标签分页(实用)

    分页主要是为了处理大量数据时避免一次性加载所有记录,而是将数据分割成若干小块(页)逐次加载。分页的核心概念包括:当前页、每页显示条数、总页数、总记录数等。 2. **Struts标签库** Struts提供了丰富的标签...

    Java+Struts教程(chinese)

    Struts提供了控制器Servlet、动作类、配置文件(struts-config.xml)以及一系列标签库,便于开发者实现页面跳转、数据传递等功能。 在“Java+Struts教程(chinese).pdf”中,你可以期待涵盖以下知识点: 1. **Java...

    图书馆管理系统【jsp+struts】

    【图书馆管理系统【jsp+struts】】 图书馆管理系统是一款利用Java Web技术实现的信息...此外,还可以深入学习Maven、Eclipse或IntelliJ IDEA等开发工具的使用,以及版本控制工具如Git的应用,提升项目开发的整体水平。

    简单时尚无聊通用OA系统部署版

    系统结构mvc,采用技术jsp+servlet+javabeans+jstl+el+displaytag+ext+md5+sql2000+cvs 因为比较大,所以源码单独上传,见 :简单时尚无聊通用OA系统部署版源码 数据库连接池的配置在META-INF/context.xml下,修改...

    java学习线路

    * Web 编程进阶:自定义标签库、MVC 和 DAO、Servlet、标签的作用、JSTL、DisplayTag 等常见标签库用法 * Web 编程原理:请求/响应、架构、Http 协议、深刻理解 Jsp 运行原理、掌握 Web 容器底层的线程池、socket ...

    JAVA体系总结内容.doc

    11. **Web编程基础**:Tomcat作为Servlet容器,JSP、EL和内置对象处理动态内容,Servlet API处理请求和响应。 12. **Web编程进阶**:自定义标签扩展JSP,MVC模式和DAO设计,使用JSTL和DisplayTag等标签库。 13. **...

Global site tag (gtag.js) - Google Analytics