rescriptum · an answer written for this machine
EN
On this page

Working on rescriptum

rescriptum is a small, focused thing: it works out which install config each machine should get, composes it from layers, and serves it. Around 4,000 lines of Rust, 308 tests, and a short list of constraints that are not up for casual revision.

This space is the why. The Guide is the what.

Get it running

git clone https://github.com/z29k/rescriptum && cd rescriptum
cargo test                      # 308 tests
cargo run -- --help

Try a change against the worked examples rather than only against tests — they are the only place all the formats are shown composing together:

RESCRIPTUM_ANSWERS_DIR=examples cargo run -- check
RESCRIPTUM_ANSWERS_DIR=examples cargo run -- render --query "path=/rhel/ks&serial=7ABC123"

Before opening a PR:

cargo fmt --all
cargo clippy --all-targets --all-features -- -D warnings
cargo test --all-features
cargo build --release --no-default-features   # the smallest build must keep working

Those four are exactly what CI runs.

The repository

PathHolds
src/main.rsruntime setup, accept loop, connection serving, routing, and the blocking half of a request
src/lib.rsthe crate. main.rs is a thin binary over it, so behaviour is testable directly
src/select.rsnormalization, matching, layering — the behaviour that matters
src/facts.rswhat a request says about the machine
src/format/one interface per document format; xml.rs holds the XML tree
src/merge.rsthe TOML merge, used by format
src/store/where documents come from: file.rs, sqlite.rs, behind a thin trait
src/admin.rsthe write API, and the guarantee that a write cannot break the fleet
src/config.rsenvironment configuration
src/envfile.rsthe optional file of defaults RESCRIPTUM_ENV_FILE names — never discovered, only named
src/capture.rsrecording what machines actually send
src/cli.rsthe render, check, import and export subcommands
src/log.rsone line per event, UTC timestamps without a date crate, and the two knobs over both
tests/the real binary over a socket (integration, admin, guards), its command line (cli), and the two-store conformance suite (stores)
examples/a worked example of every supported format
docs/this site

Never re-declare a module in main.rs. It compiles a second copy, runs every unit test twice, and lets the two copies drift.

Where to start reading

  • The constraints — first. They explain most of the code’s shape, and several of them look like things worth “improving” until you know why they are there.
  • Architecture — the module map and what flows between them.
  • The request lifecycle — a request from accept to response.
  • Selection — the part with the most behaviour per line.
  • Traps already hit — a list of things that cost time once. Reading it is cheaper than rediscovering them.

Conventions

  • English for code, comments, commit messages, and the source of the documentation. The docs are additionally published in French (*.fr.md siblings) — see the documentation site.
  • Behaviour belongs in tests/stores.rs, which runs every case against both stores and requires the identical outcome. A test covering one store proves half of what it claims. See testing.
  • Arrays replace, they do not append, in every format.
  • Fail loudly. A missing group, an unfillable template, a document that will not parse — all are errors with a reason. Serving a half-built answer installs a machine wrongly, and nobody finds out until it is running.
  • Adding a dependency needs a reason in the commit message. This binary runs as root on other people’s hardware, and CI’s audit job is the other half of that rule: a reason to add one is not a reason to keep it.
  • Conventional commits with a scopefeat(http): …, fix(select): ….

Also worth reading

CLAUDE.md at the repository root is the architecture document written for coding agents. It overlaps this space heavily and is the file to update when a constraint changes.

Updated Edit this page