gpt4 book ai didi

java - 在 WebClient 中处理异常抛出 io.netty.handler.timeout.ReadTimeoutException

转载 作者:行者123 更新时间:2023-11-30 09:59:58 78 4
gpt4 key购买 nike

所以我是 Reactive 编程的新手,我写了一些我想测试的代码。这些更像是一个集成测试,因为我正在实时复制文件,然后检查它们是否相同。我有一个 MockWebServer mock 我的回答是4xx这在代码中处理得很好。不幸的是,我也收到了 io.netty.handler.timeout.ReadTimeoutException这掩盖了我的习惯WebClientResponseException所以在测试中我得到了错误的异常。基本上我有两个问题,为什么我会得到这个 io.netty.handler.timeout.ReadTimeoutException异常(exception)?它只出现在 doOnError() 之后出于某种原因的方法,我不确定它为什么会发生。

现在代码是同步的,我很清楚这一点。

第二个问题是,在给定的重试次数后,我如何处理测试中的自定义异常?现在它是 3,只有到那时我才希望抛出我的另一个异常。

代码如下:

AsynchronousFileChannel fileChannel = AsynchronousFileChannel.open(targetPath, StandardOpenOption.WRITE);

Flux<DataBuffer> fileDataStream = Mono.just(filePath)
.map(file -> targetPath.toFile().exists() ? targetPath.toFile().length() : 0)
.map(bytes -> webClient
.get()
.uri(uri)
.accept(MediaType.APPLICATION_OCTET_STREAM)
.header("Range", String.format("bytes=%d-", bytes))
.retrieve()
.onStatus(HttpStatus::is4xxClientError, clientResponse -> Mono.error(new CustomException("4xx error")))
.onStatus(HttpStatus::is5xxServerError, clientResponse -> Mono.error(new CustomException("5xx error")))
.bodyToFlux(DataBuffer.class)
.doOnError(throwable -> log.info("fileDataStream onError", throwable))
)
.flatMapMany(Function.identity());

return DataBufferUtils
.write(fileDataStream, fileChannel)
.map(DataBufferUtils::release)
.doOnError(throwable -> {
try {
fileChannel.force(true);
} catch (IOException e) {
throw new WritingException("failed force update to file channel", e);
}
})
.retry(3)
.doOnComplete(() -> {
try {
fileChannel.force(true);
} catch (IOException e) {
log.warn("failed force update to file channel", e);
throw new WritingException("failed force update to file channel", e);
}
})
.doOnError(throwable -> targetPath.toFile().delete())
.then(Mono.just(target));

响应是Mono<Path>因为我只对 Path 感兴趣新创建和复制的文件。

欢迎对代码提出任何意见。

复制机制是基于这个线程Downlolad and save file from ClientRequest using ExchangeFunction in Project Reactor

最佳答案

所以基本上问题出在测试中。我有一个 MockResponse 只排队到 MockWebServer 一次,所以在 WebClient 中重试时模拟服务器没有任何响应集(基本上它表现得像它根本不可用,因为没有模拟响应)。

为了能够在服务器完全关闭的情况下处理异常,在我看来,值得将类似这样的行添加到您的通量链中:

.doOnError(ChannelException.class, e -> {
throw new YourCustomExceptionForHandlingServerIsDownSituation("Server is unreachable", e);
})

这将帮助您处理来自 Netty 的 ReadTimeoutException(在服务器无法访问的情况下),因为它扩展了 ChannelException 类。始终处理您的异常。

关于java - 在 WebClient 中处理异常抛出 io.netty.handler.timeout.ReadTimeoutException,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58417422/

78 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com