0

0

springMVC对异常处理的支持

巴扎黑

巴扎黑

发布时间:2017-06-26 09:21:20

|

1364人浏览过

|

来源于php中文网

原创

无论做什么项目,进行异常处理都是非常有必要的,而且你不能把一些只有程序员才能看懂的错误代码抛给用户去看,所以这时候进行统一的异常处理,展现一个比较友好的错误页面就显得很有必要了。跟其他mvc框架一样,springmvc也有自己的异常处理机制。
springmvc提供的异常处理主要有两种方式,一种是直接实现自己的handlerexceptionresolver,当然这也包括使用spring已经为我们提供好的simplemappingexceptionresolver和defaulthandlerexceptionresolver,另一种是使用注解的方式实现一个专门用于处理异常的controller——exceptionhandler。

 

得推共享菜园系统
得推共享菜园系统

得推共享菜园系统是一款专门针对家共享菜园开发的,可以通过基地加盟,轻松实现共享菜园平台建设。系统可以支持wap\公众号\小程序\APP. 基本功能:基地管理、菜园分类、菜园订单、菜园维护、菜园动态等 管理后台: 1.网站设置:站点信息,支付配置,短信配置,邮箱配置等 2.账户管理:账户审核,实名认证,用户充值,黑名单等 3.订单管理:服务订单、确认、处理、退单

下载

 

1、实现自己的HandlerExceptionResolver,HandlerExceptionResolver是一个接口,springMVC本身已经对其有了一个自身的实现——DefaultHandlerExceptionResolver,该解析器只是对其中的一些比较典型的异常进行了拦截,然后返回对应的错误码,当然你也可以继承DefaultHandlerExceptionResolver类,然后重写其中的一些异常处理方法来实现自己的异常处理。

import javax.servlet.http.HttpServletRequest;  
import javax.servlet.http.HttpServletResponse;  
  
import org.springframework.web.servlet.HandlerExceptionResolver;  
import org.springframework.web.servlet.ModelAndView;  
  
public class ExceptionHandler implements HandlerExceptionResolver {  
  
    @Override  public ModelAndView resolveException(HttpServletRequest request,  
            HttpServletResponse response, Object handler, Exception ex) {  // TODO Auto-generated method stub  return new ModelAndView("exception");  
    }  
  
}

 

 

 上述的resolveException的第4个参数表示对哪种类型的异常进行处理。因为Exception类是所有异常类的基类,所以如果想根据异常类型的不同来进行不同的处理的话,可以在resolveException方法里面根据不同的异常类型进行不同的处理,返回不同的异常视图。如:

public class ExceptionHandler implements HandlerExceptionResolver {  
  
    @Override  public ModelAndView resolveException(HttpServletRequest request,  
            HttpServletResponse response, Object handler, Exception ex) {  // TODO Auto-generated method stub  if (ex instanceof NumberFormatException) {  //doSomething...  return new ModelAndView("number");  
        } else if (ex instanceof NullPointerException) {  //doSomething...  return new ModelAndView("null");  
        }  return new ModelAndView("exception");  
    }  
  
}

 

定义了这样一个异常处理器之后就要在applicationContext中定义这样一个bean对象,如:

bean id="exceptionResolver" class="com.tiantian.xxx.web.handler.ExceptionHandler"/>  

Spring除了实现了一个DefaultHandlerExceptionResolver之外,还实现了一个SimpleMappingExceptionResolver,这两者都是继承自抽象类AbstractHandlerExceptionResolver,而AbstractHandlerExceptionResolver是实现了HandlerExceptionResolver接口的resolveException方法的,并由此抽取出两个抽象方法,一个是在进行异常处理之前执行的方法prepareResponse(exception, response),一个是进行异常解析的doResolveException(request, response, handler, exception)方法。SimpleMappingExceptionResolver,顾名思义就是通过简单的映射关系来决定由哪个视图来处理当前的错误信息。SimpleMappingExceptionResolver提供了通过异常类型exceptionMappings来进行异常与视图之间的映射关系,提供了在发生异常时通过statusCodes来映射异常返回的视图名称和对应的HttpServletResponse的返回码。而且可以通过defaultErrorView和defaultErrorCode来指定默认值,defaultErrorView表示当没有在exceptionMappings里面找到对应的异常类型时就返回defaultErrorView定义的视图,defaultErrorCode表示在发生异常时当没有在视图与返回码的映射关系statusCodes里面找到对应的映射时默认返回的返回码。在使用SimpleMappingExceptionResolver时,当发生异常的时候,SimpleMappingExceptionResolver将会把当前的异常对象放到自身属性exceptionAttribute中,当没有指定exceptionAttribute时,exceptionAttribute就是用默认值exception。

 

以下是一个简单的例子:

 

(1)SpringMVC的servlet配置文件中申明一个SimpleMappingExceptionResolver bean,并通过配置属性exceptionMappings和defaultExceptionView来指定异常和视图的对应关系

Xml代码
  
      
          
            number  
            null  
          
      
      
      
          
            500  
            503  
          
      
      

(2)如下访问:

@Controller  
@RequestMapping("/test")  
public class TestController {  
  
    @RequestMapping("/null")  public void testNullPointerException() {  
        Blog blog = null;  //这里就会发生空指针异常,然后就会返回定义在SpringMVC配置文件中的null视图          System.out.println(blog.getId());  
    }  
      
    @RequestMapping("/number")  public void testNumberFormatException() {  //这里就会发生NumberFormatException,然后就会返回定义在SpringMVC配置文件中的number视图  Integer.parseInt("abc");  
    }  
      
    @RequestMapping("/default")  public void testDefaultException() {  if (1==1)  //由于该异常类型在SpringMVC的配置文件中没有指定,所以就会返回默认的exception视图  throw new RuntimeException("Error!");  
    }  
      
}

 

 

(3)Jsp页面中可以访问到的异常对象,这里以NumberFormatException的返回视图number.jsp作为示例:

Jsp代码  收藏代码
<%@ page language="java" import="java.util.*" pageEncoding="GB18030" isErrorPage="true"%>  
<%  String path = request.getContextPath();  
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";  
%>  
  
  
  
    
      
      
    My JSP 'number.jsp' starting page  
      
      
      
          
      
      
      
  
    
    
    
    NumberFormatException. 
<%=exception.getMessage() %>
<%=exception %>
<%=request.getAttribute("ex") %>
<%=request.getAttribute("javax.servlet.error.status_code") %>

 

(4)当请求/test/number.do的时候会返回定义好的number视图,返回结果如下:


 

2、使用@ExceptionHandler进行处理

 

使用@ExceptionHandler进行处理有一个不好的地方是进行异常处理的方法必须与出错的方法在同一个Controller里面

 

如:

Java代码  收藏代码
 
import org.springframework.stereotype.Controller;  
import org.springframework.web.bind.annotation.ExceptionHandler;  
import org.springframework.web.bind.annotation.RequestMapping;  
  
import com.tiantian.blog.web.servlet.MyException;  
  
@Controller  
public class GlobalController {  
  
      /** 
     * 用于处理异常的 
     * @return 
     */  
    @ExceptionHandler({MyException.class})  public String exception(MyException e) {  
        System.out.println(e.getMessage());  
        e.printStackTrace();  return "exception";  
    }  
      
    @RequestMapping("test")  public void test() {  throw new MyException("出错了!");  
    }  
      
      
}

 

这里在页面上访问test方法的时候就会报错,而拥有该test方法的Controller又拥有一个处理该异常的方法,这个时候处理异常的方法就会被调用

 

 

优先级

既然在SpringMVC中有两种处理异常的方式,那么就存在一个优先级的问题:

 

当发生异常的时候,SpringMVC会如下处理:

(1)SpringMVC会先从配置文件找异常解析器HandlerExceptionResolver

(2)如果找到了异常异常解析器,那么接下来就会判断该异常解析器能否处理当前发生的异常

(3)如果可以处理的话,那么就进行处理,然后给前台返回对应的异常视图

(4)如果没有找到对应的异常解析器或者是找到的异常解析器不能处理当前的异常的时候,就看当前的Controller中有没有提供对应的异常处理器,如果提供了就由Controller自己进行处理并返回对应的视图

(5)如果配置文件里面没有定义对应的异常解析器,而当前Controller中也没有定义的话,那么该异常就会被抛出来。

热门AI工具

更多
DeepSeek
DeepSeek

幻方量化公司旗下的开源大模型平台

豆包大模型
豆包大模型

字节跳动自主研发的一系列大型语言模型

通义千问
通义千问

阿里巴巴推出的全能AI助手

腾讯元宝
腾讯元宝

腾讯混元平台推出的AI助手

文心一言
文心一言

文心一言是百度开发的AI聊天机器人,通过对话可以生成各种形式的内容。

讯飞写作
讯飞写作

基于讯飞星火大模型的AI写作工具,可以快速生成新闻稿件、品宣文案、工作总结、心得体会等各种文文稿

即梦AI
即梦AI

一站式AI创作平台,免费AI图片和视频生成。

ChatGPT
ChatGPT

最最强大的AI聊天机器人程序,ChatGPT不单是聊天机器人,还能进行撰写邮件、视频脚本、文案、翻译、代码等任务。

相关专题

更多
Golang处理数据库错误教程合集
Golang处理数据库错误教程合集

本专题整合了Golang数据库错误处理方法、技巧、管理策略相关内容,阅读专题下面的文章了解更多详细内容。

39

2026.02.06

java多线程方法汇总
java多线程方法汇总

本专题整合了java多线程面试题、实现函数、执行并发相关内容,阅读专题下面的文章了解更多详细内容。

17

2026.02.06

1688阿里巴巴货源平台入口与批发采购指南
1688阿里巴巴货源平台入口与批发采购指南

本专题整理了1688阿里巴巴批发进货平台的最新入口地址与在线采购指南,帮助用户快速找到官方网站入口,了解如何进行批发采购、货源选择以及厂家直销等功能,提升采购效率与平台使用体验。

289

2026.02.06

快手网页版入口与电脑端使用指南 快手官方短视频观看入口
快手网页版入口与电脑端使用指南 快手官方短视频观看入口

本专题汇总了快手网页版的最新入口地址和电脑版使用方法,详细提供快手官网直接访问链接、网页端操作教程,以及如何无需下载安装直接观看短视频的方式,帮助用户轻松浏览和观看快手短视频内容。

150

2026.02.06

C# 多线程与异步编程
C# 多线程与异步编程

本专题深入讲解 C# 中多线程与异步编程的核心概念与实战技巧,包括线程池管理、Task 类的使用、async/await 异步编程模式、并发控制与线程同步、死锁与竞态条件的解决方案。通过实际项目,帮助开发者掌握 如何在 C# 中构建高并发、低延迟的异步系统,提升应用性能和响应速度。

11

2026.02.06

Python 微服务架构与 FastAPI 框架
Python 微服务架构与 FastAPI 框架

本专题系统讲解 Python 微服务架构设计与 FastAPI 框架应用,涵盖 FastAPI 的快速开发、路由与依赖注入、数据模型验证、API 文档自动生成、OAuth2 与 JWT 身份验证、异步支持、部署与扩展等。通过实际案例,帮助学习者掌握 使用 FastAPI 构建高效、可扩展的微服务应用,提高服务响应速度与系统可维护性。

7

2026.02.06

JavaScript 异步编程与事件驱动架构
JavaScript 异步编程与事件驱动架构

本专题深入讲解 JavaScript 异步编程与事件驱动架构,涵盖 Promise、async/await、事件循环机制、回调函数、任务队列与微任务队列、以及如何设计高效的异步应用架构。通过多个实际示例,帮助开发者掌握 如何处理复杂异步操作,并利用事件驱动设计模式构建高效、响应式应用。

11

2026.02.06

java连接字符串方法汇总
java连接字符串方法汇总

本专题整合了java连接字符串教程合集,阅读专题下面的文章了解更多详细操作。

47

2026.02.05

java中fail含义
java中fail含义

本专题整合了java中fail的含义、作用相关内容,阅读专题下面的文章了解更多详细内容。

29

2026.02.05

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

相关下载

更多

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
Spring中文手册
Spring中文手册

共0课时 | 0人学习

马士兵spring视频教程
马士兵spring视频教程

共25课时 | 9.1万人学习

Excel 教程
Excel 教程

共162课时 | 16.1万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号