elastic/elasticsearch · error · IllegalArgumentException

Exactly one provider object must be specified, but [{}] were

Error message

Exactly one provider object must be specified, but [{}] were found

What it means

Thrown by the DatabaseConfiguration ConstructingObjectParser when the number of non-null provider objects in a database configuration is not exactly one. The parser reserves slots for Maxmind, Ipinfo, Web, and Local providers and requires exactly one to be supplied; zero (missing provider) or more than one (ambiguous) both fail. IllegalArgumentException surfaces during API request parsing.

Source

Thrown at modules/ip-location/src/main/java/org/elasticsearch/ingest/geoip/direct/DatabaseConfiguration.java:107

    );

    private static final ParseField NAME = new ParseField("name");
    private static final ParseField MAXMIND = new ParseField(Maxmind.NAME);
    private static final ParseField IPINFO = new ParseField(Ipinfo.NAME);
    private static final ParseField WEB = new ParseField(Web.NAME);
    private static final ParseField LOCAL = new ParseField(Local.NAME);

    private static final ConstructingObjectParser<DatabaseConfiguration, String> PARSER = new ConstructingObjectParser<>(
        "database",
        false,
        (a, id) -> {
            String name = (String) a[0];
            Provider provider;

            // one and only one provider object must be present
            final long numNonNulls = Arrays.stream(a, 1, a.length).filter(Objects::nonNull).count();
            if (numNonNulls != 1) {
                throw new IllegalArgumentException("Exactly one provider object must be specified, but [" + numNonNulls + "] were found");
            }

            if (a[1] != null) {
                provider = (Maxmind) a[1];
            } else if (a[2] != null) {
                provider = (Ipinfo) a[2];
            } else if (a[3] != null) {
                provider = (Web) a[3];
            } else {
                provider = (Local) a[4];
            }
            return new DatabaseConfiguration(id, name, provider);
        }
    );

    static {
        PARSER.declareString(ConstructingObjectParser.constructorArg(), NAME);
        PARSER.declareObject(

View on GitHub (pinned to db6a809a66)

Solutions

  1. Include exactly one provider object (maxmind, ipinfo, web, or local) in the database configuration body.
  2. Remove any duplicate or conflicting provider block before submitting.
  3. Validate the request body shape against the rest-api-spec example for the endpoint.
  4. If writing automation, assert the provider count in a preflight check.

Example fix

// before
{"name":"city","maxmind":{"account_id":"x","license_key":"y"},"ipinfo":{"token":"z"}}
// after
{"name":"city","maxmind":{"account_id":"x","license_key":"y"}}
Defensive patterns

Strategy: validation

Validate before calling

long countProviders(Object... a) {
    return Arrays.stream(a, 1, a.length).filter(Objects::nonNull).count();
}
// call before submit: assert countProviders(...) == 1

Prevention

When it happens

Trigger: Creating/updating a database configuration via the API where the request body includes zero provider objects or two-or-more provider objects simultaneously. Arrays.stream(a, 1, a.length).filter(nonNull).count() != 1 -> throw.

Common situations: User omits the provider block entirely; user supplies both maxmind and ipinfo in one config; copy-paste error merging two example configs; client library sending null vs empty object confusion leading to multiple non-nulls.

Related errors


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