You need to enable JavaScript to run this app. 带@Async方法的单例Spring Bean内外hashcode不一致是什么原因?
优惠活动
大模型
产品
解决方案
定价
更多

带@Async方法的单例Spring Bean内外hashcode不一致是什么原因?

问题结论

二者确实不是同一个实例,hashCode不一致的核心原因是:你通过@Autowired注入的Demo实例是Spring生成的动态代理对象,而test()方法内部的this指向的是原始的目标Bean对象。


底层实现逻辑

  • Spring处理@Async、@Transactional这类需要功能增强的注解时,会通过AOP机制为目标Bean生成动态代理类。如果被代理的类没有实现接口,默认会采用CGLIB生成代理,代理类是原Demo类的子类。
  • 生成的代理对象内部会持有一个原始Demo类的实例引用,所有增强逻辑(比如@Async的异步提交线程池逻辑)都在代理对象中实现,业务方法的实际执行会转发给内部持有的原始实例完成。
  • Main类中注入的Demo实例就是这个CGLIB代理对象,所以run方法中打印的是代理对象的hashCode。
  • 调用demo.test()时,代理对象先执行异步增强逻辑,再把调用转发给内部的原始Demo实例执行test方法,此时方法内部的this指代的就是原始实例,和外部的代理对象不是同一个对象,hashCode自然不相等。

验证方法

如果需要在test()方法内部获取到和注入实例一致的代理对象,可按以下步骤操作:

  1. 在项目启动类上添加注解@EnableAspectJAutoProxy(exposeProxy = true),开启代理暴露配置
  2. 在test()方法内通过AopContext.currentProxy()获取当前代理对象,打印该对象的hashCode,就会和外部注入的demo实例hashCode完全一致。

内容的提问来源于stack exchange,提问作者K.Liu

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.20 13:36:04