pinpoint-apm/pinpoint · error · OracleConnectionStringException

parse error. token is null

Error message

parse error. token is null

What it means

checkStartToken() consumes the first token of the descriptor and requires it to be the '(' key-start token; if nextToken() returns null (empty or exhausted input) it throws 'parse error. token is null'. The parser was handed nothing to parse after the URL prefix.

Solutions

  1. Provide the full descriptor after the '@', e.g. jdbc:oracle:thin:@(DESCRIPTION=...)
  2. Check that the config/env variable holding the descriptor is non-empty and correctly wired
  3. Fall back to the simple URL format jdbc:oracle:thin:@host:port:SID if a descriptor isn't required
  4. Add a null/empty check on the JDBC URL in configuration loading and fail with a clear message

Example fix

// before
String url = "jdbc:oracle:thin:@" + desc; // desc == ""
// after
String url = "jdbc:oracle:thin:@(DESCRIPTION=(ADDRESS=(PROTOCOL=TCP)(HOST=db)(PORT=1521))(CONNECT_DATA=(SERVICE_NAME=svc)))";
Defensive patterns

Strategy: validation

Validate before calling

boolean hasDescriptorBody(String url) {
    if (url == null) return false;
    int at = url.indexOf('@');
    return at != -1 && url.substring(at + 1).trim().startsWith("(");
}

Try / catch

try {
    parser.parse(url);
} catch (OracleConnectionStringException e) {
    log.error("Oracle JDBC URL empty after '@': {}", url, e);
    throw new ConfigurationException("Missing descriptor after '@'", e);
}

Prevention

When it happens

Trigger: Parsing a URL like 'jdbc:oracle:thin:@' with nothing after the '@' — the tokenizer produces no tokens and checkStartToken()'s nextToken() returns null. Also reached via parser flows that call checkStartToken on an empty remainder.

Common situations: Config key containing only the prefix with the descriptor in a separate/missing variable; empty environment variable substituted for the host section; trimmed URL where the descriptor got stripped.

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 pinpoint-apm/pinpoint@744c3d3075 (2026-09-07). Data as JSON: /api/errors/3f63939b7ee222e4. Report an issue: GitHub.

Appendix: source

Thrown at agent-module/plugins/oracle-jdbc/src/main/java/com/navercorp/pinpoint/plugin/jdbc/oracle/parser/OracleNetConnectionDescriptorTokenizer.java:183

        }
        tokenPosition++;
    }

    public Token lookAheadToken() {
        if (tokenList.size() <= tokenPosition) {
            return null;
        }
        return tokenList.get(tokenPosition);
    }

    public void setPosition(int position) {
        this.position = position;
    }

    public void checkStartToken() {
        Token token = this.nextToken();
        if (token == null) {
            throw new OracleConnectionStringException("parse error. token is null");
        }
        // We can check by == because the token object is singleton.
        if (!(token == TOKEN_KEY_START_OBJECT)) {
            throw new OracleConnectionStringException("syntax error. Expected token='(' :" + token.getToken());
        }
    }

    public void checkEqualToken() {
        Token token = this.nextToken();
        if (token == null) {
            throw new OracleConnectionStringException("parse error. token is null. Expected token='='");
        }
        // We can check by == because the token object is singleton.
        if (!(token == TOKEN_EQUAL_OBJECT)) {
            throw new OracleConnectionStringException("Syntax error. Expected token='=' :" + token.getToken());
        }
    }

View on GitHub (pinned to 744c3d3075)