aeron-io/aeron · error · IllegalStateException

invalid end of key at index

Error message

invalid end of key at index <i> in <uri>

What it means

During ChannelUri.parse(), while accumulating a parameter key (PARAMS_KEY state), encountering '|' means the key section ended without '='; a key must be followed by '=' before the next param separator, so parse throws this IllegalStateException for the malformed URI.

Solutions

  1. Fix the URI at the reported index so each key is followed by '=' and a value before the next '|'
  2. Use ChannelUriStringBuilder instead of manual strings to guarantee well-formed key=value pairs
  3. Validate/normalize externally supplied URIs before parsing and catch IllegalStateException

Example fix

// before
ChannelUri uri = ChannelUri.parse("aeron:udp?endpoint|host:1234");
// after
ChannelUri uri = ChannelUri.parse("aeron:udp?endpoint=host:1234");
Defensive patterns

Strategy: validation

Validate before calling

static void validateParamSyntax(String uri) {
    int q = uri.indexOf('?');
    if (q < 0) return;
    for (String p : uri.substring(q + 1).split("\\|")) {
        if (!p.isEmpty() && !p.contains("=")) {
            throw new IllegalArgumentException("param without '=': " + p);
        }
    }
}

Type guard

static boolean allParamsHaveValues(String uri) {
    int q = uri.indexOf('?');
    if (q < 0) return true;
    for (String p : uri.substring(q + 1).split("\\|")) {
        if (!p.isEmpty() && p.indexOf('=') < 0) return false;
    }
    return true;
}

Try / catch

try {
    ChannelUri.parse(uri);
} catch (IllegalStateException e) {
    log.error("Bad channel URI '{}': {}", uri, e.getMessage());
    throw new IllegalArgumentException("Invalid channel URI", e);
}

Prevention

When it happens

Trigger: Calling ChannelUri.parse() on a URI where a param key is terminated by '|' instead of '=', e.g. "aeron:udp?endpoint|localhost:40456" or a trailing "|key" at the end of the params.

Common situations: Typos in hand-written channel URIs (missing '=' after a key); string-building code that forgets the '=' between name and value; copy/paste errors in configuration files.

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 aeron-io/aeron@6d60124e15 (2026-09-12). Data as JSON: /api/errors/c62f6c8af188b2bf. Report an issue: GitHub.

Appendix: source

Thrown at aeron-client/src/main/java/io/aeron/ChannelUri.java:449

                    }
                    break;

                case PARAMS_KEY:
                    if (c == '=')
                    {
                        if (builder.isEmpty())
                        {
                            throw new IllegalStateException("empty key not allowed at index " + i + " in " + uri);
                        }
                        key = builder.toString();
                        builder.setLength(0);
                        state = State.PARAMS_VALUE;
                    }
                    else
                    {
                        if (c == '|')
                        {
                            throw new IllegalStateException("invalid end of key at index " + i + " in " + uri);
                        }
                        builder.append(c);
                    }
                    break;

                case PARAMS_VALUE:
                    if (c == '|')
                    {
                        params.put(key, builder.toString());
                        builder.setLength(0);
                        state = State.PARAMS_KEY;
                    }
                    else
                    {
                        builder.append(c);
                    }
                    break;

View on GitHub (pinned to 6d60124e15)