apache/cassandra · error · InvalidRequestException

Column with name ' ' already exists

Error message

Column with name '%s' already exists

What it means

Thrown by ALTER TABLE ... ADD when a column with the given name already exists on the table and IF NOT EXISTS was not specified. The builder detects the collision via tableBuilder.getColumn(name) and rejects the statement instead of silently overwriting.

Solutions

  1. Use IF NOT EXISTS: ALTER TABLE ks.tbl ADD IF NOT EXISTS col type
  2. Verify existing column types match your intent: SELECT * FROM system_schema.columns WHERE keyspace_name=? AND table_name=?
  3. Make migrations idempotent or track applied migrations in a schema-version table

Example fix

// before
session.execute("ALTER TABLE my_app.events ADD description text");
// after
session.execute("ALTER TABLE my_app.events ADD IF NOT EXISTS description text");
Defensive patterns

Strategy: validation

Validate before calling

boolean exists = session.execute("SELECT column_name FROM system_schema.columns WHERE keyspace_name=? AND table_name=? AND column_name=?", ks, table, col).one() != null;
if (exists) log.info("Column already present; skipping ADD");

Try / catch

try {
    session.execute(alter);
} catch (InvalidRequestException e) {
    if (e.getMessage().contains("already exists"))
        log.info("Column exists, continuing: {}", alter);
    else throw e;
}

Prevention

When it happens

Trigger: 'ALTER TABLE ks.tbl ADD col type' where a column of that name already exists and ifColumnNotExists is false; re-running migration scripts that add columns; adding a column that differs only by case in an unquoted statement

Common situations: Non-idempotent schema migration executed twice; drift between environments where the column already exists in one; ORMs/tools that re-emit ADD COLUMN on startup.

Understand the failure class

Background: "already exists" / EEXIST / FileAlreadyExistsException: what the 'file already exists' error means and how to fix it — this error's family across 37 libraries.

Related errors


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

Appendix: source

Thrown at src/java/org/apache/cassandra/cql3/statements/schema/AlterTableStatement.java:356

                           .withSwapped(viewsBuilder.build());
        }

        private void addColumn(KeyspaceMetadata keyspace,
                               TableMetadata table,
                               Column column,
                               boolean ifColumnNotExists,
                               TableMetadata.Builder tableBuilder,
                               Views.Builder viewsBuilder)
        {
            ColumnIdentifier name = column.name;
            AbstractType<?> type = column.type.prepare(keyspaceName, keyspace.types).getType();
            boolean isStatic = column.isStatic;
            ColumnMask mask = column.mask == null ? null : column.mask.prepare(keyspaceName, tableName, name, type, keyspace.userFunctions);
            ColumnConstraints columnConstraints = column.constraints == null ? ColumnConstraints.NO_OP : column.constraints.prepare(name);

            if (null != tableBuilder.getColumn(name)) {
                if (!ifColumnNotExists)
                    throw ire("Column with name '%s' already exists", name);
                return;
            }

            if (type.isCounter() && (table.params.transactionalMode.accordIsEnabled || table.params.transactionalMigrationFrom.migratingFromAccord()))
                throw ire(format(ACCORD_COUNTER_COLUMN_UNSUPPORTED, keyspaceName, tableName, table.params.transactionalMode, table.params.transactionalMigrationFrom));

            if (table.isCompactTable())
                throw ire("Cannot add new column to a COMPACT STORAGE table");

            if (isStatic && table.clusteringColumns().isEmpty())
                throw ire("Static columns are only useful (and thus allowed) if the table has at least one clustering column");

            // check for nested non-frozen UDTs or collections in a non-frozen UDT
            if (type.isUDT() && type.isMultiCell())
            {
                for (AbstractType<?> fieldType : ((UserType) type).fieldTypes())
                {
                    if (fieldType.isMultiCell())

View on GitHub (pinned to 88fd0f6a0e)