jely2002/youtube-dl-gui · error · io::Error

selected entry vanished during extraction

Error message

selected entry vanished during extraction

What it means

extract_tar_bz2 unpacks an archive looking for a selected entry; if iteration finishes without ever matching/producing that entry, it returns an io::Error with ErrorKind::NotFound and the message 'selected entry vanished during extraction'. It is a NotFound guard ensuring the expected artifact actually existed in the archive.

Solutions

  1. Log the archive's actual entry names during extraction and compare with the expected path to find the rename.
  2. Update the expected entry path/pattern to match the upstream archive layout for the new version.
  3. Re-download the archive and re-verify its checksum to rule out truncation/corruption.
  4. Pin the artifact version whose archive layout matches the extractor, or make matching tolerant (match by basename).

Example fix

// before
if entry_path == expected_path { extract(entry)?; }
// after
if entry_path == expected_path
  || entry_path.ends_with(expected_path.rsplit('/').next().unwrap()) {
  extract(entry)?;
}
Defensive patterns

Strategy: validation

Validate before calling

let found = false;
for entry in archive.entries()? {
  let path = entry?.path()?.to_string_lossy().to_string();
  if path == expected_path { found = true; break; }
}
if (!found) { return Err(/* expected entry not present; inspect archive layout */); }

Type guard

fn contains_entry<R: Read + Seek>(ar: &mut tar::Archive<R>, want: &str) -> bool {
  ar.entries().map(|e| e.unwrap().path().unwrap() == Path::new(want)).any(|ok| ok)
}

Try / catch

match extract_tar_bz2(...).await {
  Ok(path) => path,
  Err(e) if e.to_string().contains("selected entry vanished") => {
    eprintln!("expected entry missing; dumping archive layout");
    // re-download or update expected path
    Err(e)
  }
  Err(e) => Err(e),
}

Prevention

When it happens

Trigger: The expected binary entry is absent from the downloaded .tar.bz2 — checksum verified but the archive layout changed upstream, the target path filter never matches (renamed entry/path prefix change), or the archive is truncated after the entry stream was skipped.

Common situations: Upstream release renamed the binary or reorganized archive directories; a partially downloaded/interrupted archive; extracting with a hardcoded path that no longer exists in the new version of the artifact.

Understand the failure class

Background: "File not found" and ENOENT errors: why libraries can't find a file that should exist — this error's family across 50 libraries.


AI-assisted analysis of jely2002/youtube-dl-gui@c402ee39c0 (2026-09-12). Data as JSON: /api/errors/ee468c98be321853. Report an issue: GitHub.

Appendix: source

Thrown at src-tauri/src/binaries/binaries_extractor.rs:265

      .and_then(|n| n.to_str())
      .unwrap_or(tool_name.as_str());
    let tmp_out = out_dir.join(format!("{base}.tmp"));
    ensure_parent(&tmp_out)?;

    for e in tar.entries()? {
      let mut e = e?;
      if !e.header().entry_type().is_file() {
        continue;
      }
      if e.path()?.as_ref() == chosen_path {
        e.unpack(&tmp_out)?;
        atomic_file_replace(&tmp_out, &canonical)?;
        return Ok(canonical);
      }
    }

    Err(
      io::Error::new(
        io::ErrorKind::NotFound,
        "selected entry vanished during extraction",
      )
      .into(),
    )
  })
  .await?
}

pub async fn extract_zip_bundle(
  archive: &Path,
  out_parent: &Path,
  final_folder_name: Option<&str>,
  entry_relative: &Path,
  rename_entry_to: Option<&str>,
) -> Result<(PathBuf, PathBuf), ExtractError> {
  let archive = archive.to_owned();
  let out_parent = out_parent.to_owned();

View on GitHub (pinned to c402ee39c0)