应用上下文中一些bean的依赖形成了一个循环
Posted
技术标签:
【中文标题】应用上下文中一些bean的依赖形成了一个循环【英文标题】:The dependencies of some of the beans in the application context form a cycle 【发布时间】:2017-05-27 07:06:43 【问题描述】:我正在使用 JPA 开发 Spring Boot v1.4.2.RELEASE 应用程序。
我定义了存储库接口和实现
ARepository
@Repository
public interface ARepository extends CrudRepository<A, String>, ARepositoryCustom, JpaSpecificationExecutor<A>
ARepositoryCustom
@Repository
public interface ARepositoryCustom
Page<A> findA(findAForm form, Pageable pageable);
ARepositoryImpl
@Repository
public class ARepositoryImpl implements ARepositoryCustom
@Autowired
private ARepository aRepository;
@Override
public Page<A> findA(findAForm form, Pageable pageable)
return aRepository.findAll(
where(ASpecs.codeLike(form.getCode()))
.and(ASpecs.labelLike(form.getLabel()))
.and(ASpecs.isActive()),
pageable);
还有服务 AServiceImpl
@Service
public class AServiceImpl implements AService
private ARepository aRepository;
public AServiceImpl(ARepository aRepository)
super();
this.aRepository = aRepository;
...
我的应用程序不会以消息开头:
****************************** 应用程序无法启动 ****************************** 描述: : |一个RepositoryImpl └──────┘我遵循http://docs.spring.io/spring-data/jpa/docs/current/reference/html/#repositories.single-repository-behaviour中描述的所有步骤
请帮忙!
劳伦特
【问题讨论】:
尝试从ARepositoryCustom
中删除注释@Repository
不需要将ARepositoryCustom
标记为@Repository
,因为您想提供它的实现而不是使用Spring Data 生成它
你有一个接口ARepository
,它扩展了ARepositoryCustom
,接下来在你使用接口ARepository
的实现中。我怀疑 SPring Data Jpa 能否解决问题。恕我直言,该方法属于您的服务而不是您的存储库。
【参考方案1】:
使用@Lazy注解即可解决
@Component
public class Bean1
@Lazy
@Autowired
private Bean2 bean2;
【讨论】:
【参考方案2】:使用@Lazy
打破循环的一种简单方法是说 Spring 懒惰地初始化其中一个 bean。也就是说:它不会完全初始化 bean,而是创建一个代理将其注入另一个 bean。注入的 bean 只有在第一次需要时才会完全创建。
@Service
public class AServiceImpl implements AService
private final ARepository aRepository;
public AServiceImpl(@Lazy ARepository aRepository)
super();
this.aRepository = aRepository;
...
来源:https://www.baeldung.com/circular-dependencies-in-spring
【讨论】:
其实@lazy帮了我 感谢添加源代码,因为它有助于以不同于@lazy
的方式解决问题【参考方案3】:
有一个简单的解决方法可以解决您原来的问题: 只需从 ARepositoryCustom 和 ARepositoryImpl 中删除 @Repository。 保留所有命名和接口/类层次结构。他们都没事。
【讨论】:
【参考方案4】:我测试了你的源代码,发现了一些棘手的问题。
首先,使用您的源代码,我收到以下错误:
There is a circular dependency between 1 beans in the application context:
- ARepositoryImpl (field private test.ARepository test.ARepositoryImpl.aRepository)
- aRepositoryImpl
然后,我猜 Spring 在 ARepository
(JPA 存储库)和 ARepositoryImpl
(自定义存储库)之间“混淆”了。
因此,我建议您将ARepository
重命名为其他名称,例如BRepository
。如果我重命名类名,它会起作用。
根据 Spring Data (https://docs.spring.io/spring-data/jpa/docs/current/reference/html/) 的官方文档:
这些类需要遵循将命名空间元素的属性repository-impl-postfix附加到找到的存储库接口名称的命名约定。 此后缀默认为 Impl
【讨论】:
以上是关于应用上下文中一些bean的依赖形成了一个循环的主要内容,如果未能解决你的问题,请参考以下文章
升级后的 Spring Boot Oauth2 自动配置周期