(菜鸟来动手-第五天)SSM整合之Controller层异常处理

本文介绍了如何在Spring MVC中进行异常统一处理,包括创建自定义异常处理器和利用Spring AOP记录异常方法的参数名称和值。通过实现HandlerExceptionResolver接口并配置AOP切面,实现异常日志打印和特定异常的定制化响应。同时,展示了如何在AOP切面中获取并分析异常方法的参数信息。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

目标:

1: 异常统一处理

2: 记录异常方法的参数名称和值


系统很多地方都会抛出异常, 而java的异常体系目标就是与逻辑解耦. 所以项目中如果每个异常都单独处理,则太累也没必要.

SpringMVC 提供了 统一的异常处理方法.

异常出现的时候,我们很想知道客户端传的参数是什么,对于判断异常原因也很有帮助, spring aop 就可以获取 方法参数名称和值


1: 异常统一处理

Spring MVC处理异常有3种方式: 
(1)使用Spring MVC提供的简单异常处理器SimpleMappingExceptionResolver; 
(2)实现Spring的异常处理接口HandlerExceptionResolver 自定义自己的异常处理器; 
(3)使用@ExceptionHandler注解实现异常处理; 

我们这里使用第二种. 先创建个异常处理类

public class MyExceptionHandler implements HandlerExceptionResolver{
	private Logger logger = Logger.getLogger(MyExceptionHandler.class);
	
	@Override
	public ModelAndView resolveException(HttpServletRequest request, HttpServletResponse response, Object handler,
			Exception ex) {
		Map<String,Object> map = new HashMap<String,Object>();
		logger.error(ex.getMessage(),ex);
		if(ex instanceof MaxUploadSizeExceededException){
			map.put("msg", "文件大小超过限制!");
			return new ModelAndView(new MappingJackson2JsonView(),map);
		}
		map.put("msg", "系统错误!");
		return new ModelAndView(new MappingJackson2JsonView(),map);
	}
}

这个异常类里面, 我们打印了异常日志,并且对某种异常类型(这里是上传文件过大)做了特殊处理. 返回值这里用的是返回json格式的.


然后在配置文件(这里放在spring-mvc.xml)中将exceptionHandler指向我们自己写的类

<bean id="exceptionHandler" class="com.dingcheng.common.exception.MyExceptionHandler"/>

就这么简单,就可以了.


2: 记录异常方法的参数名称和值

这大概分为2步, 首先拦截到controller的bean, 其次获取异常方法的参数

1)拦截controller

需要在spring-mvc.xml文件中配置spirng的aop:config,指定拦截的bean和用来处理拦截的类

	<bean id="paramAspect" class="com.dingcheng.common.aop.ParamAspect" />  
	<aop:config>
		<aop:aspect id="exParamAspect" ref="paramAspect">  
            <aop:pointcut id="exParam" expression="execution(* com.dingcheng.*.controller.*.*(..))" />  
            <aop:after-throwing pointcut-ref="exParam" method="doThrowing" throwing="ex" />  
        </aop:aspect> 
	</aop:config>	

这个aop配置要放在 spring-mvc里面,如果放在application-context.xml或者spring-mybatis.xml中可能不行.

这里配置了 aop:after-throwing, 用于方法抛出异常后调用, 当然也可以配置其他的 before,around等.


再来看看ParamAspect这个类

public class ParamAspect {
	private Logger logger = Logger.getLogger(ParamAspect.class);

	public void doThrowing(JoinPoint jp, Throwable ex) {
		//获取参数名
		Signature signature = jp.getSignature();
		MethodSignature methodSignature = (MethodSignature) signature;
		String[] paramNameArr = methodSignature.getParameterNames();

		//获取参数值
		Object[] paramValueArr = jp.getArgs();
		StringBuilder sbd = new StringBuilder("pparam-->");
		for(int i=0;i<paramValueArr.length;i++){
			sbd.append(paramNameArr[i]+":"+paramValueArr[i]+",");
		}
		logger.error(sbd);
	}
}

doThrowing方法对应aop:after-throwing里面配置的method.


2)获取异常方法的参数

上面的代码中,doThrowing方法里面已经实现了 获取异常方法参数名称和值的方法


3.测试下

	@RequestMapping(value = "add.action", method = RequestMethod.POST)
	public String list(Model model, String loginName,String password) {
		User user = new User();
		user.setLoginName(loginName);
		user.setPassword(password);
		userService.create(user);
		if(userService!=null){
			throw new RuntimeException("测试一下");
		}
		return "redirect:list.action";
	}


源码地址:https://code.youkuaiyun.com/qq315737546/ssmq/tree/master


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值