SpringMVC 拦截器 Interceptor

1、什么是 Interceptor?

SpringMVC 的拦截器 HandlerInterceptor,针对调用 Controller 的请求,进行拦截和处理。

  • 我们首先自定义一个Interceptor
public class DemoInterceptor implements HandlerInterceptor {
	// 在进入控制器之前执行
	// 如果返回值为false,阻止进入控制器
	// 用途:拦截未登录请求;控制代码
	@Override
	public boolean preHandle(HttpServletRequest arg0, HttpServletResponse arg1, Object arg2) throws Exception {
		//arg2是准备调用的 Controller方法
		System.out.println("arg2=" + arg2);
		return true;
	}

	// 控制器执行完成,进入到 jsp之前执行
	// 用途:日志记录、敏感词语过滤
	@Override
	public void postHandle(HttpServletRequest arg0, HttpServletResponse arg1, Object arg2, ModelAndView arg3)
			throws Exception {
		//arg3.getViewName()可获得准备跳转的视图逻辑名 View
		System.out.println("往" + arg3.getViewName() + "跳转");
		//arg3.getModel()可获得视图数据 Model
		System.out.println("data1的值" + arg3.getModel().get("data1"));
		String word = arg3.getModel().get("data1").toString();
		String newWord = word.replace("色情", "**");
		arg3.getModel().put("data1", newWord);
		// arg3.getModel().put("data1", "修改后的内容");
	}

	// jsp执行完成后执行或 Controller方法出现异常时执行
	// 用途:记录执行过程中出现的异常
	@Override
	public void afterCompletion(HttpServletRequest arg0, HttpServletResponse arg1, Object arg2, Exception arg3)
			throws Exception {
		// arg3是Controller方法中出现的异常
		System.out.println("arg3:" + arg3);
		if (arg3 != null) {
			//若是除零导致的,则arg3.getMessage()显示:/ by zero
			System.out.println( arg3.getMessage() );
		}
	}
}

我们从SpringMVC运行流程中也可以看出拦截器的生效时机:(留意中文注释即可)

	protected void doDispatch(HttpServletRequest request, HttpServletResponse response) throws Exception {
		...
		
		try {
			ModelAndView mv = null;
			try {
				processedRequest = checkMultipart(request);

				// Determine handler for the current request.
				mappedHandler = getHandler(processedRequest, false);
				if (mappedHandler == null || mappedHandler.getHandler() == null) {
					noHandlerFound(processedRequest, response);
					return;
				}

				// Apply preHandle methods of registered interceptors.
				// 调用拦截器的 preHandle方法
				HandlerInterceptor[] interceptors = mappedHandler.getInterceptors();
				if (interceptors != null) {
					for (int i = 0; i < interceptors.length; i++) {
						HandlerInterceptor interceptor = interceptors[i];
						if (!interceptor.preHandle(processedRequest, response, mappedHandler.getHandler())) {
							triggerAfterCompletion(mappedHandler, interceptorIndex, processedRequest, response, null);
							return;
						}
						interceptorIndex = i;
					}
				}

				// Actually invoke the handler.
				// 适配器
				HandlerAdapter ha = getHandlerAdapter(mappedHandler.getHandler());
				// ——————————— HandlerAdapter调用 Controller方法 ————————————
				mv = ha.handle(processedRequest, response, mappedHandler.getHandler());

				// Do we need view name translation?
				if (mv != null && !mv.hasView()) {
					mv.setViewName(getDefaultViewName(request));
				}

				// Apply postHandle methods of registered interceptors.
				// 调用拦截器的 postHandle方法
				if (interceptors != null) {
					for (int i = interceptors.length - 1; i >= 0; i--) {
						HandlerInterceptor interceptor = interceptors[i];
						interceptor.postHandle(processedRequest, response, mappedHandler.getHandler(), mv);
					}
				}
			}
			...
		}
	}

2、springmvc.xml 文件的拦截器配置

	<!-- 拦截器 -->
	<mvc:interceptors>
		<!--拦截所有控制器 <bean class="com.ljm.interceptor.DemoInterceptor"></bean> -->

		<!-- 拦截特定的的url -->
		<mvc:interceptor>
			<mvc:mapping path="/demo" />
			<mvc:mapping path="/demo1" />
			<mvc:mapping path="/demo2" />
			<bean class="com.bjsxt.interceptor.DemoInterceptor"></bean>
		</mvc:interceptor>
	</mvc:interceptors>

3、拦截器栈

当多个拦截器同时生效时,将组成拦截器栈。
执行顺序和Interceptor在 springmvc.xml 中的配置顺序有关。例如,先配置拦截器 A ,后配置拦截器 B ,则执行顺序为 :
preHandle(A) --> preHandle(B) --> 控制器方法 --> postHandle(B) --> postHanle(A) --> JSP --> afterCompletion(B) --> afterCompletion(A)
(先进后出)

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值