java - 当有请求正文时模拟 WebClient 帖子

标签 java spring unit-testing mockito webclient

有几个关于模拟 WebClient 对象的问题以及有用的答案。但我在用 body 发帖时仍然遇到问题。我只是使用Mockito而不是mockwebserver

这是我正在测试的方法:

public class RestClient extends BaseRestClient {
 ...
 public <T,G> Mono<T> post(String url, G req, Class<T> resp) throws IOException {
        Mono<T> response = null;

        response = this.getWebClient().post()
                    .uri(url)
                    .header(HttpHeaders.CONTENT_TYPE,JSON_CONTENT_TYPE)
                    .accept(MediaType.APPLICATION_JSON)
                    //.body(BodyInserters.fromObject(req))
                    .header(HttpHeaders.AUTHORIZATION, BEARER + token)
                    .retrieve()
                    .bodyToMono(resp).log();

        return response.map(resp::cast);
    }
 ...

注意注释掉的正文行。

这是与上面的代码配合良好的测试 - 再次注意测试中注释掉的行:

@Mock
WebClient webClient;

@Mock
WebClient.RequestBodyUriSpec requestBodyUriSpec;

@Mock
WebClient.RequestHeadersSpec requestHeadersSpec;

@Mock
WebClient.RequestBodySpec requestBodySpec;

@Mock
WebClient.ResponseSpec responseSpec;

@InjectMocks
RestClient restClient;

@Test
    public void postTest() throws IOException {
        when(webClient.post()).thenReturn(requestBodyUriSpec);
        when(requestBodyUriSpec.uri(anyString())).thenReturn(requestBodySpec);
        when(requestBodySpec.header(any(),any())).thenReturn(requestBodySpec);
        when(requestBodySpec.accept(any())).thenReturn(requestBodySpec);
        when(responseSpec.bodyToMono(ArgumentMatchers.<Class<String>>notNull()))
                .thenReturn(Mono.just("resp"));

        //when(requestBodySpec.body(any())).thenReturn(requestHeadersSpec);
        when(requestBodySpec.retrieve()).thenReturn(responseSpec);

        restClient.post("http://sampleurl",Object.class, Object.class);
    }

再次,一切正常。但是,如果我将注释掉的行放回代码中,这意味着这篇文章有一个正文,并通过将注释掉的行放回测试中来模拟正文,那么我将得到 NullPointerException代码中的.retrieve()。就像我缺少一个要模拟的对象一样。

我什至 mock 了 requestHeadersSpecrequestBodyUriSpec 的 .retrieve():

when(requestHeadersSpec.retrieve()).thenReturn(responseSpec);
when(requestBodyUriSpec.retrieve()).thenReturn(responseSpec);

但仍然没有成功。知道哪里出了什么问题吗?

最佳答案

我错过了模拟 requestHeadersSpec 的“header”方法:

when(requestHeadersSpec.header(any(),any())).thenReturn(requestHeadersSpec);

所以,现在效果很好:

@Test
    public void postTest() throws IOException {
        when(webClient.post()).thenReturn(requestBodyUriSpec);
        when(requestBodyUriSpec.uri(anyString())).thenReturn(requestBodySpec);
        when(requestBodySpec.header(any(),any())).thenReturn(requestBodySpec);

        when(requestHeadersSpec.header(any(),any())).thenReturn(requestHeadersSpec);

        when(requestBodySpec.accept(any())).thenReturn(requestBodySpec);
        when(requestBodySpec.body(any())).thenReturn(requestHeadersSpec);
        when(requestHeadersSpec.retrieve()).thenReturn(responseSpec);
        when(responseSpec.bodyToMono(ArgumentMatchers.<Class<String>>notNull()))
                .thenReturn(Mono.just("resp"));

        Assert.assertNotNull(restClient.post("http://sampleurl",Object.class, Object.class));
    }

关于java - 当有请求正文时模拟 WebClient 帖子,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58901364/

相关文章:

java - 位操作性能: masking or shifting

java - Spring/JUnit - 运行并非真正的单元测试 "tests"

java - Spring中将Controller1的方法调用到Controller2的另一个方法中

c# - 使用 Moq 模拟 HttpApplicationState 时似乎无法设置对象

android - 如何对包裹在 `runOnUiThread` 中的代码进行单元测试?

ios - XCTest 测试套件中的共享测试

java - Android 可扩展 ListView 图标(组指示器)

java - 在java中,如何通过非递归算法删除一个文件夹/目录?

java - 在微服务之间共享用户 ID 的最佳实践是什么?

Spring MVC - 发生 http 404 时的 RestTemplate 启动异常