【问题标题】:Mock API calls During Unit Test cases Spring boot在单元测试用例 Spring boot 期间模拟 API 调用
【发布时间】:2020-08-06 20:13:29
【问题描述】:

我有两个微服务微服务 A(上下文路径 - /abc)和微服务 B(上下文路径 - /def)

示例网址:test.domain.com/abc/endpoint1 ,test.domain.com/def/endpoint2

在微服务 A (test.domain.com/abc/endpoint1) 的其中一个 api 中,它在内部调用微服务 B (/def/endpoint2) -> 此内部调用的前缀生成如下 (从请求中提取域,然后附加 /def/endpoint2 进行休息调用,总 url 将变为(test.domain.com/def/endpoint2)

问题:当我们从控制器级别开始编写单元测试用例时,我们正在使用 TestRestTemplate 对于这个测试,我们需要使用 http://localhost:portnumber/abc/endpoint1 来测试..

现在 def 服务的 url 也将导出为 http://localhost:portnumber/def/endpoint2 如何模拟这个响应(注意:我们不能在同一个端口上使用模拟服务器,我们会得到端口绑定异常)。有没有相同的解决方法?

在使用 TestRestTemplate 路由 http://localhost:portnumber/def/* 调用以获取来自 mockserver 和 http://localhost:portnumber/abc/* 的响应以进行实际测试中的 API 服务?

【问题讨论】:

    标签: java unit-testing microservices spring-boot-test mockserver


    【解决方案1】:

    可以为此使用ClientHttpRequestInterceptor,并操纵实际的URI 来调用它(如果它与您的第二个微服务的路径匹配)。

    这可能是一个简单的原型实现

    public class UrlRewriter implements ClientHttpRequestInterceptor {
      @Override
      public ClientHttpResponse intercept(HttpRequest httpRequest, byte[] bytes, ClientHttpRequestExecution clientHttpRequestExecution) throws IOException {
        try {
          if (httpRequest.getURI().toString().contains("/def/abc")) {
            HttpRequest modifiedRequest = new MockClientHttpRequest(HttpMethod.GET, new URI("http://localhost:8888/def/abc"));
            return clientHttpRequestExecution.execute(modifiedRequest, bytes);
          } else {
            return clientHttpRequestExecution.execute(httpRequest, bytes);
          }
    
        } catch (URISyntaxException e) {
          e.printStackTrace();
          return null;
        }
      }
    }
    

    然后您可以为您的测试提供一个 RestTemplateBuilder 类型的自定义 bean,由 TestRestTemplate 获取:

    @SpringBootTest(webEnvironment = RANDOM_PORT)
    public class TestOne {
    
    
      @TestConfiguration
      static class TestConfig {
    
        @Bean
        public RestTemplateBuilder restTemplateBuilder() {
          return new RestTemplateBuilder().interceptors(new UrlRewriter());
        }
    
      }
    
      @Autowired
      private TestRestTemplate testRestTemplate;
    
      @Test
      public void test() {
        assertNotNull(testRestTemplate);
    
        testRestTemplate.getForObject("/abc/endpoint1", String.class);
      }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-11-05
      • 2020-08-08
      • 1970-01-01
      • 2019-07-04
      • 2020-11-13
      • 1970-01-01
      相关资源
      最近更新 更多