docs: per-bundle docs are README.md, not AGENTS.md

drops the per-bundle AGENTS.md convention and the rigid template
that went with it. each bundle has (or gets) one README.md that
serves humans and agents both.

bundles/AGENTS.md now has a "Per-bundle README" section pointing
at the more substantial existing READMEs (flask, dm-crypt, apt,
nextcloud) for orientation, plus loose guidance on what to cover
and what to skip. no required structure — match the bundle's
actual surface.

removes bundles/AGENTS.template.md; the template was prescriptive
in a way that wouldn't survive contact with this repo's actual
bundles, where READMEs range from one-paragraph balanced docs to
operational scratchpads.

phase-2 seed-bundle work stays deferred and will land as plain
README updates when bundles are materially edited.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
CroneKorkN 2026-05-10 16:02:24 +02:00
parent 04558a9189
commit 9e1bb2ac45
Signed by: cronekorkn
SSH key fingerprint: SHA256:v0410ZKfuO1QHdgKBsdQNF64xmTxOF8osF1LIqwTcVw
2 changed files with 55 additions and 84 deletions

View file

@ -22,8 +22,7 @@ bundles/<name>/
├── items.py # the items this bundle creates (files, services, packages, …) ├── items.py # the items this bundle creates (files, services, packages, …)
├── metadata.py # `defaults` + `@metadata_reactor` functions ├── metadata.py # `defaults` + `@metadata_reactor` functions
├── files/ # static or templated file payloads referenced from items.py ├── files/ # static or templated file payloads referenced from items.py
├── AGENTS.md # this bundle's doc (template at AGENTS.template.md) └── README.md # one doc per bundle, for humans and agents (see "Per-bundle README" below)
└── README.md # legacy; being phased out (see "Documentation transition" below)
``` ```
## Conventions ## Conventions
@ -63,10 +62,8 @@ bundles/<name>/
- `bw hash <node>` — confirm the change is what you expected. See - `bw hash <node>` — confirm the change is what you expected. See
[`docs/agents/commands.md`](../docs/agents/commands.md) and the [`docs/agents/commands.md`](../docs/agents/commands.md) and the
fork's hash-diff workflow. fork's hash-diff workflow.
6. Create `bundles/<name>/AGENTS.md` from 6. Add a `bundles/<name>/README.md`. See "Per-bundle README" below
[`AGENTS.template.md`](AGENTS.template.md). For a brand-new bundle for what to cover.
without consumers yet, leave `Depends on` and `Produces` empty or
marked TBD; fill them in after the first verify run.
## How to remove a bundle ## How to remove a bundle
@ -88,31 +85,66 @@ bundles/<name>/
- **Reactors writing across namespaces.** Some bundles' reactors write - **Reactors writing across namespaces.** Some bundles' reactors write
into other bundles' metadata namespaces (e.g. `nextcloud` writes into other bundles' metadata namespaces (e.g. `nextcloud` writes
into `apt.packages`, `archive.paths`). When you change such a bundle, into `apt.packages`, `archive.paths`). When you change such a bundle,
every consumer's metadata changes too. Per-bundle docs declare these every consumer's metadata changes too. The bundle's `README.md`
in an optional `## Writes into` section — read it before assuming the often calls these out — but the authoritative source is `metadata.py`
blast radius is local. itself; grep `'<other-bundle>':` in the reactors when in doubt.
- **`bw hash` doesn't accept selectors.** Use `bw hash <node>` per - **`bw hash` doesn't accept selectors.** Use `bw hash <node>` per
literal name; see the fork's runbook. literal name; see the fork's runbook.
## Documentation transition ## Per-bundle README
This repo is migrating from bundle `README.md` files to per-bundle Each bundle has (or should have) a `README.md`. One doc per bundle,
`AGENTS.md` files (one balanced doc per bundle, agents + humans). written for humans and agents both. There's no fixed structure —
match the bundle's actual surface, write what helps a future reader
(or future you) avoid trial-and-error.
- Where both exist, **`AGENTS.md` is canonical**; the `README.md` is The existing READMEs vary in quality and shape. For orientation,
being phased out. look at the bigger ones, not the two-line ones:
- ~28 bundle READMEs survive after the seed migration (the seed PR
folds in 510 of them; the rest are addressed lazily on the next - [`bundles/flask/README.md`](flask/README.md) — title + one-sentence
material edit — Phase 3 leave-as-you-go). purpose, a metadata example as a Python dict, then the contract
- Phase-3 rule: any time you (or any agent) materially edits a bundle, the consuming git repo has to satisfy + a logging pitfall. The
top-up its `AGENTS.md` or create one from closest thing to a "balanced doc" in tree.
[`AGENTS.template.md`](AGENTS.template.md). If a stale `README.md` - [`bundles/dm-crypt/README.md`](dm-crypt/README.md) — same shape,
is still around in the bundle, fold it in and remove it in the same shorter: purpose + metadata example + one sentence on effect.
commit. - [`bundles/apt/README.md`](apt/README.md) — relevant upstream URLs
at the top, then a Python metadata example with rich inline
comments (type / optionality / where keys come from).
- [`bundles/nextcloud/README.md`](nextcloud/README.md) — operational
scratchpad: iPhone-import recipe, preview-generator commands,
reset queries. Captures muscle-memory the maintainer would
otherwise re-learn each time.
Useful things to include, when relevant:
- A sentence or two on what the bundle does and when you'd attach it.
- A metadata example as a Python dict literal, with `#` comments
on each key (type, required vs default, units, where it comes
from). This is the cleanest way to communicate the schema and
matches how `metadata.py` actually looks.
- Anything non-obvious about wiring it up — required keys without
defaults, group-membership expectations, manual one-time steps.
- Cross-namespace metadata writes, when this bundle's reactors
populate another bundle's namespace. Easy to miss, cheap to flag.
- Gotchas, debug recipes, failure modes you've actually hit.
What to skip:
- An exhaustive item list — `items.py` is shorter and more accurate.
- Anything that would just rot — version numbers, "TODO" lists,
change notes. Use git history.
If a single paragraph is enough to say what's worth saying, write a
single paragraph. Verbosity isn't a goal.
Convention going forward is leave-as-you-go: any time you materially
edit a bundle, top up its README (or write one if it's missing).
Don't burn a session bulk-reformatting the existing ones — uneven
quality is part of what we accept in exchange for not blocking other
work.
## See also ## See also
- [`AGENTS.template.md`](AGENTS.template.md) — per-bundle doc template.
- [`docs/agents/conventions.md`](../docs/agents/conventions.md) — repo - [`docs/agents/conventions.md`](../docs/agents/conventions.md) — repo
idioms (vault, demagify, naming, do-not-touch list). idioms (vault, demagify, naming, do-not-touch list).
- [`docs/agents/commands.md`](../docs/agents/commands.md) — repo-specific - [`docs/agents/commands.md`](../docs/agents/commands.md) — repo-specific

View file

@ -1,61 +0,0 @@
# <bundle-name>
<!--
Per-bundle doc template. Copy to `bundles/<name>/AGENTS.md` and fill in.
For a brand-new bundle without consumers yet, leave `Depends on` and
`Produces` empty or marked TBD; fill them in after the first verify run.
Skip the `## Gotchas` section if there are no real gotchas — empty
"Gotchas: none" sections are noise.
Skip the `## Writes into` section unless this bundle's `defaults` or
reactors write into other bundles' metadata namespaces. Most don't.
-->
<13 sentences: what this bundle does and when you'd use it.>
## Usage
<How to apply: which group(s) typically include it, or how a node opts
in. Minimal example of node metadata if any keys are required.>
## Metadata
Keys read from `node.metadata`:
```python
{
'<bundle>': {
'key': 'value', # str, required — short note
'flag': True, # bool, default True
'list': [], # list[str], default [] — short note
'nested': {
'subkey': 0, # int, default 0
},
},
}
```
## Produces
<Items created: files, services, packages, users, etc. One line each.
Skip if trivially obvious from items.py.>
## Depends on
<Other bundles required, or "none". Note ordering quirks if any.>
## Writes into
<!-- Optional. Most bundles don't write cross-namespace; skip the
section if this bundle doesn't either. List the foreign metadata
namespaces this bundle's `defaults` or reactors populate (e.g.
`apt.packages`, `archive.paths`). Cross-namespace writes are the
single most surprising blast-radius source in this repo — call them
out explicitly. -->
## Gotchas
<Non-obvious behavior, manual one-time steps, known pitfalls. Omit
the section if there are none.>