Java 8 acceptEither CompletableFuture示例

时间:2018-10-08 07:24:41

标签: java java-8

我是Java 8的新手,并且正在学习CompletableFuture API。 我也有一个要求,我需要对第三方API进行异步调用,然后等待7秒。 7秒后,继续进行我的实际处理。 另外,我需要检查在这7秒钟内Async调用是否已成功完成。如果是,则记录成功响应或异步调用异常完成,然后在我的数据库中记录错误响应。

CompletableFure<Void> thridPartyCallFuture = Async Call to Third Party API;

//Wait for 7 seconds

我不需要从第三方API调用中获取任何响应,我只需要暂停7秒钟即可。

因此我尝试致电thridPartyCallFuture.get(7, TimeUnit.SECONDS); 但是问题是当我调用thridPartyCallFuture.isDone()时,它将始终返回true,但是如果thridPartyCallFuture异常完成,我将不知道,这对于在DB中记录错误响应很重要。让我们考虑一个第三方API中断并且我们的调用异常完成的情况。在这种情况下,isDone()将返回true,而isCompletedExceptionally()将返回false

检查thridPartyCallFuture是否已成功完成,然后在数据库中记录成功响应。

检查thridPartyCallFuture是否已异常完成,然后在DB中记录错误响应。

我曾尝试探索acceptEither,但做对了。

我知道在Java 9中引入了一种新方法orTimeOut(int),但是在Java 8中我们没有这种方法。

感谢您的帮助!

谢谢。

1 个答案:

答案 0 :(得分:1)

即使结果更快返回,也不确定为什么要等待7秒。 以下代码显示了如何处理API调用问题。 没错,Java 9支持超时更好。

public static void main(String[] args) throws ExecutionException, InterruptedException {
    CompletableFuture<Result> completableFuture = CompletableFuture
            .supplyAsync(() -> {
                System.out.println("Making call to API...");
                //call API here and if call fails, throw exception
                //throw new RuntimeException("HTTP call failed");
                return new Result(true, "Done");
            })
            .handle((o, throwable) -> o.isSuccess() ? o : new Result(false, throwable.getMessage()));

    Executors.newSingleThreadScheduledExecutor()
            .schedule(() -> {
                        Result result = completableFuture.getNow(new Result(false, "Timeout"));
                        System.out.println("Log to DB: "
                                + result.isSuccess()
                                + result.getMessage());
                        //other application method calls here
                    }, 7, TimeUnit.SECONDS);
}

-

public class Result {
    private boolean success;
    private String message;

    public Result(boolean success, String message) {
        this.success = success;
        this.message = message;
    }
    //getters/setters
}