GitoxideLabs/gitoxide · error · anyhow::Error

an undo reference state has an unknown encoding

Error message

an undo reference state has an unknown encoding

What it means

Decoder guard in `edit::undo::parse_state`, called from `parse_config` when reading persisted undo-queue state strings. Recognized encodings are `missing`, `object:<hex>` (with a hash-kind check), and `symbolic:<name>`; any other string stored in the undo configuration has an unknown encoding and bails. This fires on corrupted or hand-edited undo queue config data, or state written by a newer/different tool version. Fix by correcting or resetting the undo queue configuration (removing the malformed entries) rather than editing it by hand.

Solutions

  1. Inspect the raw undo-queue config value and correct it to one of the supported encodings: "missing", "object:<hex-id>", or "symbolic:<full-name>"
  2. Drop the corrupt undo queue reference and let tix rebuild it from fresh edits
  3. Upgrade/downgrade tix consistently so queue entries are written and read by the same encoding version
Defensive patterns

Strategy: validation

When it happens

Trigger: Thrown at gix-tix/src/edit/undo.rs:666 when the library encounters an invalid state.

Common situations: See trigger scenarios.


AI-assisted analysis of GitoxideLabs/gitoxide@e73179060b (2026-09-08). Data as JSON: /api/errors/88282401223b9243. Report an issue: GitHub.

Appendix: source

Thrown at gix-tix/src/edit/undo.rs:666

fn parse_state(repo: &gix::Repository, value: &BStr) -> Result<State> {
    if value == b"missing" {
        return Ok(State::Missing);
    }
    if let Some(hex) = value.strip_prefix(b"object:") {
        let id = ObjectId::from_hex(hex).context("an undo object ID is invalid")?;
        ensure!(
            id.kind() == repo.object_hash(),
            "an undo object ID uses the wrong hash kind"
        );
        return Ok(State::Object(id));
    }
    if let Some(name) = value.strip_prefix(b"symbolic:") {
        return FullName::try_from(name.as_bstr())
            .map(State::Symbolic)
            .context("an undo symbolic target is invalid");
    }
    bail!("an undo reference state has an unknown encoding")
}

fn validate_title(title: &str) -> Result<()> {
    ensure!(!title.is_empty(), "an undo operation title cannot be empty");
    ensure!(
        !title.as_bytes().iter().any(|byte| matches!(byte, b'\n' | b'\r')),
        "an undo operation title must be one line"
    );
    Ok(())
}

fn retention_parents(repo: &gix::Repository, predecessor: ObjectId, changes: &[RefChange]) -> Result<Vec<ObjectId>> {
    let mut parents = vec![predecessor];
    let mut seen = HashSet::from([predecessor]);
    for id in changes
        .iter()
        .flat_map(|change| [&change.before, &change.after])
        .filter_map(|state| match state {

View on GitHub (pinned to e73179060b)