CompleatableFuture可以在handle方法中异常完成吗?
Can CompleatableFuture be completed exceptionally in handle method?
我正在尝试将存储库异常映射到服务异常。这样的做法好吗?
@Override
public CompletableFuture<Void> delete(String id, Map<String, String> headers) {
CompletableFuture<Void> future = repository.delete(id, headers);
return future.handle((aVoid, throwable) -> {
if (throwable != null) {
Throwable cause = throwable.getCause();
if (DbExcUtils.isFKViolation(throwable)) {
future.completeExceptionally(new BadRequestException(HAS_ASSIGNED_RECORDS_MESSAGE));
} else {
future.completeExceptionally(cause);
}
}
return aVoid;
});
}
方法 handle
只会在目标 CompletableFuture
实例完成时调用它给定的 BiFunction
Returns a new CompletionStage
that, when this stage completes either
normally or exceptionally, is executed with this stage's result and
exception as arguments to the supplied function.
从这个意义上说,你无法再次完成它。 completeExceptionally
的 javadoc 状态
If not already completed, causes invocations of get()
and related
methods to throw the given exception.
当 future 已经完成时,它本质上是一个空操作。
如果你只想映射异常类型,那么使用exceptionally
。
Returns a new CompletionStage
that, when this stage completes
exceptionally, is executed with this stage's exception as the argument
to the supplied function. Otherwise, if this stage completes normally,
then the returned stage also completes normally with the same value.
这似乎在做您正在尝试的事情,即。如果有异常,则映射异常,否则 return 结果。
例如,
return future.exceptionally(throwable -> {
Throwable cause = throwable.getCause();
if (DbExcUtils.isFKViolation(throwable)) {
throw new CompletionException(new BadRequestException(HAS_ASSIGNED_RECORDS_MESSAGE));
} else {
throw new CompletionException(cause);
}
});
请注意,我们抛出了新的异常。
此外,您可能需要检查 throwable
是否是 CancellationException
(无原因)并在执行映射逻辑之前重新抛出它。
你可以使用obtrudeException
,但我不推荐它
Forcibly causes subsequent invocations of method get()
and related
methods to throw the given exception, whether or not already
completed. This method is designed for use only in error recovery
actions, and even in such situations may result in ongoing dependent
completions using established versus overwritten outcomes.
我正在尝试将存储库异常映射到服务异常。这样的做法好吗?
@Override
public CompletableFuture<Void> delete(String id, Map<String, String> headers) {
CompletableFuture<Void> future = repository.delete(id, headers);
return future.handle((aVoid, throwable) -> {
if (throwable != null) {
Throwable cause = throwable.getCause();
if (DbExcUtils.isFKViolation(throwable)) {
future.completeExceptionally(new BadRequestException(HAS_ASSIGNED_RECORDS_MESSAGE));
} else {
future.completeExceptionally(cause);
}
}
return aVoid;
});
}
方法 handle
只会在目标 CompletableFuture
实例完成时调用它给定的 BiFunction
Returns a new
CompletionStage
that, when this stage completes either normally or exceptionally, is executed with this stage's result and exception as arguments to the supplied function.
从这个意义上说,你无法再次完成它。 completeExceptionally
的 javadoc 状态
If not already completed, causes invocations of
get()
and related methods to throw the given exception.
当 future 已经完成时,它本质上是一个空操作。
如果你只想映射异常类型,那么使用exceptionally
。
Returns a new
CompletionStage
that, when this stage completes exceptionally, is executed with this stage's exception as the argument to the supplied function. Otherwise, if this stage completes normally, then the returned stage also completes normally with the same value.
这似乎在做您正在尝试的事情,即。如果有异常,则映射异常,否则 return 结果。
例如,
return future.exceptionally(throwable -> {
Throwable cause = throwable.getCause();
if (DbExcUtils.isFKViolation(throwable)) {
throw new CompletionException(new BadRequestException(HAS_ASSIGNED_RECORDS_MESSAGE));
} else {
throw new CompletionException(cause);
}
});
请注意,我们抛出了新的异常。
此外,您可能需要检查 throwable
是否是 CancellationException
(无原因)并在执行映射逻辑之前重新抛出它。
你可以使用obtrudeException
,但我不推荐它
Forcibly causes subsequent invocations of method
get()
and related methods to throw the given exception, whether or not already completed. This method is designed for use only in error recovery actions, and even in such situations may result in ongoing dependent completions using established versus overwritten outcomes.