繁体   English   中英

如何在单元测试中模拟 REST API?

[英]How to Mock REST API in unit testing?

我正在使用 RestTemplate exchange HttpMethod.POST方法来 POST 到端点。 在我的测试文件中,我正在测试 POST 方法是否success 但是,在我当前的测试中,发出 POST 请求时401 Unauthorized error 在测试文件中发出 POST 请求时,我需要帮助来模拟 API

这是我的主文件


@Component
public class DataTestRepo {

    private final RestTemplate restTemplate;
    private final String url;
    private final AllBuilder headersBuilder;

    public DataTestRepo(
            @Qualifier(Oauth.BEAN_NAME) AllBuilder headersBuilder,
            RestTemplate restTemplate, String url) {
        this.headersBuilder = headersBuilder;
        this.restTemplate = restTemplate;
        this.url = url;
    }
    public ResponseEntity<String> postJson(Set<String> results) {
        ResponseEntity<String> result = null;

        try {
            JSONObject jsonObject = new JSONObject(body);

            HttpEntity<String> request = new HttpEntity<String>(jsonObject.toString(), null);
            restTemplate.getMessageConverters().add(stringConvertor);
            result = restTemplate.exchange(url, HttpMethod.POST,
                    new HttpEntity<>(request, getHttpHeaders()), String.class);
         } 
        return result;
    }
}

这是我的测试文件

@RunWith(MockitoJUnitRunner.class)
@TestPropertySource
public class DataTestRepoTest {

    private static final String url = "http://localhost:8080/data/name";

    @Mock
    private DataTestRepo DataTestRepo;
    RestTemplate restTemplate = new RestTemplate();

    @Test
    public void restTemplateHttpPost_success() throws URISyntaxException {
        URI uri = new URI(url);
        Set<String> mockData = Stream.of("A","B").collect(Collectors.toSet());
        Map<String, String> body = new HashMap<>();
        body.put("Name", "Aws");
        JSONObject jsonObject = new JSONObject(body);

        HttpEntity<String> request = new HttpEntity<>(jsonObject.toString(), null);

        ResponseEntity<String> result = restTemplate.exchange(uri, HttpMethod.POST,
                new HttpEntity<>(request, DataTestRepo.getHttpHeaders()), String.class);

        Assert.assertEquals(201, result.getStatusCodeValue());
    }
}


您正在测试 DataTestRepo 类中的逻辑,因此不应模拟它。 RestTemplate 是 DataTestRepo 中的一个依赖项,所以这正是您需要模拟的。 一般来说,它在你的测试中应该是这样的:

@InjectMocks
private DataTestRepo DataTestRepo;
@Mock
RestTemplate restTemplate;

此外,您必须为模拟的依赖项提供返回值,如下所示:

Mockito.when(restTemplate.exchange(ArgumentMatchers.any(), ArgumentMatchers.any(), ArgumentMatchers.any(), ArgumentMatchers.any())).thenReturn(new ResponseEntity<>(yourExpectedDataHere, HttpStatus.OK));
enter code here

这只是一个简单的例子。 一个好的做法是检查传递给模拟的参数是否等于预期的参数。 一种方法是用真实的预期数据替换 ArgumentMatchers.any()。 另一种是单独验证,像这样:

Mockito.verify(restTemplate, Mockito.times(1)).exchange(ArgumentsMatchers.eq(yourExpectedDataHere), ArgumentsMatchers.eq(yourExpectedDataHere), ArgumentsMatchers.eq(yourExpectedDataHere), ArgumentsMatchers.eq(yourExpectedDataHere));

这是关于这个主题的一个很好的阅读: https : //reflectoring.io/spring-boot-web-controller-test/

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM