Java 弹簧圆形参考示例
在使用spring的一个项目中,我有一个循环引用,我无法修复该引用,启动时出现以下错误:Java 弹簧圆形参考示例,java,spring,dependency-injection,autowired,circular-reference,Java,Spring,Dependency Injection,Autowired,Circular Reference,在使用spring的一个项目中,我有一个循环引用,我无法修复该引用,启动时出现以下错误: 'org.springframework.security.authenticationManager': Requested bean is currently in creation: Is there an unresolvable circular reference? 我在一个示例项目中尝试在较小的层次上重新创建相同的问题(没有我工作项目的所有细节)。然而,我无法提出一个合理的场景,即sprin
'org.springframework.security.authenticationManager': Requested bean is currently in creation: Is there an unresolvable circular reference?
我在一个示例项目中尝试在较小的层次上重新创建相同的问题(没有我工作项目的所有细节)。然而,我无法提出一个合理的场景,即spring因错误而失败。
以下是我所拥有的:
public class ClassA {
@Autowired
ClassB classB;
}
public class ClassB {
@Autowired
ClassC classC;
}
@Component
public class ClassC {
@Autowired
ClassA classA;
}
@Configuration
public class Config {
@Bean
public ClassA classA() {
return new ClassA();
}
@Bean
public ClassB classB() {
return new ClassB();
}
}
我的项目中有一个类似的场景,失败了,我希望spring也会在我的示例项目中抱怨。但是它很好用!有人能给我一个简单的例子,如何打破弹簧的圆形参考误差
编辑:我使用javax.inject.Provider解决了这个问题。这两个项目中唯一的区别是使用的注释是javax.inject.inject和javax.annotation.ManagedBean,而不是@Autowired和@Component。您可以使用
@Lazy
来指示bean是惰性创建的,从而打破了自动连接的急迫循环
其思想是,可以将循环中的某些bean实例化为代理,并在真正需要它的时候对其进行初始化。这意味着,除了作为代理的bean之外,所有bean都被初始化。第一次使用它将触发配置,因为其他bean已经配置好了,所以不会有问题
摘自《春吉拉》的一期:
@可与@Configuration一起使用的惰性注释
指示该配置类中的所有bean都应
懒散地初始化。当然,@Lazy也可以结合使用
使用单个@Bean方法来指示
一个接一个。
这意味着将bean注释为@Lazy
就足够了。或者,如果您愿意,只需将配置类注释为@Lazy
,如下所示:
@Configuration
@Lazy
public class Config {
@Bean
public ClassA classA() {
return new ClassA();
}
@Bean
public ClassB classB() {
return new ClassB();
}
}
如果您实现了bean的接口,这将非常有效。根据Spring文档,通过使用构造函数注入可以获得循环依赖性问题或
beancurrentlyIncrementationException
解决这个问题的方法是使用setter而不是构造函数注入
参考资料。这是一条老线索,所以我想你几乎忘记了这个问题,但我想让你知道这个秘密。我遇到了同样的问题,我的问题并没有神奇地消失,所以我必须解决这个问题。我会一步一步地解决你的问题 1。为什么无法复制循环引用异常? 因为 2。那么为什么您的项目会产生异常?
- 正如@sperumal所说,如果使用构造函数注入,Spring可能会产生循环异常
- 根据日志,您在项目中使用Spring安全性
- 在Spring安全配置中,它们确实使用构造函数注入
- 注入
的bean具有循环引用authenticationManager
*context.xml
文件,并在web.xml中使用下面类似的配置加载它们
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:*-context.xml</param-value>
</context-param>
上下文配置位置
类路径:*-context.xml
xml文件将由XmlWebApplicationContext
类加载,文件的加载顺序不保证。它只是从文件系统加载文件。问题就在这里。如果该类首先加载应用程序上下文文件,则没有问题,因为当您的bean用于Spring安全性的构造注入时,它们已经被创建。但是,如果它首先加载Spring安全上下文文件,就会出现循环引用问题,因为Spring会在创建bean之前尝试在构造函数注入中使用bean
4。如何解决问题?
强制xml文件的加载顺序。在本例中,我使用
在应用程序上下文文件的末尾加载了安全上下文xml文件。即使使用相同的代码,加载顺序也可以根据环境进行更改,因此我建议设置加载顺序以消除潜在问题。我认为您误解了其中的内容:如果您主要使用构造函数注入,可以创建无法解决的循环依赖场景。构造函数注入优于setter注入-直到构造函数调用完成,您的bean才存在,使用setter注入时,您可能会忽略一些必要的参数,并且bean会在未正确配置的状态下存在一段时间,这只是为了补充一点,我们遇到了一个类似的问题(使用SpringTemplateEngine的注入)。“setter注入”解决方案没有帮助,但是@Lazy
注释起到了作用。感觉就像是一个创伤性的创可贴,但现在我要赢得胜利,然后走开。谢谢你,斯佩斯先生。