Add reproducible S1 handoff workplan
Assistant: codex Assistant-Model: gpt-5.6-sol Assistant-Session: 01a02994-7685-7940-bf34-3555b8256018
This commit is contained in:
parent
3734a1c3bc
commit
c8cb1c8edf
2 changed files with 243 additions and 0 deletions
|
|
@ -14,6 +14,7 @@
|
||||||
| workplan | RAIL-HO-WP-0008 | finished | — | workplans/RAIL-HO-WP-0008-railiance01-resource-and-commercial-evidence.md |
|
| workplan | RAIL-HO-WP-0008 | finished | — | workplans/RAIL-HO-WP-0008-railiance01-resource-and-commercial-evidence.md |
|
||||||
| workplan | RAIL-HO-WP-0009 | finished | — | workplans/RAIL-HO-WP-0009-firewall-declared-state-and-api-exposure.md |
|
| workplan | RAIL-HO-WP-0009 | finished | — | workplans/RAIL-HO-WP-0009-firewall-declared-state-and-api-exposure.md |
|
||||||
| workplan | RAIL-HO-WP-0010 | finished | — | workplans/RAIL-HO-WP-0010-new-reef-ports-need-a-grant.md |
|
| workplan | RAIL-HO-WP-0010 | finished | — | workplans/RAIL-HO-WP-0010-new-reef-ports-need-a-grant.md |
|
||||||
|
| workplan | RAIL-HO-WP-0011 | ready | — | workplans/RAIL-HO-WP-0011-reproducible-s1-declaration-and-handoff.md |
|
||||||
| task | ADHOC-2026-08-22-T01 | done | — | workplans/ADHOC-2026-08-22.md |
|
| task | ADHOC-2026-08-22-T01 | done | — | workplans/ADHOC-2026-08-22.md |
|
||||||
| task | ADHOC-2026-08-22-T02 | done | — | workplans/ADHOC-2026-08-22.md |
|
| task | ADHOC-2026-08-22-T02 | done | — | workplans/ADHOC-2026-08-22.md |
|
||||||
| task | ADHOC-2026-08-22-T03 | done | — | workplans/ADHOC-2026-08-22.md |
|
| task | ADHOC-2026-08-22-T03 | done | — | workplans/ADHOC-2026-08-22.md |
|
||||||
|
|
@ -40,3 +41,11 @@
|
||||||
| task | RAIL-HO-WP-0009-T05 | done | — | workplans/RAIL-HO-WP-0009-firewall-declared-state-and-api-exposure.md |
|
| task | RAIL-HO-WP-0009-T05 | done | — | workplans/RAIL-HO-WP-0009-firewall-declared-state-and-api-exposure.md |
|
||||||
| task | RAIL-HO-WP-0009-T06 | done | — | workplans/RAIL-HO-WP-0009-firewall-declared-state-and-api-exposure.md |
|
| task | RAIL-HO-WP-0009-T06 | done | — | workplans/RAIL-HO-WP-0009-firewall-declared-state-and-api-exposure.md |
|
||||||
| task | RAIL-HO-WP-0010-T01 | done | — | workplans/RAIL-HO-WP-0010-new-reef-ports-need-a-grant.md |
|
| task | RAIL-HO-WP-0010-T01 | done | — | workplans/RAIL-HO-WP-0010-new-reef-ports-need-a-grant.md |
|
||||||
|
| task | RAIL-HO-WP-0011-T01 | todo | — | workplans/RAIL-HO-WP-0011-reproducible-s1-declaration-and-handoff.md |
|
||||||
|
| task | RAIL-HO-WP-0011-T02 | todo | — | workplans/RAIL-HO-WP-0011-reproducible-s1-declaration-and-handoff.md |
|
||||||
|
| task | RAIL-HO-WP-0011-T03 | todo | — | workplans/RAIL-HO-WP-0011-reproducible-s1-declaration-and-handoff.md |
|
||||||
|
| task | RAIL-HO-WP-0011-T04 | todo | — | workplans/RAIL-HO-WP-0011-reproducible-s1-declaration-and-handoff.md |
|
||||||
|
| task | RAIL-HO-WP-0011-T05 | todo | — | workplans/RAIL-HO-WP-0011-reproducible-s1-declaration-and-handoff.md |
|
||||||
|
| task | RAIL-HO-WP-0011-T06 | todo | — | workplans/RAIL-HO-WP-0011-reproducible-s1-declaration-and-handoff.md |
|
||||||
|
| task | RAIL-HO-WP-0011-T07 | todo | — | workplans/RAIL-HO-WP-0011-reproducible-s1-declaration-and-handoff.md |
|
||||||
|
| task | RAIL-HO-WP-0011-T08 | todo | — | workplans/RAIL-HO-WP-0011-reproducible-s1-declaration-and-handoff.md |
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,234 @@
|
||||||
|
---
|
||||||
|
id: RAIL-HO-WP-0011
|
||||||
|
type: workplan
|
||||||
|
title: "Make the S1 declaration reproducible and the handoff verifiably green"
|
||||||
|
domain: financials
|
||||||
|
repo: railiance-infra
|
||||||
|
status: ready
|
||||||
|
owner: codex
|
||||||
|
topic_slug: railiance
|
||||||
|
created: "2026-08-23"
|
||||||
|
updated: "2026-08-23"
|
||||||
|
related:
|
||||||
|
- RAIL-HO-WP-0002
|
||||||
|
- RAIL-HO-WP-0009
|
||||||
|
---
|
||||||
|
|
||||||
|
# RAIL-HO-WP-0011 — reproducible S1 declaration and handoff
|
||||||
|
|
||||||
|
## Goal
|
||||||
|
|
||||||
|
Close the highest-leverage gaps identified in
|
||||||
|
`history/2026-08-23-scope-against-intent.md`: distinguish adopted resources
|
||||||
|
from provider-managed resources, make the host baseline contract executable,
|
||||||
|
produce a green per-host handoff gate, and make every declared secret input
|
||||||
|
fail closed. Then add the evidence and rotation mechanics needed for an
|
||||||
|
auditable provisioning path.
|
||||||
|
|
||||||
|
This workplan improves the source and validation path. It does **not** authorize
|
||||||
|
a Terraform apply or destroy, a live firewall change, a credential rotation,
|
||||||
|
or any other live-host mutation. Those actions require their normal reviewed
|
||||||
|
plan and operator approval.
|
||||||
|
|
||||||
|
## Delivery Order
|
||||||
|
|
||||||
|
The critical path is T01 → T02 and T03 → T04 → T05. T06 can proceed
|
||||||
|
independently. T07 depends on T02 and T05. T08 depends on T06.
|
||||||
|
|
||||||
|
## T01 — Define and validate adopted-versus-managed inventory
|
||||||
|
|
||||||
|
```task
|
||||||
|
id: RAIL-HO-WP-0011-T01
|
||||||
|
status: todo
|
||||||
|
priority: high
|
||||||
|
```
|
||||||
|
|
||||||
|
Define one explicit inventory contract for common host identity and
|
||||||
|
provider-specific lifecycle fields. At minimum it must distinguish:
|
||||||
|
|
||||||
|
- provider (`hosteurope`, `hetzner`, or a documented extension value)
|
||||||
|
- lifecycle mode (`adopted` versus provider-managed)
|
||||||
|
- connection identity used by Ansible
|
||||||
|
- provider-specific provisioning fields used by Terraform
|
||||||
|
|
||||||
|
Add a side-effect-free validator and fixtures for the two current adopted Host
|
||||||
|
Europe hosts, a valid provisionable Hetzner host, and invalid mixed records.
|
||||||
|
Preserve stable host names and connection behavior.
|
||||||
|
|
||||||
|
**Done when:** the current inventory validates as adopted Host Europe
|
||||||
|
resources, a complete Hetzner fixture validates, incomplete or contradictory
|
||||||
|
records fail with actionable errors, and no provider command is needed to run
|
||||||
|
the validation.
|
||||||
|
|
||||||
|
## T02 — Make Hetzner planning select only managed Hetzner resources
|
||||||
|
|
||||||
|
```task
|
||||||
|
id: RAIL-HO-WP-0011-T02
|
||||||
|
status: todo
|
||||||
|
priority: high
|
||||||
|
```
|
||||||
|
|
||||||
|
Update the Terraform and helper path to consume the T01 contract and exclude
|
||||||
|
adopted or non-Hetzner records. Audit any existing Terraform state before
|
||||||
|
changing resource addresses or selection logic. Correct provisioning docs and
|
||||||
|
Make targets so they name the provider-token source actually used.
|
||||||
|
|
||||||
|
Add an isolated plan test or equivalent deterministic validation that proves
|
||||||
|
the current Host Europe records cannot become Hetzner creates or destroys.
|
||||||
|
|
||||||
|
**Done when:** current adopted records pass through the inventory-to-Terraform
|
||||||
|
boundary without missing-field errors or managed resources, a provisionable
|
||||||
|
Hetzner fixture produces the expected resource shape, and a reviewed plan shows
|
||||||
|
no unintended create, replace, or destroy. Do not apply the plan in this task.
|
||||||
|
|
||||||
|
## T03 — Model host-specific baseline profiles and reconcile declared state
|
||||||
|
|
||||||
|
```task
|
||||||
|
id: RAIL-HO-WP-0011-T03
|
||||||
|
status: todo
|
||||||
|
priority: high
|
||||||
|
```
|
||||||
|
|
||||||
|
Replace the permanent `CoulombCore` expected failure with an explicit baseline
|
||||||
|
profile or declared exception. Reconcile `spec/server-baseline.yaml`, Ansible,
|
||||||
|
and the intended live posture for packages, users/sudo, SSH, firewall,
|
||||||
|
fail2ban, SOPS tooling, swap, and resource limits.
|
||||||
|
|
||||||
|
Exceptions must say which control replaces the default, why it is accepted,
|
||||||
|
and who owns removing it. An unmanaged control must not silently count as
|
||||||
|
verified.
|
||||||
|
|
||||||
|
**Done when:** both current hosts resolve to complete declared profiles, the
|
||||||
|
UFW-managed and externally-filtered postures have explicit assertions, and the
|
||||||
|
spec no longer claims properties that convergence neither establishes nor
|
||||||
|
deliberately delegates.
|
||||||
|
|
||||||
|
## T04 — Add automated baseline contract-parity tests
|
||||||
|
|
||||||
|
```task
|
||||||
|
id: RAIL-HO-WP-0011-T04
|
||||||
|
status: todo
|
||||||
|
priority: high
|
||||||
|
```
|
||||||
|
|
||||||
|
Add repository tests that fail when the human baseline, convergence roles, and
|
||||||
|
Goss assertions diverge on governed properties. Prefer a single
|
||||||
|
machine-readable model or generated artifacts where that reduces duplicated
|
||||||
|
declarations; otherwise implement explicit parity checks with clear failure
|
||||||
|
messages.
|
||||||
|
|
||||||
|
Cover the profiles introduced by T03 and run the tests in Forgejo CI without
|
||||||
|
requiring host access or secrets.
|
||||||
|
|
||||||
|
**Done when:** a deliberate mismatch in a governed package, SSH setting,
|
||||||
|
firewall rule, service, or user property fails locally and in CI, while all
|
||||||
|
declared profiles pass from a clean checkout.
|
||||||
|
|
||||||
|
## T05 — Provide a fresh green S1 handoff gate
|
||||||
|
|
||||||
|
```task
|
||||||
|
id: RAIL-HO-WP-0011-T05
|
||||||
|
status: todo
|
||||||
|
priority: high
|
||||||
|
```
|
||||||
|
|
||||||
|
Provide one operator-facing, non-ambiguous command that checks inventory and
|
||||||
|
contract validity, runs the applicable profile for every selected host,
|
||||||
|
collects evidence, and exits non-zero if any required control is failed,
|
||||||
|
unknown, stale, or skipped without an accepted declaration.
|
||||||
|
|
||||||
|
The receipt must identify the source revision, inventory digest, host/profile,
|
||||||
|
check time, and result without including credentials or sensitive host output.
|
||||||
|
Define freshness and the exact interface S2 can consume.
|
||||||
|
|
||||||
|
**Done when:** both current hosts can return green against their declared
|
||||||
|
profiles in an attended verification run, a failing or stale host makes the
|
||||||
|
aggregate gate fail, and the evidence is sufficient for an S2 handoff without
|
||||||
|
interpreting an expected-red exception.
|
||||||
|
|
||||||
|
## T06 — Repair and enforce the secret-source contract
|
||||||
|
|
||||||
|
```task
|
||||||
|
id: RAIL-HO-WP-0011-T06
|
||||||
|
status: todo
|
||||||
|
priority: high
|
||||||
|
```
|
||||||
|
|
||||||
|
Remove, relocate, or SOPS-encrypt the plaintext
|
||||||
|
`inventory/group_vars/secrets.sops.yaml` placeholder. Inventory every path that
|
||||||
|
documentation or automation describes as secret-bearing, extend the
|
||||||
|
pre-commit/CI check to those paths, and make playbooks fail clearly when an
|
||||||
|
expected encrypted input is absent or malformed.
|
||||||
|
|
||||||
|
Align README, provisioning, convergence, Make targets, and playbooks on the
|
||||||
|
actual Hetzner token source and on the fact that the host role installs tools
|
||||||
|
but does not distribute an age private key.
|
||||||
|
|
||||||
|
**Done when:** plaintext fixtures at any declared secret path are rejected,
|
||||||
|
the committed tree contains no file falsely presented as encrypted input, and
|
||||||
|
the documented controller and host secret flows match the executable paths.
|
||||||
|
|
||||||
|
## T07 — Emit non-secret provisioning and handoff receipts
|
||||||
|
|
||||||
|
```task
|
||||||
|
id: RAIL-HO-WP-0011-T07
|
||||||
|
status: todo
|
||||||
|
priority: medium
|
||||||
|
```
|
||||||
|
|
||||||
|
Define a versioned receipt linking inventory and source revisions, provider
|
||||||
|
plan/apply identity, provider resource ID, cloud-init completion, Ansible
|
||||||
|
convergence, and the T05 handoff result. Separate plan, apply, and verification
|
||||||
|
events so a plan receipt cannot be mistaken for proof of a live change.
|
||||||
|
|
||||||
|
Exercise the format with a dry-run or synthetic fixture first. A live provider
|
||||||
|
apply remains separately approved and is not required merely to prove schema
|
||||||
|
and redaction behavior.
|
||||||
|
|
||||||
|
**Done when:** the receipt schema validates, sensitive fields and provider
|
||||||
|
tokens cannot be serialized, incomplete phases fail closed, and a synthetic
|
||||||
|
end-to-end example is consumable without prose interpretation.
|
||||||
|
|
||||||
|
## T08 — Automate bounded SOPS recipient rotation
|
||||||
|
|
||||||
|
```task
|
||||||
|
id: RAIL-HO-WP-0011-T08
|
||||||
|
status: todo
|
||||||
|
priority: medium
|
||||||
|
```
|
||||||
|
|
||||||
|
Build a dry-run-first rotation workflow for the repository's SOPS files. It
|
||||||
|
must inventory affected files and recipients, detect recipient drift, require a
|
||||||
|
reviewed change set, verify decryption through an approved non-printing check,
|
||||||
|
and emit a metadata-only receipt. Never print a decrypted value or private age
|
||||||
|
key.
|
||||||
|
|
||||||
|
Live recipient removal or credential replacement requires explicit operator
|
||||||
|
approval after the dry run. Scheduling may be proposed only after rollback and
|
||||||
|
recovery-key custody are documented.
|
||||||
|
|
||||||
|
**Done when:** CI can detect recipient drift without secrets, an attended dry
|
||||||
|
run identifies the exact files and before/after recipient set, rollback is
|
||||||
|
documented, and a sample receipt proves verification without exposing values.
|
||||||
|
|
||||||
|
## Acceptance
|
||||||
|
|
||||||
|
- [ ] Adopted Host Europe records and provider-managed Hetzner records cannot
|
||||||
|
be confused by validation or Terraform selection.
|
||||||
|
- [ ] The declared baseline, Ansible convergence, and Goss verification have an
|
||||||
|
automated parity contract.
|
||||||
|
- [ ] Every current host can produce a fresh green result against an explicit
|
||||||
|
profile, and the aggregate handoff fails closed.
|
||||||
|
- [ ] Every documented secret-bearing path is encrypted or deliberately absent
|
||||||
|
and protected by local and CI checks.
|
||||||
|
- [ ] Provisioning/handoff and rotation paths emit metadata-only receipts with
|
||||||
|
reviewed redaction behavior.
|
||||||
|
- [ ] No live provider, firewall, credential, or host mutation occurs without a
|
||||||
|
separately reviewed plan and the required operator approval.
|
||||||
|
|
||||||
|
## Completion Evidence
|
||||||
|
|
||||||
|
Record the final inventory schema and examples, Terraform plan safety result,
|
||||||
|
baseline parity tests, CI run, attended all-host gate receipt, secret-path
|
||||||
|
negative tests, provisioning receipt fixture, and SOPS rotation dry-run receipt
|
||||||
|
here before marking the workplan finished.
|
||||||
Loading…
Add table
Add a link
Reference in a new issue