ZArchiveSharp 1.0.2

Requires NuGet 5.0 or higher.

dotnet add package ZArchiveSharp --version 1.0.2
                    
NuGet\Install-Package ZArchiveSharp -Version 1.0.2
                    
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="ZArchiveSharp" Version="1.0.2" />
                    
For projects that support PackageReference, copy this XML node into the project file to reference the package.
<PackageVersion Include="ZArchiveSharp" Version="1.0.2" />
                    
Directory.Packages.props
<PackageReference Include="ZArchiveSharp" />
                    
Project file
For projects that support Central Package Management (CPM), copy this XML node into the solution Directory.Packages.props file to version the package.
paket add ZArchiveSharp --version 1.0.2
                    
#r "nuget: ZArchiveSharp, 1.0.2"
                    
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
#:package ZArchiveSharp@1.0.2
                    
#:package directive can be used in C# file-based apps starting in .NET 10 preview 4. Copy this into a .cs file before any lines of code to reference the package.
#addin nuget:?package=ZArchiveSharp&version=1.0.2
                    
Install as a Cake Addin
#tool nuget:?package=ZArchiveSharp&version=1.0.2
                    
Install as a Cake Tool

ZArchiveSharp

Pure-C# port of the ZArchive 0.1.2 library: directory-tree archives with per-block zstd compression. No native dependencies, BCL only; trimmable and AOT-compatible (net8.0/net9.0/net10.0).

Layout

// Pack a directory (each 64 KiB block zstd level 6 by default).
ZArchiveTool.Pack(@"C:\game", @"C:\game.zar");

// Extract it back.
ZArchiveTool.Extract(@"C:\game.zar", @"C:\game_out");
// Low-level writer/reader with an explicit compressor choice.
using var output = File.Create("game.zar");
using var writer = new ZArchiveWriter(output); // default: ZstdCompressor level 6
writer.StartNewFile("readme.txt");
writer.AppendData("hello"u8);
writer.Finalize();

using var reader = ZArchiveReader.TryOpen("game.zar");
// Standalone zstd frames (RFC 8878), levels 1-22, byte-identical to libzstd.
var compressor = new ZstdCompressor(ZstdCompressionOptions.FromLevel(6));
byte[] frame = compressor.CompressBlock(data); // single-shot, any size
byte[] back = ZstdCompressor.DecompressFrame(frame, maxSize: data.Length);
// Batch pipeline with progress, pause, cancellation and collision policies.
var results = ZarPipeline.PackBatch(dirs, destDir, new ZarPipelineOptions
{
    MaxDegreeOfParallelism = 4,
    CollisionPolicy = ZarCollisionPolicy.AutoRename,
}, progress);

// Callable zarchive.exe contract (same defaults, messages and exit codes).
int code = ZarchiveCli.Run(["input_dir", "out.zar"], log: Console.WriteLine);
// Seekable zstd (Foot + Head), zeekstd-compatible framing.
var writer = new SeekableWriter(new SeekableOptions { FrameSize = 8192 });
writer.Write(chunk);
byte[] file = writer.Finish();
var reader = new SeekableReader(file);
byte[] slice = reader.DecompressRange(offset, length);

Blocks that do not compress smaller are stored raw (same rule as upstream StoreBlock); the raw-only ZarRawCompressor stays available for tests and benchmarks.

Byte-identity target

The encoder, the archive container and the seekable framing are byte-identical to the frozen references (libzstd 1.5.7, zeekstd): the test suite proves it against the native tools on thousands of vectors, and ZArchiveSharp.Tests/Goldens/ pins native bytes (libzstd one-shots, a zarchive.exe pack, C-library seekable files) so CI holds the line with no toolchain installed.

Two known boundaries:

  • The shipped zarchive.exe bundles libzstd 1.5.2, whose level 6 can differ from 1.5.7 on multi-transition hetero 64 KiB blocks. Our frames follow the frozen 1.5.7: packs are byte-identical to the exe wherever the two libzstd versions agree (homogeneous/single-transition blocks, verified), and extract interops both ways regardless.
  • The reference C seekable library writes plain zstd frames while zeekstd (our parity target) sets the frame content-checksum flag when checksums are on. Both flavors are valid; our reader decodes both, our writer emits the zeekstd flavor.

ZarchiveCli deliberately deviates in three places where native behavior is a bug: an unopenable extract output throws (native writes into the dead stream), a mid-file input read error fails the pack with -16 (native packs a silent truncation), and error-string paths use / on every OS.

Limits

  • No zstd dictionary training, LDM, legacy frames, or multithreading inside one frame. Dictionary use (ZstdDictionary, --dict) is supported.
  • Decoder caps (configurable via ZstdDecoderOptions): 512 MiB window, 512 MiB frame content.
  • Corrupt archives throw documented exceptions (ZarArchiveOpenException, ZarInputOpenException, ZarEntryCreateException, ZstdException, IOException); truncations always fail the open. Neither implementation verifies archive integrity (data blocks carry no checksums), so flipped bytes may decode to different content instead of throwing — same as native.

Release process

Versions derive from git tags via MinVer; tags must be v-prefixed annotated tags (v1.0.0-style — MinVerTagPrefix=v in Directory.Build.props; without it MinVer 8 silently ignores v* tags). Every push builds and tests on Ubuntu/Windows/macOS; dotnet pack runs for the library and the CLI tool (API-validated, symbols + SourceLink), and pushed v* tags publish to NuGet. See .github/workflows/ci.yml.

License

MIT — see LICENSE.

Product Compatible and additional computed target framework versions.
.NET net8.0 is compatible.  net8.0-android was computed.  net8.0-browser was computed.  net8.0-ios was computed.  net8.0-maccatalyst was computed.  net8.0-macos was computed.  net8.0-tvos was computed.  net8.0-windows was computed.  net9.0 is compatible.  net9.0-android was computed.  net9.0-browser was computed.  net9.0-ios was computed.  net9.0-maccatalyst was computed.  net9.0-macos was computed.  net9.0-tvos was computed.  net9.0-windows was computed.  net10.0 is compatible.  net10.0-android was computed.  net10.0-browser was computed.  net10.0-ios was computed.  net10.0-maccatalyst was computed.  net10.0-macos was computed.  net10.0-tvos was computed.  net10.0-windows was computed. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.
  • net10.0

    • No dependencies.
  • net8.0

    • No dependencies.
  • net9.0

    • No dependencies.

NuGet packages (1)

Showing the top 1 NuGet packages that depend on ZArchiveSharp:

Package Downloads
XISOSharp

A library for creating, extracting, listing, and rewriting Xbox ISO (XISO) disc images. C# port of extract-xiso v2.7.1, extended with XboxKit archival (Redump video/filler/seed/wipe/trim/petrify/rebuild, ZAR) and xdvdfs packing (build-image, CISO). Supports RAW, GLOBAL, XGD1, XGD2, XGD3, and Hybrid disc layouts. Provides both synchronous and asynchronous APIs with cancellation support. Strong-named and trimmable, with an AOT-compatible library surface.

GitHub repositories

This package is not used by any popular GitHub repositories.

Version Downloads Last Updated
1.0.2 29 9/11/2026
1.0.1 39 9/11/2026
1.0.0 39 9/11/2026

v1.0.2 fix: the v1.0.1 zar tool package failed at startup with FileNotFoundException (mixed build outputs packed; that version is unlisted, v1.0.0 was unaffected) — repacked from a clean Release build and install-verified (pack/extract roundtrip). No functional library changes since v1.0.1.