`

《研磨struts2》第五章 Result 之 5.5 Struts2的异常映射

 
阅读更多

5.5  Struts2的异常映射

5.5.1  异常映射基础

在Action中execute方法的方法签名为public String execute() throws Exception,这样,Action可以抛出任何Exception,那么,Exception抛给谁呢?

1:自己实现异常处理

来做一个简单的试验,在Action的方法中这样写:

 

java代码:
  1. public String execute() throws Exception {  
  2.         int a = 5/0;  
  3.         return this.SUCCESS;  
  4. }  

上面的代码中有int a=5/0;,很显然,会抛出除数为0的错误,这个错误是RuntimeException,我们的程序没有进行相应的例外处理,则会抛给Struts2去处理。运行结果如下图所示:

图5.3  报例外的页面

可见,这个错误直接被抛给了web容器,Struts2并没有处理。那么,在实际的项目中很显然不能这么简单而粗暴的处理错误,一种简单的处理方法就是跳转到一个错误处理页面。

       假设要求这个Action,在出现“ArithmeticException”的时候,跳转到一个叫math-exception的Result,而其他错误跳转到另一个叫otherwise-exception的Result。那么,在Action中可以这么写。

 

java代码:
  1. public String execute() throws Exception {  
  2.     try {  
  3.         int a = 5/0;  
  4.     } catch (ArithmeticException e) {  
  5.         e.printStackTrace();  
  6.         return "math-exception";  
  7.     } catch (Exception e){  
  8.         e.printStackTrace();  
  9.         return "otherwise-exception";  
  10.     }  
  11.     return "success";  
  12. }  

这样,在运行中出现ArithmeticException就会跳转到math-exception指定的页面,而其他Exception就会跳转到otherwise-exception指定的页面,如果没有出错,就会跳转到success指定的页面。

在struts.xml的Action中,只要配置好上述三个Result就可以正常运行了。

2:使用Struts2的异常机制

       介绍到这里,我们还没有接触Struts2的异常机制,只是把Struts2的异常机制要做的事情,自己用编码实现了一遍。下面,来看看如何使用Struts2的异常机制。

       在<action>元素中设置<exception-mapping>元素,可以指定在execute方法抛出指定错误的时候,跳转到哪个指定的页面。

       修改上面的代码,使用Struts2的异常机制就不需要自己手动去try-catch了,Action的代码还原为如下所示:

 

java代码:
  1. public String execute() throws Exception {  
  2.         int a = 5/0;  
  3.         return this.SUCCESS;  
  4. }  

       然后在struts.xml的<action>元素中增加<exception-mapping>子元素,示例如下:

 

java代码:
  1. <action name="helloworldAction" class="cn.javass.action.action.HelloWorldAction">  
  2.     <exception-mapping result="math-exception" exception="java.lang.ArithmeticException"/>  
  3.     <exception-mapping result="math-exception" exception="java.lang.Exception"/>  
  4.     <result name="math-exception">/error.jsp</result>  
  5.     <result>/s2impl/welcome.jsp</result>  
  6. </action>  

在<action>元素里面,增加了两个<exception-mapping>元素,其execption属性指定了一个Exception的全类名,如果Action的execute方法抛出的错误是这个Exception类的实例或其派生类的实例,则会跳转到对应的result属性所指定的结果。当然,它们指定的名称为“math-exception”的Result,还是需要另行配置的。

       这里配置的名称为“math-exception”的Result,指向了web应用根下的error.jsp,在里面只是简单的输出了一句话,示例如下:

 

java代码:
  1. <%@ page language="java" contentType="text/html; charset=gb2312"  
  2.     pageEncoding="gb2312"%>  
  3. <html>  
  4. <head>  
  5. <meta http-equiv="Content-Type" content="text/html; charset=gb2312">  
  6. <title>Insert title here</title>  
  7. </head>  
  8. <body>  
  9. 对不起,出错了  
  10. </body>  
  11. </html>  

这样一来,当Action的execute方法抛出错误的时候,如果其<action>元素配置了<exception-mapping>子元素,则会按顺序寻找,找到第一个符合条件的<exception-mapping>元素,跳转到其指定的Result;如果找不到符合条件的<exception-mapping>元素,仍然把错误交给web容器处理。

       对比一下,使用了异常机制之后,Action的execute方法跟以前的实现是一样的,不需要自己去try-catch了,而原来对应的多个catch块,实际上都变成了<exception-mapping>的配置。

一般情况下,实际开发中会使用异常机制,可以把重复的catch块提炼到配置文件中,便于统一的配置和维护。

5.5.2  局部异常映射与全局异常映射

上面的<exception-mapping>元素是作为<action>元素的子元素来配置的,只对本<action>元素有效。其实跟局部Result和全局Result一样,也可以把<exception-mapping>提到父包中,做成全局的异常映射。

       全局异常映射仍然是<exception-mapping>元素,只不过不再是<action>元素的子元素,而是<global-exception-mappings>元素的子元素,而<global-exception-mappings>元素是<package>元素的子元素。

当然,配置了<global-exception-mappings>,自然需要配置<global-results>,而且<global-results>还必须在<global-exception-mappings>之前,示例如下:

 

java代码:
  1. <package name="helloworld"  extends="struts-default">  
  2.         <global-results>  
  3.             <result name="math-exception">/error.jsp</result>  
  4.         </global-results>  
  5.         <global-exception-mappings>  
  6.             <exception-mapping result="math-exception" exception="java.lang.ArithmeticException"/>  
  7.             <exception-mapping result="math-exception" exception="java.lang.Exception"/>  
  8.         </global-exception-mappings>        
  9.   
  10.         <action name="helloworldAction" class="cn.javass.action.action.HelloWorldAction">  
  11.             <result>/s2impl/welcome.jsp</result>  
  12.         </action>  
  13.     </package>  

对比局部结果和全局结果的查找顺序,可以很容易的理解局部异常映射和全局异常映射的查找顺序。

(1)首先,找自己的<action>元素的内的<exception-mapping >元素是否有匹配的,如果有就执行这个exception的映射配置,如果没有,下一步。

(2)其次,找自己的包里面的全局异常映射,也就是到自己的<action>所在的package中,找<global-exception-mappings >元素内的< exception-mapping >元素,看看是否有匹配的,如果有就执行这个exception的映射配置,如果没有,下一步。

(3)再次,递归的寻找自己的包的父包、祖父包中的全局异常映射是否有匹配的,如果有就执行这个exception的映射配置,如果没有,下一步。

(4)最后,如果上述三种情况都没有的话,则将Exception抛出给Struts2去处理。

       注意:如果出现同样符合条件的异常映射,上述的顺序也是异常映射之间的优先顺序,也就是说,如果Action的execute方法抛出一个异常,而局部异常映射和全局异常映射中都有相应的配置,那会以局部异常映射为准。

5.5.3  在页面输出异常信息

在前面的示例中,当Action的execute方法抛出一个异常之后,跳转到指定的页面,也就是error.jsp后,只是简单的输出一句信息,并没有把具体的异常信息展示出来。那么,想要在error.jsp页面上展示Exception的错误信息,该怎么做呢?

可以使用Struts2提供的标签,来输出Exception的错误信息,如下:

  • <s:property value=”exception”/>:仅仅简单打印出exception对象的例外消息。
  • <s:property value=”exceptionStack”/>可以打印出exception的堆栈信息。

       在error.jsp页面上使用上面的s标签即可,示例如下:

 

java代码:
  1. <%@ page language="java" contentType="text/html; charset=gb2312"  
  2.     pageEncoding="gb2312"%>  
  3. <html>  
  4. <head>  
  5. <meta http-equiv="Content-Type" content="text/html; charset=gb2312">  
  6. <title>Insert title here</title>  
  7. </head>  
  8. <body>  
  9. <%@ taglib prefix="s" uri="/struts-tags"%>  
  10. <font color=red><b>对不起,出错了,错误信息为:</b></font><br>  
  11. <s:property value="exception"/>  
  12. <br>  
  13. <font color=red><b>错误的堆栈信息为:</b></font><br>  
  14. <s:property value="exceptionStack"/>  
  15. </body>  
  16. </html>  

       运行结果如下图所示:

图5.4  显示例外信息的页面

私塾在线网站原创《研磨struts2》系列

转自请注明出处:【http://sishuok.com/forum/blogPost/list/0/4054.html

欢迎访问http://sishuok.com获取更多内容

分享到:
评论
1 楼 悲剧了 2012-05-03  
原来struts2本身有类似的全局异常对应处理,我还自己写了个拦截器处理,我比较关心是这块配置反应到源码层面如何映射的

相关推荐

    研磨Struts2配书视频对应的演示源代码

    这个压缩包中的“研磨Struts2配书视频对应的演示源代码”是《研磨Struts2》一书作者为了帮助读者更好地理解和实践书中理论知识而提供的实际示例代码。 首先,让我们深入理解Struts2的核心概念和技术特性: 1. **...

    研磨Struts2

    ### 知识点一:Struts2入门(MVC HelloWorld) #### 1.1 Struts2简介 ...以上就是关于“研磨Struts2”的主要知识点梳理,通过深入学习这些内容,开发者可以更好地掌握Struts2框架的核心技术和实践技巧。

    研磨struts2 高清版

    由于文件较大,我把这个文档切割为2部分,这是第一部分,请下载完第一部分后一定要下载第二部分,否则不能阅读。

    研磨Struts2配书视频对应的PPT

    《研磨Struts2》这本书是专门针对Struts2框架的学习指南,通过深入浅出的方式讲解了Struts2的核心概念和技术。其配套的PPT和视频旨在帮助读者更直观地理解书中的理论知识,并将其付诸实践。 在研读《研磨Struts2》...

    《研磨Struts 2》PDF版本下载.txt

    根据提供的文件信息,我们可以推断出这是一份关于《研磨Struts 2》书籍PDF版本的下载资源。为了更好地理解和概括这份资料所涉及的知识点,我们先来了解一下Struts 2框架及其重要性,然后深入探讨《研磨Struts 2》这...

    研磨struts

    12. **其他重要知识**:Struts2还涉及国际化、异常处理、主题与皮肤、动态方法调用等多个高级主题,这些内容使得Struts2能够应对复杂的Web应用需求。 通过《研磨Struts2》,读者可以系统地学习Struts2框架的各个...

    研磨Struts2 高清完整版.part2

    研磨Struts2 高清完整版,请和第一部分一起下载啊

    研磨Struts2_12859679_高清完整版.part2.rar

    研磨Struts2_12859679_高清完整版

    研磨Struts2-高清-完整目录-2011年10月

    研磨Struts2-高清-完整目录-2011年10月,分享给所有需要的人

    研磨设计模式(完整带书签).part2.pdf

    第5章 单例模式(Singleton) 第6章 工厂方法模式(Factory Method) 第7章 抽象工厂模式(Abstract Factory) 第8章 生成器模式(Builder) 第9章 原型模式(Prototype) 第10章 中介者模式(Mediator) 第11...

    Java工程师三大框架面试题.pdf

    Java工程师三大框架面试题.pdf

    研磨设计模式-part2

    第5章 单例模式(Singleton) 第6章 工厂方法模式(Factory Method) 第7章 抽象工厂模式(Abstract Factory) 第8章 生成器模式(Builder) 第9章 原型模式(Prototype) 第10章 中介者模式(Mediator) 第11...

    研磨设计模式.part2

    研磨设计模式.part2 一定要下载5部分

    研磨设计模式.part2(共4个)

    第5章 单例模式(Singleton) 第6章 工厂方法模式(Factory Method) 第7章 抽象工厂模式(Abstract Factory) 第8章 生成器模式(Builder) 第9章 原型模式(Prototype) 第10章 中介者模式(Mediator) ...

Global site tag (gtag.js) - Google Analytics