【发布时间】:2020-06-21 11:16:54
【问题描述】:
尝试为 CircuitBreaker 代码示例编写单元测试时出现以下错误。
org.springframework.beans.factory.UnsatisfiedDependencyException: 创建具有名称的 bean 时出错 'com.foosball.team.Service.TeamServiceUnitTest':不满意 通过字段“注册表”表示的依赖关系;嵌套异常是 org.springframework.beans.factory.NoSuchBeanDefinitionException: 否 符合条件的 bean 类型 'io.github.resilience4j.circuitbreaker.CircuitBreakerRegistry' 可用:预计至少有 1 个符合 autowire 条件的 bean 候选人。依赖注解: {@org.springframework.beans.factory.annotation.Autowired(required=true)}
团队服务:
@Service
public class TeamService {
@Autowired
private ITeamRepository teamRepository;
@Autowired
private PlayerClient playerClient;
Logger logger = LoggerFactory.getLogger(TeamService.class);
.
.
.
团队服务单元测试:
@SpringBootTest(classes = {
TeamService.class
})
@RunWith(SpringRunner.class)
@DirtiesContext
public class TeamServiceUnitTest extends AbstractCircuitBreakerTest {
@MockBean
private ITeamRepository teamRepository;
@MockBean
private PlayerClient playerClient;
@Autowired
private TeamService service;
private TeamEntity teamEntity;
private Logger logger = LoggerFactory.getLogger(TeamServiceUnitTest.class);
@Before
public void setUp(){
teamEntity = new TeamEntity();
teamEntity.setId(1L);
teamEntity.setPlayerOne("One");
teamEntity.setPlayerTwo("Two");
teamEntity.setPlayerThree("Three");
teamEntity.setPlayerFour("Four");
}
@Test
@DisplayName("when Player Client Fails 11 Times Then CircuitBreaker Should Be In OPEN State")
public void whenPlayerClientFailsElevenTimesThenCircuitBreakerShouldBeInOPENState(){
//Given
when(teamRepository.findAll()).thenReturn(new ArrayList<>());
when(playerClient.get(Mockito.anyString())).thenThrow(new RuntimeException());
//When
for(int i=0; i<11; i++){
try {
service.addTeam(teamEntity);
} catch (Exception ignore) {
logger.info(ignore.getClass().getName());
}
}
//Then
checkHealthStatus(BACKEND_B, CircuitBreaker.State.OPEN);
}
}
参考类:
public class AbstractCircuitBreakerTest {
protected static final String BACKEND_A = "backendA";
protected static final String BACKEND_B = "playerClientCircuitBreaker";
@Autowired
protected CircuitBreakerRegistry registry;
@Before
public void setup(){
transitionToClosedState(BACKEND_A);
transitionToClosedState(BACKEND_B);
}
protected void checkHealthStatus(String circuitBreakerName, CircuitBreaker.State state) {
CircuitBreaker circuitBreaker = registry.circuitBreaker(circuitBreakerName);
assertThat(circuitBreaker.getState()).isEqualTo(state);
}
protected void transitionToOpenState(String circuitBreakerName) {
CircuitBreaker circuitBreaker = registry.circuitBreaker(circuitBreakerName);
if(!circuitBreaker.getState().equals(CircuitBreaker.State.OPEN)){
circuitBreaker.transitionToOpenState();
}
}
protected void transitionToClosedState(String circuitBreakerName) {
CircuitBreaker circuitBreaker = registry.circuitBreaker(circuitBreakerName);
if(!circuitBreaker.getState().equals(CircuitBreaker.State.CLOSED)){
circuitBreaker.transitionToClosedState();
}
}
}
参考项目:https://github.com/resilience4j/resilience4j-spring-boot2-demo
提议的Soln讨论:https://github.com/resilience4j/resilience4j-spring-boot2-demo/issues/33
提议的Soln项目:https://github.com/shah-smit/resilience4j-spring-boot2-demo-maven
【问题讨论】:
-
嗨@Smit,你成功完成了测试吗?我有代码编译但测试失败的问题,因为断路器没有打开。
-
嗨@PauloWeverton,您能否确保您的计算机有足够的资源来打开断路器。当我在 Jenkins 中运行构建时,测试通过就好了,但有时在我的计算机上它不起作用。
-
我愿意。当运行应用程序并使用测试系统使用它时,一切都很顺利,CircuitBreaker 和 FeignClient 等。但是 junit 测试没有:(
标签: java spring spring-boot resilience4j