alibaba/ARouter · error · NullPointerException
TimeUnit must not be null.
Error message
TimeUnit must not be null.
What it means
InterceptorInitState.await(timeout, unit) converts the timeout to nanoseconds using the TimeUnit, so a null unit cannot be handled. It throws NullPointerException immediately to fail fast instead of dying inside unit.toNanos().
Source
Thrown at arouter-api/src/main/java/com/alibaba/android/arouter/core/InterceptorInitState.java:75
lock.notifyAll();
}
}
void fail(Throwable cause) {
if (cause == null) {
throw new IllegalArgumentException("Interceptor initialization failure must have a cause.");
}
synchronized (lock) {
status = Status.FAILED;
failure = cause;
lock.notifyAll();
}
}
Result await(long timeout, TimeUnit unit) throws InterruptedException {
if (unit == null) {
throw new NullPointerException("TimeUnit must not be null.");
}
long timeoutNanos = unit.toNanos(timeout);
long startNanos = System.nanoTime();
synchronized (lock) {
while (status != Status.SUCCEEDED && status != Status.FAILED) {
long elapsedNanos = System.nanoTime() - startNanos;
long remainingNanos = timeoutNanos - elapsedNanos;
if (remainingNanos <= 0) {
return new Result(Outcome.TIMEOUT, null);
}
TimeUnit.NANOSECONDS.timedWait(lock, remainingNanos);
}
if (status == Status.FAILED) {
return new Result(Outcome.FAILURE, failure);View on GitHub (pinned to 84f451d244)
Solutions
- Pass an explicit TimeUnit, e.g. TimeUnit.SECONDS, at every await() call site
- If the unit is configurable, default it before calling await
- Prefer the MILLIS/SECONDS constant that matches the timeout magnitude to avoid silent unit bugs
Example fix
// before Result r = initState.await(timeout, null); // after Result r = initState.await(timeout, TimeUnit.SECONDS);
Defensive patterns
Strategy: validation
Validate before calling
Objects.requireNonNull(unit, "TimeUnit must not be null"); Result r = initState.await(timeout, unit);
Try / catch
try {
return initState.await(timeout, TimeUnit.SECONDS);
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
return Result.INTERRUPTED;
} Prevention
- Always pass an explicit TimeUnit constant
- Default configurable units before the await call
- Prefer SECONDS/MILLIS constants over dynamic unit lookup
When it happens
Trigger: Calling await(timeout, null) — usually because a TimeUnit constant was deleted, refactored to a nullable parameter, or a caller passed a unit variable that was never initialized.
Common situations: Configurable timeout code where the TimeUnit is read from config/defaults and a default was omitted; tests passing null to shortcut the wait.
Related errors
- Interceptor initialization failure must have a cause.
- Interceptor timeout has already been scheduled.
- No postcard!
- More than one interceptors use same priority [%d], They are
- String.format(tipText, key)
AI-assisted analysis of alibaba/ARouter@84f451d244 (2026-09-06).
Data as JSON: /api/errors/56f11663206f99ce.
Report an issue: GitHub.