slpc
The library half of the Rust implementation of slipcase, a container format that attaches metadata to a file.
A .slpc file is a ZIP archive holding a payload file of any type together with a TOML metadata document describing it. The two become one file, so copying, moving, or sending the payload carries its metadata along.
Reading
fn main() -> Result<(), slpc::Error> {
let mut c = slpc::Container::open("report.pdf.slpc")?;
println!("{} holds {}", c.version(), c.payload_name());
std::io::copy(&mut c.payload()?, &mut std::io::stdout())?;
Ok(())
}
The payload is a stream and is never read into memory. Metadata is exposed as a document that keeps comments, key order, and whitespace across a rewrite, and as the member's bytes for a caller who wants a different parser or a hash.
Writing
Four free functions, because none of them takes or returns a container: each reads a stream and writes a stream.
use slpc::toml_edit::DocumentMut;
fn main() -> Result<(), slpc::Error> {
let out = std::fs::File::create("report.pdf.slpc")?;
slpc::pack_file("report.pdf", DocumentMut::new(), out)?;
Ok(())
}
The metadata argument is anything convertible into a DocumentMut, which is a
document, a table, or, with toml_edit's serde feature turned on by the
caller, whatever toml_edit::ser::to_document makes of a struct or a map.
Building metadata from nothing has no formatting to preserve, so there is
nothing for that conversion to lose.
pack_reader takes a payload from any Read and needs no Seek at either end,
so a container can be packed from a pipe into a socket. rewrite_metadata
replaces a container's metadata and copies every other member through
untouched, compressed members included.
Validating
fn main() -> Result<(), slpc::Error> {
match slpc::validate(std::fs::File::open("report.pdf.slpc")?)? {
slpc::Verdict::Conformant => println!("conformant"),
other => println!("{other}"),
}
Ok(())
}
Four verdicts rather than two. A container whose metadata member cannot be read is neither conformant nor non-conformant, and one declaring a version this build does not implement is outside the question rather than failing it.
No vocabulary
The two structural keys have typed accessors. Every other key is passed through unexamined, because there is nothing to examine it against.
The specification lives in excelano/slipcase and is the authority on the format.
This crate implements it and has no standing to change it. The command-line tool
built on it is slipcase, in the same repository.
License
MIT. See LICENSE.