io.sphere.sdk.utils.CompletableFutureUtils Maven / Gradle / Ivy
package io.sphere.sdk.utils;
import io.sphere.sdk.utils.functional.TriFunction;
import org.apache.commons.lang3.tuple.Pair;
import java.util.NoSuchElementException;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.CompletionException;
import java.util.concurrent.CompletionStage;
import java.util.concurrent.ExecutionException;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Supplier;
public final class CompletableFutureUtils {
private CompletableFutureUtils() {
}
public static CompletableFuture successful(final T object) {
return CompletableFuture.completedFuture(object);
}
static Throwable blockForFailure(final CompletionStage future) {
try {
future.toCompletableFuture().join();
throw new NoSuchElementException(future + " did not complete exceptionally.");
} catch (final CompletionException e1) {
return e1.getCause();
}
}
public static CompletableFuture failed(final Throwable e) {
final CompletableFuture future = new CompletableFuture<>();
future.completeExceptionally(e);
return future;
}
public static void transferResult(final CompletionStage source,
final CompletableFuture target) {
source.whenComplete((result, throwable) -> {
final boolean isSuccessful = throwable == null;
if (isSuccessful) {
target.complete(result);
} else {
target.completeExceptionally(throwable);
}
});
}
public static CompletionStage onFailure(final CompletionStage future, final Consumer super Throwable> consumer) {
return future.whenCompleteAsync((value, throwable) -> {
if (throwable != null) {
consumer.accept(throwable);
}
});
}
public static CompletionStage onSuccess(final CompletionStage future, final Consumer super T> consumer) {
return future.whenCompleteAsync((value, throwable) -> {
if (throwable == null) {
consumer.accept(value);
}
});
}
public static CompletionStage recover(final CompletionStage future, final Function f) {
return future.exceptionally(f);
}
public static CompletionStage recoverWith(final CompletionStage future, final Function super Throwable, CompletionStage> f) {
final CompletableFuture result = new CompletableFuture<>();
final BiConsumer action = (value, error) -> {
if (value != null) {
result.complete(value);
} else {
final CompletionStage alternative = f.apply(error);
alternative.whenComplete((alternativeValue, alternativeError) -> {
if (alternativeValue != null) {
result.complete(alternativeValue);
} else {
result.completeExceptionally(alternativeError);
}
});
}
};
future.whenComplete(action);
return result;
}
public static T orElseThrow(final CompletionStage stage, Supplier extends X> exceptionSupplier) throws X, ExecutionException, InterruptedException {
final CompletableFuture future = stage.toCompletableFuture();
if (future.isDone()) {
return future.get();
} else {
throw exceptionSupplier.get();
}
}
public static T orElseGet(final CompletionStage stage, final Supplier other) throws ExecutionException, InterruptedException {
final CompletableFuture future = stage.toCompletableFuture();
return future.isDone() ? future.get() : other.get();
}
public static CompletionStage map(final CompletionStage future, final Function super T,? extends U> f) {
return future.thenApply(f);
}
public static CompletionStage flatMap(final CompletionStage future, final Function super T, CompletionStage> f) {
return future.thenCompose(f);
}
public static CompletionStage thenCombine(final CompletionStage a, final CompletionStage b, final CompletionStage c, final TriFunction f) {
final CompletionStage> pairCompletionStage = a.thenCombine(b, (aa, bb) -> Pair.of(aa, bb));
return pairCompletionStage.thenCombine(c, (pp, cc) -> f.apply(pp.getLeft(), pp.getRight(), cc));
}
}
© 2015 - 2024 Weber Informatics LLC | Privacy Policy