railiance-infra/docs/s1-handoff.md
codex b93af8cc78
Some checks failed
CI Smoke / source-contract (push) Failing after 2s
CI Smoke / host-smoke (push) Successful in 0s
CI Smoke / container-smoke (push) Successful in 1s
Implement reproducible S1 handoff contracts
Assistant: codex
Assistant-Model: gpt-5.6-sol
Assistant-Session: 01a02994-7685-7940-bf34-3555b8256018
2026-08-23 12:02:23 +02:00

39 lines
1.4 KiB
Markdown

# S1 Handoff Gate
`make s1-handoff` is the operator-facing gate from host substrate (S1) to the
cluster layer (S2). It validates inventory and baseline contracts, requires a
clean checkout, runs the applicable Goss profile for every selected host, and
emits a metadata-only JSON receipt under `reports/`.
A passing receipt pins:
- source revision and inventory digest
- every selected host and its baseline profile
- observed time and 24-hour default freshness boundary
- per-host exit status
- SHA-256 digests of the resulting TAP evidence
Any failed host fails the aggregate. A passing receipt without host evidence is
invalid. `make s1-handoff-dry-run` validates local inputs but records
`status: not-run`; it cannot authorize S2 handoff.
The current profiles are:
- `Railiance01`: `ufw-managed`
- `CoulombCore`: `external-firewall`, which verifies the declared iptables
INPUT default-drop replacement control
The verification play installs or refreshes the Goss check surface before it
runs. Treat the first run after source changes as an attended host change:
review the rendered contract and access path first. The command does not run
Terraform, change provider resources, rotate credentials, or converge the base
role.
Receipts validate with:
```bash
python3 scripts/s1_receipt.py reports/s1-handoff-*.json
```
S2 should accept only `status: pass` receipts whose source and inventory match
the intended handoff and whose `fresh_until` has not elapsed.