PlayWS-如何在达到请求超时时引发异常?

时间:2018-11-08 07:38:01

标签: java playframework java-8

在使用CompletableFuture的PlayWS执行长时间下载时,这些下载有时会达到定义的请求超时。发生这种情况时,PlayWS似乎不会引发异常(至少在我的配置中),因此即使数据已损坏,也无法将下载标记为失败并进行处理。

请原谅这段可憎的代码:

final CompletionStage<WSResponse> futureResponse = this.playWS.client
        .url(importSource.getDownloadUrl())
        .setMethod(HttpMethod.GET)
        .setRequestTimeout(Duration.ofSeconds(5)) // When the timeout is reached, the download gets canceled
        .stream();

try {
    futureResponse
            .thenAccept(res -> {
                try (OutputStream outputStream = Files.newOutputStream(file.toPath())) {
                    final Source<ByteString, ?> responseBody = res.getBodyAsSource();
                    final Sink<ByteString, CompletionStage<Done>> outputWriter =
                            Sink.foreach(bytes -> {
                                outputStream.write(bytes.toArray());
                            });
                    responseBody
                            .runWith(outputWriter, this.playWS.materializer)
                            .whenComplete((value, error) -> {
                                System.out.println("VALUE: "+value); // == "Done"
                                System.out.println("Error: "+error); // == null
                            })
                            .exceptionally(exception -> {
                                throw new IllegalStateException("Download failed for: " + importSource.getDownloadUrl(), exception);
                            })
                            .toCompletableFuture().join();
                } catch (final IOException e) {
                    throw new IllegalStateException("Couldn't open or write to OutputStream.", e);
                }
            })
            .exceptionally(exception -> {
                throw new IllegalStateException("Download failed for: " + importSource.getDownloadUrl(), exception);
            })
            .toCompletableFuture().get();
} catch (InterruptedException | ExecutionException e) {
    throw new IllegalStateException("Couldn't complete CompletableFuture.", e);
}

我是从根本上做错了还是这是一个错误?

我看到的唯一解决方案是:

  1. 计算接收到的字节并将其与Content-Length header进行比较。
  2. 将请求超时设置为-1(不确定)。

感谢您的任何建议。

1 个答案:

答案 0 :(得分:1)

我认为有些复杂化。

您可以仅将new_dates=[] indices=[] for i, date in sorted(enumerate(dates), key = lambda x: x[1]): new_dates.append(date) indices.append(i) new_prices=[] for i, price in sorted(enumerate(prices), key = lambda x: indices.index(x[0]): new_prices.append(price) Future附加到CompletableStage。 Akka Streams具有比Source更强大的API(我认为)

CompletableFuture