BigPizzaV3/CodexPlusPlus · error

sidebar restore requires a Codex home

Error message

sidebar restore requires a Codex home

What it means

restore_backups can restore the special `__sidebar` table only if the caller supplies the Codex home directory, because validating the sidebar snapshot requires reading the live catalog under that home. When a backup contains a `__sidebar` table but `codex_home` is None, this error is raised before any backup is written.

Solutions

  1. Pass the Codex home directory (e.g. ~/.codex) to restore_backups so the sidebar snapshot can be validated
  2. Strip the `__sidebar` table from the backup if you intentionally want to restore without sidebar validation
  3. Use the standard undo entry point which resolves the default Codex home automatically
  4. Re-create the backup without sidebar snapshot if the target environment has no Codex home

Example fix

// before
restore_backups(db, &backups, None)?;
// after
restore_backups(db, &backups, Some(&codex_home))?;
Defensive patterns

Strategy: validation

Validate before calling

let needs_home = backup["tables"].as_object().map_or(false, |t| t.contains_key("__sidebar"));
if needs_home && codex_home.is_none() {
    return Err("__sidebar backup requires codex_home".into());
}

Try / catch

match restore_backups(db, &backups, codex_home) {
    Err(e) if e.to_string().contains("sidebar restore requires a Codex home") => {
        // retry with Some(default_codex_home()) or strip __sidebar
    }
    other => other?,
}

Prevention

When it happens

Trigger: Calling restore_backups (e.g. from `undo`) with a backup whose tables include `__sidebar` while passing codex_home: None — typically via an API path or command that omits the home argument.

Common situations: Scripted or programmatic undo calls that don't pass the Codex home; restoring a backup taken with sidebar snapshotting into an environment where home detection was skipped; CLI flags omitting the home override.

Understand the failure class

Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.

Related errors


AI-assisted analysis of BigPizzaV3/CodexPlusPlus@b1ed92e5e4 (2026-09-19). Data as JSON: /api/errors/65212586e642a7a7. Report an issue: GitHub.

Appendix: source

Thrown at crates/codex-plus-data/src/storage.rs:908

fn restore_backups(
    backups: &[Value],
    fallback_db_path: &Path,
    allowed_db_paths: &[PathBuf],
    codex_home: Option<&Path>,
) -> anyhow::Result<()> {
    for backup in backups {
        let Some(tables) = backup["tables"].as_object() else {
            continue;
        };
        let source_db = backup_source_db(backup, fallback_db_path, allowed_db_paths)?;
        let db = Connection::open_with_flags(&source_db, OpenFlags::SQLITE_OPEN_READ_WRITE)?;
        validate_restore_tables(tables)?;
        detect_restore_conflicts(&db, tables)?;
        detect_file_restore_conflicts(tables)?;
        preflight_restore_rows(&db, tables)?;
        if let Some(sidebar) = tables.get("__sidebar") {
            let home = codex_home
                .ok_or_else(|| anyhow::anyhow!("sidebar restore requires a Codex home"))?;
            crate::provider_sync::validate_thread_sidebar_snapshot(home, sidebar)?;
        }
    }

    for backup in backups {
        let Some(tables) = backup["tables"].as_object() else {
            continue;
        };
        let source_db = backup_source_db(backup, fallback_db_path, allowed_db_paths)?;
        let mut db = Connection::open_with_flags(&source_db, OpenFlags::SQLITE_OPEN_READ_WRITE)?;
        let tx = db.transaction()?;
        restore_rows(&tx, tables)?;
        tx.commit()?;
        if let Some(files) = tables.get("__files").and_then(Value::as_array) {
            for file in files {
                let Some(path) = file.get("path").and_then(Value::as_str) else {
                    continue;
                };

View on GitHub (pinned to b1ed92e5e4)