apache/shardingsphere · error · PostgreSQLProtocolException

Can not find `%s` in PostgreSQL command packet type.

Error message

Can not find `%s` in PostgreSQL command packet type.

What it means

Thrown by PostgreSQLCommandPacketType.valueOf(int) when the leading byte of a command message does not match any known PostgreSQL command tag (Q, P, B, D, E, S, etc.). The value is matched against registered enum codes; failure means the byte stream does not start with a valid command tag — usually a desynchronized, TLS-garbled, or non-PostgreSQL connection.

Source

Thrown at database/protocol/dialect/postgresql/src/main/java/org/apache/shardingsphere/database/protocol/postgresql/packet/command/PostgreSQLCommandPacketType.java:76

    private static final Set<PostgreSQLCommandPacketType> EXTENDED_PROTOCOL_PACKET_TYPES = EnumSet.of(
            PARSE_COMMAND, BIND_COMMAND, DESCRIBE_COMMAND, EXECUTE_COMMAND, SYNC_COMMAND, CLOSE_COMMAND, FLUSH_COMMAND);
    
    private final char value;
    
    /**
     * Value of integer.
     *
     * @param value integer value
     * @return command packet type enum
     * @throws PostgreSQLProtocolException PostgreSQL protocol exception
     */
    public static PostgreSQLCommandPacketType valueOf(final int value) {
        for (PostgreSQLCommandPacketType each : values()) {
            if (value == each.value) {
                return each;
            }
        }
        throw new PostgreSQLProtocolException("Can not find `%s` in PostgreSQL command packet type.", value);
    }
    
    /**
     * Check if the packet type is extended protocol packet type.
     *
     * @param commandPacketType command packet type
     * @return is extended protocol packet type
     */
    public static boolean isExtendedProtocolPacketType(final CommandPacketType commandPacketType) {
        return EXTENDED_PROTOCOL_PACKET_TYPES.contains(commandPacketType);
    }
}

View on GitHub (pinned to e952770a21)

Solutions

  1. Log the offending byte as a char/code — 'HTTP GET' bytes (0x47/0x50) or 0x16 (TLS handshake) immediately reveal wrong-protocol traffic
  2. Align sslmode between client and proxy listener (both TLS or both plaintext)
  3. Point health checks at a proper TCP check instead of sending HTTP to the PG port
  4. If a legitimate new command tag from a newer PostgreSQL version, add it to the enum and report upstream
Defensive patterns

Strategy: validation

Validate before calling

// before dispatch, check the tag byte corresponds to a registered command type
int tag = buffer.readUnsignedByte();
boolean known = Arrays.stream(PostgreSQLCommandPacketType.values())
        .anyMatch(t -> t.getValue() == tag);
if (!known) {
    // wrong protocol or TLS mismatch (0x16 = TLS handshake); reject the connection with a clear error
    rejectConnection("unknown command tag byte: " + tag);
}

Try / catch

try {
    PostgreSQLCommandPacketType.valueOf(value);
} catch (PostgreSQLProtocolException ex) {
    // non-PostgreSQL/TLS/garbled input: log the byte value and close the socket; do not retry
    connection.close();
    log.info("rejected non-protocol connection: {}", ex.getMessage());
}

Prevention

When it happens

Trigger: valueOf() receives a byte that is not a registered command tag — e.g. an SSLRequest/GSSENCRequest negotiation byte interpreted as a command, a TLS handshake read as plaintext, or HTTP traffic hitting the PostgreSQL port.

Common situations: sslmode misconfiguration (client expects TLS, proxy reads handshake as commands); health-check probes (HTTP/TCP) hitting the port; clients speaking a protocol version with new tags the enum lacks.

Related errors


AI-assisted analysis of apache/shardingsphere@e952770a21 (2026-08-14). Data as JSON: /api/errors/0a6610d8f222f409. Report an issue: GitHub.