apache/druid · warning · RE

Current thread is interrupted after

Error message

Current thread is interrupted after [%s] tries

What it means

RetryUtils.retry(...) stops retrying immediately when the current thread is interrupted. After running cleanup and exhausting that check, it throws a RejectedExecutionException (RE) reporting the number of tries at which the interruption was observed. This surfaces the thread's interrupt status rather than masking it with further retries.

Solutions

  1. Let the thread terminate: don't swallow this — treat it as cancellation and unwind the operation.
  2. Check Thread.currentThread().isInterrupted() before entering long retry loops and abort early.
  3. Fix whatever is interrupting the thread prematurely (cancellation logic, executor shutdown timing, timeouts too short).
  4. If interruption is expected and safe to continue (rare), clear and re-check policy explicitly — usually not recommended.

Example fix

// before
T result = RetryUtils.retry(task, shouldRetry, 5);
// after
if (!Thread.currentThread().isInterrupted()) {
  T result = RetryUtils.retry(task, shouldRetry, 5);
} else {
  throw new InterruptedException("Cancelled before retrying");
}
Defensive patterns

Strategy: try-catch

Validate before calling

if (Thread.currentThread().isInterrupted()) { throw new InterruptedException("Interrupted before retry"); }

Try / catch

try {
  result = RetryUtils.retry(task, shouldRetry, maxTries);
} catch (RejectedExecutionException | InterruptedException e) {
  Thread.currentThread().interrupt(); // preserve status and unwind
  throw new CancellationException("Operation cancelled");
}

Prevention

When it happens

Trigger: The calling thread's interrupt flag is set while inside RetryUtils.retry — e.g. a Druid query is cancelled/times out and its task thread is interrupted, or shutdown interrupts a worker thread mid-retry.

Common situations: Query cancellation in Druid (cancellation or timeout interrupts task threads that are retrying an HTTP fetch or segment load); service shutdown interrupting background retry loops.

Understand the failure class

Background: Request timed out: what client-side request timeouts mean across libraries (Request timed out, TIMED_OUT, APITimeoutError) — this error's family across 39 libraries.

Related errors


AI-assisted analysis of apache/druid@9b90983fd2 (2026-09-07). Data as JSON: /api/errors/e690ecf664c173b0. Report an issue: GitHub.

Appendix: source

Thrown at processing/src/main/java/org/apache/druid/java/util/common/RetryUtils.java:148

      }
      catch (Throwable e) {
        if (cleanupAfterFailure != null) {
          cleanupAfterFailure.cleanup();
        }
        if (nTry < maxTries && shouldRetry.apply(e)) {
          if (!skipSleep) {
            awaitNextRetry(e, messageOnRetry, nTry, maxRetries, nTry <= quietTries);
          }
        } else {
          Throwables.propagateIfInstanceOf(e, Exception.class);
          throw new RuntimeException(e);
        }
      }
    }
    if (cleanupAfterFailure != null) {
      cleanupAfterFailure.cleanup();
    }
    throw new RE("Current thread is interrupted after [%s] tries", nTry);
  }

  public static <T> T retry(final Task<T> f, Predicate<Throwable> shouldRetry, final int maxTries) throws Exception
  {
    return retry(f, shouldRetry, 0, maxTries);
  }

  public static <T> T retry(
      final Task<T> f,
      final Predicate<Throwable> shouldRetry,
      final int quietTries,
      final int maxTries
  ) throws Exception
  {
    return retry(f, shouldRetry, quietTries, maxTries, null, null);
  }

  public static <T> T retry(

View on GitHub (pinned to 9b90983fd2)