@getpipher/armory-todo 0.5.5 → 0.7.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.
- package/README.md +74 -7
- package/docs/superpowers/plans/2026-07-29-reap-safety-protocol.md +858 -0
- package/docs/superpowers/specs/2026-07-29-reap-safety-protocol-design.md +187 -0
- package/extensions/todo.ts +112 -7
- package/package.json +2 -2
- package/src/archive.ts +1 -1
- package/src/config.ts +35 -2
- package/src/health.ts +21 -3
- package/src/index.d.ts +5 -1
- package/src/index.ts +1 -0
- package/src/panel-data.ts +26 -2
- package/src/panel.ts +22 -6
- package/src/reap.ts +90 -0
- package/src/todo-store.ts +8 -2
- package/src/triage-prompt.ts +81 -0
- package/src/triage.ts +474 -0
package/README.md
CHANGED
|
@@ -16,7 +16,7 @@
|
|
|
16
16
|
</p>
|
|
17
17
|
|
|
18
18
|
<p align="center">
|
|
19
|
-
<strong>lifecycle boxes</strong> · <strong>title + notes</strong> · <strong>auto-prune</strong> · <strong>interactive panel</strong> · <strong>health diagnostics</strong> · <strong>hard-prune gate</strong>
|
|
19
|
+
<strong>lifecycle boxes</strong> · <strong>title + notes</strong> · <strong>auto-prune</strong> · <strong>source-aware reap safety</strong> · <strong>interactive panel</strong> · <strong>health diagnostics</strong> · <strong>hard-prune gate</strong>
|
|
20
20
|
</p>
|
|
21
21
|
|
|
22
22
|
---
|
|
@@ -25,8 +25,9 @@
|
|
|
25
25
|
|
|
26
26
|
The package `exports` entry (`./src/index.ts`) is the **stable public surface** —
|
|
27
27
|
`addTodo`, `listTodos`, `updateTodo`, `getTodo`, `completeTodo`, `parkTodo`,
|
|
28
|
-
`deleteTodo`, and the `Todo` / `AddInput` /
|
|
29
|
-
`
|
|
28
|
+
`deleteTodo`, `loadStore`, `saveStore`, and the `Todo` / `AddInput` /
|
|
29
|
+
`UpdateInput` / `ListFilter` / `Priority` / `Status` / `Store` /
|
|
30
|
+
`SaveStoreOptions` types (plus `TodoError`). Other `src/*` paths
|
|
30
31
|
are internal and may change without notice. Depend on `@getpipher/armory-todo`
|
|
31
32
|
(the public entry), never deep-import `src/*`.
|
|
32
33
|
|
|
@@ -77,6 +78,17 @@ reports what moved (`auto-pruned N stale done (>7d): …` + a `restore` hint);
|
|
|
77
78
|
it's a transient message, not a prompt injection. Reversible via `restore <id>`.
|
|
78
79
|
`prune --all` (move fresh done too) and `prune --hard` (irreversible) stay manual.
|
|
79
80
|
|
|
81
|
+
**Source-aware stale-active reap (v0.6.0):** producers can leave tracked todos
|
|
82
|
+
`open`/`in_progress` forever when a worker dies before reporting a terminal
|
|
83
|
+
status. On `session_start`, armory-todo now self-heals configured producer
|
|
84
|
+
sources: stale `armory-fleet` todos (default: untouched for 2d) become
|
|
85
|
+
`cancelled` and move directly to the archive, where `restore <id>` works
|
|
86
|
+
immediately. Real/manual todos are never auto-mutated; non-policy active todos
|
|
87
|
+
untouched for 14d get an advisory `ORPHAN` health flag and ⌛ panel marker.
|
|
88
|
+
Both thresholds are editable in the Config tab. Expected live→archive drops
|
|
89
|
+
keep rolling backup, drop-snapshot, and audit protection without emitting a
|
|
90
|
+
false wipe alert.
|
|
91
|
+
|
|
80
92
|
The only irreversible action is `prune --hard` (hard-prune) — it requires an
|
|
81
93
|
explicit `confirm: true` and is always user-confirmed. See **Self-awareness**
|
|
82
94
|
below.
|
|
@@ -87,7 +99,7 @@ below.
|
|
|
87
99
|
~/.pi/agent/todo/
|
|
88
100
|
todo.json # active + parked
|
|
89
101
|
todo-archive.json # done + cancelled (sealed history)
|
|
90
|
-
todo.config.json # prune
|
|
102
|
+
todo.config.json # prune/health/reap thresholds + notify settings
|
|
91
103
|
```
|
|
92
104
|
|
|
93
105
|
A v1 single-file store at `~/.pi/agent/todo.json` is migrated automatically on
|
|
@@ -136,6 +148,47 @@ Three caps keep the store (and its auto-injected prompt block) from bloating sil
|
|
|
136
148
|
|
|
137
149
|
**Backwards-compat:** zero migration (store v3, config v1, registry v1 unchanged in shape). Oversize notes grandfathered. The `maxOpen` advisory→enforced graduation is a documented behavior change for any v0.4.0 user who set a slot (the block message tells them how to raise/clear).
|
|
138
150
|
|
|
151
|
+
## Agent-validated triage (`/todo triage`)
|
|
152
|
+
|
|
153
|
+
Rules alone can't clean a store that accretes agent-run debris, stale backlog,
|
|
154
|
+
and prune hesitation. Triage adds judgment: one command that gathers
|
|
155
|
+
candidates, has the agent validate each against a versioned rubric, and closes
|
|
156
|
+
nothing without an explicit batch approval.
|
|
157
|
+
|
|
158
|
+
```
|
|
159
|
+
/todo triage [scope] [--yes]
|
|
160
|
+
1. GATHER stale(30d) + orphans(14d) + over-cap projects + agent-source items
|
|
161
|
+
2. VALIDATE agent checks each candidate (read-only git/gh/npm probes — rubric ships in-package: src/triage-prompt.ts)
|
|
162
|
+
3. PROPOSE table: verdict + evidence + confidence
|
|
163
|
+
4. APPROVE one batch confirm — nothing mutates before it (the load-bearing gate)
|
|
164
|
+
5. EXECUTE close(cancel) / park / keep → one prune --all sweep (reversible)
|
|
165
|
+
6. FILE each closed item as a CLOSED issue in the private getpipher/todo-ledger
|
|
166
|
+
7. REPORT before/after counts, filed links, anything deferred
|
|
167
|
+
```
|
|
168
|
+
|
|
169
|
+
Safety rails (the point of the feature):
|
|
170
|
+
|
|
171
|
+
- **No silent close, ever.** The agent classifies; only the user's batch
|
|
172
|
+
approval mutates. `--yes` (`autoSafe:true`) executes ONLY the mechanical safe
|
|
173
|
+
class — fleet-run prompt debris (prompt-shaped title + agent context) — and
|
|
174
|
+
still reports what it closed. Unverifiable items stay proposals; zero
|
|
175
|
+
false-closes is the success metric.
|
|
176
|
+
- **The ledger never blocks.** Issues are matched by client-side title search
|
|
177
|
+
(idempotent — GitHub's search index lags fresh issues), created then PATCHed
|
|
178
|
+
closed, labeled `todo-archive` + `project/<name>` + `verdict/cancel`, and
|
|
179
|
+
embed the full original note. gh down → items archive locally anyway and the
|
|
180
|
+
skip is reported; `TODO_TRIAGE_SKIP_FILING=1` forces that path (air-gapped
|
|
181
|
+
runs). `TODO_LEDGER_REPO` overrides the repo for scratch runs.
|
|
182
|
+
- **The rubric is versioned** (`triage-rubric/v1`) and ships in the package —
|
|
183
|
+
judgment quality evolves deliberately, not per-session.
|
|
184
|
+
- Composes with the existing machinery: thresholds come from
|
|
185
|
+
`health.activeStaleDays` / `reap.orphanFlagAfterDays`, over-cap from the
|
|
186
|
+
registry, and reap-policy sources stay owned by the v0.6.0 auto-reap.
|
|
187
|
+
|
|
188
|
+
A Triage tab in the interactive panel is planned for v2; today the loop runs
|
|
189
|
+
through the agent (the tool returns the candidates + rubric, the agent
|
|
190
|
+
validates and proposes, you approve, one `approve:[…]` call executes + files).
|
|
191
|
+
|
|
139
192
|
## Interactive panel (SPEC-3)
|
|
140
193
|
|
|
141
194
|
Run `/todo` (no arg) in a TUI session to open the interactive triage panel:
|
|
@@ -177,6 +230,7 @@ Typed subcommands (`/todo park <id>`, `/todo prune`, etc.) all still work alongs
|
|
|
177
230
|
/todo prune --hard permanent deletion (interactive confirm prompt)
|
|
178
231
|
/todo archive [filter] archive summary, or filtered slice (project:X / text:Y)
|
|
179
232
|
/todo health bloat report across all boxes + flags + suggestions
|
|
233
|
+
/todo triage [scope] [--yes] agent-validated prune: gather → validate → propose → approve → close/park → file to ledger
|
|
180
234
|
/todo clean clear all done (deprecated — use prune)
|
|
181
235
|
/todo path show the store file path
|
|
182
236
|
```
|
|
@@ -196,6 +250,7 @@ Typed subcommands (`/todo park <id>`, `/todo prune`, etc.) all still work alongs
|
|
|
196
250
|
| `restore` | `id` | bring an archived TODO back as open |
|
|
197
251
|
| `health` | (none) | bloat report across active/parked/archive + flags + suggestions |
|
|
198
252
|
| `prune` (hard) | `hard:true`, `confirm:true`, `box?`, `olderThan?`, `project?`, `tag?` | PERMANENT deletion — the only irreversible action |
|
|
253
|
+
| `triage` | `scope?`, `autoSafe?`, `approve?: [{id, verdict, reason?, evidence?, confidence?, survivorId?}]` | two-phase agent-validated prune: bare call gathers candidates + returns the versioned rubric (nothing mutates); `autoSafe` executes ONLY mechanical debris; `approve` executes the user-approved batch, sweeps the archive, and files closed items to the private ledger
|
|
199
254
|
| `clear` | `status?` (default `done`) | bulk-clear a status (deprecated — use prune) |
|
|
200
255
|
|
|
201
256
|
Each TODO carries `id, title (≤120 chars), notes (any length), project, tags, priority (low|med|high|critical), status (open|in_progress|parked|done|cancelled), source, createdAt, updatedAt, closedAt`. The auto-injected block + list/panel show `title` only; `notes` is read via `get` and never injected.
|
|
@@ -206,9 +261,11 @@ Each TODO carries `id, title (≤120 chars), notes (any length), project, tags,
|
|
|
206
261
|
- **`todo` tool** — model CRUD + lifecycle (above).
|
|
207
262
|
- **`/todo` command** — human triage (above).
|
|
208
263
|
- **Auto-inject** — on every `before_agent_start`, a compact `## Open TODOs (N)` block (titles + ids, sorted by priority) is appended to the system prompt, so the agent starts every turn already aware of pending work. The block is **cap-aware** (v0.5.0): under `health.activeMaxOpen` (default 15) it lists the rows; **over** the cap it collapses to a lean summary (counts + over-budget projects + a `todo list` pointer) so the prompt stays bounded when the store bloats. Only `open` + `in_progress` are injected — `parked` and archived todos are excluded (the lifecycle-box boundary). Mutations refresh it on the next turn.
|
|
264
|
+
- **Source-aware safety protocol** — on `session_start`, policy-source stale actives (default `armory-fleet` >2d) move live→archive as immediately-restorable `cancelled` records. Non-policy stale actives are flagged only; never mutated. The Archive tab reports the cumulative number of auto-reaped runs.
|
|
209
265
|
- **Archive query** — `list` with `archived:true` is summary-first (counts by project + month) then filtered/paginated on demand, so a large archive never bloats a single query.
|
|
210
266
|
|
|
211
267
|
Full design + decisions:
|
|
268
|
+
- v0.6.0 (source-aware reap safety protocol): [`docs/superpowers/specs/2026-07-29-reap-safety-protocol-design.md`](docs/superpowers/specs/2026-07-29-reap-safety-protocol-design.md)
|
|
212
269
|
- v0.4.0 (project-scope management): [`docs/superpowers/specs/2026-07-21-project-scope-management-design.md`](docs/superpowers/specs/2026-07-21-project-scope-management-design.md)
|
|
213
270
|
- v0.3.1 (auto-prune + unified Done view): [`docs/superpowers/specs/2026-07-21-auto-prune-done-view-design.md`](docs/superpowers/specs/2026-07-21-auto-prune-done-view-design.md)
|
|
214
271
|
- v0.3.0 (title + notes split): [`docs/superpowers/specs/2026-07-21-title-notes-split-design.md`](docs/superpowers/specs/2026-07-21-title-notes-split-design.md)
|
|
@@ -230,15 +287,25 @@ Full design + decisions:
|
|
|
230
287
|
"health": { "activeMaxOpen": 15, "activeStaleDays": 30, "parkedMax": 10,
|
|
231
288
|
"parkedStaleDays": 60, "archiveMax": 200, "archiveOldDays": 180,
|
|
232
289
|
"perProjectDefaultMax": 8, "maxNotesBytes": 8192 },
|
|
233
|
-
"notify": { "sessionStartCount": true }
|
|
290
|
+
"notify": { "sessionStartCount": true },
|
|
291
|
+
"reap": {
|
|
292
|
+
"orphanFlagAfterDays": 14,
|
|
293
|
+
"policy": { "armory-fleet": { "reapAfterDays": 2, "reapTo": "cancelled" } }
|
|
294
|
+
}
|
|
234
295
|
}
|
|
235
296
|
```
|
|
236
297
|
|
|
237
298
|
| `notify.*` | default | purpose |
|
|
238
299
|
|---|---|---|
|
|
239
|
-
| `sessionStartCount` | `true` | Show the `armory-todo: N open TODOs` startup line. Set `false` to silence it — safety messages (wipe
|
|
300
|
+
| `sessionStartCount` | `true` | Show the `armory-todo: N open TODOs` startup line. Set `false` to silence it — safety messages (wipe recovery, auto-prune, reap) still surface. |
|
|
301
|
+
|
|
302
|
+
| `reap.*` | default | purpose |
|
|
303
|
+
|---|---:|---|
|
|
304
|
+
| `orphanFlagAfterDays` | `14` | Advisory ORPHAN threshold for active todos whose source is not auto-reaped; never mutates them. |
|
|
305
|
+
| `policy.armory-fleet.reapAfterDays` | `2` | Move stale fleet-tracked active todos directly to archive as cancelled. |
|
|
306
|
+
| `policy.armory-fleet.reapTo` | `cancelled` | Fixed reversible terminal status; `done` is intentionally unsupported. |
|
|
240
307
|
|
|
241
|
-
Run the store tests: `npm test` (
|
|
308
|
+
Run the store tests: `npm test` (497/497 across 15 suites).
|
|
242
309
|
|
|
243
310
|
## Known issues
|
|
244
311
|
|