elastic/elasticsearch · error · IllegalArgumentException

node cannot be null

Error message

node cannot be null

What it means

Constructor guard on RestClientBuilder: each entry in the nodes list must be non-null. A null slot is rejected because the client would dereference it on every request.

Source

Thrown at client/rest/src/main/java/org/elasticsearch/client/RestClientBuilder.java:140

            + ",t="
            + metaVersion
            + ",hc="
            + (httpClientVersion == null ? "" : httpClientVersion.getRelease())
            + LanguageRuntimeVersions.getRuntimeMetadata();
    }

    /**
     * Creates a new builder instance and sets the hosts that the client will send requests to.
     *
     * @throws IllegalArgumentException if {@code nodes} is {@code null} or empty.
     */
    RestClientBuilder(List<Node> nodes) {
        if (nodes == null || nodes.isEmpty()) {
            throw new IllegalArgumentException("nodes must not be null or empty");
        }
        for (Node node : nodes) {
            if (node == null) {
                throw new IllegalArgumentException("node cannot be null");
            }
        }
        this.nodes = nodes;
    }

    /**
     * Sets the default request headers, which will be sent along with each request.
     * <p>
     * Request-time headers will always overwrite any default headers.
     *
     * @throws NullPointerException if {@code defaultHeaders} or any header is {@code null}.
     */
    public RestClientBuilder setDefaultHeaders(Header[] defaultHeaders) {
        Objects.requireNonNull(defaultHeaders, "defaultHeaders must not be null");
        for (Header defaultHeader : defaultHeaders) {
            Objects.requireNonNull(defaultHeader, "default header must not be null");
        }
        this.defaultHeaders = defaultHeaders;

View on GitHub (pinned to db6a809a66)

Solutions

  1. Filter nulls out of the host list before constructing the builder.
  2. Fix the producer that yielded null (e.g. skip blank lines when parsing hosts file/env).
  3. Add a unit test asserting the parsed list has no nulls.

Example fix

// before
List<Node> nodes = lines.stream().map(l -> l.isBlank() ? null : parse(l)).toList();
new RestClientBuilder(nodes);
// after
List<Node> nodes = lines.stream().filter(l -> !l.isBlank()).map(l -> parse(l)).toList();
new RestClientBuilder(nodes);
Defensive patterns

Strategy: validation

Validate before calling

nodes.removeIf(Objects::isNull);
if (nodes.isEmpty()) throw new IllegalArgumentException("no non-null nodes");

Type guard

nodes.stream().allMatch(Objects::nonNull)

Prevention

When it happens

Trigger: Passing a List<Node> containing a null element, e.g. from a stream/map that produced null for a malformed entry.

Common situations: Parsing hosts where a blank line produced null; Collections.nCopies or array conversion slipping in a null; builder used with varargs where one arg was null.

Related errors


AI-assisted analysis of elastic/elasticsearch@db6a809a66 (2026-08-12). Data as JSON: /api/errors/f85863233093e5a0. Report an issue: GitHub.