berth init
This commit is contained in:
104
berth/STALE.md
Normal file
104
berth/STALE.md
Normal file
@@ -0,0 +1,104 @@
|
||||
# berth — withdrawn assumptions
|
||||
|
||||
**Everything in this file is no longer true.**
|
||||
|
||||
It exists so the live docs stay short and so a withdrawn assumption cannot quietly return:
|
||||
each entry carries a **check**, and `ctrl/selftest.sh` runs every one of them. A retraction
|
||||
that is only prose is a retraction nobody re-reads.
|
||||
|
||||
Kept rather than deleted for the reason the docgen thread already wrote down —
|
||||
*a requirement that disappears without explanation comes back.*
|
||||
|
||||
### For agents
|
||||
|
||||
- **Do not restate these** in a plan, a README or a comment. One line pointing here is enough.
|
||||
- **Ids are stable.** Cite `✖ B3`; do not re-explain it.
|
||||
- **When you withdraw an assumption, move it here** — quoted claim, where it came from, what
|
||||
superseded it and why, what changed in the code, and a check that proves it is gone.
|
||||
- **Only withdrawn things belong here.** A warning that is still actionable is a live rule,
|
||||
however historical it sounds, and stays where it is.
|
||||
|
||||
---
|
||||
|
||||
**✖ B1 — "Pulumi is the source in spr, and Terraform must match the config."**
|
||||
*(INDEX §5, carried from 35.3)* Withdrawn 2026-09-12. berth uses **OpenTofu and only
|
||||
OpenTofu**. The rule assumed *open source* and *industry standard* pull apart — Terraform
|
||||
being BUSL, Pulumi being the open alternative. OpenTofu is both: the standard language, plain
|
||||
Terraform-compatible HCL, under MPL-2.0. Swappability was never bought by keeping two
|
||||
renderings; it is bought by `estate/*.json` being the artifact — a rendering you *can*
|
||||
produce, not one you *must* maintain.
|
||||
**Gone from:** `ctrl/versions.env` (no `PULUMI_VERSION`), `ctrl/estate.sh` (`plan` runs one
|
||||
executor), `ctrl/lib/config.sh` (`PULUMI_STACK` → `TOFU_WORKSPACE`), `ctrl/check.sh`
|
||||
(toolchain list).
|
||||
**Deliberately kept:** `README.md` and `estate/mcrn.json` both record that `ppl/infra/` was
|
||||
written and never applied — *"no `~/.pulumi`, no venv, no stack state"*. That is a historical
|
||||
fact about the estate, not a live dependency.
|
||||
**Check:** no `pulumi` in `ctrl/` or `Makefile`.
|
||||
|
||||
**✖ B2 — "ctlptl's rejection is the precedent for *the seam belongs in a script, not a tool*."**
|
||||
*(INDEX §5, `berth/README.md`)* Withdrawn 2026-09-12. **ctlptl was reinstated** — pinned in
|
||||
`rig/ctrl/versions.env` at v0.9.4 — and had been removed for the wrong reason. The rule may
|
||||
still hold; it now has to stand on its own reasoning rather than that example.
|
||||
**Gone from:** `README.md` — the argument is stated directly, with no borrowed evidence.
|
||||
**Check:** `ctlptl` appears nowhere in berth.
|
||||
|
||||
**✖ B3 — "`wg show` is safe; `wg showconf` is not."** *(my own note, 2026-09-12)* Incomplete,
|
||||
and the gap is the dangerous one. There are **three** forms, and `wg show <if> dump` puts the
|
||||
**private key in field 1 of the first line**. Stated as a two-way distinction, the `dump` form
|
||||
reads as safe.
|
||||
**Now:** `wg show` plain is safe; `dump` and `showconf` are not. `ctrl/vpn.sh capture` refuses
|
||||
the latter two **by shape**, rather than parsing around them.
|
||||
**Check:** `vpn.sh` names all three forms, and `capture` rejects both unsafe ones.
|
||||
|
||||
**✖ B4 — "A roaming peer must set `PersistentKeepalive` on its own entry."**
|
||||
*(`ctrl/vpn.sh`, first draft)* Wrong side, and wrong in the direction that looks fine:
|
||||
`PersistentKeepalive` is set per-peer in a config, so the roaming machine sets it on the entry
|
||||
for the peer it **dials**. The original check would have **warned on a correctly configured
|
||||
overlay**.
|
||||
**Now:** checked once per overlay — if anything roams, some peer entry must carry a keepalive.
|
||||
**Check:** the invariant is not keyed on the roaming peer's own `keepalive` field.
|
||||
|
||||
**✖ B5 — "The Makefile's pass-through block goes near the top, with the other variables."**
|
||||
*(`Makefile`, inherited from rig's layout)* Withdrawn 2026-09-12. When a subcommand **names a
|
||||
real target**, make has two recipes for it and the **last definition wins** — so with the block
|
||||
first, `make host ports` ran `ctrl/host.sh ports` *and* `ctrl/ports.sh ports`, the second
|
||||
failing because `ports` is not one of its verbs. Same for `make host services`, `make vpn
|
||||
check`, `make vpn show estate`.
|
||||
**Now:** the `$(eval $(ARGS):;@:)` block is **last in the file**, so the no-op wins and the
|
||||
word is swallowed — which is what an argument is. Make's *"overriding recipe"* warning is the
|
||||
swallow working.
|
||||
**Check:** every colliding invocation dispatches to exactly one script.
|
||||
|
||||
**✖ B6 — "A base64 key in the description can be caught by its shape."**
|
||||
*(`ctrl/vpn.sh check`, first draft)* WireGuard **public** keys are also 44-char base64 and
|
||||
legitimately live in the estate, so shape alone proves nothing and would flag correct data.
|
||||
**Now:** two assertions instead — **no field named `priv*`**, and **no base64 key outside a
|
||||
`public_key` field**.
|
||||
**Check:** the estate's public keys do not trip the secret check.
|
||||
|
||||
**✖ B7 — "`network.wireguard` is where the overlay is described."** *(`estate/mcrn.json`)*
|
||||
Superseded 2026-09-12: WireGuard is berth's network layer, not one service's transport, so it
|
||||
is a top-level `vpn` block with named overlays and peers. `ctrl/check.sh` and
|
||||
`ctrl/registry.sh` were repointed.
|
||||
**Gone from:** the estate schema — a `wireguard_moved` tombstone marks the old key.
|
||||
**Check:** nothing reads `network.wireguard.*`.
|
||||
|
||||
**✖ B8 — "berth and rig are related through their first uses."** *(early framing)* Withdrawn:
|
||||
**rig and berth are peers — neither depends on the other.** They match on shape (dispatch,
|
||||
config layering, key names) and consistency is verified by **recomputation**, never by
|
||||
dependency. A shared library would put something outside `rig/` on rig's path.
|
||||
**Check:** berth imports nothing from rig; `ports.sh` recomputes the port formula and agrees
|
||||
with rig's golden values.
|
||||
|
||||
**✖ B9 — "`langfuse.mcrn.ar` is an exception that cannot be generated."**
|
||||
*(`estate/mcrn.json`, `raw: true`)* Withdrawn 2026-09-14. It was filed as the one route a
|
||||
template could not express — a static `upstream{}` to a WireGuard address, with no `resolver`
|
||||
and no `set $var`. It was not an exception; it was **the first instance of the general case**.
|
||||
Those three properties are not three decisions, they are one: *this service is reached by
|
||||
address on the overlay, not by name on the docker network.* Naming that decision —
|
||||
`placement` — makes the file renderable.
|
||||
**Gone from:** `estate/mcrn.json` — `lng` and `langfuse` were **two entries for one socket**
|
||||
and are now one service with `placement: local`, `peer: nrft`, and a `local_host` for the
|
||||
name it answers to locally. `raw` is dropped.
|
||||
**Check:** the generated vhost matches the hand-written one, normalised for comments and
|
||||
whitespace — proof against a live route rather than an assertion.
|
||||
Reference in New Issue
Block a user