apache/cassandra · error · ProtocolException

CQL version is not supported by the binary protocol…

Error message

CQL version %s is not supported by the binary protocol (supported version are >= 3.0.0)

What it means

The binary protocol only speaks CQL version 3.0.0 and later; if the STARTUP message's CQL_VERSION parses to something older than 2.99.0, StartupMessage rejects it with a ProtocolException. A malformed version string also surfaces here as a ProtocolException wrapping the parse error.

Solutions

  1. Set CQL_VERSION to "3.0.0" (or a supported 3.x value) in the STARTUP options
  2. Upgrade or replace pre-CQL3 clients with a native-protocol-capable driver
  3. Validate the version string parses as a valid version before sending
  4. Audit config migration so legacy thrift settings aren't reused for the native protocol

Example fix

// before
options.put("CQL_VERSION", "2.0.0"); // thrift-era
// after
options.put("CQL_VERSION", "3.0.0");
Defensive patterns

Strategy: validation

Validate before calling

CassandraVersion v = new CassandraVersion(options.get("CQL_VERSION"));
if (v.compareTo(new CassandraVersion("2.99.0")) < 0)
    throw new IllegalArgumentException("native protocol requires CQL >= 3.0.0");

Try / catch

try {
    connection.startup(options);
} catch (ProtocolException e) {
    if (e.getMessage().contains("not supported by the binary protocol")) {
        options.put("CQL_VERSION", "3.0.0");
        connection.startup(options);
    } else throw e;
}

Prevention

When it happens

Trigger: Sending a STARTUP with CQL_VERSION values like "2.0.0", "1.2.0", or unparseable strings — typically from very old clients, or ports of legacy thrift-era configs into the native protocol.

Common situations: Migrating ancient client libraries (pre-CQL3) to the native protocol; copying thrift connection configs; typos in the version string in hand-rolled clients.

Related errors


AI-assisted analysis of apache/cassandra@88fd0f6a0e (2026-09-10). Data as JSON: /api/errors/4cd96c3174352d70. Report an issue: GitHub.

Appendix: source

Thrown at src/java/org/apache/cassandra/transport/messages/StartupMessage.java:93

    public final Map<String, String> options;

    public StartupMessage(Map<String, String> options)
    {
        super(Message.Type.STARTUP);
        this.options = options;
    }

    @Override
    protected Message.Response execute(QueryState state, Dispatcher.RequestTime requestTime, boolean traceRequest)
    {
        String cqlVersion = options.get(CQL_VERSION);
        if (cqlVersion == null)
            throw new ProtocolException("Missing value CQL_VERSION in STARTUP message");

        try
        {
            if (new CassandraVersion(cqlVersion).compareTo(new CassandraVersion("2.99.0")) < 0)
                throw new ProtocolException(String.format("CQL version %s is not supported by the binary protocol (supported version are >= 3.0.0)", cqlVersion));
        }
        catch (IllegalArgumentException e)
        {
            throw new ProtocolException(e.getMessage());
        }

        if (options.containsKey(COMPRESSION))
        {
            String compression = toLowerCaseLocalized(options.get(COMPRESSION));
            if (compression.equals("snappy"))
            {
                if (Compressor.SnappyCompressor.instance == null)
                    throw new ProtocolException("This instance does not support Snappy compression");

                if (getSource().header.version.isGreaterOrEqualTo(ProtocolVersion.V5))
                    throw new ProtocolException("Snappy compression is not supported in protocol V5");

                connection.setCompressor(Compressor.SnappyCompressor.instance);

View on GitHub (pinned to 88fd0f6a0e)