Documentation · v0.6.0 · schema_version "2"

The CLI reference, as implemented.

This page covers 0.6.0 (schema 2); 0.5.1 used schema 1. Check the interface migration before upgrading. Features that are still planned are marked planned. The full long-form guide is START.md in the repository.

Command syntax

One format-independent syntax. There are no ZIP-specific or TAR-specific top-level commands.

grammar
arcthis <command> <archive> [entry] [options]

The default workflow is access before extraction: inspect → tree/list → stat/read → extract only what you actually need. Full extraction is always an explicit operation.

Output rules

Strict output separation makes Arcthis safe to drive from scripts and agents.

  • stdout carries result data only. stderr carries diagnostics, warnings and progress.
  • --json makes supported commands emit machine-readable JSON; read always prints raw file contents and rejects --json.
  • JSON output and output not attached to a terminal contain no color or styling. --no-color and NO_COLOR disable color in a terminal.
  • If the program on the other end of a pipe quits early (like | head), that counts as success — arcthis read a.zip big.bin | head exits 0.
  • Non-UTF-8 filenames are flagged explicitly through path_encoding; extraction refuses unresolved names by default; explicit --encoding strictly decodes names before safety checks.

Global options

Accepted before the subcommand, from arcthis --help.

OptionDefaultMeaning
--jsonoffEmit stable machine-readable JSON where supported
--no-syncon: per-file fsyncSkip per-file fsync for extract/extract-all/convert; retains staging and rollback, reduces power-loss durability
--entry-index <N>—Exact stat/read/hash/extract instance; only final within archive
--encoding <name>—Strict utf8/cp437/gbk/shift-jis decoding; safety/collision checks still apply
--stdin-name <name>stdinVirtual name for read-only stdin source -
--max-stdin-bytes <bytes>64 MiBBound actual compressed stdin buffering
--no-coloroffDisable terminal color decoration
--within <entry>—Step into an archive inside the archive; repeat to go deeper (up to 8 levels)
--max-nested-entry-size <bytes>268435456Maximum memory (bytes) a single file inside a nested archive may use
--password-file <path>—Read the archive password from this file (trailing newlines are removed). Passwords are never passed on the command line
--volume <path>—Add one part of a multi-volume archive; repeat in exact volume order
--index-directory <path>platform cacheChange where index files are stored (defaults to the system cache directory)

Commands

Signatures match the real CLI; descriptions come from arcthis --help.

inspectarcthis inspect <archive> [--json]

Show an archive's basic info, capabilities and risk warnings: file counts, sizes, compression ratio, and capability flags such as random_access (can jump to any file), solid (compressed as one block) and encrypted — enough for an agent to estimate what an operation will cost before running it.

listarcthis list <archive> [--json]

Preserve archive order and all duplicate instances, including ZIP. Ambiguous name selection returns collision; --entry-index selects by archive_index.

treearcthis tree <archive> [--json]

Display archive contents as a file tree. JSON output is a nested tree array. Paths are limited to 4096 bytes and 256 components; larger paths return resource_limit.

statarcthis stat <archive> [entry] [--verbose] [--json]

Show entry metadata; --verbose includes original names, CRC, timestamps and encoding. Select by --entry-index; omit entry when there is only one regular file. Unavailable metadata is null.

readarcthis read <archive> [entry] [--verify-first]

Stream raw bytes by default; CRC failure can follow partial output, so check the exit code. --verify-first validates in anonymous temporary storage before stdout, with a default actual-byte limit of 4 GiB. read --json returns invalid_argument/2 before source/password I/O.

findarcthis find <archive> --glob <pattern> [--json]

Find files whose paths match a wildcard pattern. Only full paths are matched; file contents are never read.

greparcthis grep <archive> <literal> [--glob <pattern>] [--json]

Search literal text directly. Defaults: 16 MiB per file, 10,000 matches and 1 MiB per retained line. --max-result-bytes limits total match output across files to 16 MiB; omitted matches set matches_truncated. Binary files are skipped unless you pass --binary. ZIP/TAR/7z/RAR reuse content traversal and bounded result budgets.

hasharcthis hash <archive> [entry] [--algorithm sha256|sha512]

Compute a file's checksum. SHA-256 is the default; SHA-512 is also supported. The result is lowercase hexadecimal.

indexarcthis index [archive] [--refresh|--delete|--list|--prune] [--dry-run]

Queries consume valid caches; archive.index_used reports hits. --list inventories caches; --prune removes stale/expired indexes with --dry-run and --max-age-seconds (30 days by default). Only hash-named index JSON is managed; Unix also checks ctime/dev/inode.

extractarcthis extract <archive> [entry] [--output <path>] [--dry-run]

Safely extract everything or one selected file. The full file list is checked first; output is written to a temporary location next to the destination and saved only after every file succeeds. Related flags: --dry-run, --delete-source, and exactly one of --overwrite / --skip-existing / --rename. Safe ./ normalization is supported; duplicate and normalized collisions remain refused. --no-sync explicitly reduces fsync overhead; successful source deletion gets a receipt.

extract-allarcthis extract-all <directory> [--recursive] [--workers <n>]

Use bounded workers and deterministic results. --continue-on-error isolates corrupt archives, planning errors and path conflicts while independent archives proceed. Partial failure exits 12 with per-archive JSON; dry-run also reports errors.

packarcthis pack <source> --output <archive> [--dry-run]

Pack files or a directory into an archive, then verify it. A temporary archive is built next to the destination, reopened and checked file by file, and only then saved as the final result. An output path inside the source directory, or one that points at the same file as the source, is rejected. --strip-root packs directory contents; output follows umask, and Gzip writes FNAME/mtime.

verifyarcthis verify <archive> [--json]

Read the archive start to finish once, verifying its structure and every readable file's data. JSON output adds a verification object with verified, entries_checked and bytes_checked.

convertarcthis convert <archive> --output <archive> [--dry-run]

Convert an archive to another format: extract safely to a temporary location, then pack and verify. File paths are preserved, resource and path safety checks run before anything is written to disk, and the new archive is verified and saved before --delete-source can remove the original.

mcparcthis mcp --allow-root <path> [--allow-output-root <path>]

Serve local MCP clients using protocol revision 2025-06-18. Input roots enable nine read-only tools. Output roots enable six plan-and-execute tools for extract, pack and convert. Source deletion requires both server and request permission. Schema 2 shares read-only structures and typed error envelopes with CLI. Read-only requests accept root-authorized password_file references (at most 4096 bytes), never inline password values; entry_index is supported. Clean EOF exits 0; mcp --json is invalid.

--max-concurrent-requests defaults to 4 (range 1–64) and --max-response-bytes to 16 MiB, counting the tool result's JSON and text copies. Per-request ceilings are --max-entries 100,000, --max-decoded-bytes 1 GiB, --max-results 10,000 find/grep results, and --max-read-window 1 MiB per archive_read window. Excess calls or oversized results return resource_limit. Clients cannot raise server limits; MCP grep also fits within the response limit.

JSON & errors

Every successful structured response is one JSON document followed by a newline. Command-specific fields extend a shared base structure.

base structure + entry object
{
  "schema_version": "2",
  "archive": {
    "path": "/data/dataset.zip",
    "path_lossy": false,
    "index_used": false,
    "format": "zip"
  },
  "entry": {
    "archive_index": 42,
    "path": "train/data.csv",
    "path_encoding": "utf8",
    "path_raw_hex": "747261696e2f646174612e637376",
    "kind": "file",
    "size": 1048576,
    "compressed_size": 182341,
    "modified_time": null,
    "modified_time_local": "2026-08-27T12:00:00",
    "encrypted": false,
    "executable": false,
    "symlink_target": null,
    "crc32": "c0ffee00",
    "mime_guess": "text/csv"
  }
}

With --json, command errors are JSON on stderr and stdout stays empty:

machine error — stderr
{
  "schema_version": "2",
  "error": {
    "code": "entry_not_found",
    "message": "archive entry was not found",
    "details": { "entry": "README.md" }
  }
}

Stable error categories:

invalid_argument not_an_archive unsupported_format invalid_archive corrupted_archive entry_not_found permission_denied unsafe_path resource_limit password_required wrong_password collision unsupported_operation verification_failed partial_failure io_error

Schema 2 changes executable to nullable, separates modified_time_local from absolute RFC3339 time, and preserves adapter-exposed name bytes in path_raw_hex. Shared solid-7z compressed sizes are null; ratio limits apply to blocks. CLI/MCP read-only results share a shape. Source references are absolute; stdin/nested references stay virtual. ADR 0002

Exit codes

Each error category maps to a fixed exit code.

ExitCategory
0Success, including BrokenPipe consumer stop
1General I/O error
2Command-line syntax or usage error
3unsupported_format / not_an_archive
4invalid_archive or corrupted_archive
5entry_not_found
6permission_denied
7unsafe_path
8resource_limit
9collision
10unsupported_operation, password categories
11verification_failed
12partial_failure

Resource limits

Limits are enforced while actually writing and decompressing — not just as warnings when you look inside.

OptionDefault
--max-entries100,000
--max-total-size16 GiB
--max-entry-size4 GiB
--max-compression-ratioDisabled unless specified
--max-entry-duration-secondsDisabled unless specified
grep --max-result-bytes16 MiB
mcp --max-entries100,000
mcp --max-decoded-bytes1 GiB
mcp --max-results10,000
mcp --max-read-window1 MiB
mcp --max-concurrent-requests4
mcp --max-response-bytes16 MiB

Safety defaults

The short version; exact guarantees and known limits live in docs/SECURITY.md.

  • Path checks. One unified check rejects .., absolute paths, Windows drive/UNC prefixes, NUL bytes, and links that could escape the destination.
  • No automatic links or special files. Symlinks, hardlinks and special files are not restored by default.
  • All-or-nothing writes. Output is staged in a temporary location and saved only when complete; pack reopens and verifies the new archive before it appears where you asked.
  • Overlap checks. All writes reject equal or nested source and destination paths. Batches also check path conflicts between archives.
  • Delete-source last. --delete-source runs only after the new files are written, verified and saved; errors, interruptions and failed checks keep the source. Dry-runs never write or delete.
  • No passwords on the command line. Passwords come from --password-file only and are hidden from debug output.

Planned

These features remain planned. See ROADMAP.md.

preview · planned recursive cross-archive search · planned native RAR multi-volume archives · planned password input / providers · planned remote archives · planned