apache/cassandra · error · InvalidRequestException

Keyspace name '%s' doesn't match index name '%s'

Error message

Keyspace name '%s' doesn't match index name '%s'

What it means

Same keyspace-consistency check as for the table, but applied to the index name: when CREATE INDEX gives the index a keyspace qualifier, it must equal the resolved keyspace of the table, otherwise the statement is rejected.

Source

Thrown at src/java/org/apache/cassandra/cql3/statements/schema/CreateIndexStatement.java:386

        {
            this.tableName = tableName;
            this.indexName = indexName;
            this.rawIndexTargets = rawIndexTargets;
            this.attrs = attrs;
            this.ifNotExists = ifNotExists;
        }

        public CreateIndexStatement prepare(ClientState state)
        {
            String keyspaceName = tableName.hasKeyspace()
                                ? tableName.getKeyspace()
                                : indexName.hasKeyspace() ? indexName.getKeyspace() : state.getKeyspace();

            if (tableName.hasKeyspace() && !keyspaceName.equals(tableName.getKeyspace()))
                throw ire(KEYSPACE_DOES_NOT_MATCH_TABLE, keyspaceName, tableName);

            if (indexName.hasKeyspace() && !keyspaceName.equals(indexName.getKeyspace()))
                throw ire(KEYSPACE_DOES_NOT_MATCH_INDEX, keyspaceName, tableName);
            
            // Set the configured default 2i implementation if one isn't specified with USING:
            if (attrs.customClass == null)
            {
                if (DatabaseDescriptor.getDefaultSecondaryIndexEnabled())
                    attrs.customClass = DatabaseDescriptor.getDefaultSecondaryIndex();
                else
                    // However, operators may require an implementation be specified
                    throw ire(MUST_SPECIFY_INDEX_IMPLEMENTATION);
            }
            
            // If we explicitly specify the index type "legacy_local_table", we can just clear the custom class, and the
            // non-custom 2i creation process will begin. Otherwise, if an index type has been specified with 
            // USING, make sure the appropriate custom index is created.
            if (attrs.customClass != null)
            {
                if (!attrs.isCustom && attrs.customClass.equalsIgnoreCase(CassandraIndex.NAME))
                    attrs.customClass = null;

View on GitHub (pinned to 88fd0f6a0e)

Solutions

  1. Qualify index and table with the same keyspace: CREATE INDEX ks.idx ON ks.t (col).
  2. Drop the keyspace qualifier from the index name and rely on the session keyspace.
  3. Regenerate the DDL script with consistent keyspace substitution for both identifiers.

Example fix

// before
CREATE INDEX wrongks.idx ON ks.t (col);

// after
CREATE INDEX ks.idx ON ks.t (col);
Defensive patterns

Strategy: validation

Validate before calling

if (indexName.includesKeyspace() && !indexName.getKeyspace().equals(resolveTableKeyspace(tableName))) throw new IllegalArgumentException("Index keyspace must match table keyspace");

Try / catch

try { session.execute(ddl); } catch (InvalidQueryException e) { if (e.getMessage().startsWith("Keyspace name")) { /* align index-name qualifier with table keyspace */ } else throw e; }

Prevention

When it happens

Trigger: CREATE INDEX otherks.idx ON ks.t (col) — indexName.hasKeyspace() is true but its keyspace differs from the resolved keyspaceName of the table.

Common situations: Typos in the keyspace prefix on the index name; template-generated DDL where table and index keyspaces are substituted from different variables; multi-tenant scripts reusing one statement across keyspaces.

Understand the failure class

Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.

Related errors


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