3.27 EnableAspectJAutoProxy的exposeProxy屬性


戴着假發的程序員出品  抖音ID:戴着假發的程序員  歡迎關注

[查看視頻教程]

前面我們以及解釋完了AOP的所有配置和使用方式。

現在我們來看看下面的案例:

我們准備一個業務類:在業務類中我們有兩個方法showMessage和formartMsg。我們再showMessage中調用formartMsg方法:

 1 /**
 2  * @author 戴着假發的程序員
 3  * 
 4  * @description
 5  */
 6 @Component
 7 public class MessageService {
 8     public String showMessage(String info) {
 9         System.out.println("OtherInfoServcie-showMessage展示信息:"+info);
10         this.formartMsg(info);
11         return null;
12     }
13     public String formartMsg(String info){
14         System.out.println("OtherInfoServcie-formartMsg對象消息"+info+"進行格式化");
15         return  info;
16     }
17 }

添加一個Aspect類,在其中增加一個前置通知:

 1 /**
 2  * @author 戴着假發的程序員
 3  * 
 4  * @description
 5  */
 6 @Component
 7 @Aspect
 8 public class DKAspect1 {
 9     @Pointcut("this(com.st.dk.demo8.service.MessageService)")
10     public void pointcut1(){}
11 
12     @Before("pointcut1()")
13     public void before(JoinPoint joinPoint){
14         System.out.println("前置通知,被增強的方法是:"+joinPoint.toString());
15     }
16 }

測試:

1 ApplicationContext ac =
2         new AnnotationConfigApplicationContext(AppConfig.class);
3 MessageService bean = ac.getBean(MessageService.class);
4 bean.showMessage("戴着假發的程序員");

結果:

這是我們會發現,shwoMessage方法被攔截了,但是formartMsg方法並沒有被攔截。

這是什么原因,其實spring官方已經給了明確的解釋,解釋的內容有點繁雜,我就不在這里截圖。

我簡答解釋一下,就是我們使用AOP,必然會生成一個MessageService的代理對象。所以我們調用showMessage方法就是調用了代理對象的showMessage方法,必然會被增強,但是在shwoMessage中使用的this並非代理對象,而是我們的原生對象,所以this.formartMsg必然不會被增強。

如果解決呢?

方案1:

我們在我們的業務類中注入一個自己本身,然后把this替換為注入的對象,就可以解決問題。

這種方式很顯然,非常的不優雅。

所以spring 提供了其他的解決方案。

方案二:

修改EnableAspectJAutoProxy的屬性exposeProxy為true,這是我們的代理對象接口會被暴漏在ThreadLocal中,我們就可以直接獲取了。

1 @EnableAspectJAutoProxy(exposeProxy=true)

使用 方式:

 1 /**
 2  * @author 戴着假發的程序員
 3  * 
 4  * @description
 5  */
 6 @Component
 7 public class MessageService {
 8     public String showMessage(String info) {
 9         System.out.println("OtherInfoServcie-showMessage展示信息:"+info);
10         //使用AopContext的靜態方法獲取當前的代理對象
11         ((MessageService)AopContext.currentProxy()).formartMsg(info);
12         return null;
13     }
14     public String formartMsg(String info){
15         System.out.println("OtherInfoServcie-formartMsg對象消息"+info+"進行格式化");
16         return  info;
17     }
18 }

在測試:


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM