Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/spring/14.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 如何在SpringWebClient中设置和处理超时?_Java_Spring_Spring Webflux_Project Reactor_Reactive - Fatal编程技术网

Java 如何在SpringWebClient中设置和处理超时?

Java 如何在SpringWebClient中设置和处理超时?,java,spring,spring-webflux,project-reactor,reactive,Java,Spring,Spring Webflux,Project Reactor,Reactive,Spring docs表示需要手动为WebClient配置http客户端以设置超时:。 但由于WebClient返回的是被动Mono,所以(api方面)可以应用.timeout方法 它有同样的效果吗 此外,当使用.timeout方法时,反应堆的TimeoutException是预期的。如果手动完成配置,流中是否会出现相同的错误,即doError(TimeoutException.class,…)正常工作?我的发现 以http客户端特定的方式设置超时将导致http客户端特定的异常,即WebClie

Spring docs表示需要手动为WebClient配置http客户端以设置超时:。 但由于WebClient返回的是被动Mono,所以(api方面)可以应用
.timeout
方法

它有同样的效果吗


此外,当使用
.timeout
方法时,反应堆的
TimeoutException
是预期的。如果手动完成配置,流中是否会出现相同的错误,即
doError(TimeoutException.class,…)
正常工作?

我的发现

以http客户端特定的方式设置超时将导致http客户端特定的异常,即
WebClient
不包装异常:

@Test
void test() {
    var host = "localhost";
    var endpoint = "/test";
    var port = 8089;
    var timeout = Duration.ofSeconds(3);

    WireMockServer wireMockServer = new WireMockServer(wireMockConfig().port(8089));
    wireMockServer.start();
    WireMock.configureFor(host, wireMockServer.port());

    WireMock.stubFor(get(urlEqualTo(endpoint))
        .willReturn(aResponse().withFixedDelay((int) timeout.toMillis())));

    HttpClient httpClient = HttpClient.create()
        .tcpConfiguration(client ->
            client.doOnConnected(conn -> conn
                .addHandlerLast(new ReadTimeoutHandler((int) (timeout.toSeconds() / 2)))
                .addHandlerLast(new WriteTimeoutHandler((int) (timeout.toSeconds() / 2)))));

    WebClient webClient = WebClient.builder()
        .baseUrl(format("http://%s:%d", host, port))
        .clientConnector(new ReactorClientHttpConnector(httpClient)).build();

    webClient.get().uri(endpoint).retrieve().bodyToMono(Recommendation.class).block();
}
这将导致
io.netty.handler.timeout.ReadTimeoutException

.timeout(timeout.dividedBy(2)).block()
会导致常规的
TimeoutException
java.util.concurrent
),但web客户端是否会在事后处理连接(可能不会)仍是一个悬而未决的问题


我的解决方案是使用http客户机特定的配置,以确保以本机和正确的方式利用连接,同时添加新的处理程序,将http客户机相关的异常包装成更通用的异常(或
java.util.concurrent.TimeoutException
)因此,
WebClient
客户端将不依赖于提供程序异常。

您是否尝试使用Wiremock来检查这一点,该Wiremock将模拟响应时间超过超时的端点?您将需要这些静态导入:导入static com.github.tomakehurst.Wiremock.client.Wiremock.aResponse;导入静态com.github.tomakehurst.wiremock.client.wiremock.get;导入静态com.github.tomakehurst.wiremock.client.wiremock.urlEqualTo;导入静态com.github.tomakehurst.wiremock.core.WireMockConfiguration.wireMockConfig;您是如何测试WriteTimeoutException的?