当前位置: 首页 > 知识库问答 >
问题:

让CompletableFuture异常()处理供应Async()异常

况浩邈
2023-03-14

问题很简单:我正在寻找一种优雅的方式,将<code>CompletableFuture#与<code>CompletableFuture#supplySync</code>一起使用。这是不起作用的:

private void doesNotCompile() {
    CompletableFuture<String> sad = CompletableFuture
            .supplyAsync(() -> throwSomething())
            .exceptionally(Throwable::getMessage);
}

private String throwSomething() throws Exception {
    throw new Exception();
}

我认为异常()背后的想法正是为了处理抛出异常的情况。然而,如果我这样做,它会起作用:

private void compiles() {
    CompletableFuture<String> thisIsFine = CompletableFuture.supplyAsync(() -> {
        try {
            throwSomething();
            return "";
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }).exceptionally(Throwable::getMessage);
}

我可以这样做,但是这看起来很可怕,而且让事情更难维护。有没有一种不需要将所有< code>Exception转换为< code>RuntimeException的方法来保持这种简洁?

共有1个答案

苏骏
2023-03-14

这可能不是一个超级受欢迎的库,但我们使用它(有时我也在那里工作;次要的)内部:没有例外。它真的,真的很适合我的口味。这不是它唯一拥有的东西,但肯定涵盖了您的使用案例:

以下是一个示例:

import com.machinezoo.noexception.Exceptions;
import java.util.concurrent.CompletableFuture;

public class SO64937499 {

    public static void main(String[] args) {
        CompletableFuture<String> sad = CompletableFuture
            .supplyAsync(Exceptions.sneak().supplier(SO64937499::throwSomething))
            .exceptionally(Throwable::getMessage);
    }

    private static String throwSomething() throws Exception {
        throw new Exception();
    }
}

或者,您可以自己创建这些:

final class CheckedSupplier<T> implements Supplier<T> {

    private final SupplierThatThrows<T> supplier;

    CheckedSupplier(SupplierThatThrows<T> supplier) {
        this.supplier = supplier;
    }

    @Override
    public T get() {
        try {
            return supplier.get();
        } catch (Throwable exception) {
            throw new RuntimeException(exception);
        }
    }
}



@FunctionalInterface
interface SupplierThatThrows<T> {

    T get() throws Throwable;
}

和用法:

 CompletableFuture<String> sad = CompletableFuture
        .supplyAsync(new CheckedSupplier<>(SO64937499::throwSomething))
        .exceptionally(Throwable::getMessage);
 类似资料:
  • 假设我有这个示例代码,在中遇到了一个异常。我的问题是,这个异常是否会阻止作为在与此代码的调用者方法相同的线程中运行。 我已经浏览了这个主题,它解释了如何处理从异步块抛出的异常(即通过阻塞和使用)。我想知道如果”,块中的代码是否会被执行。 更新: 我运行了一些代码来测试: 它不会打印任何内容,这意味着异常不会从异步块“传播到/到达”调用方方法的线程。我现在了解这里的预期行为,但我有以下问题: 为什么

  • 我有一个Spring Boot服务,其中包含一些用于并行异步调用的代码,如下所示: CompletableFuture future1=accountManager。getResult(url1); CompletableFuture future2=accountManager。getResult(url2); 复杂的Future.allOf(未来1,未来2)。 字符串result1=futur

  • 我是Spring Boot的新手。在一个项目中,我想异步发送一封电子邮件。下面,你可以看到我到目前为止有什么。 我遇到的一个问题是:外部系统向控制器发送POST请求。如果在生成或发送邮件时发生异常,则不会调用。因此,控制器总是返回HTTP 201,因此调用者认为一切正常。 我将如何集成我的异常处理程序与在这样的异步方法? 控制器 服务 异常处理程序

  • 我不知道该怎么办。 当我试图从解析器获取语法错误的数量时,它显示0。 编辑: 它返回null。

  • Blade 内置了 异常处理器,在开发者模式下它会将异常输出在前端页面,并在控制台打印堆栈信息,生产环境只打印在控制台。 有些时候不满足我们的需求,这时候就需要自定义异常处理了,比如针对某个自定义的异常进行特殊处理。 我们用一个例子来解释如何操作。 定义了一个名为 TipException 的运行时异常类,用于输出错误消息到前台。 按照上面对异常的处理情况这个异常的堆栈信息会被输出在控制台,生产环

  • 任何方法都可以抛出不同类型的异常。这些异常可能是需要应用程序重新部署来解决的编程错误,或者是不需要重新部署但可以解决的暂时性错误。 Hangfire可以处理所有内部的(属于Hangfire本身)和相关的外部方法(任务,过滤器等)的异常,因此不会导致整个应用程序被关闭。所有内部异常都被记录(所以不要忘记 启用日志),最糟糕的情况是导致后台任务被暂停并延时重试 10 次。 当Hangfire遇到在执行