eclipse-vertx/vert.x · error · IllegalArgumentException

Invalid resolver idle timeout

Error message

Invalid resolver idle timeout

What it means

HttpClientBuilderInternal.resolverIdleTimeout validates the idle timeout Duration used to expire idle resolver results. A null-or-not, but zero or negative Duration is rejected with this IllegalArgumentException because the resolver requires a strictly positive timeout.

Source

Thrown at vertx-core/src/main/java/io/vertx/core/http/impl/HttpClientBuilderInternal.java:123

    this.redirectHandler = handler;
    return this;
  }

  @Override
  public HttpClientBuilderInternal withAddressResolver(AddressResolver<?> resolver) {
    this.addressResolver = resolver;
    return this;
  }

  @Override
  public HttpClientBuilderInternal withLoadBalancer(LoadBalancer loadBalancer) {
    this.loadBalancer = loadBalancer;
    return this;
  }

  public HttpClientBuilderInternal resolverIdleTimeout(Duration timeout) {
    if (timeout.isNegative() || timeout.isZero()) {
      throw new IllegalArgumentException("Invalid resolver idle timeout");
    }
    this.resolverIdleTimeout = timeout;
    return this;
  }

  private CloseFuture resolveCloseFuture() {
    ContextInternal context = vertx.getContext();
    return context != null ? context.closeFuture() : vertx.closeFuture();
  }

  private EndpointResolver endpointResolver(HttpClientConfig co) {
    LoadBalancer _loadBalancer = loadBalancer;
    AddressResolver<?> _addressResolver = addressResolver;
    if (_addressResolver != null) {
      if (_loadBalancer == null) {
        _loadBalancer = LoadBalancer.ROUND_ROBIN;
      }
      return new EndpointResolverImpl<>(vertx, _addressResolver.endpointResolver(vertx), _loadBalancer, resolverIdleTimeout.toMillis());

View on GitHub (pinned to fb308bd8c3)

Solutions

  1. Pass a strictly positive Duration, e.g. Duration.ofSeconds(30).
  2. Sanitize config-sourced values: if <= 0, fall back to a positive default before calling the builder.
  3. If you intend 'no timeout', omit the call rather than passing zero (check the builder's default behavior).

Example fix

// before
builder.resolverIdleTimeout(Duration.ofMillis(config.idleTimeoutMs())); // 0 from config
// after
long ms = Math.max(config.idleTimeoutMs(), 1);
builder.resolverIdleTimeout(Duration.ofMillis(ms));
Defensive patterns

Strategy: validation

Validate before calling

if (timeout == null || timeout.isZero() || timeout.isNegative()) {
  timeout = Duration.ofSeconds(30);
}
builder.resolverIdleTimeout(timeout);

Prevention

When it happens

Trigger: Calling resolverIdleTimeout(Duration.ZERO), Duration.ofSeconds(-5), or a Duration computed from config (e.g. Duration.ofMillis(cfg.getIdle())) where the configured value is 0 or negative.

Common situations: Config files where idle timeout defaults to 0 meaning 'unset'; arithmetic like (timeoutA - timeoutB) producing zero/negative values; ported code from APIs where 0 meant 'disabled'.

Understand the failure class

Background: "Invalid value" and "allowed values are" config errors: what your library rejected and how to fix it — this error's family across 41 libraries.

Related errors


AI-assisted analysis of eclipse-vertx/vert.x@fb308bd8c3 (2026-09-06). Data as JSON: /api/errors/d5a81f1b2bd48755. Report an issue: GitHub.