首页 > 编程知识 正文

java的环绕通知注解,java 环绕通知

时间:2023-12-27 22:26:19 阅读:324138 作者:VBJV

本文目录一览:

AOP环绕通知中proceed方法可以有一个Object参数不知有何用处

Java代码

// 环绕通知

@Around("anyMethod() args(id)")

public Object Around(ProceedingJoinPoint pjp, Integer id) throws Throwable {

Object result = null;

if (id == 4) {

System.out.println(id);

result = pjp.proceed();

} else {

result = "我被改变了";

}

return result;

}

这是切面中环绕通知的一个方法。其中一个pjp.proceed()方法个人理解为是一个对业务方法的模拟,可是在这个方法前后插入想做的事情。

Spring aop 关于around环绕通知几点疑惑,该如何处理怎么解决

您好,这样的:这个还真没有 好像 , 你自己写一个吧! 就不判断methodName直接判断Method 这个对象。

切面的优先级

为项目增加一个新的切面类,负责验证功能,则需要指定切面执行的顺序。即切面的优先级。具体方法是给切面类增加@Order注解,并指定具体的数字,值越小优先级越高

1 package com.yl.spring.aop;

2

3 import java.util.Arrays;

4

5 import org.aspectj.lang.JoinPoint;

6 import org.aspectj.lang.annotation.Aspect;

7 import org.aspectj.lang.annotation.Before;

8 import org.springframework.core.annotation.Order;

9 import org.springframework.stereotype.Component;

10

11 /**

12 * 可以使用@Order注解指定切面的优先级,值越小优先级越高

13 * @author yul

14 *

15 */

16 @Order(2)

17 @Component

18 @Aspect

19 public class ValidationAspect {

20

21 @Before("execution(public int com.yl.spring.aop.ArithmeticCalculator.*(..))")

22 public void vlidateArgs(JoinPoint joinPoint) {

23 System.out.println("validate: " + Arrays.asList(joinPoint.getArgs()));

24 }

25 }

切点表达式的重用:

在LoggingAspect类中,切点的表达式可以先定义,在使用。

1 package com.yl.spring.aop;

2

3 import java.util.Arrays;

4

5 import org.aspectj.lang.JoinPoint;

6 import org.aspectj.lang.ProceedingJoinPoint;

7 import org.aspectj.lang.annotation.After;

8 import org.aspectj.lang.annotation.AfterReturning;

9 import org.aspectj.lang.annotation.AfterThrowing;

10 import org.aspectj.lang.annotation.Around;

11 import org.aspectj.lang.annotation.Aspect;

12 import org.aspectj.lang.annotation.Before;

13 import org.aspectj.lang.annotation.Pointcut;

14 import org.springframework.core.annotation.Order;

15 import org.springframework.stereotype.Component;

16 @Order(1)

17 @Component

18 @Aspect

19 public class LoggingAspect {

20

21 /**

22 * 定义一个方法,用于声明切入点表达式。一般的,该方法中再不需要添加其他的代码

23 * 使用@Pointcut 来声明切入点表达式

24 * 后面的其他通知直接使用方法名直接引用方法名即可

25 */

26 @Pointcut("execution(public int com.yl.spring.aop.ArithmeticCalculator.*(..))")

27 public void declareJoinPointExpression() {

28

29 }

30

31 /**

32 * 在com.yl.spring.aop.ArithmeticCalculator接口的每一个实现类的每一个方法开始之前执行一段代码

33 */

34 @Before("declareJoinPointExpression()")

35 public void beforeMethod(JoinPoint joinPoint) {

36 String methodName = joinPoint.getSignature().getName();

37 Object[] args = joinPoint.getArgs();

38 System.out.println("The method " + methodName + " begins with " + Arrays.asList(args));

39 }

40

41 /**

42 * 在com.yl.spring.aop.ArithmeticCalculator接口的每一个实现类的每一个方法执行之后执行一段代码

43 * 无论该方法是否出现异常

44 */

45 @After("declareJoinPointExpression()")

46 public void afterMethod(JoinPoint joinPoint) {

47 String methodName = joinPoint.getSignature().getName();

48 Object[] args = joinPoint.getArgs();

49 System.out.println("The method " + methodName + " ends with " + Arrays.asList(args));

50 }

51

52 /**

53 * 方法正常结束后执行的代码

54 * 返回通知是可以访问到方法的返回值的

55 */

56 @AfterReturning(value="declareJoinPointExpression()", returning="result")

57 public void afterReturning(JoinPoint joinPoint, Object result) {

58 String methodName = joinPoint.getSignature().getName();

59 System.out.println("The method " + methodName + " return with " + result);

60 }

61

62 /**

63 * 在方法出现异常时会执行的代码

64 * 可以访问到异常对象,可以指定在出现特定异常时在执行通知代码

65 */

66 @AfterThrowing(value="declareJoinPointExpression()", throwing="ex")

67 public void afterThrowing(JoinPoint joinPoint, Exception ex) {

68 String methodName = joinPoint.getSignature().getName();

69 System.out.println("The method " + methodName + " occurs exception: " + ex);

70 }

71

72 /**

73 * 环绕通知需要携带ProceedingJoinPoint类型的参数

74 * 环绕通知类似于动态代理的全过程:ProceedingJoinPoint类型的参数可以决定是否执行目标方法。

75 * 而且环绕通知必须有返回值,返回值即为目标方法的返回值

76 */

77 @Around("declareJoinPointExpression()")

78 public Object aroundMethod(ProceedingJoinPoint pjd) {

79 Object result = null;

80 String methodName = pjd.getSignature().getName();

81 //执行目标方法

82 try {

83 //前置通知

84 System.out.println("The method " + methodName + " begins with " + Arrays.asList(pjd.getArgs()));

85 result = pjd.proceed();

86 //返回通知

87 System.out.println("The method " + methodName + " ends with " + Arrays.asList(pjd.getArgs()));

88 } catch (Throwable e) {

89 //异常通知

90 System.out.println("The method " + methodName + " occurs expection : " + e);

91 throw new RuntimeException(e);

92 }

93 //后置通知

94 System.out.println("The method " + methodName + " ends");

95 return result;

96 }

97

98 }

当处于不同的类,甚至不同的包时,可以使用包名.类名.方法名

具体代码如下:

1 package com.yl.spring.aop;

2

3 import java.util.Arrays;

4

5 import org.aspectj.lang.JoinPoint;

6 import org.aspectj.lang.annotation.Aspect;

7 import org.aspectj.lang.annotation.Before;

8 import org.springframework.core.annotation.Order;

9 import org.springframework.stereotype.Component;

10

11 /**

12 * 可以使用@Order注解指定切面的优先级,值越小优先级越高

13 * @author yul

14 *

15 */

16 @Order(2)

17 @Component

18 @Aspect

19 public class ValidationAspect {

20

21 @Before("com.yl.spring.aop.LoggingAspect.declareJoinPointExpression()")

22 public void vlidateArgs(JoinPoint joinPoint) {

23 System.out.println("validate: " + Arrays.asList(joinPoint.getArgs()));

24 }

25 }

java spring 环绕通知 ProceedingJoinPoint 执行proceed方法的作用是什么

环绕通知ProceedingJoinPoint 执行proceed方法的作用是让目标方法执行,这也是环绕通知和前置、后置通知方法的一个最大区别。

这是Spring框架最基础的部分,它提供了依赖注入(DependencyInjection)特征来实现容器对Bean的管理。

这里最基本的概念是BeanFactory,它是任何Spring应用的核心。BeanFactory是工厂模式的一个实现,它使用IoC将应用配置和依赖说明从实际的应用代码中分离出来。

扩展资料:

轻量——从大小与开销两方面而言Spring都是轻量的。完整的Spring框架可以在一个大小只有1MB多的JAR文件里发布。

并且Spring所需的处理开销也是微不足道的。此外,Spring是非侵入式的:典型地,Spring应用中的对象不依赖于Spring的特定类。

控制反转——Spring通过一种称作控制反转(IoC)的技术促进了松耦合。当应用了IoC,一个对象依赖的其它对象会通过被动的方式传递进来,而不是这个对象自己创建或者查找依赖对象。

参考资料来源:百度百科-spring框架

云南北大青鸟java培训告诉你动态SpringAOP的是如何实现的?

SpringAOP是利用代理模式,在运行时生成一个目标对象的代理,并且使用代理代替目标对象,整个过程对使用者透明,使用者无法像使用目标对象一样使用代理对象,代理对象类型是目标对象所属类的子类或者接口实现,丽江IT培训认为这个子类也是在运行时动态生成,这个生成子类的过程使用操作字节码技术,Spring框架中使用两种字节码技术:JDK动态代理和CGLIB,当目标类实现了接口时使用JDK动态代理,否则使用CGLIB代理。

AOP的实现包含下面几个步骤:

根据配置或注解解析切面。

生成AOP代理对象,给目标对象生成一个代理类以及代理类实例,根据解析出的切面,生成通知链设置到代理对象,在代理的回调中会执行通知链。

把AOP代理对象注册到容器中代替目标对象,当使用者向容器请求目标bean时,容器会返回代理对象。

下面对这几个步骤逐一的分析。

切面解析

在分析切面解析过程之前,首先先了解一下几个关键的接口,看下面的类图。

PointCut:描述切点,在进行切点匹配时,使用ClassFilter进行类匹配,MethodMatcher进行执行方法匹配。

Advice:通知,AfterAdvice后通知,BeforeAdvice前通知,DynamicIntroductionAdvice引用通知,环绕通知通过Interceptor实现。

Advisor:通知器,也就是切面,PointcutAdvisor切点通知器,IntroductionAdvisor引用通知器。

在创建AOP代理之前需要把相关的切面配置解析成上面类图中的接口子类的对象,对于ProxyFactoryBean来说,没有这个过程,因为这种方式下不能使用切点。

切面解析完成之后,把解析出的通知添加通知链中,AOP代理对象引用该通知链执行切面通知逻辑。对于aop标签方式和注解方式添加通知链这个动作的代码是类似的,解析切面这个过程有些差异。

版权声明:该文观点仅代表作者本人。处理文章:请发送邮件至 三1五14八八95#扣扣.com 举报,一经查实,本站将立刻删除。