# AGENTS.md — ZDDC ## Commands ```bash # ── Lockstep release driver: every invocation is a publish action. ──────── # Alpha is the default since "alpha = active dev iteration" and that's # what running the build IS. Coordinated version (for release): max # across all six tools' latest tags + 1. Workflow: # alpha = active dev → beta = ready for general testing → stable = ship ./build # cut alpha (default) — cascades nothing ./build beta # cut beta — cascades alpha → beta ./build release # cut stable — coordinated next version, # cascades all to the new version ./build release 1.2.0 # cut stable at explicit version ./build help # usage # Build a single HTML tool's dist/ for testing (does NOT touch the # website worktree's release artifacts): sh tool/build.sh # archive|transmittal|classifier|mdedit|landing # Single-tool release (rare; prefer the lockstep ./build above so # versions don't drift between tools). Same flag form as before. sh tool/build.sh --release [|alpha|beta] ./freshen-channel # rebuild one tool's alpha/beta from its current stable tag # Test all tools npm test # Test single tool npx playwright test tool # archive | transmittal | classifier | mdedit # Dev server (cache-busting HTTP, on port 8000) ./dev-server start ./dev-server stop ``` No lint, typecheck, or format commands exist — the project is plain sh + vanilla JS. The build ends with a **channel-link verifier** that asserts every `_{stable,beta,alpha}.html` (and zddc-server's per-platform binary mirrors + stub pages) resolves. Build fails if any link is dangling. Output goes to `${ZDDC_DEPLOY_RELEASES_DIR:-$HOME/src/zddc-website/releases}` — the website branch's worktree, what Caddy serves. **Nothing is pushed automatically;** review with `git -C ~/src/zddc-website status`, commit + push the website branch yourself when ready. ## Architecture Five independent single-file HTML tools (`archive`, `transmittal`, `classifier`, `mdedit`, `landing`). Each compiles to one self-contained `.html` in `dist/` with all CSS and JS inlined — the first four name their output `dist/tool.html`; `landing` writes `dist/index.html` (it's served at `/` by `zddc-server`). Tools share a small set of canonical helpers in `shared/` (filename parsing, ZDDC filter UI, theme, help) — see "Shared modules" below. ``` tool/ css/ source stylesheets (concatenated in order) js/ vanilla JS IIFEs (concatenated in order) template.html placeholder markers: {{CSS_PLACEHOLDER}}, {{JS_PLACEHOLDER}}, {{BUILD_LABEL}} build.sh assembles dist/tool.html dist/tool.html generated output — committed with `git add -f` shared/ base.css CSS tokens and primitives included first by every tool's CSS build zddc.js canonical filename/folder/revision parsers, formatters, status validation zddc-filter.js shared ZDDC project/status filter UI module theme.js light/dark theme switcher help.js shared help dialog module build-lib.sh POSIX sh helpers (ensure_exists, concat_files, build_timestamp) sourced by every tool's build.sh via: . "$root_dir/../shared/build-lib.sh" # Website lives on the `website` orphan branch of this same repo # (NOT in main's tree). Worktree typically at ~/src/zddc-website/: # index.html, reference.html, css/, js/, img/ hand-edited content # releases/ # index.html regenerated by `./build` # _v.html per-version (committed, immutable) # _v.html -> ... symlink chain (regular git symlinks) # _stable.html -> ... channel mirror, follows latest stable # _{beta,alpha}.html -> ... channels (cascade to stable when idle) # zddc-server_v_ per-platform binary (LFS-tracked) # zddc-server__ channel binary mirror (symlink) # zddc-server_.html stub page surfacing 4 platform DLs # .gitattributes LFS rules for binaries helm/ zddc-server-prod/ production-shaped Helm chart (compiles from source via init container) zddc-server-dev/ dev-shaped variant (tracks main HEAD; debug-level logging; faster probes) README.md chart design rationale + quick-start ``` **Critical:** `dist/` files are gitignored. They're the canonical built artifact for testing and the source for `--release` writes into `~/src/zddc-website/releases/`, but they aren't checked in. Never edit them directly. **Release artifacts live on the `website` orphan branch** of this same Codeberg repo, not on `main`. A `git worktree` of that branch — typically at `~/src/zddc-website/` — is what the system Caddy bind-mounts and serves at `zddc.varasys.io/`. The build pipeline writes its release outputs to `${ZDDC_DEPLOY_RELEASES_DIR:-$HOME/src/zddc-website/releases}` directly, then the operator commits + pushes that worktree separately from `main`. Per-version HTML and per-version zddc-server binaries are real bytes (binaries are LFS-tracked; HTML stays regular git); partial-version pins (`_v`, `_v`) and channel mirrors (`_stable`, `_beta`, `_alpha`) are symlinks. `shared/build-lib.sh` provides `promote_release` (HTML tools) and `promote_zddc_server` (binaries + matching stub pages); the top-level `./build` calls them in lockstep. No Codeberg release-asset publication anymore; everything serves from `zddc.varasys.io/releases/`. ## Shared CSS (`shared/base.css`) Included as the **first** positional arg to every tool's `concat_files` CSS call. Provides: - `:root` CSS custom properties — `--primary`, `--bg`, `--text`, `--border`, `--font`, etc. - Brand color: `--primary: #2a5a8a` (matches zddc.varasys.io) - Button primitive: `.btn`, `.btn-primary`, `.btn-secondary`, `.btn-sm`, `.btn-lg`, `.btn-link` - `.app-header` + `.app-header__title` chrome rules - `.build-timestamp`, `.hidden`, `.truncate`, webkit scrollbars **Do not** define these in any tool's own CSS — they come from shared. **Toast CSS** lives in `classifier/css/base.css` only (classifier is the only tool that uses toasts). ## Transmittal CSS quirks - `transmittal/css/base.css` overrides `html { font-size: 16px }` inside `@media screen` — this must stay. `shared/base.css` sets `14px`; transmittal's floating labels are rem-based and were designed for 16px. - The floating label position is defined in `transmittal/css/forms.css`, not Tailwind classes. If adding new Tailwind classes to `template.html`, add them to `transmittal/css/utilities.css` too — there is no Tailwind build step. ## Build system rules - Every `build.sh` sources `shared/build-lib.sh` first (provides `ensure_exists`, `concat_files`, `build_timestamp`). Set `root_dir` before sourcing. - Build scripts use **POSIX sh** (`#!/bin/sh` with `set -eu`), not bash. - `concat_files` accepts **positional args only** (not array names). - `awk` processes `template.html`, replacing `{{PLACEHOLDER}}` markers and stripping CDN `