mockito - 使用 Http.outboundGateway() 和配置的 RestTemplate 测试 spring 集成流程

标签 mockito spring-integration junit5 spring-test

我遇到的情况是,我正在为依赖于执行身份验证的配置 RestTemplate 的 IntegrationFlow 编写单元测试。

@Configuration
public class XXIntegrationConfig {
    @Autowired
    private RestTemplate restTemplate;

    @Bean
    public IntegrationFlow readRemote() {
        return f ->
            f.handle(
                Http.outboundGateway("http://localhost:8080/main/{mainId}", restTemplate)
                    .httpMethod(HttpMethod.GET)
                    .uriVariable("mainId", "headers.mainId")
                    .expectedResponseType(String.class)
            )
            .transformers(Transformers.fromJson())
            .enrich(enrichSecondary())
            .transform(Transformers.toJson());
    }

    @Bean
    public Consumer<EnricherSpec> enrichSecondary() {
        return e ->
            e.requestSubFlow(
                esf -> esf.handle(
                    Http.outboundGateway("http://localhost:8080/main/{mainId}/secondary", restTemplate)
                        .httpMethod(HttpMethod.GET)
                        .uriVariable("mainId", "headers.mainId")
                        .mappedResponseHeaders()
                        .expectedResponseType(String.class)
                )
                .transform(Transformers.fromJson())
            )
            .propertyExpression("secondary", "payload.value");
    }
}

我在建立测试时遇到困难,其中restTemplate(即@Autowired)是模拟。

我尝试过类似以下内容但没有成功

@SpringBootTest
@SpringIntegrationTest
public class XXIntegrationConfigTests {
    @Mock
    private RestTemplate restTemplate;

    @InjectMocks
    @Autowired
    private XXIntegrationConfig xxIntegrationConfig;

    @Autowired
    private IntegrationFlowContext integrationFlowContext;

    @Test
    public void testEnrichSecondary() {
        when(restTemplate.exchange(..... arg matchers ....)).thenReturn(
              new ResponseEntity("test document", HttpStatus.OK)
        );

        final Consumer<EnricherSpec> enrichSecondary = xxIntegrationConfig.enrichSecondary();
        IntegrationFlow flow =
            f -> f.enrich(enrichSecondary());
        IntegrationFlowContext.IntegrationFlowRegistration flowRegistration =
            integrationFlowContext.registration(flow).register();

        final Message<?> request =
                MessageBuilder.withPayload(new HashMap<String,Object>())
                        .setHeader("mainId", "xx-001")
                        .build();

        Message<?> response = 
                flowRegistration.getMessagingTemplate().sendAndReceive(request); 
    }
}

XXIntegrationConfig 中构造 bean 之前,此测试似乎不会覆盖配置类上注入(inject)的 RestTemplate

对此的任何想法将不胜感激。

最佳答案

参见Spring Boot的@MockBean:https://docs.spring.io/spring-boot/docs/current/reference/html/features.html#features.testing.spring-boot-applications.mocking-beans 。因此,您只需使用此注释在测试中标记您的 RestTemplate 属性,Spring Boot 就会在预期的配置中为您处理它的注入(inject)。

关于mockito - 使用 Http.outboundGateway() 和配置的 RestTemplate 测试 spring 集成流程,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/69166418/

相关文章:

java - 使用 Spring Boot RestController 进行 Junit 测试

java - 如何模拟服务并测试 POST Controller 方法

java - Spring Integration Gateway 中的超时表达式

spring - Spring集成方法发送WebSocket消息时不广播

java - IBM 字符集 header 导致异常

android - 将 Espresso 添加到项目时出现 Mockito 异常

java - mockito stub 返回 null

java - 如何为 JUnit 测试用例运行启用全局超时?

java - 使用 Maven 在 Eclipse 中为 JUnit 5 配置类路径

spring-boot - 使用Gradle 4.6的jUnit 5 HTML报告