Spring this调用当前类方法无法拦截的示例代码


Posted in Java/Android onMarch 20, 2022

先给出代码示例

package com.example.demo.service;
import org.springframework.stereotype.Service;
@Service
public class ProxyService {
    public void  testA(){
        System.out.println("进入A");
        this.testB();
    }
    public void testB() {
        System.out.println("进入b");
    }

}
package com.example.demo.annotation;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.stereotype.Component;
@Aspect
@Component
public class AspectjTest {
    @Around("execution(* com.example.demo.service.ProxyService.testB())")
    public void recordProxy(ProceedingJoinPoint joinPoint) throws Throwable {
        long start = System.currentTimeMillis();
        joinPoint.proceed();
        long end = System.currentTimeMillis();
        System.out.println("花费时间:"+(end-start));
    }
}
package com.example.demo.api;
import com.example.demo.service.ProxyService;
import com.example.demo.service.UserService;
import org.springframework.aop.framework.AopContext;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PostMapping;
@Controller
public class ProxyApi {
//    @Autowired
//    ProxyService proxyService1;
    @Autowired
    private ApplicationContext applicationContext;
    @PostMapping("/proxy")
    public String test1() {
        ProxyService proxyService1 =  applicationContext.getBean(ProxyService.class);;
        proxyService1.testA();
        return "string";
    }
}

运行上面的代码会发现 配置aop 拦截方法不会被执行

Spring this调用当前类方法无法拦截的示例代码

我们通过debug 查看这个proxyService1 和this的区别,看看他们的值是什么

Spring this调用当前类方法无法拦截的示例代码

Spring this调用当前类方法无法拦截的示例代码

发现不一样,其实这就是问题的原因。

1、当我们在aop配置拦截的时候会指定类下面的方法路径,在spring启动的时候会先去加载这个ProxyService类,生成一个bean,但是因为你用aop配置了,所以需要代理这个ProxyService类,所以最终存在spring容器中的bean对象就是被代理后的bean对象。所以,我们在用容器获取bean或者用依赖注入获取bean的地址路径显示的是被代理后的bean 。
2、this获取的当前对象方法的一个引用,所以在调用testB方法的时候用的不是被代理的对象,自热不会经过aop拦截,原理和我们使用普通动态代理一样,只能是代理对象才能走自定义的方法。
3、可以通过debug 查看当ProxyService类被代理前和后的zhi值

Spring this调用当前类方法无法拦截的示例代码

Spring this调用当前类方法无法拦截的示例代码

发现是和之前的debug截图里面的值相符合的哈。

解决方法,就是在调用testB方法的时候用spring容器里的bean对象

@Service
public class ProxyService {
    @Autowired
    private  ProxyService proxyService;
    
    public void  testA(){
        System.out.println("进入A");
        proxyService.testB();
    }
    public void testB() {
        System.out.println("进入b");
}

或者

@Service
public class ProxyService {
    public void  testA(){
        System.out.println("进入A");
        ProxyService currentProxy = (ProxyService) AopContext.currentProxy();
        currentProxy.testB();
    }
    public void testB() {
        System.out.println("进入b");
    }
}

最终结果正确

Spring this调用当前类方法无法拦截的示例代码

到此这篇关于Spring this调用当前类方法无法拦截的文章就介绍到这了,更多相关Spring this无法拦截内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Java/Android 相关文章推荐
Win10系统下配置Java环境变量
Jun 13 Java/Android
eclipse创建项目没有dynamic web的解决方法
Jun 24 Java/Android
springboot集成flyway自动创表的详细配置
Jun 26 Java/Android
解决MultipartFile.transferTo(dest) 报FileNotFoundExcep的问题
Jul 01 Java/Android
Spring Boot mybatis-config 和 log4j 输出sql 日志的方式
Jul 26 Java/Android
Java面试题冲刺第十九天--数据库(4)
Aug 07 Java/Android
JavaWeb实现显示mysql数据库数据
Mar 19 Java/Android
Flutter集成高德地图并添加自定义Maker的实践
Apr 07 Java/Android
引用计数法和root搜索算法以及JVM中判定对象需要回收的方法
Apr 19 Java/Android
详解Android中的TimePickerView(时间选择器)的用法
Apr 30 Java/Android
Java实现字符串转为驼峰格式的方法详解
Jul 07 Java/Android
SpringBoot详解自定义Stater的应用
Jul 15 Java/Android
SpringCloud Feign请求头删除修改的操作代码
Mar 20 #Java/Android
JavaWeb实现显示mysql数据库数据
关于Mybatis中SQL节点的深入解析
springboot 自定义配置 解决Boolean属性不生效
Mar 18 #Java/Android
使用Java去实现超市会员管理系统
Mar 18 #Java/Android
详解Spring Security中的HttpBasic登录验证模式
RestTemplate如何通过HTTP Basic Auth认证示例说明
You might like
人工智能开始玩《星际争霸2》 你的操作跟得上吗?
2017/08/11 星际争霸
DC的38部超级英雄动画电影
2020/03/03 欧美动漫
PHP截取中文字符串的问题
2006/07/12 PHP
php去除重复字的实现代码
2011/09/16 PHP
PHP实现将科学计数法转换为原始数字字符串的方法
2014/12/16 PHP
php使用timthumb生成缩略图的方法
2016/01/22 PHP
PHP使用file_get_content设置头信息的方法
2016/02/14 PHP
JavaScript 应用类库代码
2008/06/02 Javascript
JScript 脚本实现文件下载 一般用于下载木马
2009/10/29 Javascript
javascript 常见功能汇总
2015/06/11 Javascript
深入理解Javascript中的自执行匿名函数
2016/06/03 Javascript
基于原生js淡入淡出函数封装(兼容IE)
2016/10/20 Javascript
AngularJS实现tab选项卡的方法详解
2017/07/05 Javascript
Vue入门之animate过渡动画效果
2018/04/08 Javascript
对angularJs中ng-style动态改变样式的实例讲解
2018/09/30 Javascript
微信小程序wx.request拦截器使用详解
2019/07/09 Javascript
JS正则表达式验证端口范围(0-65535)
2020/01/06 Javascript
OpenLayers3实现对地图的基本操作
2020/09/28 Javascript
数据挖掘之Apriori算法详解和Python实现代码分享
2014/11/07 Python
在Python中操作文件之read()方法的使用教程
2015/05/24 Python
Python实现的文本编辑器功能示例
2017/06/30 Python
python中matplotlib实现随鼠标滑动自动标注代码
2020/04/23 Python
使用Python绘制台风轨迹图的示例代码
2020/09/21 Python
Vichy薇姿加拿大官网:法国药妆,全球专业敏感肌护肤领先品牌
2018/07/11 全球购物
中学生操行评语
2014/04/24 职场文书
人力资源管理专业毕业生自荐书
2014/05/25 职场文书
运动会横幅标语
2014/06/17 职场文书
浪漫婚礼主题活动策划方案
2014/09/15 职场文书
社保代办委托书怎么写
2014/10/06 职场文书
市场部岗位职责范本
2015/04/15 职场文书
农贸批发市场管理制度
2015/08/07 职场文书
Python答题卡识别并给出分数的实现代码
2021/06/22 Python
JUnit5常用注解的使用
2021/07/02 Java/Android
centos8安装MongoDB的详细过程
2021/10/24 MongoDB
简单聊一聊SQL注入及防止SQL注入
2022/03/23 MySQL
Javascript中Microtask和Macrotask鲜为人知的知识点
2022/04/02 Javascript