In the previous article, we talked about the XML implementation of spring. Here we talk about how to implement aop using annotations. I have already talked about the simple understanding of aop before, so I won’t go into details here.
The annotation method to implement aop is mainly divided into the following steps (organized by myself, if there is a better method, welcome to communicate with codecjh@163.com):
1. In the aspect class (The class that serves pointcuts) is decorated with the @Aspect annotation and declared as an aspect class.
2. Use the @Pointcut annotation to declare a pointcut in order to tell the aspect who its service object is. (The method body of the method modified by this annotation is empty, and there is no need to write functions such as public void say(){};. The method name can be referenced by the specific service function on call, and it can be understood as a pointcut object. A proxy object method)
3. Modify the corresponding method with the corresponding notification type annotation, declare the corresponding method as an aspect function, and serve for the purpose of pointcut
4. Enable aop annotation automatic proxy in the spring configuration file. For example:
It may still be very abstract, so without further ado, let’s talk about the code. The code is as follows:
Knight class: (See If you have read the previous article, you will know what a knight is, hehehe)
1 package com.cjh.aop2; 2 3 import org.springframework.stereotype.Component; 4 5 /** 6 * @author Caijh 7 * 8 * 2017年7月11日 下午3:53:19 9 */10 @Component("knight")11 public class BraveKnight {12 public void saying(){13 System.out.println("我是骑士..(切点方法)");14 }15 }
Aspect class: (the comments are mainly reflected here)
1 package com.cjh.aop2; 2 3 import org.aspectj.lang.ProceedingJoinPoint; 4 import org.aspectj.lang.annotation.After; 5 import org.aspectj.lang.annotation.Around; 6 import org.aspectj.lang.annotation.Aspect; 7 import org.aspectj.lang.annotation.Before; 8 import org.aspectj.lang.annotation.Pointcut; 9 import org.springframework.stereotype.Component;10 11 /**12 * @author Caijh13 * email:codecjh@163.com14 * 2017年7月12日 上午9:31:4315 */16 /**17 * 注解方式声明aop18 * 1.用@Aspect注解将类声明为切面(如果用@Component("")注解注释为一个bean对象,那么就要在spring配置文件中开启注解扫描,<context:component-scan base-package="com.cjh.aop2"/>19 * 否则要在spring配置文件中声明一个bean对象)20 * 2.在切面需要实现相应方法的前面加上相应的注释,也就是通知类型。21 * 3.此处有环绕通知,环绕通知方法一定要有ProceedingJoinPoint类型的参数传入,然后执行对应的proceed()方法,环绕才能实现。22 */23 @Component("annotationTest")24 @Aspect25 public class AnnotationTest {26 //定义切点27 @Pointcut("execution(* *.saying(..))")28 public void sayings(){}29 /**30 * 前置通知(注解中的sayings()方法,其实就是上面定义pointcut切点注解所修饰的方法名,那只是个代理对象,不需要写具体方法,31 * 相当于xml声明切面的id名,如下,相当于id="embark",用于供其他通知类型引用)32 * <aop:config>33 <aop:aspect ref="mistrel">34 <!-- 定义切点 -->35 <aop:pointcut expression="execution(* *.saying(..))" id="embark"/>36 <!-- 声明前置通知 (在切点方法被执行前调用) -->37 <aop:before method="beforSay" pointcut-ref="embark"/>38 <!-- 声明后置通知 (在切点方法被执行后调用) -->39 <aop:after method="afterSay" pointcut-ref="embark"/>40 </aop:aspect>41 </aop:config>42 */43 @Before("sayings()")44 public void sayHello(){45 System.out.println("注解类型前置通知");46 }47 //后置通知48 @After("sayings()")49 public void sayGoodbey(){50 System.out.println("注解类型后置通知");51 }52 //环绕通知。注意要有ProceedingJoinPoint参数传入。53 @Around("sayings()")54 public void sayAround(ProceedingJoinPoint pjp) throws Throwable{55 System.out.println("注解类型环绕通知..环绕前");56 pjp.proceed();//执行方法57 System.out.println("注解类型环绕通知..环绕后");58 }59 }
spring configuration file:
1 <?xml version="1.0" encoding="UTF-8"?> 2 <beans xmlns="http://www.springframework.org/schema/beans" 3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 4 xmlns:context="http://www.springframework.org/schema/context" 5 xmlns:aop="http://www.springframework.org/schema/aop" 6 xsi:schemaLocation="http://www.springframework.org/schema/beans 7 http://www.springframework.org/schema/aop/spring-aop-4.3.xsd 8 http://www.springframework.org/schema/context/spring-context-4.3.xsd"> 9 <!-- 开启注解扫描 -->10 <context:component-scan base-package="com.cjh.aop2"/>11 <!-- 开启aop注解方式,此步骤s不能少,这样java类中的aop注解才会生效 -->12 <aop:aspectj-autoproxy/>13 </beans>
Test code:
1 package com.cjh.aop2; 2 3 import org.springframework.context.ApplicationContext; 4 import org.springframework.context.support.ClassPathXmlApplicationContext; 5 6 /** 7 * 8 * @author Caijh 9 * email:codecjh@163.com10 * 2017年7月11日 下午6:27:0611 */12 public class Test {13 public static void main(String[] args) {14 ApplicationContext ac = new ClassPathXmlApplicationContext("com/cjh/aop2/beans.xml");15 BraveKnight br = (BraveKnight) ac.getBean("knight");16 br.saying();17 }18 }
Running result:
Annotation type surround notification. . Before wrapping
Annotation type pre-notification
I am a knight.. (point-cutting method)
Annotation type wrapping notification.. After wrapping
Annotation type post-notification
= =======================Separating line========================== ==========
Since the annotation method is used, the configuration file has a lot less content. It only needs one sentence: <context:component-scan base -package="com.cjh.aop2"/>Declare the package to be scanned, and the framework will automatically scan the annotations and generate bean objects. There is an annotation @Component("knight"), which has the same meaning as
If Spring aop: error at ::0 can't find referenced pointcut sleepPonit error occurs during operation, then it is likely to be the spring package version Question,
I am using the spring4 version, and then I need to add two packages, aspectjrt-1.7.4.jar and aspectjweaver-1.7.4.jar, cloud disk address: link : Password: nc4i
The project directory is as follows: (Don’t worry about the coding class, just to avoid misleading everyone, so I crossed it out)
Notification annotation types are as follows:
The above is the detailed content of An example explanation of how to implement aop annotation in spring. For more information, please follow other related articles on the PHP Chinese website!