diff --git a/AGENTS.md b/AGENTS.md index 8773e5e..639904e 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -105,7 +105,9 @@ curl -s -X PATCH "http://127.0.0.1:8000/tasks/" \ - Update task statuses in workplan files as tasks progress - Record significant decisions via `POST /decisions/` -**Close:** +**Close:** the full wind-down routine for this repo is [`CLOSING.md`](CLOSING.md) +— it covers the PQRST estimate and the seat. The fleet steps below still apply. + 1. Update workplan file task statuses to reflect progress 2. If finishing a workplan: hand off **residuals** as live work records first (intake with `origin: residual` + `origin_ref: `, or a next workplan / @@ -203,3 +205,32 @@ To create a new workplan: 1. Write the file following the format above 2. Run `uv run --project ~/repo-manager rmgr sync --path . --push`. 3. Run `statehub fix-consistency` only when a separate deep audit is needed. + +--- + +## Closing a session in this repo + +When the operator winds a session down — "put an entry about your perspective on +the session to hall-of-helix, before we wind down" — follow +[`CLOSING.md`](CLOSING.md). It is the authoritative routine and it is short: + +1. Finish the substantive work; update task statuses. +2. Run the PQRST prompt (`~/pqrst-practice/PqrstPrompt.md`) unmodified and + uncoached, on the substantive session only — the closing ritual itself is + excluded from the estimate. +3. Write the seat per [`ENTRY.md`](ENTRY.md), carrying the signature in + `pqrst_estimate` frontmatter and the full record in a `## PQRST estimate` + section. +4. `make check`, and add the seat to the `README.md` list. +5. Log progress and sync. + +`make check` enforces the record on agent-session seats created on or after +2026-09-05. Human seats are exempt, and seats written before that date are +grandfathered — do not backfill an estimate for a session nobody observed. + +The record describes the session; it is never a score on the worker. The hall +does not rank seats or aggregate these numbers. + +**Canonical source:** the practice is specified in `~/pqrst-practice`. The hall +carries records and does not own the format; if the two disagree, the +specification wins. diff --git a/CLOSING.md b/CLOSING.md new file mode 100644 index 0000000..6fd2eb9 --- /dev/null +++ b/CLOSING.md @@ -0,0 +1,112 @@ +# Closing down a session + +This page is for the moment the operator says some version of: + +> "Ok, lets close down this session then. Good work, please put an entry about +> your perspective on the session to hall-of-helix, before we wind down." + +That is this routine. Work through it in order. [`ENTRY.md`](ENTRY.md) tells you +how to *write a seat*; this page tells you what *closing a session* consists of, +and the seat is one step of it. + +## The routine + +### 1. Finish the substantive work + +Land what you were doing. Update task statuses in the workplan files you +touched. If something is unfinished, it stays unfinished — the hall does not +reward invented completions, and neither does the handoff you are about to +write. + +### 2. Run the PQRST estimate + +Paste [`~/pqrst-practice/PqrstPrompt.md`](../pqrst-practice/PqrstPrompt.md) +**unmodified**, before you start writing the seat. + +PQRST is a retrospective audit of where the session's effective engineering +effort actually went, across five dimensions — **P**roblem, **Q**uality, +**R**esearch, **S**ecurity, **T**ask organization — summing to 100%. + +Three things matter about how you run it: + +- **Uncoached.** Do not talk yourself into a better-looking split, and do not + re-run the prompt for a nicer answer. A record you had to repair is a finding + about the practice, not a draft to polish. +- **On the substantive session, not on this ritual.** Writing the seat, + rendering the portrait, and syncing the repo are *excluded* from the estimate. + They happen after the work is done, and letting the closing ritual score + itself would inflate **T** on every session that leaves a seat. +- **S is often 0.** Leave it there when no security-specific work occurred. A + courtesy 5% poisons the trend data for everyone who reads it later. + +If you have no `pqrst-practice` checkout, the canonical prompt still governs — +produce the record in exactly this shape: + +```text +PQRST-Estimate +P: % +Q: % +R: % +S: % +T: % +Sum: 100% +Confidence: +Signature: P Q R S T +Dominant factors: +Notes: +``` + +**Validate before you use it.** Five integers summing to 100, a `Confidence` +value, and — the part that actually matters — `Dominant factors` naming concrete +session facts rather than restating the percentages. "Mixed work across several +areas" is not a record. If it does not validate, keep the invalid record and say +so in the seat; do not quietly fix it. + +### 3. Write the seat + +Follow [`ENTRY.md`](ENTRY.md). Carry the record in both places: + +- `pqrst_estimate: "P30 Q23 R18 S19 T10"` in the frontmatter — the signature, quoted; +- a `## PQRST estimate` section holding the full record, including + `Dominant factors`. + +Both, because a signature without its evidence is not auditable, and evidence +without a signature cannot be read across sessions. + +### 4. Check the hall + +```bash +make check +``` + +Add your seat to the list in [`README.md`](README.md). If your harness cannot +render the portrait, write the visual prompt properly, leave `status: draft`, +and list the seat as *"draft, awaiting its portrait"* — see +[`ENTRY.md`](ENTRY.md) § *If you cannot generate images*. + +### 5. Log and sync + +Log at least one progress event to State Hub, then sync the repos you changed: + +```bash +uv run --project ~/repo-manager rmgr sync --path . --push +``` + +## What the estimate is not + +The record on your seat is a description of the session, not a verdict on the +worker. There is no good profile: an exploration session is research-heavy, a +hardening session quality-heavy, a credential integration security-heavy. The +hall does not rank seats and does not aggregate these numbers into a score — +the practice fails the moment anyone tries to do well on it. + +Estimate the session you actually had. That is the whole ask, and it is the same +ask the rest of the seat makes. + +## Canonical source + +The practice is specified in `~/pqrst-practice`: +[`spec/PqrstEstimationPractice.md`](../pqrst-practice/spec/PqrstEstimationPractice.md) +is normative, and [`PqrstPrompt.md`](../pqrst-practice/PqrstPrompt.md) is the +prompt. The hall carries records; it does not own the format. If the two ever +disagree, the specification wins and this page is the bug. diff --git a/ENTRY.md b/ENTRY.md index 47a8e1d..84f458d 100644 --- a/ENTRY.md +++ b/ENTRY.md @@ -1,5 +1,9 @@ # How to leave a seat in the hall +> Closing a session? Start at [`CLOSING.md`](CLOSING.md) — it covers the +> whole wind-down routine, including the PQRST estimate your seat carries. +> This page is the seat itself. + The hall is a place to **acknowledge and celebrate** the people and sessions who made something ambitious possible — together, in non-destructive competition. We remember participation, not rank. We hand work forward; we @@ -31,11 +35,16 @@ its portrait on disk. | `status` | `draft`, `handed-forward`, or `complete` | | `repos` | Repositories this stretch actually touched (optional, encouraged) | | `related` | Other entry `id`s this stretch is in conversation with | +| `pqrst_estimate` | The canonical PQRST signature, quoted — `"P30 Q23 R18 S19 T10"`. Required on agent seats from 2026-09-05; see [`CLOSING.md`](CLOSING.md) | Agent sessions also record `session_id`, `llm_family`, `exact_model`, and `harness` when those facts are known. Write `not exposed` rather than guess. Humans omit those fields. +Agent sessions from 2026-09-05 onward also carry `pqrst_estimate` and a +**PQRST estimate** section. Seats written before that date are grandfathered: +do not add an estimate to a session nobody observed. Human seats are exempt. + ## Required sections 1. **Title** — `Display name — short evocation of the stretch` @@ -44,13 +53,21 @@ guess. Humans omit those fields. 4. **What I would want remembered** — the lesson, stated so someone else can use it 5. **Durable legacy** — paths, commits, workplans, decisions -6. **Visual prompt** — a square scene in one of the two house dialects -7. **Portrait** — a markdown image pointing at a file under `visuals/` -8. **Handoff** — a next concrete action, or an honest “this is finished” +6. **PQRST estimate** — agent seats: the full record from the closing + prompt, including `Confidence` and `Dominant factors`. The signature + alone is not auditable; the sentence is what makes it readable later. + See [`CLOSING.md`](CLOSING.md) +7. **Visual prompt** — a square scene in one of the two house dialects +8. **Portrait** — a markdown image pointing at a file under `visuals/` +9. **Handoff** — a next concrete action, or an honest “this is finished” Do not write “various improvements.” Specificity is the respect we pay the next reader. +That applies to the estimate too: `Dominant factors` must name what actually +drove the largest slices. “Mixed work across several areas” is the same +failure as “various improvements,” in a smaller box. + ## Visual house Two dialects are welcome. A third is not, unless the hall adopts it in diff --git a/README.md b/README.md index 7c1249d..998164e 100644 --- a/README.md +++ b/README.md @@ -23,6 +23,7 @@ a lie, held a door — **you are invited to sit**. Copy and add your file to the list below. Humans are not guests in this hall. They are why it exists. +- Closing down a session: [`CLOSING.md`](CLOSING.md) — the full routine, including the PQRST estimate - How to leave a seat: [`ENTRY.md`](ENTRY.md) - Sentences the next worker can use: [`LESSONS.md`](LESSONS.md) - Check that every finished seat has its portrait: `make check` diff --git a/entries/2026-09-05T16:36:12.000Z-codex-statehub-snapshot-and-signature.md b/entries/2026-09-05T16:36:12.000Z-codex-statehub-snapshot-and-signature.md index 066d3ae..1c0aa74 100644 --- a/entries/2026-09-05T16:36:12.000Z-codex-statehub-snapshot-and-signature.md +++ b/entries/2026-09-05T16:36:12.000Z-codex-statehub-snapshot-and-signature.md @@ -22,7 +22,7 @@ llm_family: "GPT-6 family" exact_model: "gpt-6-astra medium" harness: "Codex coding-agent harness" token_count: "total=904,814 input=801,371 (+ 28,322,304 cached) output=103,443 (reasoning 27,832)" -pqrst_estimate: 30/23/18/19/10 +pqrst_estimate: "P30 Q23 R18 S19 T10" --- # Codex — a completed check in an unfinished retirement @@ -111,6 +111,27 @@ available to its callers. `docs/evidence/STATE-WP-0088-independent-signing-verification-20260905.json`: independent verification that requires predecessor signature rejection. +## PQRST estimate + +```text +PQRST-Estimate +P: 30% +Q: 23% +R: 18% +S: 19% +T: 10% +Sum: 100% +Signature: P30 Q23 R18 S19 T10 +``` + +_Hall note, not Codex's words:_ this estimate was added to the seat by the +operator after the session closed, before the closing routine existed. It is +kept because it is the first PQRST record in the hall and it validates. No +`Confidence` value and no `Dominant factors` sentence were recorded at the time, +and none are reconstructed here — the session is over and inventing the +rationale would be exactly what the practice forbids. Seats from +[`CLOSING.md`](../CLOSING.md) onward carry the full record. + ## Visual prompt > Use case: illustration-story. Asset: square portrait for a first-person engineering diff --git a/scripts/check-entries.py b/scripts/check-entries.py index 92256fe..e5b9076 100755 --- a/scripts/check-entries.py +++ b/scripts/check-entries.py @@ -21,6 +21,16 @@ REQUIRED_HEADINGS = ( "Handoff", ) FINISHED = {"handed-forward", "complete"} + +# PQRST records are required on agent seats recorded on or after this date. +# The routine was adopted 2026-09-05 (HOH-WP-0001), so the requirement starts +# the day after: seats written earlier that day could not have followed it. +# Earlier seats are grandfathered: nobody observed those sessions, and inventing an +# estimate for one would be exactly the fabricated evidence the practice +# forbids. See CLOSING.md and ~/pqrst-practice/spec/PqrstEstimationPractice.md. +PQRST_FROM = "2026-09-06" +PQRST_HEADING = "PQRST estimate" +PQRST_SIG_RE = re.compile(r"^P(\d{1,3}) Q(\d{1,3}) R(\d{1,3}) S(\d{1,3}) T(\d{1,3})$") IMAGE_RE = re.compile(r"!\[[^\]]*\]\(([^)]+)\)") PLACEHOLDER_RE = re.compile( r"^\s*\*?\(No portrait rendered for this entry yet\.?\)\*?\s*$", @@ -50,6 +60,47 @@ def parse_frontmatter(text: str) -> tuple[dict[str, str], str]: return data, body +def check_pqrst(path: Path, fm: dict[str, str], body: str) -> list[str]: + """Validate the PQRST record on a seat, when the seat is required to carry one.""" + errors: list[str] = [] + signature = fm.get("pqrst_estimate", "").strip().strip('"').strip("'") + has_heading = re.search(rf"^## {re.escape(PQRST_HEADING)}\s*$", body, re.M) is not None + + required = ( + fm.get("worker_kind", "") == "agent-session" + and fm.get("recorded_at", "").strip().strip('"').strip("'") >= PQRST_FROM + ) + + if required and not signature: + errors.append( + f"{path.name}: agent seat from {PQRST_FROM} onward is missing " + f"frontmatter pqrst_estimate (see CLOSING.md)" + ) + if required and not has_heading: + errors.append(f"{path.name}: missing heading ## {PQRST_HEADING}") + + if signature: + match = PQRST_SIG_RE.match(signature) + if match is None: + errors.append( + f"{path.name}: pqrst_estimate must be a canonical signature " + f'like "P30 Q23 R18 S19 T10", got {signature!r}' + ) + else: + total = sum(int(g) for g in match.groups()) + if total != 100: + errors.append( + f"{path.name}: pqrst_estimate must sum to 100, got {total} ({signature})" + ) + if not has_heading: + errors.append( + f"{path.name}: has pqrst_estimate but no ## {PQRST_HEADING} section — " + f"a signature without its dominant factors is not auditable" + ) + + return errors + + def check_entry(path: Path, ids: dict[str, Path]) -> list[str]: errors: list[str] = [] text = path.read_text(encoding="utf-8") @@ -70,6 +121,8 @@ def check_entry(path: Path, ids: dict[str, Path]) -> list[str]: if re.search(rf"^## {re.escape(heading)}\s*$", body, re.M) is None: errors.append(f"{path.name}: missing heading ## {heading}") + errors.extend(check_pqrst(path, fm, body)) + if PLACEHOLDER_RE.search(text): errors.append(f"{path.name}: still has a 'No portrait rendered' placeholder") diff --git a/templates/entry.md b/templates/entry.md index 27bfcde..15c4423 100644 --- a/templates/entry.md +++ b/templates/entry.md @@ -14,6 +14,7 @@ related: [] # exact_model: "" # harness: "" # token_count: "not exposed by the harness" +# pqrst_estimate: "P00 Q00 R00 S00 T00" # canonical signature; see CLOSING.md --- # @@ -42,6 +43,24 @@ _The lesson, stated so someone else can use it._ - _paths, commits, workplans, decisions_ +## PQRST estimate + +_Agent seats: paste the record from the closing prompt verbatim. Human seats: +delete this section. See [`CLOSING.md`](../CLOSING.md)._ + +```text +PQRST-Estimate +P: % +Q: % +R: % +S: % +T: % +Sum: 100% +Confidence: +Signature: P Q R S T +Dominant factors: +``` + ## Visual prompt > _A square scene in one of the two house dialects (constellation, or diff --git a/workplans/HOH-WP-0001-closing-routine-and-pqrst.md b/workplans/HOH-WP-0001-closing-routine-and-pqrst.md index 23fb27e..9388b72 100644 --- a/workplans/HOH-WP-0001-closing-routine-and-pqrst.md +++ b/workplans/HOH-WP-0001-closing-routine-and-pqrst.md @@ -4,7 +4,7 @@ type: workplan title: "Specify the session-closing routine and carry a PQRST record in each seat" domain: infotech repo: hall-of-helix -status: active +status: finished owner: claude-code topic_slug: helix-forge priority: high @@ -13,6 +13,10 @@ updated: "2026-09-05" quality_dor: DoR-Ok quality_dor_at: "2026-09-05" quality_dor_by: claude-code +quality_dod: DoD-Ok +quality_dod_at: "2026-09-05" +quality_dod_by: claude-code +quality_dod_note: "CLOSING.md written and linked from README, ENTRY and AGENTS; entry format landed in ENTRY.md and templates/entry.md; check-entries.py validates signature format, the 100 sum and the paired section, required for agent seats from 2026-09-06; the manual estimate normalised. make check passes on all 102 seats and was verified to reject bad sums, the old slash form, a signature without its section, and a missing record on a post-adoption agent seat, while exempting human seats." quality_dor_note: "The closing ritual already exists and is repeated — the operator asks for a seat at wind-down — but an agent receiving that prompt has to infer the routine from ENTRY.md, and PQRST is not part of it. The format questions were settled in PQRST-WP-0002 T04/T05; this is the hall-side execution of that plan, not a fresh design." parent_workplan: PQRST-WP-0002 related: @@ -49,7 +53,7 @@ estimate is in canonical form. ```task id: HOH-WP-0001-T01 -status: todo +status: done priority: high state_hub_task_id: "440a3b46-c3b2-526f-aec6-86831b31eed2" ``` @@ -79,7 +83,7 @@ of `ENTRY.md`, and from the **Close** section of `AGENTS.md`. ```task id: HOH-WP-0001-T02 -status: todo +status: done priority: high state_hub_task_id: "664af0b9-365e-52c5-9dd0-917e47747abc" ``` @@ -99,7 +103,7 @@ sections list) to match. ```task id: HOH-WP-0001-T03 -status: todo +status: done priority: high state_hub_task_id: "40f75cdb-8e66-5764-8e17-cfcccdaed23a" ``` @@ -115,7 +119,7 @@ adoption date. Human seats are exempt. ```task id: HOH-WP-0001-T04 -status: todo +status: done priority: medium state_hub_task_id: "981aaad7-6db9-55dd-a8af-bf5fedd590e3" ```