Spring AOP
Spring 支持 AspectJ 注解切面编程
1. 使用@Aspect 声明切面。
2. 使用@After, @Before, @Around 定义建言advice,可以直接将拦截规则(切点)作为参数。
3. 其中@After, @Before, @Around 参数的拦截规则为切点(PointCut),为了是切点复用,可使用@PointCut专门定义拦截规则,然后在@After,@Before,@Around的参数中调用。
4. 其中符合条件的每一个被拦截处为连接点(JoinPoint)。
例:
1. 创建注解
package com.cz.aop; import java.lang.annotation.*; /** * 拦截规则注解 * Created by Administrator on 2017/5/7. */ @Target(ElementType.METHOD) @Retention(RetentionPolicy.RUNTIME) @Documented public @interface Action { String name(); String value(); }
2. 创建基于注解的业务类
package com.cz.aop; import org.springframework.stereotype.Service; /** * 基于注解的拦截业务类 * Created by Administrator on 2017/5/7 */ @Service public class DemoAnnotationService { @Action(name = "注解方式拦截add()操作之后", value = "注解方式拦截add()操作之前") public void add(){ System.out.println("DemoAnnotationService run "); }; }
3. 创建基于方法拦截业务类
package com.cz.aop; import org.springframework.stereotype.Service; /** * 基于方法的拦截业务类 * Created by Administrator on 2017/5/7. */ @Service public class DemoMethodService { public void add(){ System.out.println("DemoMethodService run"); }; }
4. 创建切面
package com.cz.aop; import org.aspectj.lang.JoinPoint; import org.aspectj.lang.Signature; import org.aspectj.lang.annotation.After; import org.aspectj.lang.annotation.Aspect; import org.aspectj.lang.annotation.Before; import org.aspectj.lang.annotation.Pointcut; import org.aspectj.lang.reflect.MethodSignature; import org.springframework.stereotype.Component; import java.lang.reflect.Method; /** * 切面 * Created by Administrator on 2017/5/7. */ @Aspect // 注解切面 @Component // Spring 组件 public class LogAspect { // 切入点 @Pointcut("@annotation(com.cz.aop.Action)") public void annotionPointCut(){}; @Before("annotionPointCut()") public void demoAnnotionBefore(JoinPoint joinPoint){ MethodSignature signature = (MethodSignature)joinPoint.getSignature(); Method method = signature.getMethod(); Action action = method.getAnnotation(Action.class); System.out.println(action.value()); } @After("annotionPointCut()") public void demoAnnotionAfter(JoinPoint joinPoint){ MethodSignature signature = (MethodSignature)joinPoint.getSignature(); Method method = signature.getMethod(); Action action = method.getAnnotation(Action.class); System.out.println(action.name()); } @Before("execution(* com.cz.aop.DemoMethodService.*(..))") public void demoMethodBefore(JoinPoint joinPoint){ MethodSignature methodSignature = (MethodSignature)joinPoint.getSignature(); Method method = methodSignature.getMethod(); System.out.println("方法拦截之前:" + method.getName()); } @After("execution(* com.cz.aop.DemoMethodService.*(..))") public void demoMetyhodAfter(JoinPoint joinPoint){ MethodSignature methodSignature = (MethodSignature)joinPoint.getSignature(); Method method = methodSignature.getMethod(); System.out.println("方法拦截之后:" + method.getName()); } }
5. 创建JAVA配置类
package com.cz.aop; import org.springframework.context.annotation.ComponentScan; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.EnableAspectJAutoProxy; /** * Created by Administrator on 2017/5/7. */ @Configuration @ComponentScan("com.cz.aop") @EnableAspectJAutoProxy public class AopConfig { }
6. 创建测试类
package com.cz.aop; import org.springframework.context.annotation.AnnotationConfigApplicationContext; /** * Created by Administrator on 2017/5/7. */ public class TestAop { public static void main(String[] args) { AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(AopConfig.class); DemoAnnotationService demoAnnotationService = context.getBean(DemoAnnotationService.class); demoAnnotationService.add(); DemoMethodService demoMethodService = context.getBean(DemoMethodService.class); demoMethodService.add(); context.close(); } }
7. Run Application 结果