GitoxideLabs/gitoxide · error
Cannot derive archive format from a file without extension
Error message
Cannot derive archive format from a file without extension
What it means
`format_from_ext` derives the archive format from the output filename's extension. If the path has no extension at all, no format can be inferred and the function bails. gitoxide does not guess archive formats from content.
Solutions
- Rename the output file to include a supported extension (.tar, .gz, .zip, .stream)
- Use `.tar` explicitly when a plain uncompressed archive is wanted
- Generate the filename programmatically to always append a valid extension
Example fix
// before
let out = Path::new("archive-2024");
// after
let out = Path::new("archive-2024.tar"); Defensive patterns
Strategy: validation
Validate before calling
fn ensure_supported_name(path: &Path) -> anyhow::Result<()> {
let ext = path.extension().and_then(|e| e.to_str()).unwrap_or("");
anyhow::ensure!(matches!(ext, "tar" | "gz" | "zip" | "stream"), "output path needs a supported archive extension");
Ok(())
} Try / catch
match archive::stream(repo, rev, out, path_without_ext) {
Err(e) if e.to_string().contains("without extension") => {
// append ".tar" and retry
}
other => other?,
} Prevention
- Always generate archive output names with an explicit extension
- Whitelist tar/gz/zip/stream in filename builders
- Never derive output filenames from commit ids without appending an extension
When it happens
Trigger: Calling `archive::stream` with an output path lacking a `.tar`/`.gz`/`.zip`/`.stream` extension - e.g. `out`, `archive.v1`, or a path whose final component has no dot.
Common situations: Writing to a named pipe or versioned filename without extension; deriving output names in scripts from commit ids; users expecting a default tar format.
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
- Format for extension
- lines in ' ' could not be parsed
- Invalid pathspec - path must not be empty, not be excluded…
- : Validation failed with mismatches out of
- path does not name a file
AI-assisted analysis of GitoxideLabs/gitoxide@e73179060b (2026-09-08).
Data as JSON: /api/errors/68e80fe7f505c799.
Report an issue: GitHub.
Appendix: source
Thrown at gitoxide-core/src/repository/archive.rs:97
}
fn fetch_rev_info(
object: gix::Object<'_>,
) -> anyhow::Result<(Option<gix::date::SecondsSinceUnixEpoch>, gix::ObjectId)> {
Ok(match object.kind {
gix::object::Kind::Commit => {
let commit = object.into_commit();
(Some(commit.committer()?.seconds()), commit.tree_id()?.detach())
}
gix::object::Kind::Tree => (None, object.id),
gix::object::Kind::Tag => fetch_rev_info(object.peel_to_kind(gix::object::Kind::Commit)?)?,
gix::object::Kind::Blob => bail!("Cannot derive commit or tree from blob at {}", object.id),
})
}
fn format_from_ext(path: &Path) -> anyhow::Result<archive::Format> {
Ok(match path.extension().and_then(std::ffi::OsStr::to_str) {
None => bail!("Cannot derive archive format from a file without extension"),
Some("tar") => archive::Format::Tar,
Some("gz") => archive::Format::TarGz {
compression_level: None,
},
Some("zip") => archive::Format::Zip {
compression_level: None,
},
Some("stream") => archive::Format::InternalTransientNonPersistable,
Some(ext) => bail!("Format for extension '{ext}' is unsupported"),
})
}
View on GitHub (pinned to e73179060b)