[英]Throwing exceptions from within CompletableFuture exceptionally clause
[英]Throwing exceptions from sync portions of async methods returning CompletableFuture
此问题特定于Java和CompletableFuture
。
如果我有一个类似下面的异步方法,
CompletableFuture<String> get() {
/* Step #1: Do some sync prep work */
String s = doSomethingSync();
/* Step #2: Do something async (returning CompletableFuture) */
return doSomethingAsync(s);
}
如果抛出步骤1中的代码,则get()
调用者将在获取其返回的CompletableFuture
之前获得异常,而如果抛出步骤2中的CompletableFuture
内的代码引发,则调用者仅在与返回的CompletableFuture
交互时才会获得异常。 。
这表明get()
调用者应编写一些复杂的异常处理代码来解决这两种情况。
这是另一个异步方法invokeGet()
的示例,该方法调用get()
并返回它返回的String
的长度:
CompletableFutre<Integer> InvokeGet() {
try {
CompletableFuture future = get();
return furure.handle((result, throwable) -> {
if (throwable != null) {
/* Handle exception thrown in step #2 in get(), e.g. rethrow */
} else {
return result.length();
}
});
} catch (Exception e) {
/* Handle exception thrown in step #1 in get() */
/* Return some value or throw */
}
}
我的问题是:
是get()
写得不好,是因为它要求调用者执行这种复杂的异常处理,还是这是一种通常且常见的模式? 返回CompletableFuture
的异步方法是否应该将自身限制为在出现错误的情况下返回有故障的期货,从而使调用者不必编写此类错误处理代码?
我认为抛出异常以进行参数验证是适当的,因为调用者不应该处理这些异常–非法参数是必须修复的错误。
但是,最好将其他异常放入返回的CompletableFuture
,以便调用者可以使用标准的CompletableFuture
异常处理和链接。 同样,你也不会返回一个null
未来,但未来有完成null
。 另请参见CompletableFuture(已完成,带有异常) 。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.