SpringAop及拦截器
一、Aop
Aop,面向切面编程,提供了一种机制,在执行业务前后执行另外的代码。
切面编程包括切面(Aspect),连接点(Joinpoint)、通知(Advice)、切入点(Pointcut)、引入(Introduction)
通知(Advice)又分为前置通知,后置通知,最终通知,环绕通知,异常通知等。
在Spring中,Aop思想可以通过拦截器体现。
二、Aop应用:
1.Junit单元测试中,也用到了AOP思想,比如其中的before(),after()方法。
2.事务管理。业务逻辑之前是事务的开启begin,业务逻辑之后是事务的提交commit。
3.日志的管理。过滤,格式处理等
4.Spring中的拦截器。
三、拦截器:
在Spring中,拦截器可以分为方法前执行的拦截器、方法后执行的拦截器、异常拦截器
1.方法前拦截器类,需要实现MethodBeforeAdvice接口;
2.方法后拦截器类,需要实现AfterReturningAdvice接口;
3.异常拦截器类,需要实现ThrowsAdvice接口.
四、拦截器中的Aop及代理模式:
Advisor(通知):实现了Advice接口的拦截器(interceptor),是AOP中的Advisor(通知)
Pointcut(切入点):NameMatchMethodPointcutAdvisor类是AOP中的Pointcut(切入点),
将各种拦截器配置到NameMatchMethodPointcutAdvisor上。
"切入点"负责指定区域,而"通知"负责插入指定的代码。
Spring无法将Service实现类与拦截器类直接组装,因此没有对应的getter、setter方法,
安装时借助的是Spring的代理类ProxyFactoryBean,即把拦截器安装到切入点NameMatchMethodPointcutAdvisor中,
把自定义的Service安装到ProxyFactoryBean中,然后组装在一起.(代理模式)
ProxyFactoryBean通过setInterceptorNames()方法设置拦截器,通过setTarget()方法设置拦截对象,可以在xml中配置 。
五、区分Filter(过滤器)和Interceptor(拦截器):

四、示例如下:
Service接口:
public interface IAopService {
public void withAop() throws Exception;
public void withoutAop() throws Exception;
}
Service接口实现类:
import javax.security.auth.login.AccountException;
public class AopServiceImpl implements IAopService {
private String name;
@Override
public void withAop() throws Exception {
System.out.println("有AOP的函数运行。name: " + name);
if (name.trim().length() == 0) {
throw new AccountException("name属性不能为空");
}
}
@Override
public void withoutAop() throws Exception {
System.out.println("没有AOP的函数运行。");
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
三个拦截器如下所示:
方法前拦截器如下:
import org.springframework.aop.MethodBeforeAdvice;
import java.lang.reflect.Method; public class MethodBeforeInterceptor implements MethodBeforeAdvice { @Override
public void before(Method method, Object[] args, Object instance)
throws Throwable {
System.out.println("即将要执行方法:" + method.getName());
if (instance instanceof AopServiceImpl) {
String name = ((AopServiceImpl) instance).getName();
if (name == null) {
throw new NullPointerException("name属性不能为null");
}
}
}
}
方法后拦截器如下:
import org.springframework.aop.AfterReturningAdvice;
import java.lang.reflect.Method;
public class MethodAfterInterceptor implements AfterReturningAdvice {
@Override
public void afterReturning(Object value, Method method, Object[] args,
Object instance) throws Throwable {
System.out.println("方法 " + method.getName() + "运行完毕,返回值为:" + value);
}
}
异常拦截器如下:
import org.springframework.aop.ThrowsAdvice; import javax.security.auth.login.AccountException;
import java.lang.reflect.Method; public class ThrowsInterceptor implements ThrowsAdvice {
public void afterThrowing(Method method, Object[] args, Object instance,
AccountException ex) throws Throwable {
System.out.println("方法" + method.getName() + " 抛出了异常:" + ex);
} public void afterThrowing(NullPointerException ex) throws Throwable {
System.out.println("抛出了异常:" + ex);
}
}
Main方法如下:
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext; public class AopRun {
public static void main(String[] args) throws Exception {
ApplicationContext context= new ClassPathXmlApplicationContext("applicationContext.xml");
IAopService aopService = (IAopService) context.getBean("aopService");
aopService.withAop();
aopService.withoutAop();
}
}
applicationContext.xml如下:
<!--将拦截器配置到代理类上-->
<bean id="aopService" class="org.springframework.aop.framework.ProxyFactoryBean">
<!--拦截器-->
<property name="interceptorNames">
<list>
<value>aopMethodBeforeInterceptor</value>
<value>aopMethodAfterInterceptor</value>
<value>aopThrowInterceptor</value>
</list>
</property>
<!--拦截对象 -->
<property name="target">
<bean class="com.aop.AopServiceImpl">
<property name="name" value="Rui"></property>
</bean>
</property>
</bean> <!--拦截器在方法前运行,安装到NameMatchMethodPointcutAdvisor-->
<bean id="aopMethodBeforeInterceptor"
class="org.springframework.aop.support.NameMatchMethodPointcutAdvisor">
<property name="advice">
<bean class="com.aop.MethodBeforeInterceptor"></bean>
</property>
<property name="mappedName" value="withAop"></property>
</bean> <!--拦截器在方法后运行,安装到NameMatchMethodPointcutAdvisor-->
<bean id="aopMethodAfterInterceptor" class="org.springframework.aop.support.NameMatchMethodPointcutAdvisor">
<property name="advice" >
<bean class="com.aop.MethodAfterInterceptor"></bean>
</property>
<property name="mappedName" value="withAop"></property>
</bean> <!--拦截器在异常抛出运行,安装到NameMatchMethodPointcutAdvisor-->
<bean id="aopThrowInterceptor" class="org.springframework.aop.support.NameMatchMethodPointcutAdvisor">
<property name="advice">
<bean class="com.aop.ThrowsInterceptor"></bean>
</property>
<property name="mappedName" value="withAop"></property>
</bean>
注:示例摘自《JavaWeb整合开发王者归来》
SpringAop及拦截器的更多相关文章
- Spring异步调用原理及SpringAop拦截器链原理
一.Spring异步调用底层原理 开启异步调用只需一个注解@EnableAsync @Target(ElementType.TYPE) @Retention(RetentionPolicy.RUNTI ...
- spring---aop(3)---Spring AOP的拦截器链
写在前面 时间断断续续,这次写一点关于spring aop拦截器链的记载.至于如何获取spring的拦截器,前一篇博客已经写的很清楚(spring---aop(2)---Spring AOP的JDK动 ...
- Spring拦截器和SpringAop实现
一.拦截器 1.aop是面向切面编程,原理是java的发射技术. 2.分为三类,before.after.arround 3.springMvc为我们提供了一个适配器HandlerIntercepto ...
- Spring Mvc 的自定义拦截器
spring mvc的拦截器 SpringMVC 中的Interceptor 拦截器也是相当重要和相当有用的,它的主要作用是拦截用户的请求并进行相应的处理.比如通过它来进行权限验证,或者是来判断用户 ...
- Spring MVC 使用拦截器优雅地实现权限验证功能
在上一篇 SpringAOP 实现功能权限校验功能 中虽然用AOP通过抛异常,请求转发等勉强地实现了权限验证功能,但感觉不是那么完美,应该用拦截器来实现才是最佳的,因为拦截器就是用来拦截请求的,在请求 ...
- SpringMVC12拦截器
创建登陆界面 <%@ page language="java" import="java.util.*" pageEncoding="utf-8 ...
- Spring AOP原理及拦截器
原理 AOP(Aspect Oriented Programming),也就是面向方面编程的技术.AOP基于IoC基础,是对OOP的有益补充. AOP将应用系统分为两部分,核心业务逻辑(Core bu ...
- StringMVC(拦截器)
单个拦截器 使用jar包 创建FirstController.java @Controller public class FirstController { @RequestMapping(" ...
- (转)spring中的拦截器(HandlerInterceptor+MethodInterceptor)
1. 过滤器跟拦截器的区别 在说拦截器之前,不得不说一下过滤器,有时候往往被这两个词搞的头大. 其实我们最先接触的就是过滤器,还记得web.xml中配置的<filter>吗~ 你应该知道 ...
随机推荐
- 模板方法模式templeteMethod
引出模板模式: 考试试卷问题,提炼后的代码: package com.disign.templetemethod; import org.junit.Test; /** * Created by zh ...
- linux提权辅助工具(四):LinEnum.sh
来自:https://raw.githubusercontent.com/rebootuser/LinEnum/master/LinEnum.sh #!/bin/bash #A script to e ...
- iMac 10年
10年前,也就是1998年8月15号,Apple 推出了蓝色半透明的 iMac G3(指上市,发布时间为当年5月6号),当年销售200万台,从此开启了它的一个时代,人们一旦说起设计,那么 Apple ...
- Objective-C教程备忘单
终极版本的Objective-C教程备忘单帮助你进行iOS开发. 想开始创建你的第一个iOS应用程序么?那么看一下这篇很棒的教程吧:Create your first iOS 7 Hello Worl ...
- [BZOJ5312]冒险
bzoj CSAcademy description 一个序列\(a_i\),支持区间与一个数,区间或一个数,求区间最大值. \(n,m\le2\times10^5\) sol 线段树每个节点上维护区 ...
- 重新学习之spring第三个程序,整合struts2+spring
第一步:导入Struts2jar包+springIOC的jar包和Aop的Jar包 第二步:建立applicationContext.xml文件+struts.xml文件+web.xml文件 web. ...
- HDU 4825 字典树
HDU 4825 对于给定的查询(一个整数),求集合中和他异或值最大的值是多少 按位从高位往低位建树,查询时先将查询取反,然后从高位往低位在树上匹配,可以匹配不可以匹配都走同一条边(匹配表示有一个异或 ...
- HDU5033 Building(单调栈)
题意是说在水平轴上有很多建筑物(没有宽度),知道每个建筑物的位置与高度.有m个查询,每次查询位置x所能看到的天空的角度. 方法是将建筑与查询一起排序,从左往右计算一遍,如果是建筑物,则比较最后两个(当 ...
- 在css中使用hover来控制其他元素的样式,该两个元素必须是父子元素
.col-3:hover .check-box { display: block; } 在css中使用hover来控制其他元素的样式,该两个元素必须是父子元素!!!!
- Phonegap 原生控件(Android)与html混合
1. 用命令创建cordova项目 cordova coreate hello com.example.hello hello 2.打开MainActivity 在onCreate方法中加入 setC ...