influxdata/influxdb · info · CatalogError
no catalog changes to apply
Error message
no catalog changes to apply: {details} What it means
CatalogError::NoCatalogChange { details } is returned when a requested mutation is idempotent: applying it would not change any catalog state. It is informational in nature — the current state already matches the requested state. details explains what was already in place.
Solutions
- Treat this variant as success in idempotent apply flows
- Skip the operation if the resource already matches the desired definition
- Compare requested vs existing schema/config before calling the API
- Match on CatalogError::NoCatalogChange and log at info level
Example fix
// before
let t = db.create_table(schema).await?;
// after
let t = match db.create_table(schema).await {
Ok(t) => t,
Err(CatalogError::NoCatalogChange { .. }) => db.table(schema.name()).unwrap(),
Err(e) => return Err(e.into()),
}; Defensive patterns
Strategy: try-catch
Validate before calling
// Rust: diff desired vs current before applying
if db.table_schema(name)? == desired_schema {
eprintln!("schema already matches; skipping create");
} Type guard
fn is_no_change(err: &CatalogError) -> bool {
matches!(err, CatalogError::NoCatalogChange { .. })
} Try / catch
match db.create_table(schema).await {
Ok(t) => t,
Err(CatalogError::NoCatalogChange { details }) => {
tracing::info!("idempotent apply: {details}");
db.table(schema.name()).unwrap()
}
Err(e) => return Err(e.into()),
} Prevention
- Write DDL migrations as idempotent desired-state applies
- Log this variant at info, not error
- Compare definitions before issuing create calls
- Deduplicate migration runs with a marker table
When it happens
Trigger: Creating a table with a schema identical to the existing one; re-adding a column that already exists with the same type; re-running an idempotent DDL migration; setting a cache/trigger configuration identical to the current one.
Common situations: Deployment scripts or IaC re-applying desired-state DDL on every deploy; retry of a create that actually succeeded earlier; running migrations multiple times.
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
- {0}
- Adding a new database would exceed limit of
- attempted to create a resource that already exists
- attempted to modify resource that was already deleted
- auto field family exists
AI-assisted analysis of influxdata/influxdb@06200ef96b (2026-09-19).
Data as JSON: /api/errors/87fa872797ae2cc9.
Report an issue: GitHub.
Appendix: source
Thrown at influxdb3_catalog/src/error.rs:60
Enterprise(#[from] EnterpriseCatalogError),
#[error("object store error: {0:?}")]
ObjectStore(#[from] ObjectStoreCatalogError),
#[error("catalog format error: {0}")]
Format(#[from] FormatError),
#[error("attempted to create a resource that already exists")]
AlreadyExists,
#[error("the requested resource was not found: {0}")]
NotFound(String),
#[error("attempted to modify resource that was already deleted: {0}")]
AlreadyDeleted(String),
/// Request is idempotent: no catalog state would change.
#[error("no catalog changes to apply: {details}")]
NoCatalogChange { details: String },
/// Request is invalid.
#[error("catalog internal error: {details}")]
Internal { details: String },
#[error(
"persisted catalog checkpoint sequence {checkpoint_sequence} is ahead of live catalog sequence {live_sequence}"
)]
BackupCheckpointAhead {
checkpoint_sequence: u64,
live_sequence: u64,
},
#[error("invalid configuration provided: {message}")]
InvalidConfiguration { message: Box<str> },
#[error("only tag and string columns are supported in the distinct cache")]View on GitHub (pinned to 06200ef96b)