模拟对单元测试的请求实体调用

时间:2019-03-25 06:13:26

标签: java rest junit mockito resttemplate

我想模拟请求实体和响应,以测试控制器方法上的方法,此代码已由另一位开发人员编写,我应该使用模拟测试它。我正在模拟控制器类

我正在尝试模拟请求实体值和respionse实体值,但是它不起作用,并且在尝试调试时出现反射错误

    public class InquiryController {

private static final Logger log = 
    LoggerFactory.getLogger(InquiryController.class);

@Autowired
private InquiryProperties inquiryProperties;

@Autowired
private InquiryService inquiryService;


@Autowired
RestTemplate restTemplate;

public static int count = 0;


@Bean
private RestTemplate getRestTemplate() {
    return new RestTemplate();
}

    @PostMapping(value = "/endCustomer", produces = { MediaType.APPLICATION_JSON_VALUE }, consumes = {
        MediaType.APPLICATION_JSON_VALUE })
public ResponseEntity<List<EndCustomerDTO>> endCustomer(@RequestBody CustomerInfo customerInfo)
        throws IOException, JSONException {

    log.info("### InquiryController.endCustomer() ===>");
    List<EndCustomerDTO> endCustomerDTOs = null;

    try {

        //RestTemplate restTemplate = new RestTemplate();
        RequestEntity<CustomerInfo> body = RequestEntity.post(new URI(inquiryProperties.getEndCustomer()))
                .accept(MediaType.APPLICATION_JSON).body(customerInfo);
        ResponseEntity<List<EndCustomerDTO>> response = restTemplate.exchange(body,
                new ParameterizedTypeReference<List<EndCustomerDTO>>() {
                });
        endCustomerDTOs = (response != null ? response.getBody() : new ArrayList<EndCustomerDTO>());

    } catch (RestClientException | URISyntaxException e) {
        log.error("InquiryController.endCustomer()" + e.getMessage());
    }

    log.info("### END InquiryController.endCustomer()  ===>");

    if (null == endCustomerDTOs) {
        return new ResponseEntity<List<EndCustomerDTO>>(new ArrayList<EndCustomerDTO>(), HttpStatus.OK);
    }
    return new ResponseEntity<List<EndCustomerDTO>>(endCustomerDTOs, HttpStatus.OK);

}

2 个答案:

答案 0 :(得分:0)

这是因为在进行REST调用时,RestTemplate的实例未通过Spring IOC注入。您需要在组件类中声明getRestTemplate方法,该方法在应用程序启动过程中或换句话说在组件扫描过程中进行扫描。因此,restTemplate可用于autowire

答案 1 :(得分:0)

按照@chrylis的建议将配置与控制器分开后,就可以像这样进一步进行。

您必须尝试模拟RequestEntity.post方法。请注意,这是一个静态方法,其模拟方式与通常的公共实例方法略有不同。为此,您需要使用PowerMockito,因为Mockito不会这样做。

像这样在pom中添加依赖项:

<dependency>
    <groupId>org.powermock</groupId>
    <artifactId>powermock-module-junit4</artifactId>
    <version>1.6.5</version>
    <scope>test</scope>
</dependency>
<dependency>
    <groupId>org.powermock</groupId>
    <artifactId>powermock-api-mockito</artifactId>
    <version>1.6.5</version>
    <scope>test</scope>
</dependency>

然后用@RunWith@PrepareForTest注释测试类,如下所示:

@RunWith(PowerMockRunner.class)
@PrepareForTest({RequestEntity.class})
public class TestClass {
}

以及模拟post方法:

PowerMockito.mockStatic(RequestEntity.class);  when(RequestEntity.post(any(URI.class))).thenReturn(getRequestEntityResponseBody());
private RequestEntity< CustomerInfo > getRequestEntityResponseBody(){
 //code
}

更新

CustomerInfo customerInfo = new CustomerInfo();
HttpHeaders responseHeaders = new HttpHeaders();
responseHeaders.set("MyResponseHeader", "MyValue");
RequestEntity<CustomerInfo> customerInfoRequestEntity = new ResponseEntity<CustomerInfo>(customerInfo, responseHeaders, HttpStatus.OK);
PowerMockito.mockStatic(RequestEntity.class);
when(RequestEntity.post(any(URI.class))).thenReturn(customerInfoRequestEntity);