利用的是代理模式的思想。
术语:
连接点:目标对象的方法。
切入点:目标对象中需要被代理对象实现的方法。
通知/增强处理:在定义好的切入点处需要执行的程序,可以理解为切面中的方法。
目标对象:被代理的对象,本身需要实现那些方法的类。
织入:把切面类应用到目标对象中来创建新的代理对象的过程。
动态代理:动态生成代理类,并不是整整存在的类。
JDK动态代理:针对目标对象接口进行代理。
public interface UserDao{
public void addUser();
public void deleteUser();
}
public class UserDaoImpl implements UserDao{
public void addUser(){
system.out.println("添加用户!");
}
public void deleteUser(){
system.out.println("删除用户!");
}
}
1.切面类
2.可以存在多个通知Advice(即增强的方法)
public class MyAspect{
public void check_Permissions(){
System.out.println("模拟检查权限");
}
public void log(){
System.out.println("模拟记录日志");
}
}
JDK代理类
public void JdkProxy implements InvocationHandler{
//声明目标类接口
private UserDao userDao;
//创建代理方法
public Object createProxy(UserDao userDao){
this.userDao=userDao;
1.类加载器
ClassLoader classLoader =JdkProxy.class.getClassLoader();
2.被代理对象实现的所有接口
Class[] clazz =userDao.getClass().getInterfaces();
3.使用代理类,进行增强,返回的是代理后的对象
return Proxy.newProxyInstance(ClassLoader,clazz,this)
}
@Override
public Object invoke(Object proxy,Method method,Object[] args) throws Throwable{
//声明切片
MyAspect myAspect = new MyAspect();
//前增强
myAspect.chech_Permission();
//在目标类上调用方法,并传入参数
Object obj = method.invoke(userDao,args);
//后增强
myAspect.log();
retrun obj;
}
}
public class JdkTest{
public static void main(String[] args){
//创建代理对象
JdkProxy jdkProxy=new JdkProxy();
//创建目标
UserDao userDao = new UserDaoImpl();
//从代理对象中获得增强后的目标对象
UserDao userDao1=(UserDao)JdkProxy.createProxy(userDao);
//执行方法
userDao1.addUser();
userDao1.deteleUser();
}
}
CGIB代理类:
针对于Jdk动态代理的局限性,即目标对象必须实现了一个或多个接口,在没有实现接口的时候就可以用CDLB动态代理。
这个代理类必须要实现MethInterceptor接口,并且重写实现Intercep()方法.
基于代理类的AOP实现:
使用ProxyFactoryBean创建AOP代理对象。首先在xml文件中配置目标对象,如userDao,然后在配置切面类,最后配置代理对象,但是代理对象是class=ProxyFactoryBean。不过在切面类里面要根绝增强的方式实现响应的接口。
AspectJ开发:
基于XML的声明式AspectJ:
首先在xml文件中,bean目标类,切面类。然后在配置文件中配置切面,<aop:config> <aop.aspect><aop:pointcut> <aop:before> <aop:after-returning> <aop:around> <aop:after-throwing> <aop:after>
基于注解的声明式AspectJ
@Aspect注解定义切面,然后@Component注解@Poincut来配置切入点。最后在xml文件中扫描,最后用来启动基于注解 的声明式AspectJ支持<aop:aspectj-autoproxy>。