首页 > 其他分享 >项目循环依赖解决

项目循环依赖解决

时间:2023-11-20 14:23:24浏览次数:28  
标签:依赖 IntermediateService intermediateService Bean 循环 解决 public 注入

问题:项目启动时报出错误信息,


The dependencies of some of the beans in the application context form a cycle:

┌─────┐ ````| intermediateService defined in file [E:\projects\business-server\target\classes\com\hyit\business\server\Intermediate\IntermediateService.class] ````↑ ↓ ````| accountTreeServiceImpl defined in file [E:\projects\business-server\target\classes\com\hyit\business\server\service\impl\AccountTreeServiceImpl.class]

以上信息是由于,服务之间出现相互注入,之后产生循环依赖,我开始使用中间服务,进行解决,但是仍然报出错误。

猜想:

由于此项目性能过差,不能在使用懒加载和构造注入来解决问题。

解决方案:

放弃使用自动注入的方式,使用手动依赖查找来满足需求,依赖查找的方式是指,在需要依赖的时候从容器中获取对应的 Bean 对象,而不是在构造函数或setter方法中注入。具体方法是创建一个对象工厂,然后从 BeanFactory 中获取需要的依赖。这种方式可以避免循环依赖。

实现如下:

@Service
public class IntermediateService {

    private final AccountTreeService accountTreeService;
    private final BaseOrgDataAuthService baseOrgDataAuthService;

    public IntermediateService(AccountTreeService accountTreeService, BaseOrgDataAuthService baseOrgDataAuthService) {
        this.accountTreeService = accountTreeService;
        this.baseOrgDataAuthService = baseOrgDataAuthService;
    }

    public AccountTreeService getAccountTreeService() {
        return accountTreeService;
    }

    public BaseOrgDataAuthService getBaseOrgDataAuthService() {
        return baseOrgDataAuthService;
    }
}
@Component
public class IntermediateServiceFactory implements BeanFactoryAware {


    private BeanFactory beanFactory;
    private volatile IntermediateService intermediateService;

    @Override
    public void setBeanFactory(BeanFactory beanFactory) throws BeansException {
        this.beanFactory = beanFactory;
    }


    /**
     *
     * 暂定使用volatile保证并发和性能问题
     */
    public IntermediateService getIntermediateService() {
        if (intermediateService == null) {
            synchronized (this) {  // 加锁
                if (intermediateService == null) {
                    intermediateService = beanFactory.getBean(IntermediateService.class);
                }
            }
        }
        return intermediateService;
    }
}
关于为什么手动查找依赖对象可以避免并解决相互依赖的问题

在 Spring 容器中,当两个 Bean 互相依赖时,容器必须确定将哪个 Bean 注入给先创建的 Bean。如果采用自动注入或setter方法注入依赖对象,Spring 容器会根据配置的注入顺序和 Bean 定义信息自动完成依赖注入,而这种自动注入或setter方法注入的方式存在循环依赖问题。

当 A 和 B 两个 Bean 互相依赖时,如果采用自动注入或setter方法注入依赖对象,Spring 容器会先创建 A 实例,然后发现 A 需要依赖 B,于是容器又会创建 B 实例。但是创建 B 实例的过程中,发现 B 又需要依赖 A,于是容器又会返回已经创建过的 A 实例,但是此时 A 的依赖 B 尚未被注入完成,导致出现循环依赖的问题。

而采用依赖查找的方式获取依赖对象,则不会出现循环依赖问题。因为依赖查找是由代码手动触发的,可以控制依赖对象的获取顺序和时机。因此,即使存在循环依赖,也可以通过工厂类等手动进行延迟注入,从而避免了循环依赖问题。

总之,手动查找依赖对象可以对依赖关系进行更细粒度的控制,避免了自动注入或setter方法注入方式可能产生的循环依赖问题。但是,手动查找的方式同时也增加了代码的复杂度,需要更多的代码和维护工作,因此需要根据具体情况进行选择。

标签:依赖,IntermediateService,intermediateService,Bean,循环,解决,public,注入
From: https://www.cnblogs.com/stephenllf/p/17843835.html

相关文章

  • VS 2022 不支持 .NET Framework 4.5 项目解决办法(Visual Studio 2022)
    VS2022不支持.NETFramework4.5项目解决办法(VisualStudio2022)默认VisualStudio2022不再支持安装.NETFramework4.5组件@选择组件里面已经不能选择4.5/4.0的框架了此时如果打开基于.NETFramework4.5的项目会收到提示:xxxx面向不再受支持的。NETFramewo......
  • 采用开源工具搭建网络监控平台的解决方案
    目标建立一个全面、可扩展的网络监控系统,实时监控公司网络的健康状况、性能指标和安全警报,以提高网络可靠性和效率。解决方案采用集成多个开源工具的方法,构建一个包括实时监控、数据分析、可视化和告警的综合网络监控平台。核心组件数据采集:使用Prometheus作为主要的数据采集系统。......
  • Python中用requests时遇到的错误警告解决方案
    最近,我在Python2.7.6(Ubuntu14.04.2LTS)环境中将requests库的版本从2.5.3升级到2.6.0,却遇到了’AtrueSSLContextobjectisnotavailable’警告。每当我在Python2.7.6环境中尝试使用requests库访问’github’时,都会看到这个警告。mkvirtualenvrequests260-irequests==2.6.0......
  • Chain-Of-Note:解决噪声数据、不相关文档和域外场景来改进RAG的表现
    CoN要点CoN框架由三种不同的类型组成,研究称之为阅读笔记。上面的图像,类型(A)显示了检索到的数据或文档回答查询的位置。LLM仅使用NLG从提供的数据中格式化答案。 https://avoid.overfit.cn/post/1a108bbaf6c84b5fbc51554fefa222cd......
  • Ftrans自动同步软件:解决企业级数据同步的烦恼
    随着数字经济的发展,企业数字化的办公场景越来越复杂,其中一个急需解决的问题就是企业不同服务器之间的文件自动同步的需求。然而,目前市场上的同步软件通常有很多的缺点,让用户感到困扰。1、数据安全:在同步数据的过程中,如果同步软件的安全性不足,就可能导致企业的敏感信息被泄露。这......
  • win11笔记本换内存后,报错,及解决:0x00007FF8011F6693指令引用了0x0000000000000000内存
    笔记本原装内存为一对镁光8GDDR54800MHz换单条镁光32GDDR55600MHz内存后,重启电脑出现如下报错:0x00007FF8011F6693指令引用了0x0000000000000000内存。该内存不能为read。要终止程序,请单击”确定” 联系内存的卖家客服提供的解决步骤虽然我没看到滚屏,但是重启后问题一样......
  • 与CNAME有关的DNS解决实例
    故障现象:1,通过DNS管理平台添加或者更新的DNS记录,使用rndcreload显示执行成功,但不能生效。2,BIND进程重启后,无法提供服务。3,日志报错:15-Feb-201712:04:38.604general:error:dns_master_load:sdo.com/zone_beijing_CMCC:198:sdo.com:CNAMEandotherdata15-Feb-201712......
  • pymssql 报20002错误解决办法:DB-Lib error message 20002, severity 9
    python版本:3.6 win32版本(因为一些特殊原因必须使用3.6)pymssql版本:2.2.0   连接数据库:importpymssql**defInitMssql(self):try:host=self.IniConfig.get('default','dbhost',"host***")user=self.IniC......
  • 解决UnboundLocalError: local variable 'time' referenced before assignment
    解决UnboundLocalError:localvariable'time'referencedbeforeassignment介绍在Python开发中,经常会遇到UnboundLocalError:localvariable'xxx'referencedbeforeassignment的错误。这个错误通常发生在在一个函数内部,尝试访问一个在函数内定义的局部变量之前。这篇文章将......
  • for循环
    ......