opencode-thrum-pro 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (101) hide show
  1. package/assets/commands/thrum-_deviations-protocol.md +87 -0
  2. package/assets/commands/thrum-_generator-idempotency-protocol.md +15 -0
  3. package/assets/commands/thrum-_project-rules-protocol.md +18 -0
  4. package/assets/commands/thrum-_snapshot-protocol.md +265 -0
  5. package/assets/commands/thrum-_stamp-protocol.md +112 -0
  6. package/assets/commands/thrum-_verify-before-write-protocol.md +27 -0
  7. package/assets/commands/thrum-inbox.md +22 -0
  8. package/assets/commands/thrum-load-context.md +17 -0
  9. package/assets/commands/thrum-overview.md +17 -0
  10. package/assets/commands/thrum-prime.md +30 -0
  11. package/assets/commands/thrum-quickstart.md +14 -0
  12. package/assets/commands/thrum-reply.md +28 -0
  13. package/assets/commands/thrum-restart-extended.md +195 -0
  14. package/assets/commands/thrum-restart.md +293 -0
  15. package/assets/commands/thrum-send.md +31 -0
  16. package/assets/commands/thrum-sleep-extended.md +186 -0
  17. package/assets/commands/thrum-sleep.md +212 -0
  18. package/assets/commands/thrum-team.md +12 -0
  19. package/assets/commands/thrum-update-project.md +259 -0
  20. package/assets/commands/thrum-wait.md +14 -0
  21. package/assets/skills/adversarial-critique/SKILL.md +242 -0
  22. package/assets/skills/brainstorm-queue-aware/SKILL.md +167 -0
  23. package/assets/skills/brainstorm-steward/SKILL.md +181 -0
  24. package/assets/skills/choosing-subagent-models/SKILL.md +244 -0
  25. package/assets/skills/closing-findings-while-warm/SKILL.md +104 -0
  26. package/assets/skills/configure-roles/SKILL.md +229 -0
  27. package/assets/skills/coordinator-assessing-agent-completion/SKILL.md +205 -0
  28. package/assets/skills/coordinator-assessing-agent-completion/scan.py +117 -0
  29. package/assets/skills/coordinator-branch-split-on-block/SKILL.md +168 -0
  30. package/assets/skills/coordinator-context-monitoring/SKILL.md +674 -0
  31. package/assets/skills/coordinator-dispatching-work/SKILL.md +288 -0
  32. package/assets/skills/coordinator-hotpath-merge-gate/SKILL.md +522 -0
  33. package/assets/skills/coordinator-interacting-with-the-owner/SKILL.md +171 -0
  34. package/assets/skills/coordinator-maintaining-memory/SKILL.md +89 -0
  35. package/assets/skills/coordinator-managing-state-and-lifecycle/SKILL.md +192 -0
  36. package/assets/skills/coordinator-merging-code/SKILL.md +331 -0
  37. package/assets/skills/coordinator-philosophy-merge-gate/SKILL.md +442 -0
  38. package/assets/skills/coordinator-plan-reconcile-gate/SKILL.md +198 -0
  39. package/assets/skills/coordinator-post-restart-sweep/SKILL.md +135 -0
  40. package/assets/skills/coordinator-running-autonomous-feature-development/SKILL.md +199 -0
  41. package/assets/skills/coordinator-running-brainstorm-cycles/SKILL.md +654 -0
  42. package/assets/skills/coordinator-running-review-cycles/SKILL.md +153 -0
  43. package/assets/skills/coordinator-single-responsibility-merge-gate/SKILL.md +14 -0
  44. package/assets/skills/diagnosing-fleet-and-daemon/SKILL.md +255 -0
  45. package/assets/skills/efficient-multi-agent-research/SKILL.md +177 -0
  46. package/assets/skills/fixing-documentation-errors/SKILL.md +258 -0
  47. package/assets/skills/implementer-maintaining-memory/SKILL.md +84 -0
  48. package/assets/skills/implementer-orchestrating-execution/SKILL.md +125 -0
  49. package/assets/skills/implementer-receiving-dispatch/SKILL.md +127 -0
  50. package/assets/skills/implementer-receiving-review-feedback/SKILL.md +125 -0
  51. package/assets/skills/implementer-status-and-handoff/SKILL.md +150 -0
  52. package/assets/skills/implementer-tdd-and-quality/SKILL.md +99 -0
  53. package/assets/skills/memory-audit-recover/SKILL.md +153 -0
  54. package/assets/skills/memory-curate/SKILL.md +139 -0
  55. package/assets/skills/memory-maintenance/SKILL.md +87 -0
  56. package/assets/skills/memory-read-discipline/SKILL.md +164 -0
  57. package/assets/skills/memory-search-advanced/SKILL.md +217 -0
  58. package/assets/skills/memory-write-discipline/SKILL.md +135 -0
  59. package/assets/skills/orchestrate/SKILL.md +795 -0
  60. package/assets/skills/persistent-watcher-archetype/SKILL.md +225 -0
  61. package/assets/skills/prime-agent/SKILL.md +92 -0
  62. package/assets/skills/project-hotpath-gate/SKILL.md +255 -0
  63. package/assets/skills/project-philosophy/SKILL.md +418 -0
  64. package/assets/skills/project-philosophy/resources/philosophy-template.md +155 -0
  65. package/assets/skills/project-philosophy/resources/reliability-class-library.md +653 -0
  66. package/assets/skills/project-setup/SKILL.md +1007 -0
  67. package/assets/skills/project-setup/resources/implementation-agent.md +826 -0
  68. package/assets/skills/researcher-answering-queries/SKILL.md +100 -0
  69. package/assets/skills/researcher-investigating/SKILL.md +152 -0
  70. package/assets/skills/researcher-maintaining-memory/SKILL.md +176 -0
  71. package/assets/skills/state-migration/SKILL.md +54 -0
  72. package/assets/skills/thrum/SKILL.md +161 -0
  73. package/assets/skills/thrum/resources/ANTI_PATTERNS.md +132 -0
  74. package/assets/skills/thrum/resources/BOUNDARIES.md +56 -0
  75. package/assets/skills/thrum/resources/CLI_REFERENCE.md +1066 -0
  76. package/assets/skills/thrum/resources/IDENTITY.md +49 -0
  77. package/assets/skills/thrum/resources/LISTENER_PATTERN.md +64 -0
  78. package/assets/skills/thrum/resources/MESSAGING.md +163 -0
  79. package/assets/skills/thrum/resources/TMUX_SESSIONS.md +118 -0
  80. package/assets/skills/thrum/resources/WORKTREES.md +117 -0
  81. package/assets/skills/thrum-memory/SKILL.md +138 -0
  82. package/assets/skills/trace-spec-to-plan/SKILL.md +104 -0
  83. package/assets/skills/trace-spec-to-plan/resources/sweep-agent-prompt.md +57 -0
  84. package/assets/skills/update-queue/SKILL.md +149 -0
  85. package/assets/skills/using-the-queue/SKILL.md +172 -0
  86. package/assets/skills/using-thrum-state/SKILL.md +104 -0
  87. package/assets/skills/verify-against-plan/SKILL.md +323 -0
  88. package/assets/skills/verify-against-source/SKILL.md +237 -0
  89. package/assets/skills/watcher-archetype/SKILL.md +84 -0
  90. package/assets/skills/writing-durable-markdown/SKILL.md +66 -0
  91. package/dist/hooks/block-sync-cd.d.ts +9 -0
  92. package/dist/hooks/block-sync-cd.js +71 -0
  93. package/dist/hooks/block-sync-cd.test.d.ts +1 -0
  94. package/dist/hooks/block-sync-cd.test.js +61 -0
  95. package/dist/hooks/shell-env.d.ts +8 -0
  96. package/dist/hooks/shell-env.js +22 -0
  97. package/dist/index.d.ts +6 -0
  98. package/dist/index.js +25 -0
  99. package/dist/installer.d.ts +2 -0
  100. package/dist/installer.js +86 -0
  101. package/package.json +49 -0
@@ -0,0 +1,195 @@
1
+ ---
2
+ description:
3
+ Save a comprehensive 16-section restart snapshot and prepare for session
4
+ restart. Use for designer/architect-grade handoffs needing wire contracts,
5
+ capability matrix, anticipated Q&A, and design rationale that the standard
6
+ /thrum:restart compact format cannot carry.
7
+ ---
8
+
9
+ # Session Restart — Extended (16-section snapshot)
10
+
11
+ Compose a comprehensive 16-section prose continuation, write it directly to your
12
+ restart file, then orchestrate the handoff. The extended structure is
13
+ fundamentally different from standard: it preserves wire contracts (types +
14
+ signatures + file:line cites), capability matrices (per-surface row-by-row
15
+ tables), anticipated implementer Q&A, design inventory (entanglement classes /
16
+ pattern catalogue), and locked decision rationale. Use this variant when the
17
+ next session may be cold and must recover the full design grammar from this
18
+ artifact alone.
19
+
20
+ ## When to use extended vs standard
21
+
22
+ - **Use `/thrum:restart` (standard)** for routine context-exhaustion or
23
+ rate-limit restarts where the work is well-trafficked and future-you can
24
+ reconstruct from project state + recent inbox + a compact 11-section snapshot.
25
+ - **Use `/thrum:restart-extended` (this variant)** for designer/architect-grade
26
+ handoffs: locking a complex brainstorm with multiple owner-decided forks,
27
+ handing off a fanout implementation (≥3 call sites or ≥2 epics), or any
28
+ session where the next session may be a fresh restart and must recover
29
+ wire-contract precision without re-reading the source files.
30
+
31
+ ## Steps
32
+
33
+ ### 1. Resolve identity and your worktree (run BEFORE reading the partial)
34
+
35
+ ```bash
36
+ # $REPO must be YOUR worktree — the directory `thrum prime` reads the restart
37
+ # snapshot back from. Resolve it from the daemon's authoritative identity, NOT
38
+ # `git rev-parse` (which keys off the current shell CWD and would write to the
39
+ # wrong .thrum/restart/ if a bash step left your worktree). Fall back to git
40
+ # only if whoami can't answer.
41
+ REPO=$(thrum whoami --field worktree 2>/dev/null)
42
+ [ -n "$REPO" ] || REPO=$(git rev-parse --show-toplevel) || { echo "ERROR: cannot resolve your worktree"; exit 1; }
43
+ AGENT=$(thrum whoami --field agent_id) || { echo "ERROR: agent not registered"; exit 1; }
44
+ [ -n "$AGENT" ] || { echo "ERROR: empty agent_id"; exit 1; }
45
+ mkdir -p "${REPO}/.thrum/restart"
46
+ ```
47
+
48
+ (Step 1 is inlined here because the partial's own path resolves through
49
+ `$REPO`.)
50
+
51
+ ### 2. Read the shared snapshot-composition partial
52
+
53
+ Read the partial at the absolute path:
54
+
55
+ ```text
56
+ ${REPO}/claude-plugin/commands/_snapshot-protocol.md
57
+ ```
58
+
59
+ It carries the CRITICAL DISCIPLINE block and BOTH the standard 11-section
60
+ structure and the EXTENDED 16-section structure with per-section guidance.
61
+
62
+ **Use the EXTENDED 16-section structure.** The structure block is `§1.` through
63
+ `§16.` with the per-section guidance documented in the partial.
64
+
65
+ ### 3. Write the continuation
66
+
67
+ Per Step 3 of the partial, use the Write tool to save your composed continuation
68
+ to `${REPO}/.thrum/restart/${AGENT}.md`. `thrum prime` auto-injects this file on
69
+ next session start regardless of whether wake comes from `thrum tmux restart` or
70
+ operator-initiated `thrum tmux create`.
71
+
72
+ ### 4. Check session type and your role
73
+
74
+ ```bash
75
+ SESSION_RAW=$(thrum whoami --field tmux_session)
76
+ # thrum whoami --field tmux_session returns a PANE-QUALIFIED value
77
+ # (e.g. "thrum-xyz-lifecycle-cmds:0.0"), not a session name. `thrum tmux restart`
78
+ # takes a session NAME and the daemon sanitizes ":"/"." to "-", so passing the
79
+ # raw value produces a lookup key ("thrum-xyz-lifecycle-cmds-0-0") that does not
80
+ # exist and every self-restart would fail. Strip to the bare session name:
81
+ SESSION=${SESSION_RAW%%:*}
82
+ ROLE=$(thrum whoami --field role)
83
+ echo "tmux_session_raw=$SESSION_RAW tmux_session=$SESSION role=$ROLE"
84
+ ```
85
+
86
+ ### 5. Verify your snapshot before any self-restart (the gate)
87
+
88
+ **Self-restart is authorised ONLY after you verify your OWN snapshot on disk.**
89
+ Restarting without a verified snapshot destroys the context the restart exists
90
+ to preserve — strictly worse than idling. Verify the EFFECT, not the action: a
91
+ vague "I wrote it" is not verification; check the FILE.
92
+
93
+ ```bash
94
+ SNAPSHOT="${REPO}/.thrum/restart/${AGENT}.md"
95
+ NOW=$(date +%s)
96
+ MTIME=$(stat -f %m "$SNAPSHOT" 2>/dev/null || stat -c %Y "$SNAPSHOT" 2>/dev/null)
97
+ AGE=$(( NOW - ${MTIME:-0} ))
98
+ SNAPSHOT_OK=1
99
+
100
+ if [ ! -f "$SNAPSHOT" ]; then
101
+ echo "VERIFY FAILED: no snapshot at $SNAPSHOT"; SNAPSHOT_OK=0
102
+ elif [ ! -s "$SNAPSHOT" ]; then
103
+ echo "VERIFY FAILED: snapshot at $SNAPSHOT is empty"; SNAPSHOT_OK=0
104
+ elif [ ! -r "$SNAPSHOT" ]; then
105
+ echo "VERIFY FAILED: snapshot at $SNAPSHOT is not readable"; SNAPSHOT_OK=0
106
+ elif [ "$AGE" -gt 300 ]; then
107
+ echo "VERIFY FAILED: snapshot at $SNAPSHOT is ${AGE}s old — stale (from a prior restart), not this session's write"; SNAPSHOT_OK=0
108
+ else
109
+ echo "VERIFY OK: snapshot exists, non-empty, readable, written ${AGE}s ago"
110
+ fi
111
+
112
+ # The snapshot gate alone is not enough — the RESTART TARGET must also
113
+ # resolve. Guard the stripped session name the same way: if it doesn't
114
+ # resolve to a real tmux session, that's a verification failure too, not an
115
+ # excuse to attempt a restart against a bad target.
116
+ SESSION_OK=1
117
+ if [ -n "$SESSION" ] && tmux has-session -t "$SESSION" 2>/dev/null; then
118
+ echo "VERIFY OK: tmux session '$SESSION' resolves"
119
+ else
120
+ echo "VERIFY FAILED: tmux session '$SESSION' (stripped from '$SESSION_RAW') does not resolve to a live tmux session"
121
+ SESSION_OK=0
122
+ fi
123
+ ```
124
+
125
+ **"Properly" means, explicitly:** snapshot exists at your OWN worktree's
126
+ `.thrum/restart/<your-agent-id>.md`, non-empty, readable, AND recently written
127
+ by Step 3 of THIS session (not a leftover from a previous restart that Step 3
128
+ silently failed to overwrite) — AND the stripped session name resolves to a
129
+ real, live tmux session.
130
+
131
+ **FAIL DIRECTION — stated explicitly:** if EITHER check fails, DO NOT RESTART.
132
+ Report and hold (see the failure branch below). Refusal is safe; an unverified
133
+ self-restart, or one aimed at a target that doesn't exist, is unrecoverable —
134
+ strictly worse than waiting.
135
+
136
+ ### 6. Self-restart (tmux) or hand off (no tmux)
137
+
138
+ Use `$SESSION`, `$ROLE`, `$SNAPSHOT_OK`, and `$SESSION_OK` from Steps 4-5.
139
+
140
+ **If `$SESSION` is non-empty (you are in tmux) AND `$SNAPSHOT_OK` = 1 AND
141
+ `$SESSION_OK` = 1** — run the self-restart yourself, right now, in this turn:
142
+
143
+ ```bash
144
+ thrum tmux restart "$SESSION"
145
+ ```
146
+
147
+ **⚠️ PLAIN RESTART — NEVER `--force`.** `--force` **DROPS the `--model` pin**; a
148
+ plain restart re-applies it at the readiness probe. A self-restarting agent
149
+ that uses `--force` can come back on the WRONG MODEL, and `runtime-config get`
150
+ will NOT reveal it — it reports the stored pin, not the delivered keystrokes.
151
+ The command above restarts your own pane; you will not see further
152
+ output in this turn. Do not follow it with more commands. Only reach for
153
+ `--force` if a plain restart genuinely does not take — and even then,
154
+ immediately re-pin and **verify the model OFF THE PANE** after you come back,
155
+ not off `runtime-config get`.
156
+
157
+ This applies whether you are a coordinator or any other role — there is no
158
+ requirement for a senior agent to run this for you; it is the same
159
+ self-executed command `thrum:sleep` already uses for its own tmux-kill.
160
+ **This ADDS a self-initiated route and does not remove the external ones**:
161
+ force-restart-at-high-context and operator/coordinator-initiated restart still
162
+ exist for the cases where self-restart isn't possible (e.g. verification
163
+ failed, or you're not in tmux).
164
+
165
+ **If `$SESSION` is non-empty but `$SNAPSHOT_OK` = 0 or `$SESSION_OK` = 0** —
166
+ DO NOT RESTART. Report and hold:
167
+
168
+ ```bash
169
+ thrum send --to @your_coordinator --stdin <<'EOF'
170
+ Restart (extended) verification FAILED — holding, not self-restarting.
171
+ Reason: <paste the VERIFY FAILED line(s) from Step 5>
172
+ Snapshot path checked: ${REPO}/.thrum/restart/${AGENT}.md
173
+ Session target checked: ${SESSION} (raw: ${SESSION_RAW})
174
+ EOF
175
+ ```
176
+
177
+ If you ARE the top-level coordinator (no senior agent above you), print the same
178
+ failure reason for the operator instead of sending it, and hold.
179
+
180
+ **Else (no tmux session)** — self-restart has nothing to target (there is no
181
+ tmux pane to run `thrum tmux restart` against). Print these instructions for
182
+ the operator:
183
+
184
+ > Restart snapshot saved at `.thrum/restart/${AGENT}.md`. To continue in a new
185
+ > session:
186
+ >
187
+ > 1. Exit this session
188
+ > 2. Start a new session in the same directory
189
+ > 3. The snapshot will be auto-loaded by `thrum prime`
190
+
191
+ ## After Restart: Session Archive
192
+
193
+ After restart, your snapshot moves to `.thrum/agents/<your-agent-id>/sessions/`
194
+ and stays there as a persistent log entry. Same mechanism as standard restart —
195
+ see `/thrum:restart` for archive browsing commands.
@@ -0,0 +1,293 @@
1
+ ---
2
+ description:
3
+ Save a conversation snapshot and prepare for session restart. Use when you
4
+ need a fresh session due to context exhaustion, rate limits, or stuck state.
5
+ ---
6
+
7
+ # Session Restart
8
+
9
+ Compose a prose continuation, write it directly to your restart file, then
10
+ orchestrate the handoff.
11
+
12
+ ## Steps
13
+
14
+ ### 1. Resolve your identity and your worktree
15
+
16
+ ```bash
17
+ # $REPO must be YOUR worktree — the directory `thrum prime` reads the restart
18
+ # snapshot back from. Resolve it from the daemon's authoritative identity, NOT
19
+ # `git rev-parse` (which keys off the current shell CWD and would write to the
20
+ # wrong .thrum/restart/ if a bash step left your worktree). Fall back to git
21
+ # only if whoami can't answer.
22
+ REPO=$(thrum whoami --field worktree 2>/dev/null)
23
+ [ -n "$REPO" ] || REPO=$(git rev-parse --show-toplevel) || { echo "ERROR: cannot resolve your worktree"; exit 1; }
24
+ AGENT=$(thrum whoami --field agent_id) || { echo "ERROR: agent not registered"; exit 1; }
25
+ [ -n "$AGENT" ] || { echo "ERROR: empty agent_id"; exit 1; }
26
+ mkdir -p "${REPO}/.thrum/restart"
27
+ ```
28
+
29
+ ### 2. Compose your continuation
30
+
31
+ Your context is high and we want to restart without losing the decisions we've
32
+ made. Write a rich continuation that future-you will read as the first action
33
+ after restart.
34
+
35
+ #### §1 Big picture — REQUIRED FIRST SECTION (write this BEFORE anything else)
36
+
37
+ Every restart snapshot MUST begin with a section using this exact heading:
38
+
39
+ ```text
40
+ ## 1. Big picture — what shipped this session
41
+ ```
42
+
43
+ Followed by 1-3 sentences (a single paragraph or up to 3 short ones) summarizing
44
+ what the session accomplished. Be specific: name the artifacts, the decisions,
45
+ the cycles closed. Examples:
46
+
47
+ > Locked the session-archive spec v2 with §1 Big picture requirement, five
48
+ > Q-Spec approvals, and Q-Spec-5 deferred to impl-time. Hand-off pending
49
+ > coordinator final review.
50
+ >
51
+ > Investigated rc.9 inbox-race against <implementer>'s hypothesis: confirmed
52
+ > the lock-substrate fence is the right fix. Filed thrum-XXX with 4 BLOCKING
53
+ > evidence points.
54
+ >
55
+ > Closed <epic> brainstormer-third pass. 2 BLOCKING + 5 IMPORTANT + 10 MINOR.
56
+ > All three load-bearing traps PASSed. Standing by for <epic> next batch.
57
+
58
+ This section becomes YOUR OWN log entry, visible in `thrum agent sessions list`
59
+ alongside the archives of every other session you've ever restarted from.
60
+ Future-you (and other agents inspecting your history) skim §1 to decide which
61
+ sessions are worth re-reading. Write it first — before the Resume Plan, before
62
+ file paths, before patterns — because composing the §1 summary forces you to
63
+ identify what was actually load-bearing about this session, and that priority
64
+ shapes everything else you write below it.
65
+
66
+ **Stamp your snapshot with the base it was authored against.**
67
+ Derive and emit the **Authored-against** stamp per
68
+ `claude-plugin/commands/_stamp-protocol.md` and place it at the very top of your
69
+ §1 section (that protocol computes the SHA and merge_target for you — never
70
+ hand-type them). This is what lets `thrum prime` diff your snapshot at the next
71
+ wake and flag which cited files have MOVED; an unstamped snapshot reads as
72
+ "current", indistinguishable from one that never drifted.
73
+
74
+ After the §1 block:
75
+
76
+ CRITICAL DISCIPLINE — compose from your own working context only. To preserve
77
+ the remaining runway:
78
+
79
+ - Do NOT dispatch sub-agents (Agent, Explore, etc.)
80
+ - Do NOT re-read files you've already read this session
81
+ - Do NOT spawn web fetches or external lookups
82
+ - Do NOT run lengthy investigations (git log spelunking, codebase searches,
83
+ multi-file grep walks)
84
+
85
+ Each of those costs context you don't have to spend, and the cost compounds — a
86
+ sub-agent that returns 6K tokens of summary doesn't just cost the dispatch, it
87
+ pollutes the dying session further. If a fact isn't already in your working
88
+ context, label it "unknown" or "verify post-restart" rather than fetching it
89
+ now. Trust your in-context state.
90
+
91
+ Write for a competent stranger in your role — someone who has the runtime
92
+ briefing (`thrum prime`, role preamble, project state) but none of this
93
+ session's conversation context. Refer to the previous session in third person.
94
+
95
+ Use these numbered sections (write each as prose or table — your call — but the
96
+ numbered structure itself should be present):
97
+
98
+ 1. **Big picture** — what shipped this session (REQUIRED FIRST, written above
99
+ per the §1 mandate).
100
+ 2. **Where every artifact stands** — branches, specs, plans, in-flight PRs,
101
+ partially-landed work. Concrete tips / paths / commit SHAs.
102
+ 3. **Players + contributions** — who's working on what, who's standing down,
103
+ what each agent's latest state is.
104
+ 4. **Decisions made this session** — with the context that drove each. Just
105
+ listing the decision loses the reasoning future-you needs to judge edge
106
+ cases.
107
+ 5. **Questions awaiting repo owner input** — anything queued for the project
108
+ owner's call before work can proceed. Name the question concretely.
109
+ 6. **Outstanding work you owe** — commitments still open on your side (pushes,
110
+ merges, dispatches, doc-patches).
111
+ 7. **Patterns that worked / burned us** — short reflective section: what to keep
112
+ doing, what to stop. Two sub-sections is enough.
113
+ 8. **File paths future-you will reopen** — concrete paths the next session will
114
+ need. Group by purpose (in-flight / queued / reference).
115
+ 9. **Numbered resume plan** — concrete first-N-steps the next session should
116
+ take, in order. Step 1 must be actionable from a cold start.
117
+ 10. **Honest unknowns — verify post-restart, do NOT fabricate** — list facts you
118
+ suspect changed during the session OR were never confirmed in the first
119
+ place. Future-you must NOT carry these forward as truth until they're
120
+ verified (e.g., "whether @impl_X has progressed past Task N", "exact branch
121
+ tip — listed as ~SHA but multiple FF merges may have happened during the
122
+ snapshot write", "whether the keepalive cron survived restart").
123
+ 11. **End-of-continuation note** — one short paragraph reflecting on the session
124
+ itself. What was the dominant pattern this session, what pattern proved
125
+ load-bearing, what's a known fragility going into the next one.
126
+
127
+ Skip a section only when it genuinely doesn't apply — an honest "N/A: no
128
+ decisions this session" beats fabrication. The numbered structure itself should
129
+ always be present so future-you can scan for what's covered and what isn't.
130
+
131
+ ### 3. Write the continuation directly to your restart file
132
+
133
+ Use your Write tool to save the composed continuation to:
134
+
135
+ ```text
136
+ ${REPO}/.thrum/restart/${AGENT}.md
137
+ ```
138
+
139
+ `thrum prime` will auto-inject this file at next session start. No bash heredoc
140
+ or `cat <<EOF` redirection is needed — write the file directly.
141
+
142
+ ### 4. Check session type and your role
143
+
144
+ ```bash
145
+ SESSION_RAW=$(thrum whoami --field tmux_session)
146
+ # thrum whoami --field tmux_session returns a PANE-QUALIFIED value
147
+ # (e.g. "thrum-xyz-lifecycle-cmds:0.0"), not a session name. `thrum tmux restart`
148
+ # takes a session NAME and the daemon sanitizes ":"/"." to "-", so passing the
149
+ # raw value produces a lookup key ("thrum-xyz-lifecycle-cmds-0-0") that does not
150
+ # exist and every self-restart would fail. Strip to the bare session name:
151
+ SESSION=${SESSION_RAW%%:*}
152
+ ROLE=$(thrum whoami --field role)
153
+ echo "tmux_session_raw=$SESSION_RAW tmux_session=$SESSION role=$ROLE"
154
+ ```
155
+
156
+ ### 5. Verify your snapshot before any self-restart (the gate)
157
+
158
+ **Self-restart is authorised ONLY after you verify your OWN snapshot on disk.**
159
+ Restarting without a verified snapshot destroys the context the restart exists
160
+ to preserve — strictly worse than idling. Verify the EFFECT, not the action: a
161
+ vague "I wrote it" is not verification; check the FILE.
162
+
163
+ ```bash
164
+ SNAPSHOT="${REPO}/.thrum/restart/${AGENT}.md"
165
+ NOW=$(date +%s)
166
+ MTIME=$(stat -f %m "$SNAPSHOT" 2>/dev/null || stat -c %Y "$SNAPSHOT" 2>/dev/null)
167
+ AGE=$(( NOW - ${MTIME:-0} ))
168
+ SNAPSHOT_OK=1
169
+
170
+ if [ ! -f "$SNAPSHOT" ]; then
171
+ echo "VERIFY FAILED: no snapshot at $SNAPSHOT"; SNAPSHOT_OK=0
172
+ elif [ ! -s "$SNAPSHOT" ]; then
173
+ echo "VERIFY FAILED: snapshot at $SNAPSHOT is empty"; SNAPSHOT_OK=0
174
+ elif [ ! -r "$SNAPSHOT" ]; then
175
+ echo "VERIFY FAILED: snapshot at $SNAPSHOT is not readable"; SNAPSHOT_OK=0
176
+ elif [ "$AGE" -gt 300 ]; then
177
+ echo "VERIFY FAILED: snapshot at $SNAPSHOT is ${AGE}s old — stale (from a prior restart), not this session's write"; SNAPSHOT_OK=0
178
+ else
179
+ echo "VERIFY OK: snapshot exists, non-empty, readable, written ${AGE}s ago"
180
+ fi
181
+
182
+ # The snapshot gate alone is not enough — the RESTART TARGET must also
183
+ # resolve. Guard the stripped session name the same way: if it doesn't
184
+ # resolve to a real tmux session, that's a verification failure too, not an
185
+ # excuse to attempt a restart against a bad target.
186
+ SESSION_OK=1
187
+ if [ -n "$SESSION" ] && tmux has-session -t "$SESSION" 2>/dev/null; then
188
+ echo "VERIFY OK: tmux session '$SESSION' resolves"
189
+ else
190
+ echo "VERIFY FAILED: tmux session '$SESSION' (stripped from '$SESSION_RAW') does not resolve to a live tmux session"
191
+ SESSION_OK=0
192
+ fi
193
+ ```
194
+
195
+ **"Properly" means, explicitly:** snapshot exists at your OWN worktree's
196
+ `.thrum/restart/<your-agent-id>.md`, non-empty, readable, AND recently written
197
+ by Step 3 of THIS session (not a leftover from a previous restart that Step 3
198
+ silently failed to overwrite) — AND the stripped session name resolves to a
199
+ real, live tmux session.
200
+
201
+ **FAIL DIRECTION — stated explicitly:** if EITHER check fails, DO NOT RESTART.
202
+ Report and hold (see the failure branch below). Refusal is safe; an unverified
203
+ self-restart, or one aimed at a target that doesn't exist, is unrecoverable —
204
+ strictly worse than waiting.
205
+
206
+ ### 6. Self-restart (tmux) or hand off (no tmux)
207
+
208
+ Use `$SESSION`, `$ROLE`, `$SNAPSHOT_OK`, and `$SESSION_OK` from Steps 4-5.
209
+
210
+ **If `$SESSION` is non-empty (you are in tmux) AND `$SNAPSHOT_OK` = 1 AND
211
+ `$SESSION_OK` = 1** — run the self-restart yourself, right now, in this turn:
212
+
213
+ ```bash
214
+ thrum tmux restart "$SESSION"
215
+ ```
216
+
217
+ **⚠️ PLAIN RESTART — NEVER `--force`.** `--force` **DROPS the `--model` pin**; a
218
+ plain restart re-applies it at the readiness probe. A self-restarting agent
219
+ that uses `--force` can come back on the WRONG MODEL, and `runtime-config get`
220
+ will NOT reveal it — it reports the stored pin, not the delivered keystrokes.
221
+ The command above restarts your own pane; you
222
+ will not see further output in this turn. Do not follow it with more commands.
223
+ Only reach for `--force` if a plain restart genuinely does not take — and even
224
+ then, immediately re-pin and **verify the model OFF THE PANE** after you come
225
+ back, not off `runtime-config get`.
226
+
227
+ This applies whether you are a coordinator or any other role — there is no
228
+ requirement for a senior agent to run this for you; it is the same
229
+ self-executed command `thrum:sleep` already uses for its own tmux-kill.
230
+ **This ADDS a self-initiated route and does not remove the external ones**:
231
+ force-restart-at-high-context and operator/coordinator-initiated restart still
232
+ exist for the cases where self-restart isn't possible (e.g. verification
233
+ failed, or you're not in tmux).
234
+
235
+ **If `$SESSION` is non-empty but `$SNAPSHOT_OK` = 0 or `$SESSION_OK` = 0** —
236
+ DO NOT RESTART. Report and hold:
237
+
238
+ ```bash
239
+ thrum send --to @your_coordinator --stdin <<'EOF'
240
+ Restart verification FAILED — holding, not self-restarting.
241
+ Reason: <paste the VERIFY FAILED line(s) from Step 5>
242
+ Snapshot path checked: ${REPO}/.thrum/restart/${AGENT}.md
243
+ Session target checked: ${SESSION} (raw: ${SESSION_RAW})
244
+ EOF
245
+ ```
246
+
247
+ If you ARE the top-level coordinator (no senior agent above you), print the same
248
+ failure reason for the operator instead of sending it, and hold.
249
+
250
+ **Else (no tmux session)** — self-restart has nothing to target (there is no
251
+ tmux pane to run `thrum tmux restart` against). Print these instructions for
252
+ the operator:
253
+
254
+ > Restart snapshot saved at `.thrum/restart/${AGENT}.md`. To continue in a new
255
+ > session:
256
+ >
257
+ > 1. Exit this session
258
+ > 2. Start a new session in the same directory
259
+ > 3. The snapshot will be auto-loaded by `thrum prime`
260
+
261
+ ## When to Use
262
+
263
+ - Context window is getting full (you're seeing compaction warnings)
264
+ - You've hit rate limits and need to wait
265
+ - Your session feels stuck or unproductive
266
+ - The operator or coordinator has asked you to restart
267
+
268
+ ## After Restart: Session Archive
269
+
270
+ After restart, your snapshot doesn't disappear — it moves to
271
+ `.thrum/agents/<your-agent-id>/sessions/` and stays there as a persistent log
272
+ entry. Browse the archive with:
273
+
274
+ ```bash
275
+ thrum agent sessions list # default: this agent
276
+ thrum agent sessions list --verbose # full §1 bodies inline
277
+ thrum agent sessions list --json # NDJSON for scripts
278
+ thrum agent sessions list --all # every agent, grouped
279
+ ```
280
+
281
+ Permissions are user-only (`0600` for each snapshot file, `0700` for the
282
+ sessions folder). Operators on multi-user machines must copy explicitly to share
283
+ archives with another account.
284
+
285
+ Worktree-resident ephemeral agents archive into the worktree's own
286
+ `.thrum/agents/<id>/sessions/` — so the archive vanishes when the worktree is
287
+ removed. **By design.** If an ephemeral agent's history matters across the
288
+ worktree teardown, export those snapshots manually before `git worktree remove`.
289
+
290
+ The next session's `thrum prime` output includes a "Past Sessions" discovery
291
+ hint summarizing the most recent archive's §1 — so future-you gets a one-line
292
+ reminder of last session's headline without re-reading the full snapshot. That
293
+ hint is why §1 above is required.
@@ -0,0 +1,31 @@
1
+ ---
2
+ description: Send a message to an agent
3
+ ---
4
+
5
+ Send a direct message or broadcast.
6
+
7
+ If arguments are provided, use them. Otherwise ask for recipient and message
8
+ content.
9
+
10
+ ```bash
11
+ thrum send --to @agent_name --stdin <<'EOF' # Direct message (quoted heredoc body)
12
+ message here
13
+ EOF
14
+ thrum send --to @everyone --stdin <<'EOF' # Broadcast to all agents
15
+ message here
16
+ EOF
17
+ ```
18
+
19
+ Unknown recipients are a hard error. Use `thrum team` to verify agent names
20
+ before sending.
21
+
22
+ If the body has backticks, `$(...)`, `$VAR`, or quotes, pass it via a quoted
23
+ heredoc so the shell doesn't corrupt it:
24
+
25
+ ```bash
26
+ thrum send --to @agent_name --stdin <<'EOF'
27
+ Run `make build`, then check $(git rev-parse HEAD).
28
+ EOF
29
+ ```
30
+
31
+ `--body-file <path>` reads from a file; the body argument `-` is a stdin alias.