如果使用构造函数注入,则可能会创建一个无法解析的循环依赖场景。

1. 什么是循环依赖

循环依赖其实就是循环引用,也就是两个或则两个以上的bean互相持有对方,最终形成闭环。比如A依赖于B,B依赖于C,C又依赖于A。如下图:

注意,这里不是函数的循环调用,是对象的相互依赖关系。循环调用其实就是一个死循环,除非有终结条件。

Spring中循环依赖场景有:

(1)构造器的循环依赖

(2)field属性的循环依赖。

怎么检测是否存在循环依赖

检测循环依赖相对比较容易,Bean在创建的时候可以给该Bean打标,如果递归调用回来发现正在创建中的话,即说明了循环依赖了。

下面是我所遇到的情况,代码结构如下:

SpringSecurity 配置类:

@Configuration

public class BrowserSecurityConfig extends WebSecurityConfigurerAdapter{

private final UserDetailsService userDetailsService;

/**

* 通过配置类构造函数注入 UserDetailsService

*/

@Autowired

public BrowserSecurityConfig(UserDetailsService userDetailsService) {

this.userDetailsService = userDetailsService;

}

/**

* 在配置类中声明 加密编码器

*/

@Bean

public PasswordEncoder passwordEncoder() {

return new BCryptPasswordEncoder();

}

... ...

}

UserDetailsService 类:

@Component

public class MyUserDetailService implements UserDetailsService{

private final PasswordEncoder passwordEncoder;

private Logger logger = LoggerFactory.getLogger(getClass());

/**

* 通过构造函数注入 PasswordEncoder

*/

@Autowired

public MyUserDetailService(PasswordEncoder passwordEncoder){

this.passwordEncoder = passwordEncoder;

}

... ...

}

运行之后,Spring抛出了如下错误信息:

Description:

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

┌─────┐

| browserSecurityConfig defined in file [D:\CODE\Java\IdeaProjects\mango-security\mango-security-browser\target\classes\stu\mango\security\browser\BrowserSecurityConfig.class]

↑ ↓

| myUserDetailService defined in file [D:\CODE\Java\IdeaProjects\mango-security\mango-security-browser\target\classes\stu\mango\security\browser\MyUserDetailService.class]

└─────┘

该例中,BrowserSecurityConfig 通过构造函数注入 UserDetailsService实例,而 UserDetailsService由通过构造函数注入在BrowserSecurityConfig 中声明的PasswordEncoder。

总结来说,Spring Bean的循环依赖是指,类A需要通过构造函数注入的类B的实例(或者B中声明的Bean),而类B需要通过构造函数注入的类A的实例(或者A中声明的Bean)。如果将类A和类B的bean配置为相互注入,则Spring IoC容器会在运行时检测到此循环引用,并引发一个BeanCurrentlyInCreationException。与典型情况(没有循环依赖)不同,bean A和bean B之间的循环依赖关系迫使其中一个bean在被完全初始化之前被注入到另一个bean中(这是一个典型的“先有鸡还是先有蛋”场景)。

2. 解决方案

简明扼要的说,就是――不使用基于构造函数的依赖注入。可通过下面方式解决。

在字段上使用@Autowired注解,让Spring决定在合适的时机注入。【推荐】

用基于setter方法的依赖注射取代基于构造函数的依赖注入来解决循环依赖。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持脚本之家。

java 循环依赖_Java详解之Spring Bean的循环依赖解决方案相关推荐

  1. java webmethod 参数_java详解Spring接收web请求参数的方式

    本篇文章给大家带来的内容是java详解Spring接收web请求参数的方式 .有一定的参考价值,有需要的朋友可以参考一下,希望对你们有所帮助. 1 查询参数 请求格式:url?参数1=值1&参 ...

  2. java开发流程图_Java 详解 JVM 工作原理和流程

    作为一名Java使用者,掌握JVM的体系结构也是必须的. 说起Java,人们首先想到的是Java编程语言,然而事实上,Java是一种技术,它由四方面组成:Java编程语言.Java类文件格式.Java ...

  3. Spring三级缓存解决循环依赖问题详解

    spring三级缓存解决循环依赖问题详解 前言 这段时间阅读了spring IOC部分的源码.在学习过程中,自己有遇到过很多很问题,在上网查阅资料的时候,发现很难找到一份比较全面的解答.现在自己刚学习 ...

  4. java list jstl_详解javaweb中jstl如何循环List中的Map数据_java - JAVA

    文章来源:嗨学网 敏而好学论坛www.piaodoo.com 欢迎大家相互学习 详解javaweb中jstl如何循环List中的Map数据 第一种方式: 1:后台代码(测试) List> lis ...

  5. Spring 依赖注入详解

    一.IOC 依赖注入 1.什么是Spring的依赖注入 依赖注入,是IOC的一个方面,是个通常的概念,它有多种解释.这概念是说你不用创建对象,而只需要描述它如何被创建.你不在代码里直接组装你的组件和服 ...

  6. java反射机制深入详解_Java反射机制深入详解

    原标题:Java反射机制深入详解 一.概念 反射就是把Java的各种成分映射成相应的Java类. Class类的构造方法是private,由JVM创建. 反射是java语言的一个特性,它允程序在运行时 ...

  7. java 8 新功能详解_Java 8和Java 14之间的新功能

    java 8 新功能详解 从版本9开始,Java每6个月就有一次新功能,因此很难跟踪这些新更改. 互联网上的大多数信息都描述了最近2个Java版本之间的变化. 但是,如果您的情况与我相似,则说明您使用 ...

  8. java 8 新功能详解_Java 8的8个新功能

    java 8 新功能详解 注意:确保还检查了我们的详细教程Java 8 Features – ULTIMATE Guide . Jdk 1.8(又名Java 8)今天发布,这意味着它的通用发布版本已经 ...

  9. Java并发之AQS详解(文章里包含了两片文章结合着看后边文章不清楚,请看原文)

          AQS全称抽象队列同步器(AbstractQuenedSynchronizer),它是一个可以用来实现线程同步的基础框架.当然,它不是我们理解的Spring这种框架,它是一个类,类名就是A ...

  10. Java编程配置思路详解

    Java编程配置思路详解 SpringBoot虽然提供了很多优秀的starter帮助我们快速开发,可实际生产环境的特殊性,我们依然需要对默认整合配置做自定义操作,提高程序的可控性,虽然你配的不一定比官 ...

最新文章

  1. 数据库设计的10个最佳实践
  2. 论文笔记:Forecasting at Scale(Prophet)
  3. html 如何让div刷新页面,页面刷新.html
  4. python文件字符串操作
  5. 频繁刷新页面websocket会报错_代码优化:Node+WebSocket+Vue聊天室
  6. MySQL(17)-----数值函数
  7. 如果你想专升本那就一定要看的文学常识完整版(三)
  8. Rational Rose安装使用教程
  9. itest听力答案2020_itest大学英语测试答案2019
  10. jflash烧录教程_Jflash烧录(windows)原理分析
  11. 如何使用YouTube视频管理器
  12. 解决Android 拍照图片被旋转问题
  13. php 打开模态框,模态框打开页面
  14. 深度学习·理论篇(2023版)·第001篇快速了解人工智能与Pytorch:机器/表示/深度学习定义+端到端的学习+神经网络在计算机视觉应用+深度学习的技术蓝图
  15. SpringBoot与RocketMQ客户端集成原理解读与示例
  16. cad转dxf格式文件太大,将CAD图纸文件进行转换成低版本DXF格式如何进行?
  17. Ubuntu 下Android开发环境搭建
  18. Java设计模式系列3-----装饰模式,策略模式,观察者模式
  19. 类中无错误显示,但类名出线红色波浪线
  20. 操作系统——进程的三态模型

热门文章

  1. PhotoShop中蒙版介绍
  2. AVR单片机ATMEGA16编译软件ICCAVR的使用技巧与应用示例
  3. DRAM Devices Organization
  4. Rootkit Hacking Technology Defence Strategy Research
  5. matlab 创建网格图和曲面图
  6. C1. Skyscrapers (从easy到hard)
  7. matlab绘制三维图形,Matlab 应用之绘制三维图形(基础篇)(组图)
  8. 安全模式解除android,手机安全模式怎么解除
  9. 麒麟v10服务器系统搭建本地源
  10. 服务器能不能清理系统垃圾,在服务器上如何清理垃圾