1.web.xml中異常處理
通常爲了給用戶提供良好的人機接口,我們都會爲整個web應用,提供處理異常或者 錯誤的通用頁面,而這些通用頁面需要在web.xml中進行配置。
主要是兩種方式:其一根據HTTP響應狀態碼;其二是根據異常類名進行配置。
<error-page>
<exception-type>完整的異常類名</exception-type>
<location>以”/”開頭的異常處理頁面路徑</location>
</error-page>
<error-page>
<error-code>HTTP響應狀態碼</error-code>
<location>以”/”開頭的異常處理頁面路徑</location>
</error-page>
項目案例:
@Controller
@RequestMapping(value="/exception")
public class TestException {
@RequestMapping("/exception/{id}")
@ResponseBody
public Object hello(@PathVariable String id) {
if (id.equals("1")) {//NullPointerException控制值異常
throw new NullPointerException("空指針異常");
} else if (id.equals("2")) {//數學運算異常
int value = 1 / 0;
return "java.lang.ArithmeticException";
} else {
return "ok";
}
}
代碼分析:
http://127.0.0.1:8080/maven-springmvc-spring-springjdbc/exception/exception/1
輸入1到瀏覽器,程序出現空指針異常;
http://127.0.0.1:8080/maven-springmvc-spring-springjdbc/exception/exception/2
輸入2到瀏覽器,程序出現空指針異常
http://127.0.0.1:8080/maven-springmvc-spring-springjdbc/exception/exception/3
輸入其它到瀏覽器,程序正常運行
錯誤展示頁面和頁面對應錯誤信息
error_web_404.jsp :對應404錯誤
error_web_null.jsp :對應空指針異常
error_spring_404.jsp :對應404錯誤
error_spring_null.jsp :對應空指針異常
如下圖代碼,相應的錯誤信息指向對應的錯誤提示頁面
<!-- 異常處理 -->
<!-- 接收空指針錯誤 -->
<error-page>
<exception-type>java.lang.NullPointerException</exception-type>
<location>/WEB-INF/views/commons/error/error_web_null.jsp</location>
</error-page>
<!-- 404 頁面不存在錯誤 -->
<error-page>
<error-code>404</error-code>
<location>/WEB-INF/views/commons/error/error_web_404.jsp</location>
</error-page>
<!-- 接收405錯誤 -->
<error-page>
<error-code>405</error-code>
<location>/WEB-INF/views/commons/error/error405.jsp</location>
</error-page>
<!-- 500 服務器內部錯誤 -->
<error-page>
<error-code>500</error-code>
<location>/WEB-INF/views/commons/error/error500.jsp</location>
</error-page>
啓動項目:
1.輸入http://127.0.0.1:8080/maven-springmvc-spring-springjdbc/exception/exception/1
結果分析:web.xml中接收到空指針異常,指向error_web_null.jsp頁面
2.輸入http://127.0.0.1:8080/maven-springmvc-spring-springjdbc/exception/exception/2
嚴重: Servlet.service() for servlet [spring] in context with path [/maven-springmvc-spring-springjdbc] threw exception [Request processing failed; nested exception is java.lang.ArithmeticException: / by zero] with root cause
java.lang.ArithmeticException: / by zero
at com.controller.test.exception.TestException.hello(TestException.java:28)
結果分析:頁面未跳轉到任何錯誤提示頁面,這是因爲我們沒有在web.xml中配置ava.lang.ArithmeticException相關錯誤的異常處理界面
3.輸入http://127.0.0.1:8080/maven-springmvc-spring-springjdbc/exception/exception/3
結果分析:根據程序代碼運行結果得知程序正常執行
4.輸入http://127.0.0.1:8080/maven-springmvc-spring-springjdbc/exception/exceptionss
結果分析:web.xml中接收到404錯誤,跳轉指向error_web_404.jsp頁面
備註:在web.xml中配置的異常處理信息,使用error-page節點。
2.在springmvc上配置全局異常(配置文件的方式)
在spring-servlet.xml(springmvc的配置文件)中配置
<!-- Spring MVC提供的簡單異常處理器SimpleMappingExceptionResolver-全局異常配置 start -->
<bean class="org.springframework.web.servlet.handler.SimpleMappingExceptionResolver">
<!-- 默認的錯誤信息頁面 -->
<property name="defaultErrorView" value="error"/>
<property name="exceptionMappings">
<props>
<prop key="java.lang.NullPointerException">commons/error/error_spring_null</prop>
<prop key="java.lang.ArithmeticException">commons/error/error_spring_math</prop>
</props>
</property>
</bean>
<!-- 全局異常配置 end -->
TestException .java 異常測試類
@Controller
@RequestMapping(value="/exception")
public class TestException {
@RequestMapping("/exception/{id}")
@ResponseBody
public Object hello(@PathVariable String id) {
if (id.equals("1")) {//NullPointerException控制值異常
throw new NullPointerException("空指針異常");
} else if (id.equals("2")) {//數學運算異常
int value = 1 / 0;
return "java.lang.ArithmeticException";
} else {
return "ok";
}
}
代碼分析:
http://127.0.0.1:8080/maven-springmvc-spring-springjdbc/exception/exception/1
輸入1到瀏覽器,程序出現空指針異常;
http://127.0.0.1:8080/maven-springmvc-spring-springjdbc/exception/exception/2
輸入2到瀏覽器,程序出現空指針異常
http://127.0.0.1:8080/maven-springmvc-spring-springjdbc/exception/exception/3
輸入其它到瀏覽器,程序正常運行
錯誤展示頁面和頁面對應錯誤信息
error.jsp :默認異常處理頁面
error_spring_404.jsp :對應404錯誤
error_spring_null.jsp :對應空指針異常
1.輸入http://127.0.0.1:8080/maven-springmvc-spring-springjdbc/exception/exception/1
結果分析:spring-servlet.xml中接收到空指針異常,指向error_spring_null.jsp頁面
2.輸入http://127.0.0.1:8080/maven-springmvc-spring-springjdbc/exception/exception/2
結果分析:spring-servlet.xml中接收到數學算術運算異常,指向error_spring_math.jsp頁面
總結點
如果同時使用web.xml和spring-servlet.xml配置同樣的異常,會出現什麼結果,web.xml 和spring-servlet.xml配置會不會衝突?
這涉及到web.xml中元素的加載順序
元素節點的加載順序與它們在 web.xml 文件中的先後順序無關,通常是
ServletContext -> listener -> filter -> servlet---->------>error-page
web.xml中部分代碼段
<!-- springmvc -->
<servlet>
<servlet-name>spring</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<!-- 自定義spring mvc的配置文件名稱和路徑 -->
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:springMVC/spring-servlet.xml</param-value>
</init-param>
<!-- 自定義啓動順序,讓這個Servlet隨Servlet容器一起啓動 -->
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>spring</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
<!-- 異常處理 -->
<!-- 接收空指針錯誤 -->
<error-page>
<exception-type>java.lang.NullPointerException</exception-type>
<location>/WEB-INF/views/commons/error/error_web_null.jsp</location>
</error-page>
<!-- 404 頁面不存在錯誤 -->
<error-page>
<error-code>404</error-code>
<location>/WEB-INF/views/commons/error/error_web_404.jsp</location>
</error-page>
<!-- 接收405錯誤 -->
<error-page>
<error-code>405</error-code>
<location>/WEB-INF/views/commons/error/error405.jsp</location>
</error-page>
<!-- 500 服務器內部錯誤 -->
<error-page>
<error-code>500</error-code>
<location>/WEB-INF/views/commons/error/error500.jsp</location>
</error-page>
結果顯而易見,spring-servlet.xml的加載順序比error-page的快,異常會當有相同配置的錯誤時,會優先spring-servlet.xml中配置。只有當spring-servlet.xml沒有處理的錯誤異常,纔會在web.xml的error-page節點中查找對應異常。
spring-servlet.xml採用配置文件的方式的缺點:配置文件可以根據拋出的異常類的類信息配置錯誤的頁面。但是這樣我們無法手動對其定製異常。
故出現第三種方式
3.第三種方式採用自定義異常類,定製異常集中處理
ExceptionUtil .java 自定義的異常處理類
//自己手動編寫Java代碼來實現定製異常信息處理
package com.util.exception;
/**
* 所屬類別:工具類
* 用途:自定義的異常類
* @author yilei
* version:1.0
*/
public class ExceptionUtil extends RuntimeException {
public ExceptionUtil(String string) {
super(string);
}
}
在spring-servlet.xml ,相比於第二種方法多了com.util.exception.ExceptionUtil,可以配置自定義異常處理類進行接收異常
<!-- Spring MVC提供的簡單異常處理器SimpleMappingExceptionResolver-全局異常配置 start -->
<bean class="org.springframework.web.servlet.handler.SimpleMappingExceptionResolver">
<!-- 默認的錯誤信息頁面-->
<property name="defaultErrorView" value=">commons/error/error"/>
<property name="exceptionMappings">
<props>
<!-- 自定義的異常類 -->
<prop key="com.util.exception.ExceptionUtil">commons/error/error_spring_ExceptionUtil</prop>
<!-- 空指針異常 -->
<prop key="java.lang.NullPointerException">commons/error/error_spring_null</prop>
<!-- 數學算術異常 -->
<prop key="java.lang.ArithmeticException">commons/error/error_spring_math</prop>
</props>
</property>
</bean>
<!-- 全局異常配置 end -->
error_spring_ExceptionUtil.jsp 自定義異常處理jsp頁面
<%@ page language="java" contentType="text/html; charset=utf-8" pageEncoding="utf-8"%>
<%
String path = request.getContextPath();
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";
%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
error_spring_ExceptionUtil.jsp<br>
spirngmvc配置異常-自定義異常
</body>
</html>
TestException.java 進行異常測試的類,throw new ExceptionUtil(“自定義有異常”);這段代碼用於拋出自定義異常類,springmvc中配置自動跳轉到commons/error/error_spring_ExceptionUtil頁面
package com.controller.test.exception;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import com.util.exception.ExceptionUtil;
@Controller
@RequestMapping(value = "/exception")
public class TestException {
@RequestMapping("/exception/{id}")
@ResponseBody
public Object hello(@PathVariable String id) {
if(id.equals("0")){
throw new ExceptionUtil("自定義有異常");
}else if (id.equals("1")) {// NullPointerException控制值異常
throw new NullPointerException("空指針異常");
} else if (id.equals("2")) {// 數學運算異常
int value = 1 / 0;
return "java.lang.ArithmeticException";
} else {
return "ok";
}
}
}
4.第四種方式去實現自定義異常處理(基於註解的方式)
ExceptionUtil .java 自定義的異常處理類
//自己手動編寫Java代碼來實現定製異常信息處理
package com.util.exception;
/**
* 所屬類別:工具類
* 用途:自定義的異常類
* @author yilei
* version:1.0
*/
public class ExceptionUtil extends RuntimeException {
public ExceptionUtil(String string) {
super(string);
}
}
TestException.java 異常測試類,使用註解ExceptionHandler來標識,在每個需要使用此異常處理的類中添加handleLocalException方法,在使用 throw new ExceptionUtil(“自定義有異常”);代碼時候,就算同時配置上面第三種方法來自定義了異常處理界面,但是也不會生效,而是由方法handleLocalException中決定異常處理結果,本類中最終有error.jsp頁面來進行異常顯示。
package com.controller.test.exception;
import javax.servlet.http.HttpServletRequest;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import com.util.exception.ExceptionUtil;
@Controller
@RequestMapping(value = "/exception")
public class TestException {
@RequestMapping("/exception/{id}")
@ResponseBody
public Object hello(@PathVariable String id) {
if(id.equals("0")){
throw new ExceptionUtil("自定義有異常");
}else if (id.equals("1")) {// NullPointerException控制值異常
throw new NullPointerException("空指針異常");
} else if (id.equals("2")) {// 數學運算異常
int value = 1 / 0;
return "java.lang.ArithmeticException";
} else {
return "ok";
}
}
//異常處理,基於註解的方式,但是需要進行自定義異常的類中都寫一個相同的方法纔可生效。如果使用這種方式。
@ExceptionHandler(value={ExceptionUtil.class})
public String handleLocalException(ExceptionUtil e, HttpServletRequest req){
req.setAttribute("error", e);
return "error/error";
}
}
error.jsp
<%@ page language="java" contentType="text/html; charset=utf-8"
pageEncoding="utf-8"%>
<%@taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<%@taglib uri="http://www.springframework.org/tags/form" prefix="sf" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>
異常拋出處理
</title>
</head>
<body>
<h1>${error.message}</h1>
</body>
</html>
**
總結
**
第一種web.xml配置和第二種基於springmvc中配置的方式是最常見的異常處理方法,通常項目中是結合一起使用
第三種和第四中方式主要是爲了定製異常,爲了滿足項目上一些特殊需求,
相對第四種方式,更建議採用第三種的方式來自定義異常處理,主要是因爲第四種(採用註解的方式),需要在每個使用了自定義異常類中都需要類似以下代碼的方法來處理異常,對程序來說比較冗餘。
//異常處理,基於註解的方式,但是需要進行自定義異常的類中都寫一個相同的方法纔可生效。如果使用這種方式。
@ExceptionHandler(value={ExceptionUtil.class})
public String handleLocalException(ExceptionUtil e, HttpServletRequest req){
req.setAttribute("error", e);
return "error/error";
}
而第三種,在第二種方法的基礎上,實現全局的配置,更便捷,因此,如果需要使用自定義異常的話,建議使用第三種方式,同時第一種和第二種相結合。
大家可以參考我的另一篇博文,在實際項目中運用到了異常處理
https://blog.csdn.net/qq_29914837/article/details/82686202