The documentation half of the same work: `DOCS-AUDIT.md` marks §1.3, §1.5, §2.3, §4.2 (all three points), §5.1, §6.1, §6.2 and §6.5 closed, each keeping its original text as the record with what closed it quoted underneath, and the "suggested order of attack" is rewritten to what is actually left — §5.2, §5.3, the two missing cube READMEs, and the two findings (§2.7, §4.4) that are stated accurately in `docs/API.md` while the code still behaves as they describe. `docs/API.md` drops the two entries from its *Known gaps* list that are no longer gaps, documents the argv and the absent shell, describes the resolution stack and the error it raises, and inverts the `.default()`/`.describe()` warning: the order used to matter and no longer does, which is worth saying outright since the old advice is in the reader's memory and in 15 manifests. The README's "topological sorting" becomes "in dependency order, with cycle detection" — the sort never existed, but until this branch neither did the thing a sort would have been for — and `--no-history` is spelled `--no-save-history` wherever it appears. One line of code rides along, because it is what a `docs/API.md` note has been asking for: `CubePackageRef` is re-exported from `src/index.ts`, so importing `NopyConfig` from `@bitsquare/nopy` no longer gives you a type whose own members you cannot name. The note in `docs/API.md` saying it is missing goes with it. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01DCzYTAm9QUhvLNr2EpdagJ
ansiblings
Infrastructure tooling monorepo: two published CLIs plus the pyinfra "cubes" they deploy.
| Path | Package | Binary | What it is |
|---|---|---|---|
packages/nopy |
@bitsquare/nopy |
nopy |
interactive pyinfra script management and execution |
packages/keyman |
@bitsquare/keyman |
keyman |
SSH key management with age encryption |
packages/nopy-cubes |
@bitsquare/nopy-cubes |
— | the authoring surface a cube's manifest.mjs imports |
packages/nopy-cubes-core |
@bitsquare/nopy-cubes-core |
— | the core bundle of deployment units nopy runs |
npm install -g @bitsquare/nopy @bitsquare/keyman
See each package's README for usage, and README.PUBLISH.md for how they get published.
Development
Requires Node ≥ 22 (the repo pins 24 in .nvmrc) and pnpm — the version is
pinned by packageManager, so corepack enable is enough.
pnpm install
| Command | Does |
|---|---|
pnpm run build |
compiles both packages with tsc |
pnpm run typecheck |
tsc --build across the workspace (see below) |
pnpm run lint |
Biome check |
pnpm run lint:fix |
Biome check with fixes applied |
pnpm test |
vitest, both packages |
pnpm run test:coverage |
vitest with the coverage gate |
pnpm run coverage:summary |
renders the last coverage run as a Markdown table |
typescript is on the 7.x native compiler, so tsc is the fast one — there is
no separate tsgo binary to keep in sync. typecheck is plain tsc --build,
not --noEmit: once a project has references, TypeScript rejects --noEmit
outright (TS6310), because a composite project has to emit the declarations its
dependents read. So the typecheck writes dist as a side effect — gitignored,
and it means the gate also proves the build works. Each package also has a dev-run script
(pnpm --filter @bitsquare/nopy run nopy) that executes the TypeScript sources
directly through tsx.
Git hooks
Installed by simple-git-hooks on pnpm install, configured in the root
package.json:
- pre-commit — Biome check with fixes, on staged files only, re-staging what it fixed. Fast; blocks only on problems it cannot fix itself.
- pre-push —
lint:ci→typecheck→test:coverage. This is the same gate CI runs, so a push that survives it will not surprise you on the runner.
Set SKIP_SIMPLE_GIT_HOOKS=1 to bypass either one; re-install them after
changing the config with pnpm exec simple-git-hooks.
Coverage
Both packages hold a hard 85 % branch floor, enforced by
coverage.thresholds in their vitest.config.ts rather than by a CI-only flag —
pnpm run test:coverage fails the same way locally, in the pre-push hook, and
on the runner. Barrel files and CLI argv wiring are excluded; everything with
behaviour in it is not.