Skip to content

Commit

Permalink
Reduce scope of suppressions in Abstract*Future classes, and make t…
Browse files Browse the repository at this point in the history
…he classes look slightly more similar to one another.

RELNOTES=n/a
PiperOrigin-RevId: 729152015
  • Loading branch information
cpovirk authored and Google Java Core Libraries committed Feb 20, 2025
1 parent a5a02ae commit 60ba1ab
Show file tree
Hide file tree
Showing 4 changed files with 78 additions and 86 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -34,11 +34,8 @@

/** Implementations of {@code Futures.catching*}. */
@GwtCompatible
@SuppressWarnings({
// Whenever both tests are cheap and functional, it's faster to use &, | instead of &&, ||
"ShortCircuitBoolean",
"nullness", // TODO(b/147136275): Remove once our checker understands & and |.
})
// Whenever both tests are cheap and functional, it's faster to use &, | instead of &&, ||
@SuppressWarnings("ShortCircuitBoolean")
abstract class AbstractCatchingFuture<
V extends @Nullable Object, X extends Throwable, F, T extends @Nullable Object>
extends FluentFuture.TrustedFuture<V> implements Runnable {
Expand All @@ -47,19 +44,19 @@ abstract class AbstractCatchingFuture<
Class<X> exceptionType,
Function<? super X, ? extends V> fallback,
Executor executor) {
CatchingFuture<V, X> future = new CatchingFuture<>(input, exceptionType, fallback);
input.addListener(future, rejectionPropagatingExecutor(executor, future));
return future;
CatchingFuture<V, X> output = new CatchingFuture<>(input, exceptionType, fallback);
input.addListener(output, rejectionPropagatingExecutor(executor, output));
return output;
}

static <X extends Throwable, V extends @Nullable Object> ListenableFuture<V> createAsync(
ListenableFuture<? extends V> input,
Class<X> exceptionType,
AsyncFunction<? super X, ? extends V> fallback,
Executor executor) {
AsyncCatchingFuture<V, X> future = new AsyncCatchingFuture<>(input, exceptionType, fallback);
input.addListener(future, rejectionPropagatingExecutor(executor, future));
return future;
AsyncCatchingFuture<V, X> output = new AsyncCatchingFuture<>(input, exceptionType, fallback);
input.addListener(output, rejectionPropagatingExecutor(executor, output));
return output;
}

/*
Expand All @@ -78,6 +75,7 @@ abstract class AbstractCatchingFuture<
}

@Override
@SuppressWarnings("nullness") // TODO(b/147136275): Remove once our checker understands & and |.
public final void run() {
@RetainedLocalRef ListenableFuture<? extends V> localInputFuture = inputFuture;
@RetainedLocalRef Class<X> localExceptionType = exceptionType;
Expand Down Expand Up @@ -148,6 +146,24 @@ public final void run() {
setResult(fallbackResult);
}

/** Template method for subtypes to actually run the fallback. */
@ForOverride
@ParametricNullness
abstract T doFallback(F fallback, X throwable) throws Exception;

/** Template method for subtypes to actually set the result. */
@ForOverride
abstract void setResult(@ParametricNullness T result);

@Override
protected final void afterDone() {
@RetainedLocalRef ListenableFuture<? extends V> localInputFuture = inputFuture;
maybePropagateCancellationTo(localInputFuture);
this.inputFuture = null;
this.exceptionType = null;
this.fallback = null;
}

@Override
protected @Nullable String pendingToString() {
@RetainedLocalRef ListenableFuture<? extends V> localInputFuture = inputFuture;
Expand All @@ -171,24 +187,6 @@ public final void run() {
return null;
}

/** Template method for subtypes to actually run the fallback. */
@ForOverride
@ParametricNullness
abstract T doFallback(F fallback, X throwable) throws Exception;

/** Template method for subtypes to actually set the result. */
@ForOverride
abstract void setResult(@ParametricNullness T result);

@Override
protected final void afterDone() {
@RetainedLocalRef ListenableFuture<? extends V> localInputFuture = inputFuture;
maybePropagateCancellationTo(localInputFuture);
this.inputFuture = null;
this.exceptionType = null;
this.fallback = null;
}

/**
* An {@link AbstractCatchingFuture} that delegates to an {@link AsyncFunction} and {@link
* #setFuture(ListenableFuture)}.
Expand All @@ -206,13 +204,13 @@ private static final class AsyncCatchingFuture<V extends @Nullable Object, X ext
@Override
ListenableFuture<? extends V> doFallback(
AsyncFunction<? super X, ? extends V> fallback, X cause) throws Exception {
ListenableFuture<? extends V> replacement = fallback.apply(cause);
ListenableFuture<? extends V> output = fallback.apply(cause);
checkNotNull(
replacement,
output,
"AsyncFunction.apply returned null instead of a Future. "
+ "Did you mean to return immediateFuture(null)? %s",
fallback);
return replacement;
return output;
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -31,27 +31,22 @@

/** Implementations of {@code Futures.transform*}. */
@GwtCompatible
@SuppressWarnings({
// Whenever both tests are cheap and functional, it's faster to use &, | instead of &&, ||
"ShortCircuitBoolean",
"nullness", // TODO(b/147136275): Remove once our checker understands & and |.
})
// Whenever both tests are cheap and functional, it's faster to use &, | instead of &&, ||
@SuppressWarnings("ShortCircuitBoolean")
abstract class AbstractTransformFuture<
I extends @Nullable Object, O extends @Nullable Object, F, T extends @Nullable Object>
extends FluentFuture.TrustedFuture<O> implements Runnable {
static <I extends @Nullable Object, O extends @Nullable Object> ListenableFuture<O> createAsync(
ListenableFuture<I> input,
AsyncFunction<? super I, ? extends O> function,
Executor executor) {
checkNotNull(executor);
AsyncTransformFuture<I, O> output = new AsyncTransformFuture<>(input, function);
input.addListener(output, rejectionPropagatingExecutor(executor, output));
return output;
}

static <I extends @Nullable Object, O extends @Nullable Object> ListenableFuture<O> create(
ListenableFuture<I> input, Function<? super I, ? extends O> function, Executor executor) {
checkNotNull(function);
TransformFuture<I, O> output = new TransformFuture<>(input, function);
input.addListener(output, rejectionPropagatingExecutor(executor, output));
return output;
Expand All @@ -70,7 +65,10 @@ abstract class AbstractTransformFuture<
}

@Override
@SuppressWarnings("CatchingUnchecked") // sneaky checked exception
@SuppressWarnings({
"CatchingUnchecked", // sneaky checked exception
"nullness", // TODO(b/147136275): Remove once our checker understands & and |.
})
public final void run() {
@RetainedLocalRef ListenableFuture<? extends I> localInputFuture = inputFuture;
@RetainedLocalRef F localFunction = function;
Expand Down Expand Up @@ -225,13 +223,13 @@ private static final class AsyncTransformFuture<
ListenableFuture<? extends O> doTransform(
AsyncFunction<? super I, ? extends O> function, @ParametricNullness I input)
throws Exception {
ListenableFuture<? extends O> outputFuture = function.apply(input);
ListenableFuture<? extends O> output = function.apply(input);
checkNotNull(
outputFuture,
output,
"AsyncFunction.apply returned null instead of a Future. "
+ "Did you mean to return immediateFuture(null)? %s",
function);
return outputFuture;
return output;
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,11 +34,8 @@

/** Implementations of {@code Futures.catching*}. */
@GwtCompatible
@SuppressWarnings({
// Whenever both tests are cheap and functional, it's faster to use &, | instead of &&, ||
"ShortCircuitBoolean",
"nullness", // TODO(b/147136275): Remove once our checker understands & and |.
})
// Whenever both tests are cheap and functional, it's faster to use &, | instead of &&, ||
@SuppressWarnings("ShortCircuitBoolean")
abstract class AbstractCatchingFuture<
V extends @Nullable Object, X extends Throwable, F, T extends @Nullable Object>
extends FluentFuture.TrustedFuture<V> implements Runnable {
Expand All @@ -47,19 +44,19 @@ abstract class AbstractCatchingFuture<
Class<X> exceptionType,
Function<? super X, ? extends V> fallback,
Executor executor) {
CatchingFuture<V, X> future = new CatchingFuture<>(input, exceptionType, fallback);
input.addListener(future, rejectionPropagatingExecutor(executor, future));
return future;
CatchingFuture<V, X> output = new CatchingFuture<>(input, exceptionType, fallback);
input.addListener(output, rejectionPropagatingExecutor(executor, output));
return output;
}

static <X extends Throwable, V extends @Nullable Object> ListenableFuture<V> createAsync(
ListenableFuture<? extends V> input,
Class<X> exceptionType,
AsyncFunction<? super X, ? extends V> fallback,
Executor executor) {
AsyncCatchingFuture<V, X> future = new AsyncCatchingFuture<>(input, exceptionType, fallback);
input.addListener(future, rejectionPropagatingExecutor(executor, future));
return future;
AsyncCatchingFuture<V, X> output = new AsyncCatchingFuture<>(input, exceptionType, fallback);
input.addListener(output, rejectionPropagatingExecutor(executor, output));
return output;
}

/*
Expand All @@ -78,6 +75,7 @@ abstract class AbstractCatchingFuture<
}

@Override
@SuppressWarnings("nullness") // TODO(b/147136275): Remove once our checker understands & and |.
public final void run() {
@RetainedLocalRef ListenableFuture<? extends V> localInputFuture = inputFuture;
@RetainedLocalRef Class<X> localExceptionType = exceptionType;
Expand Down Expand Up @@ -148,6 +146,24 @@ public final void run() {
setResult(fallbackResult);
}

/** Template method for subtypes to actually run the fallback. */
@ForOverride
@ParametricNullness
abstract T doFallback(F fallback, X throwable) throws Exception;

/** Template method for subtypes to actually set the result. */
@ForOverride
abstract void setResult(@ParametricNullness T result);

@Override
protected final void afterDone() {
@RetainedLocalRef ListenableFuture<? extends V> localInputFuture = inputFuture;
maybePropagateCancellationTo(localInputFuture);
this.inputFuture = null;
this.exceptionType = null;
this.fallback = null;
}

@Override
protected @Nullable String pendingToString() {
@RetainedLocalRef ListenableFuture<? extends V> localInputFuture = inputFuture;
Expand All @@ -171,24 +187,6 @@ public final void run() {
return null;
}

/** Template method for subtypes to actually run the fallback. */
@ForOverride
@ParametricNullness
abstract T doFallback(F fallback, X throwable) throws Exception;

/** Template method for subtypes to actually set the result. */
@ForOverride
abstract void setResult(@ParametricNullness T result);

@Override
protected final void afterDone() {
@RetainedLocalRef ListenableFuture<? extends V> localInputFuture = inputFuture;
maybePropagateCancellationTo(localInputFuture);
this.inputFuture = null;
this.exceptionType = null;
this.fallback = null;
}

/**
* An {@link AbstractCatchingFuture} that delegates to an {@link AsyncFunction} and {@link
* #setFuture(ListenableFuture)}.
Expand All @@ -206,13 +204,13 @@ private static final class AsyncCatchingFuture<V extends @Nullable Object, X ext
@Override
ListenableFuture<? extends V> doFallback(
AsyncFunction<? super X, ? extends V> fallback, X cause) throws Exception {
ListenableFuture<? extends V> replacement = fallback.apply(cause);
ListenableFuture<? extends V> output = fallback.apply(cause);
checkNotNull(
replacement,
output,
"AsyncFunction.apply returned null instead of a Future. "
+ "Did you mean to return immediateFuture(null)? %s",
fallback);
return replacement;
return output;
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -31,27 +31,22 @@

/** Implementations of {@code Futures.transform*}. */
@GwtCompatible
@SuppressWarnings({
// Whenever both tests are cheap and functional, it's faster to use &, | instead of &&, ||
"ShortCircuitBoolean",
"nullness", // TODO(b/147136275): Remove once our checker understands & and |.
})
// Whenever both tests are cheap and functional, it's faster to use &, | instead of &&, ||
@SuppressWarnings("ShortCircuitBoolean")
abstract class AbstractTransformFuture<
I extends @Nullable Object, O extends @Nullable Object, F, T extends @Nullable Object>
extends FluentFuture.TrustedFuture<O> implements Runnable {
static <I extends @Nullable Object, O extends @Nullable Object> ListenableFuture<O> createAsync(
ListenableFuture<I> input,
AsyncFunction<? super I, ? extends O> function,
Executor executor) {
checkNotNull(executor);
AsyncTransformFuture<I, O> output = new AsyncTransformFuture<>(input, function);
input.addListener(output, rejectionPropagatingExecutor(executor, output));
return output;
}

static <I extends @Nullable Object, O extends @Nullable Object> ListenableFuture<O> create(
ListenableFuture<I> input, Function<? super I, ? extends O> function, Executor executor) {
checkNotNull(function);
TransformFuture<I, O> output = new TransformFuture<>(input, function);
input.addListener(output, rejectionPropagatingExecutor(executor, output));
return output;
Expand All @@ -70,7 +65,10 @@ abstract class AbstractTransformFuture<
}

@Override
@SuppressWarnings("CatchingUnchecked") // sneaky checked exception
@SuppressWarnings({
"CatchingUnchecked", // sneaky checked exception
"nullness", // TODO(b/147136275): Remove once our checker understands & and |.
})
public final void run() {
@RetainedLocalRef ListenableFuture<? extends I> localInputFuture = inputFuture;
@RetainedLocalRef F localFunction = function;
Expand Down Expand Up @@ -225,13 +223,13 @@ private static final class AsyncTransformFuture<
ListenableFuture<? extends O> doTransform(
AsyncFunction<? super I, ? extends O> function, @ParametricNullness I input)
throws Exception {
ListenableFuture<? extends O> outputFuture = function.apply(input);
ListenableFuture<? extends O> output = function.apply(input);
checkNotNull(
outputFuture,
output,
"AsyncFunction.apply returned null instead of a Future. "
+ "Did you mean to return immediateFuture(null)? %s",
function);
return outputFuture;
return output;
}

@Override
Expand Down

0 comments on commit 60ba1ab

Please sign in to comment.