apache/cassandra · error · ConfigurationException
Can only safely increase number of transients one at a time
Error message
Can only safely increase number of transients one at a time with incremental repair run in between each time
What it means
When the total replica count changes and transient replicas are being increased, Cassandra only allows increasing transients by exactly one at a time, requiring an incremental repair between increases, because un-repaired ranges on new transient replicas could be read unsafely.
Source
Thrown at src/java/org/apache/cassandra/cql3/statements/schema/AlterKeyspaceStatement.java:226
for (TableMetadata table : current.tables)
if (!table.indexes.isEmpty())
throw new ConfigurationException("Cannot use transient replication on keyspaces using secondary indexes");
}
//This is true right now because the transition from transient -> full lacks the pending state
//necessary for correctness. What would happen if we allowed this is that we would attempt
//to read from a transient replica as if it were a full replica.
if (oldFull > newFull && oldTrans > 0)
throw new ConfigurationException("Can't add full replicas if there are any transient replicas. You must first remove all transient replicas, then change the # of full replicas, then add back the transient replicas");
//Don't increase transient replication factor by more than one at a time if changing number of replicas
//Just like with changing full replicas it's not safe to do this as you could read from too many replicas
//that don't have the necessary data. W/O transient replication this alteration was allowed and it's not clear
//if it should be.
//This is structured so you can convert as many full replicas to transient replicas as you want.
boolean numReplicasChanged = oldTrans + oldFull != newTrans + newFull;
if (numReplicasChanged && (newTrans > oldTrans && newTrans != oldTrans + 1))
throw new ConfigurationException("Can only safely increase number of transients one at a time with incremental repair run in between each time");
}
@Override
public AuditLogContext getAuditLogContext()
{
return new AuditLogContext(AuditLogEntryType.ALTER_KEYSPACE, keyspaceName);
}
public String toString()
{
return String.format("%s (%s)", getClass().getSimpleName(), keyspaceName);
}
public static final class Raw extends CQLStatement.Raw
{
private final String keyspaceName;
private final KeyspaceAttributes attrs;
private final boolean ifExists;View on GitHub (pinned to 88fd0f6a0e)
Solutions
- Increase transient replicas one at a time: '3/0' -> '3/1', run incremental repair, then '3/1' -> '3/2'.
- Run `nodetool repair -inc` on the keyspace after each single increment.
- If total replica count is unchanged, convert full->transient freely; otherwise follow the one-at-a-time rule.
Example fix
// before
"ALTER KEYSPACE ks WITH replication = {'dc1':'3/2'}"; // from '3/0'
// after
"ALTER KEYSPACE ks WITH replication = {'dc1':'3/1'}"; runIncrementalRepair();
"ALTER KEYSPACE ks WITH replication = {'dc1':'3/2'}"; Defensive patterns
Strategy: validation
Validate before calling
boolean numReplicasChanged = oldTrans + oldFull != newTrans + newFull; if (numReplicasChanged && newTrans > oldTrans && newTrans != oldTrans + 1) throw new IllegalArgumentException("increase transients by exactly 1 per step with repair between"); Try / catch
try { session.execute(alterKeyspace); } catch (ConfigurationException e) { if (e.getMessage().contains("increase number of transients one at a time")) applyOneTransientAtATime(target); else throw e; } Prevention
- Cap transient-RF increases to +1 per ALTER KEYSPACE
- Always run `nodetool repair -inc` between increments
- Encode the stepwise policy in cluster-management automation
When it happens
Trigger: `ALTER KEYSPACE ks WITH replication = {'dc1':'3/0' -> '3/2'}` (transients increased by 2 in one step) while the total replica count also changed.
Common situations: Operators jumping transient RF from 0 to 2 (or similar multi-step jump) to save capacity quickly, without running incremental repair between each increment.
Understand the failure class
Background: "Invalid state transition" errors: "status must be X, actually Y", "already rejected/charging/uninstalled", "cannot ... while running" — what they mean when a library rejects your call — this error's family across 31 libraries.
Related errors
- Transient replication is not supported with vnodes yet
- Cannot use transient replication on keyspaces using material
- Cannot use transient replication on keyspaces using secondar
- Can't add full replicas if there are any transient replicas.
- repair_session_max_tree_depth should not be < 10, but was ${
AI-assisted analysis of apache/cassandra@88fd0f6a0e (2026-09-10).
Data as JSON: /api/errors/d19d231bbab23b2d.
Report an issue: GitHub.