使用 MockRestServiceServer 集成测试 Spring 的 RestTemplate - 尽管出现 500 错误,但仍使用返回的正文

Integration-testing Spring's RestTemplate with MockRestServiceServer - using returned body despite 500 error

我正在尝试编写 RESTful 服务的集成测试,在某些情况下,该服务会响应 500 服务器错误,但仍然 returns 是一个有用的响应主体详细说明问题的消息。为了获得此响应主体,我的代码使用了自定义错误处理程序,例如:

public class Allow500ResponseErrorHandler implements ResponseErrorHandler {
  @Override
  public boolean hasError(ClientHttpResponse response) throws IOException {
    HttpStatus statusCode = response.getStatusCode();
    return !HttpStatus.OK.equals(statusCode)
      && !HttpStatus.INTERNAL_SERVER_ERROR.equals(statusCode);
  }

  @Override
  public void handleError(ClientHttpResponse response) throws IOException {
    log.error("Unexpected response code: {} {}", response.getStatusCode(),
        response.getStatusText());
  }
}

这工作正常,"healthy" 响应的集成测试也是如此:

@Test
public void testHealthyResponse() {
  MockRestServiceServer mockServer = MockRestServiceServer.createServer(restTemplate);
  mockServer.expect(requestTo("/someUri")).andExpect(method(HttpMethod.GET))
      .andRespond(withSuccess(HEALTHY_RESPONSE, MediaType.APPLICATION_JSON));
  restTemplate.setErrorHandler(new Allow500ResponseErrorHandler());

  MyCustomResult result = restTemplate
      .exchange("/someUri", HttpMethod.GET, null,
          new ParameterizedTypeReference<MyCustomResult>() {
          }).getBody();
  // assertThat(... tests go here...);

  mockServer.verify();
}

(其中 HEALTHY_RESPONSE 当然是 JSON 中的静态预期健康反应。)

但即使我在集成测试中为 "unhealthy" 响应设置相同的错误处理程序,我也会得到

org.springframework.web.client.RestClientException: Could not extract response: no suitable HttpMessageConverter found for response type [class my.package.MyCustomResult] and content type [application/octet-stream]
at org.springframework.web.client.HttpMessageConverterExtractor.extractData(HttpMessageConverterExtractor.java:110)
at org.springframework.web.client.RestTemplate$ResponseEntityResponseExtractor.extractData(RestTemplate.java:809)
at org.springframework.web.client.RestTemplate$ResponseEntityResponseExtractor.extractData(RestTemplate.java:793)
at org.springframework.web.client.RestTemplate.doExecute(RestTemplate.java:572)
at org.springframework.web.client.RestTemplate.execute(RestTemplate.java:530)
at org.springframework.web.client.RestTemplate.exchange(RestTemplate.java:476)
at [my test code]

设置与上面类似,除了期望是:

mockServer.expect(requestTo("/someUri")).andExpect(method(HttpMethod.GET))
    .andRespond(withServerError().body(UNHEALTHY_RESPONSE));

(这是使用 spring-web-4.1.7 的 RestTemplate 和 spring-test-4.1.7 的 MockRestServiceServer。)

如何使用有用的主体模拟服务器错误响应?我错过了什么?

成功了 - 错误消息有点误导,但 and content type [application/octet-stream] 应该给了我提示。

我需要做的 (doh) 就是根据期望设置媒体类型:

mockServer.expect(requestTo("/someUri")).andExpect(method(HttpMethod.GET))
  .andRespond(withServerError().body(UNHEALTHY_RESPONSE)
  .contentType(MediaType.APPLICATION_JSON));