Skip to content

boramuyar/zip

Repository files navigation

@boramuyar/zip

Compact, dependency-free ZIP reading and writing for TypeScript.

  • Keeps existing entries compressed in memory.
  • Inflates only the entry you read.
  • Reuses unchanged compressed bytes when writing.
  • Uses native deflate through small Node and browser adapters.
  • Supports custom ZIP compression methods through an explicit registry.
  • Supports ZIP64, UTF-8, CP437, comments, directories, and extra-field preservation.

Install

pnpm add @boramuyar/zip

Read a ZIP

import { ZIP_DEFLATE_METHOD, Zip } from "@boramuyar/zip";
import { nodeDeflateMethod } from "@boramuyar/zip/node";

const zip = new Zip(arrayBuffer, {
  compressionMethods: { [ZIP_DEFLATE_METHOD]: nodeDeflateMethod },
});

const text = await zip.readText("hello.txt");
const data = await zip.read("image.png");

Create a ZIP

import { ZIP_DEFLATE_METHOD, Zip } from "@boramuyar/zip";
import { nodeDeflateMethod } from "@boramuyar/zip/node";

const zip = new Zip(undefined, {
  compressionMethods: { [ZIP_DEFLATE_METHOD]: nodeDeflateMethod },
});

await zip.write("hello.txt", "hello world\n");
await zip.write("data.bin", new Uint8Array([1, 2, 3]));

const output = await zip.toArrayBuffer();

Custom compression methods

Register heavier algorithms, such as Zstandard or BZip2, in your application. The package does not bundle them.

import { ZIP_DEFLATE_METHOD, Zip, type ZipCompressionMethod } from "@boramuyar/zip";
import { nodeDeflateMethod } from "@boramuyar/zip/node";

const zstdMethod: ZipCompressionMethod = {
  name: "zstd",
  compress: (input, context) => zstdCompress(input, context),
  decompress: (input, context) => zstdDecompress(input, context),
};

const zip = new Zip(input, {
  compressionMethods: {
    [ZIP_DEFLATE_METHOD]: nodeDeflateMethod,
    93: zstdMethod,
  },
});

await zip.write("data/table.bin", data, { compressionMethod: 93 });

Each entry has one compression method. One archive can mix stored, deflated, and custom-compressed entries. Unchanged custom entries are preserved even when no handler is registered.

Browser use

import { ZIP_DEFLATE_METHOD, Zip } from "@boramuyar/zip";
import { browserDeflateMethod } from "@boramuyar/zip/browser";

const zip = new Zip(arrayBuffer, {
  compressionMethods: { [ZIP_DEFLATE_METHOD]: browserDeflateMethod },
});

The browser adapter uses CompressionStream("deflate-raw") and DecompressionStream("deflate-raw").

Node use

import { ZIP_DEFLATE_METHOD, Zip } from "@boramuyar/zip";
import { nodeDeflateMethod } from "@boramuyar/zip/node";

const zip = new Zip(arrayBuffer, {
  compressionMethods: { [ZIP_DEFLATE_METHOD]: nodeDeflateMethod },
});

The Node adapter uses node:zlib raw deflate and inflate.

The older compression: nodeCompression and compression: browserCompression options still work for method 8 deflate.

Documentation

Memory model

The constructor parses ZIP metadata but does not expand every file. read() and readText() return whole decompressed entries. toArrayBuffer() returns the whole output archive.

Unsupported features

The library rejects encrypted entries, central-directory encryption, split archives, and digital signatures. Methods other than store and deflate require user-provided registry handlers for reading or writing.

Microsoft Office password-protected .xlsx files use OOXML/OLE encryption, not ZIP encryption. Handle them in a separate package.

Development

pnpm install
pnpm test
pnpm typecheck
pnpm build

About

Compact dependency-free ZIP reading and writing for TypeScript.

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors