apache/druid · error · IllegalArgumentException

URI[ ] has invalid scheme[ ]

Error message

URI[%s] has invalid scheme[%s]

What it means

ServiceLocation.fromUri converts a URI into a service location, but only http and https schemes are supported. Any other scheme (e.g. ws, ftp, or a missing scheme) causes this IllegalArgumentException. It exists to fail fast on URIs that cannot map to an HTTP service endpoint.

Solutions

  1. Prefix the URI string with "http://" (or "https://") in the configuration or code that builds it.
  2. Check the scheme before calling fromUri and normalize known aliases to http/https.
  3. Verify the config property feeding the URI (e.g. druid.discovery URLs) is a full absolute URL.

Example fix

// before
ServiceLocation loc = ServiceLocation.fromUri(new URI("mybroker:8082"), basePath);
// after
ServiceLocation loc = ServiceLocation.fromUri(new URI("http://mybroker:8082"), basePath);
Defensive patterns

Strategy: validation

Validate before calling

String s = uri.toString();
if (!s.startsWith("http://") && !s.startsWith("https://")) {
  throw new IllegalArgumentException("Service URI must use http/https: " + s);
}

Prevention

When it happens

Trigger: Calling ServiceLocation.fromUri with a URI whose scheme is not exactly "http" or "https" — e.g. fromUri(new URI("ftp://host:8020")) or a URI built from a config string lacking a scheme.

Common situations: Misconfigured service URLs in Druid properties (forgot http:// prefix), copy-pasted internal scheme names (https vs websockets), or programmatically constructed URIs with relative paths that resolve to a null scheme.

Understand the failure class

Background: "Invalid URL" errors: why new URL(), URI.parse, and reqwest::Url reject your string — missing scheme, whitespace, and bad path format — this error's family across 39 libraries.

Related errors


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

Appendix: source

Thrown at server/src/main/java/org/apache/druid/rpc/ServiceLocation.java:119

      }
    }

    if (uri.getRawQuery() != null) {
      basePath.append('?').append(uri.getRawQuery());
    }

    if (uri.getRawFragment() != null) {
      basePath.append('#').append(uri.getRawFragment());
    }

    if (HTTP_SCHEME.equals(scheme)) {
      final int port = uri.getPort() < 0 ? HTTP_DEFAULT_PORT : uri.getPort();
      return new ServiceLocation(host, port, -1, basePath.toString());
    } else if (HTTPS_SCHEME.equals(scheme)) {
      final int port = uri.getPort() < 0 ? HTTPS_DEFAULT_PORT : uri.getPort();
      return new ServiceLocation(host, -1, port, basePath.toString());
    } else {
      throw new IAE("URI[%s] has invalid scheme[%s]", uri, scheme);
    }
  }

  /**
   * Create a service location based on a {@link DruidServerMetadata}.
   *
   * @throws IllegalArgumentException if the server metadata cannot be mapped to a service location.
   */
  public static ServiceLocation fromDruidServerMetadata(final DruidServerMetadata druidServerMetadata)
  {
    final String host = getHostFromString(
        Preconditions.checkNotNull(
            druidServerMetadata.getHost(),
            "Host was null for druid server metadata[%s]",
            druidServerMetadata
        )
    );
    int plaintextPort = getPortFromString(druidServerMetadata.getHostAndPort());

View on GitHub (pinned to 9b90983fd2)