influxdata/influxdb · critical

existing database should be updated

Error message

existing database should be updated

What it means

A panic from `.expect()` when applying a database batch. `DatabaseSchema::new_if_updated_from_batch` returned Some(new_db), meaning an update was detected, but `self.databases.update()` failed to find the existing database by id — the repository lost the entry the branch logic assumed. Its sibling insert path panics with "new database should be inserted" for the analogous insert failure.

Solutions

  1. Ensure single-writer semantics for catalog batches; concurrent mutation breaks get-then-update assumptions.
  2. Check snapshot/WAL replay boundaries for double application of the same batch.
  3. Restore catalog from a consistent backup if database entries are missing.
  4. Replace expects with explicit error mapping so a corrupt replay surfaces as a recoverable catalog error.

Example fix

// before
self.databases
    .update(db.id, new_db)
    .expect("existing database should be updated");
// after
self.databases
    .update(db.id, new_db)
    .unwrap_or_else(|| panic!(
        "database {} detected as update but missing from repository",
        db.id
    ));
Defensive patterns

Strategy: validation

Validate before calling

// verify the database still exists before update
if databases.get_by_id(db.id).is_none() { /* treat as insert or surface a catalog error */ }

Type guard

fn db_exists(dbs: &Databases, id: DbId) -> bool { dbs.get_by_id(id).is_some() }

Prevention

When it happens

Trigger: Replaying a database batch whose db.id exists per the new_if_updated_from_batch check but is missing from the databases repository at update time; concurrent database deletion during replay; for the insert variant, a database with the same id already present.

Common situations: Overlapping WAL/snapshot replay applying a batch twice, concurrent DROP DATABASE racing with writes to the same database, or corruption of the in-memory catalog.

Understand the failure class

Background: "This is a bug, please report it": internal invariant violations, unreachable panics, and SNH errors explained — this error's family across 47 libraries.

Related errors


AI-assisted analysis of influxdata/influxdb@06200ef96b (2026-09-19). Data as JSON: /api/errors/62df01137a17c652. Report an issue: GitHub.

Appendix: source

Thrown at influxdb3_catalog/src/catalog/versions/v2.rs:1904

                    if needs_update {
                        // Update the token in the repository
                        self.tokens
                            .update_token(token_id, (*updated_token).clone())
                            .expect("token to be updated");
                    }
                }
            }
        }

        // Now proceed with the normal database batch processing
        if let Some(db) = self.databases.get_by_id(&database_batch.database_id) {
            let Some(new_db) = DatabaseSchema::new_if_updated_from_batch(&db, database_batch)?
            else {
                return Ok(false);
            };
            self.databases
                .update(db.id, new_db)
                .expect("existing database should be updated");
        } else {
            let new_db = DatabaseSchema::new_from_batch(database_batch)?;
            self.databases
                .insert(new_db.id, new_db)
                .expect("new database should be inserted");
        };
        Ok(true)
    }

    fn apply_delete_batch(&mut self, delete_batch: &DeleteBatch) -> Result<bool> {
        let mut updated = false;
        for op in &delete_batch.ops {
            match op {
                DeleteOp::DeleteDatabase(db_id) => {
                    let Some(mut db_schema) = self.databases.get_by_id(db_id) else {
                        continue;
                    };

View on GitHub (pinned to 06200ef96b)