pi-smart-compact 7.20.0 → 7.21.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 (59) hide show
  1. package/CHANGELOG.md +25 -0
  2. package/README.md +265 -189
  3. package/dist/app/run-context.d.ts +6 -0
  4. package/dist/app/run-context.d.ts.map +1 -1
  5. package/dist/app/run-smart-compact.d.ts +2 -0
  6. package/dist/app/run-smart-compact.d.ts.map +1 -1
  7. package/dist/app/steps/extract.d.ts.map +1 -1
  8. package/dist/app/steps/metrics.d.ts +1 -1
  9. package/dist/app/steps/metrics.d.ts.map +1 -1
  10. package/dist/app/steps/prepare.d.ts.map +1 -1
  11. package/dist/app/steps/state.d.ts.map +1 -1
  12. package/dist/app/steps/synthesize.d.ts.map +1 -1
  13. package/dist/app/steps/verify.d.ts +4 -13
  14. package/dist/app/steps/verify.d.ts.map +1 -1
  15. package/dist/app/steps/window.d.ts.map +1 -1
  16. package/dist/constants.d.ts +9 -1
  17. package/dist/constants.d.ts.map +1 -1
  18. package/dist/domain/scrub.d.ts +19 -0
  19. package/dist/domain/scrub.d.ts.map +1 -0
  20. package/dist/domain/summary-parse.d.ts +5 -5
  21. package/dist/domain/summary-parse.d.ts.map +1 -1
  22. package/dist/domain/summary-schema.d.ts +1 -1
  23. package/dist/domain/summary-schema.d.ts.map +1 -1
  24. package/dist/domain/tool-semantics.d.ts +15 -32
  25. package/dist/domain/tool-semantics.d.ts.map +1 -1
  26. package/dist/index.d.ts +1 -1
  27. package/dist/index.d.ts.map +1 -1
  28. package/dist/index.js +5056 -4329
  29. package/dist/infra/fs.d.ts +2 -0
  30. package/dist/infra/fs.d.ts.map +1 -1
  31. package/dist/infra/services.d.ts +20 -0
  32. package/dist/infra/services.d.ts.map +1 -1
  33. package/dist/phases/explore.d.ts.map +1 -1
  34. package/dist/phases/synthesize.d.ts +6 -3
  35. package/dist/phases/synthesize.d.ts.map +1 -1
  36. package/dist/phases/verify.d.ts +9 -22
  37. package/dist/phases/verify.d.ts.map +1 -1
  38. package/dist/types.d.ts +58 -2
  39. package/dist/types.d.ts.map +1 -1
  40. package/dist/ui/overlays.d.ts +5 -2
  41. package/dist/ui/overlays.d.ts.map +1 -1
  42. package/dist/utils/cache.d.ts +4 -2
  43. package/dist/utils/cache.d.ts.map +1 -1
  44. package/dist/utils/damage.d.ts +18 -1
  45. package/dist/utils/damage.d.ts.map +1 -1
  46. package/dist/utils/file-needles.d.ts +7 -5
  47. package/dist/utils/file-needles.d.ts.map +1 -1
  48. package/dist/utils/fingerprint.d.ts +1 -0
  49. package/dist/utils/fingerprint.d.ts.map +1 -1
  50. package/dist/utils/helpers.d.ts +2 -1
  51. package/dist/utils/helpers.d.ts.map +1 -1
  52. package/dist/utils/pruning.d.ts +0 -9
  53. package/dist/utils/pruning.d.ts.map +1 -1
  54. package/dist/utils/state.d.ts +4 -2
  55. package/dist/utils/state.d.ts.map +1 -1
  56. package/dist/utils/tokens.d.ts +12 -1
  57. package/dist/utils/tokens.d.ts.map +1 -1
  58. package/docs/RELEASE.md +1 -0
  59. package/package.json +2 -1
package/CHANGELOG.md CHANGED
@@ -1,5 +1,30 @@
1
1
  # Changelog
2
2
 
3
+ ## [7.21.0] - 2026-07-15
4
+
5
+ ### Fixed
6
+ - Canonical summary parsing now recognizes canonical H3 headings, merges duplicate sections, and preserves H3-only summaries during state injection.
7
+ - File verification uses collision-aware path needles; one monorepo basename can no longer satisfy multiple modified files.
8
+ - Every deterministic verification gap is repaired regardless of scalar score; typed gaps and repair provenance replace string-prefix policy.
9
+ - Recent-tail and batch planning count structured tool-call arguments with run-scoped provider/model calibration.
10
+ - Access pruning deduplicates only identical tool name + argument signatures; read/search/list evidence no longer collapses by path alone.
11
+ - MCP snake-case edit aliases are classified as mutations without treating ambiguous `path + text` payloads universally as writes.
12
+ - Incremental extraction reconciles cached unresolved errors against successful retries in the new suffix.
13
+ - LLM call counts now come from the run-scoped metrics sink, including probes, retries, failures and patches.
14
+
15
+ ### Added
16
+ - High-confidence secret scrubbing at provider, extraction-cache, backup, state and pending-summary boundaries; optional PII scrubbing.
17
+ - Optional fail-closed manual Apply/Cancel approval gate with verification provenance.
18
+ - Exact max-call and max-latency budgets with deterministic degradation, plus `--focus` budget weighting.
19
+ - Online `session_compact` → `message_end` damage monitoring and opt-in adaptive preservation policy.
20
+ - `/smart-compact loops` manager for resolve/reopen, priority and pin/unpin overrides with stable summary identity across runs.
21
+ - Deterministic adversarial EESV release gate (`bun run gate`) covering parser, verification, tools, cache, budgets, scrubbing and damage.
22
+
23
+ ### Changed
24
+ - Public README redesigned for npm, GitHub and Pi package surfaces with install-first quick start, progressive EESV documentation, complete configuration, safety/privacy guidance and current recovery/observability flows.
25
+ - Extraction and exploration share one deduplicated fact context; runtime call accounting now comes from the metrics sink instead of inferred round counts.
26
+ - CI and the release checklist now run the adversarial EESV gate.
27
+
3
28
  ## [7.20.0] - 2026-07-14
4
29
 
5
30
  ### Fixed
package/README.md CHANGED
@@ -1,37 +1,20 @@
1
1
  <div align="center">
2
2
 
3
- <img src="./docs/assets/banner.svg" alt="pi-smart-compact" width="860" />
3
+ <a href="https://github.com/alpertarhan/pi-smart-compact">
4
+ <img src="https://raw.githubusercontent.com/alpertarhan/pi-smart-compact/main/docs/assets/banner.svg" alt="pi-smart-compact" width="860" />
5
+ </a>
4
6
 
5
7
  [![CI](https://github.com/alpertarhan/pi-smart-compact/actions/workflows/ci.yml/badge.svg)](https://github.com/alpertarhan/pi-smart-compact/actions/workflows/ci.yml)
6
8
  [![npm version](https://img.shields.io/npm/v/pi-smart-compact?color=60a5fa)](https://www.npmjs.com/package/pi-smart-compact)
7
- [![license](https://img.shields.io/npm/l/pi-smart-compact?color=22c55e)](./LICENSE)
8
- [![Pi extension](https://img.shields.io/badge/Pi-extension-fbbf24)](https://github.com/earendil-works/pi)
9
+ [![license](https://img.shields.io/npm/l/pi-smart-compact?color=22c55e)](https://github.com/alpertarhan/pi-smart-compact/blob/main/LICENSE)
10
+ [![Pi package](https://img.shields.io/badge/Pi-package-fbbf24)](https://github.com/earendil-works/pi)
9
11
 
10
- **Verification-oriented smart compaction for the [Pi Coding Agent](https://github.com/earendil-works/pi-coding-agent).**
12
+ ### Verification-oriented context compaction for the Pi Coding Agent
11
13
 
12
- </div>
13
-
14
- Default compaction trims your conversation blind. `pi-smart-compact` keeps what
15
- the agent actually needs to continue — the **goal, changed files, unresolved
16
- errors, decisions, constraints, and open loops** — through a verified
17
- **Extract → Explore → Synthesize → Verify** pipeline.
18
-
19
- > Facts first, synthesis second, verification last.
20
-
21
- ---
14
+ Preserve the agent's **working state**—goals, files, decisions, errors,
15
+ constraints, and open loops—not just a vague recap of the conversation.
22
16
 
23
- ## Why
24
-
25
- Default compaction produces a vague recap and quietly drops the operational
26
- context that matters most during coding. The result is the classic
27
- *"didn't we already fix this?"* loop.
28
-
29
- | Default compaction | `pi-smart-compact` |
30
- | --- | --- |
31
- | Trims by token count | Extracts facts deterministically (zero LLM) |
32
- | Generic prose recap | Structured working-state summary |
33
- | Loses files / errors / decisions | Preserves them, then **verifies** they survived |
34
- | No regression signal | Damage detection + metrics dashboard |
17
+ </div>
35
18
 
36
19
  ## Install
37
20
 
@@ -39,7 +22,7 @@ context that matters most during coding. The result is the classic
39
22
  pi install npm:pi-smart-compact
40
23
  ```
41
24
 
42
- From GitHub:
25
+ Or install directly from GitHub:
43
26
 
44
27
  ```bash
45
28
  pi install git:github.com/alpertarhan/pi-smart-compact
@@ -48,237 +31,330 @@ pi install git:github.com/alpertarhan/pi-smart-compact
48
31
  ## Quick start
49
32
 
50
33
  ```bash
51
- /smart-compact # interactive — pick model + profile
52
- /smart-compact anthropic/claude-sonnet-4 balanced
53
- /smart-compact "focus on auth + unresolved follow-ups"
54
- /smart-compact metrics # profile / provider comparison
55
- /smart-compact dashboard # interactive TUI dashboard
56
- /smart-compact restore # list + view + restore backups
34
+ /smart-compact # interactive model + profile picker
35
+ /smart-compact balanced # direct profile
36
+ /smart-compact anthropic/claude-sonnet-4 balanced # direct model + profile
37
+ /smart-compact balanced --focus=auth # preserve extra auth detail
38
+ /smart-compact metrics # text metrics report
39
+ /smart-compact dashboard # interactive metrics dashboard
40
+ /smart-compact restore # browse and restore backups
41
+ /smart-compact loops # manage persisted open loops
57
42
  ```
58
43
 
59
- Or let the agent call it as a tool on long sessions:
44
+ The extension also participates in Pi's native compaction flow automatically
45
+ when actual context usage crosses the configured threshold (60% by default),
46
+ and exposes a `smart_compact` tool for long-running agents.
60
47
 
61
- ```jsonc
62
- {
63
- "name": "smart_compact",
64
- "parameters": { "profile": "balanced", "dashboard": false }
65
- }
48
+ > The tool path stages a safe pending summary. It never compacts the active
49
+ > conversation in the middle of an agent turn.
50
+
51
+ ## Why smart compaction?
52
+
53
+ | Native-style recap | `pi-smart-compact` |
54
+ | --- | --- |
55
+ | Summarizes prose | Preserves operational coding state |
56
+ | Trusts one LLM response | Extracts deterministic ground truth first |
57
+ | File/error omissions can be silent | Verifies coverage and repairs known gaps |
58
+ | One strategy for every session | Chooses single-pass or hierarchical synthesis |
59
+ | No quality feedback | Tracks provenance, damage signals, and metrics |
60
+
61
+ The design principle is simple:
62
+
63
+ > **Facts first. Synthesis second. Verification before apply.**
64
+
65
+ ## EESV pipeline
66
+
67
+ ```text
68
+ Pi conversation
69
+
70
+
71
+ ┌───────────┐ ┌───────────┐ ┌────────────┐ ┌───────────┐
72
+ │ Extract │ → │ Explore │ → │ Synthesize │ → │ Verify │
73
+ │ 0 LLM │ │ adaptive │ │ 1-pass or │ │ + repair │
74
+ │ calls │ │ │ │ hierarchical│ │ │
75
+ └───────────┘ └───────────┘ └────────────┘ └───────────┘
76
+
77
+
78
+ staged/applied by Pi
66
79
  ```
67
80
 
68
- Auto-compaction also runs before Pi's native compact once context pressure
69
- crosses your threshold (default 60% **actual** context usage).
81
+ | Stage | Responsibility |
82
+ | --- | --- |
83
+ | **Extract** | Deterministically catalogs files, errors, decisions, constraints, topics, media metadata, and open loops. This is the verification ground truth. |
84
+ | **Explore** | Uses a cheaper segmentation model when a complex session needs deeper topic boundaries or error-chain inspection. Simple sessions skip it. |
85
+ | **Synthesize** | Uses one pass for short sessions and bounded chunk/assembly fallbacks for long sessions. Focus and call/latency budgets are enforced here. |
86
+ | **Verify** | Checks canonical sections and extracted facts, applies every safe deterministic repair, and escalates only unresolved low-scoring gaps to an LLM patch. |
87
+
88
+ ### What survives compaction
70
89
 
71
- ## How it works
90
+ - The current goal and user constraints
91
+ - Modified, read, and deleted files
92
+ - Unresolved **and** resolved error history
93
+ - Explicit and implicit decisions
94
+ - Open follow-ups, blockers, priorities, and pinned loops
95
+ - Next actions and critical continuation context
96
+ - Changes since the previous compaction
72
97
 
73
- ```mermaid
74
- flowchart LR
75
- A["Extract<br/>deterministic facts<br/><i>0 LLM calls</i>"] --> B["Explore<br/>optional deep<br/>analysis"]
76
- B --> C["Synthesize<br/>single-pass or<br/>chunked summary"]
77
- C --> D["Verify<br/>score gaps,<br/>repair"]
78
- D --> E["Return verified<br/>summary to Pi"]
79
- ```
98
+ Summaries use a canonical H1/H2/H3-aware structure, collision-safe file
99
+ matching, typed verification gaps, and persisted repair provenance.
80
100
 
81
- | Stage | What it does |
101
+ ## Usage surfaces
102
+
103
+ | Surface | Behavior |
82
104
  | --- | --- |
83
- | **Extract** | Deterministically pulls files, errors, decisions, constraints, topics, and open loops — no LLM, the ground truth. |
84
- | **Explore** | Optionally inspects the conversation more deeply when the session is complex. |
85
- | **Synthesize** | Single-pass for short sessions, Kamradt-style chunked + assembled for long ones. |
86
- | **Verify** | Scores the result against extracted facts and patches missing critical details. |
105
+ | `/smart-compact` | Explicit manual run. Supports picker UI, direct args, dry-run, focus, and budgets. |
106
+ | `session_before_compact` | Auto path. Runs before Pi's native compaction and returns a verification-scored result when context pressure is high. |
107
+ | `smart_compact` tool | Agent path. Produces a pending summary for Pi's next natural compact; does not compact mid-turn. |
108
+ | `/smart-compact loops` | Project-level open-loop manager: resolve/reopen, priority, pin/unpin. |
87
109
 
88
- **What it preserves:** user goal · constraints & preferences · modified / read /
89
- deleted files · unresolved & resolved errors · key decisions · open follow-up
90
- work · critical next-turn context · the delta since the previous compaction.
110
+ ### Focus and budgets
91
111
 
92
- ## Integration surfaces
112
+ ```bash
113
+ /smart-compact balanced --focus=authentication
114
+ /smart-compact aggressive --max-calls=6 --max-latency=30000
115
+ /smart-compact balanced --focus=src/auth.ts --max-calls=8
116
+ ```
93
117
 
94
- | Surface | When | Detail |
95
- | --- | --- | --- |
96
- | `/smart-compact` | Manual | Interactive picker or direct args; bypasses the adaptive gate. |
97
- | `session_before_compact` | Auto | Runs before Pi's native compaction when context pressure is high. |
98
- | `smart_compact` tool | Agent | Prepares a pending summary; Pi applies it on the next natural compact. |
118
+ - `--focus` assigns more synthesis/exploration budget to a topic or path. It
119
+ does **not** attempt unsupported non-contiguous compaction.
120
+ - `--max-calls` accepts `1–100`.
121
+ - `--max-latency` accepts `5000–600000` milliseconds.
122
+ - Call-budget exhaustion degrades to deterministic summaries. The latency
123
+ budget is a hard cancellation deadline.
99
124
 
100
- A short-lived pending summary is staged in memory (5-minute TTL) and handed to
101
- Pi when compaction is applied.
125
+ The tool exposes equivalent `focus`, `max_calls`, and `max_latency_ms`
126
+ parameters.
102
127
 
103
- ## Example output
128
+ ## Profiles
104
129
 
105
- A generated summary follows a stable, structured contract:
130
+ | Profile | Summary budget | Recent context kept | Best for |
131
+ | --- | ---: | ---: | --- |
132
+ | `light` | 10,000 tokens | 30,000 tokens | Maximum continuity and detail |
133
+ | `balanced` | 6,000 tokens | 20,000 tokens | General use; default |
134
+ | `aggressive` | 3,000 tokens | 10,000 tokens | Tight context budgets |
106
135
 
107
- ```markdown
108
- ## Goal
109
- Add retry/backoff to the LLM client so transient 429/5xx don't abort compaction.
136
+ Profiles are a starting policy. Provider/model calibration, conversation shape,
137
+ focus hints, damage feedback, and explicit budgets refine the actual run.
110
138
 
111
- ## Constraints & Preferences
112
- - [requirement] never compact mid-turn from the tool path
139
+ ## Safety and privacy
113
140
 
114
- ## Progress
115
- ### Done
116
- - [x] Added `withRetry` wrapper in src/infra/llm-retry.ts
117
- ### In Progress
118
- - [ ] Wire retry client into the services container
119
- ### Blocked
120
- - None
141
+ ### Deterministic safeguards
121
142
 
122
- ## Key Decisions
123
- - **Honor Retry-After verbatim**: providers that set it know their limits best.
143
+ - Tool-call-aware recent-tail budgeting
144
+ - Exact access-call pruning—different reads, searches, offsets, and patterns do not collapse
145
+ - Tool-call/tool-result pair integrity at the compaction boundary
146
+ - Collision-safe modified-file verification for monorepos
147
+ - Mandatory deterministic repair for patchable verification gaps
148
+ - Cross-session guard and five-minute TTL for pending summaries
149
+ - Session-log recovery for older, truncated tool results
150
+ - Retention-pruned backups before compaction
124
151
 
125
- ## Files Modified
126
- - src/infra/llm-retry.ts
127
- - src/infra/llm-client.ts
152
+ ### Secrets and PII
128
153
 
129
- ## Files Read
130
- - src/app/run-smart-compact.ts
154
+ High-confidence secret scrubbing is enabled by default at every relevant trust
155
+ boundary:
131
156
 
132
- ## Open Loops
133
- - [high] Retried but unresolved: AbortSignal ignored by some providers
157
+ ```text
158
+ provider request · extraction cache · backup · state · pending summary
159
+ ```
134
160
 
135
- ## Changes Since Last Compaction
136
- - New files touched: src/infra/llm-retry.ts
137
- - New loops: AbortSignal ignored by some providers
161
+ It covers common API keys, cloud/GitHub/Slack tokens, JWTs, bearer tokens,
162
+ private keys, and credential assignments. Optional email/phone/payment-card
163
+ scrubbing is available through `scrubPii`.
138
164
 
139
- ## Next Steps
140
- 1. Add an outer hard-timeout as a second line of defense
165
+ Secret scrubbing is defense in depth, **not a replacement for proper secret
166
+ handling or a dedicated DLP system**. See the
167
+ [security policy](https://github.com/alpertarhan/pi-smart-compact/blob/main/SECURITY.md).
141
168
 
142
- ## Critical Context
143
- - 408/425/429/5xx are retriable; 4xx (other) fails fast
169
+ ### Approval and feedback
170
+
171
+ - `requireApproval: true` adds a fail-closed manual **Apply / Cancel** decision
172
+ after the provenance review screen. Auto and tool paths retain their native
173
+ staged lifecycle.
174
+ - Online damage monitoring observes the first post-compaction messages and
175
+ records re-read files or repeated context. Remediation hints feed those files
176
+ into the next compaction.
177
+ - `adaptiveDamageFeedback` can opt a project into larger preservation budgets
178
+ after repeated high-damage reports.
144
179
 
145
- ## Topics Covered
146
- - LLM retry wrapper (high)
180
+ ## Open-loop control
181
+
182
+ ```bash
183
+ /smart-compact loops
147
184
  ```
148
185
 
149
- A machine-readable `CompactionState` is built alongside it for reuse across
150
- later compactions (delta tracking, damage detection).
186
+ The manager operates on the project's persisted `CompactionState`:
187
+
188
+ - resolve or reopen a loop
189
+ - change priority
190
+ - pin or unpin it across later compactions
191
+
192
+ Overrides use normalized summary identity instead of positional IDs, so a loop
193
+ cannot accidentally inherit another loop's state on a later run.
151
194
 
152
195
  ## Configuration
153
196
 
154
- Add to `~/.pi/agent/settings.json`:
197
+ Add `smartCompact` to `~/.pi/agent/settings.json`:
155
198
 
156
199
  ```json
157
200
  {
158
201
  "smartCompact": {
159
202
  "profile": "balanced",
160
- "summaryModel": "anthropic/claude-sonnet-4",
203
+ "summaryModel": null,
204
+ "segmentationModel": null,
161
205
  "autoTrigger": true,
162
206
  "minContextPercent": 60,
163
- "backupEnabled": true
207
+ "backupEnabled": true,
208
+ "scrubSecrets": true,
209
+ "scrubPii": false,
210
+ "requireApproval": false,
211
+ "maxLlmCalls": 0,
212
+ "maxLatencyMs": 0,
213
+ "focusWeighting": true,
214
+ "onlineDamageMonitor": true,
215
+ "adaptiveDamageFeedback": false,
216
+ "pinPaths": []
164
217
  }
165
218
  }
166
219
  ```
167
220
 
168
- | Key | Type | Default |
169
- | --- | --- | --- |
170
- | `profile` | `light \| balanced \| aggressive` | `balanced` |
171
- | `summaryModel` | `string \| null` | `null` (uses session model) |
172
- | `segmentationModel` | `string \| null` | `null` |
173
- | `autoTrigger` | `boolean` | `true` |
174
- | `autoTriggerTimeoutMs` | `number` | `120000` |
175
- | `minContextPercent` | `number` | `60` |
176
- | `backupEnabled` | `boolean` | `true` |
177
- | `backupDir` | `string` | `~/.pi/agent/compact-backups` |
178
- | `profiles` | per-profile overrides | built-ins |
179
- | `pinPaths` | `string[]` | `[]` (paths always preserved) |
180
-
181
- ### Profiles
182
-
183
- | Profile | Summary budget | Keep recent | Use when |
184
- | --- | ---: | ---: | --- |
185
- | `light` | 10000 | 30000 | preserve more detail |
186
- | `balanced` | 6000 | 20000 | default, general use |
187
- | `aggressive` | 3000 | 10000 | tighter summaries |
188
-
189
- The legacy config key `semanticCompact` is still accepted.
221
+ <details>
222
+ <summary><strong>All configuration keys</strong></summary>
223
+
224
+ | Key | Type | Default | Notes |
225
+ | --- | --- | --- | --- |
226
+ | `profile` | `light \| balanced \| aggressive` | `balanced` | Default policy profile |
227
+ | `summaryModel` | `string \| null` | `null` | Uses the active session model when null |
228
+ | `segmentationModel` | `string \| null` | `null` | Optional cheaper model for Explore |
229
+ | `autoTrigger` | `boolean` | `true` | Participate in Pi's native compact hook |
230
+ | `autoTriggerTimeoutMs` | `number` | `120000` | Hard timeout for automatic runs |
231
+ | `minContextPercent` | `number` | `60` | Actual context usage gate |
232
+ | `backupEnabled` | `boolean` | `true` | Write a pre-compaction backup |
233
+ | `backupDir` | `string` | `~/.pi/agent/compact-backups` | Empty config value uses this path |
234
+ | `profiles` | object | built-ins | Per-profile numeric overrides |
235
+ | `pinPaths` | `string[]` | `[]` | Always preserve matching paths |
236
+ | `requireApproval` | `boolean` | `false` | Manual UI only; cancel/error fails closed |
237
+ | `scrubSecrets` | `boolean` | `true` | High-confidence credential redaction |
238
+ | `scrubPii` | `boolean` | `false` | Email/phone/card-shaped redaction |
239
+ | `maxLlmCalls` | integer `0–100` | `0` | `0` means unlimited |
240
+ | `maxLatencyMs` | `0` or `5000–600000` | `0` | `0` means unlimited |
241
+ | `focusWeighting` | `boolean` | `true` | Weight focused topics/paths higher |
242
+ | `onlineDamageMonitor` | `boolean` | `true` | Observe post-compaction regression signals |
243
+ | `adaptiveDamageFeedback` | `boolean` | `false` | Increase preservation after repeated damage |
244
+
245
+ The legacy `semanticCompact` root key is still accepted for compatibility.
246
+
247
+ </details>
248
+
249
+ ## Example summary
250
+
251
+ <details>
252
+ <summary><strong>Show canonical output</strong></summary>
190
253
 
191
- ## Safeguards
254
+ ```markdown
255
+ ## Goal
256
+ Add retry/backoff to the LLM client without breaking cancellation.
192
257
 
193
- **Correctness**
258
+ ## Constraints & Preferences
259
+ - [requirement] Never compact mid-turn from the tool path.
194
260
 
195
- - Deterministic extraction before any synthesis
196
- - Verification scoring with deterministic patching **before** LLM patching
197
- - Hallucinated file-reference detection (SemVer-aware)
198
- - Open-loop injection + cross-compaction delta tracking
199
- - Pinned-path preservation (`pinPaths`) a deterministic, LLM-free guarantee
200
- - Damage auto-remediation — re-read files feed forward and get re-preserved next compaction
261
+ ## Progress
262
+ ### Done
263
+ - [x] Added `withRetry` in `src/infra/llm-retry.ts`.
264
+ ### In Progress
265
+ - [ ] Wire the retry client into run-scoped services.
266
+ ### Blocked
267
+ - None.
201
268
 
202
- **Safety**
269
+ ## Key Decisions
270
+ - **Honor Retry-After verbatim**: provider limits are authoritative.
203
271
 
204
- - Conversation backups before compaction (retention-pruned), browsable + restorable via `/smart-compact restore`
205
- - `toolCall` / `toolResult` pair integrity at the compaction boundary
206
- - Cross-session leak guard on the pending summary
207
- - Session-log recovery that bypasses truncation of older tool results
272
+ ## Files Modified
273
+ - src/infra/llm-retry.ts
274
+ - src/infra/llm-client.ts
208
275
 
209
- **Observability**
276
+ ## Open Loops
277
+ - [high] Preserve AbortSignal behavior across providers.
210
278
 
211
- - Metrics logging with profile / provider comparison
212
- - Post-compaction damage (regression) detection
213
- - Interactive TUI + HTML dashboards
279
+ ## Changes Since Last Compaction
280
+ - New files touched: src/infra/llm-retry.ts
214
281
 
215
- ## Usage notes
282
+ ## Next Steps
283
+ 1. Add an outer timeout as a second line of defense.
216
284
 
217
- - Auto / tool compaction is skipped while context is small (below 60% actual usage).
218
- - Manual `/smart-compact` bypasses that gate you asked for it.
219
- - `pi-toolkit`'s `tool=XX%` means tool-output ratio, **not** context fullness;
220
- smart-compact uses actual `context=XX%`.
221
- - The tool path does **not** compact mid-turn (it stages a pending summary).
222
- - Exploration is adaptive and may be skipped for simple sessions.
285
+ ## Critical Context
286
+ - Retry 408/425/429/5xx; fail fast on other 4xx responses.
287
+ ```
223
288
 
224
- ## Companions & compatibility
289
+ </details>
225
290
 
226
- Pi core libraries are host-provided wildcard peers and are excluded from the
227
- published bundle. This keeps the extension independent from Pi's release cadence:
228
- the lockfile provides a reproducible development baseline, while daily CI runs
229
- the full suite against the latest Pi packages without changing the manifest.
291
+ ## Observability and recovery
230
292
 
231
- `pi-smart-compact` is designed to coexist with — and recommended alongside —
232
- [`pi-toolkit`](https://github.com/ersintarhan/pi-toolkit). pi-toolkit handles
233
- everyday context hygiene (anchors, pivots, status lines, old tool-output
234
- trimming); smart-compact handles high-pressure verified compaction. The
235
- integration protects recent pi-toolkit anchors and recovers original tool
236
- outputs from the session log.
293
+ ```bash
294
+ /smart-compact metrics # text report
295
+ /smart-compact dashboard # interactive TUI; can write a local HTML report
296
+ /smart-compact restore # browse, inspect, and restore backups
297
+ ```
237
298
 
238
- Because smart-compact sits close to Pi's compaction path, take extra care with
239
- extensions that also rewrite compaction hooks, branch history, entry IDs, tool
240
- output, or the compaction boundary. If you run another automatic compaction /
241
- context-rewriting extension, prefer a single `session_before_compact` owner
242
- unless hook order is explicitly coordinated.
299
+ Metrics include method, profile, provider, phase timing, token/call estimates,
300
+ verification quality, cache behavior, redactions, adaptation, fallbacks, and
301
+ cancelled runs.
243
302
 
244
- ## Runtime artifacts
303
+ <details>
304
+ <summary><strong>Runtime artifacts</strong></summary>
245
305
 
246
- The extension writes under `~/.pi/agent/`:
306
+ All files live under `~/.pi/agent/`.
247
307
 
248
308
  | Path | Purpose |
249
309
  | --- | --- |
250
- | `settings.json` | configuration (read) |
251
- | `compact-backups/` | conversation backups (retention-pruned) |
252
- | `.cache/compact-extraction-<session>.json` | incremental extraction cache |
253
- | `.cache/compact-metrics.jsonl` | metrics log (tail-retained, 5 MiB cap) |
254
- | `.cache/smart-compact-report.html` | HTML dashboard |
255
- | `.cache/smart-compact/projects/<projectId>.json` | project fingerprint |
256
- | `.cache/smart-compact/states/<projectId>.json` | reusable compaction state |
257
- | `.cache/smart-compact/damage-reports.jsonl` | regression signals (tail-retained, 5 MiB cap) |
258
- | `.cache/smart-compact/remediation-<projectId>.json` | files to re-preserve after damage |
310
+ | `settings.json` | Configuration (read only) |
311
+ | `compact-backups/` | Retention-pruned conversation backups |
312
+ | `.cache/compact-extraction-<session>.json` | Incremental extraction cache |
313
+ | `.cache/compact-metrics.jsonl` | Tail-retained metrics log; 5 MiB cap |
314
+ | `.cache/smart-compact-report.html` | Local HTML dashboard |
315
+ | `.cache/smart-compact/projects/<projectId>.json` | Project fingerprint |
316
+ | `.cache/smart-compact/states/<projectId>.json` | Compaction state and loop overrides |
317
+ | `.cache/smart-compact/damage-reports.jsonl` | Damage reports; 5 MiB cap |
318
+ | `.cache/smart-compact/remediation-<projectId>.json` | Files to preserve after damage |
319
+
320
+ </details>
321
+
322
+ ## Compatibility
323
+
324
+ Pi core packages are host-provided wildcard peers and are excluded from the
325
+ published bundle. The lockfile gives contributors a reproducible baseline,
326
+ while CI validates the latest Pi release daily without changing the manifest.
327
+ An exact version can be checked with `bun run compat:pi <version>`.
328
+
329
+ `pi-smart-compact` is designed to coexist with
330
+ [`pi-toolkit`](https://github.com/ersintarhan/pi-toolkit): toolkit handles daily
331
+ context hygiene; smart-compact handles high-pressure verified compaction. If
332
+ another extension also owns `session_before_compact` or rewrites branch history,
333
+ coordinate hook order or prefer a single automatic compaction owner.
259
334
 
260
335
  ## Development
261
336
 
262
337
  ```bash
263
338
  bun install
264
- bun run typecheck # tsc --noEmit
265
- bun test # full test suite
266
- bun run bench # repeatable hot-path benchmark
267
- bun run compat:pi # latest Pi, without changing package.json or bun.lock
268
- bun run compat:pi 0.80.6 # optional exact Pi version
269
- bun run build # dist/ output for publishing
339
+ bun run typecheck
340
+ bun test
341
+ bun run gate # deterministic adversarial EESV release gate
342
+ bun run bench
343
+ bun run build
344
+ bun run compat:pi # isolated latest-Pi compatibility check
270
345
  ```
271
346
 
272
- Pull requests run the same verification in GitHub Actions before merge.
347
+ Pull requests run typecheck, the complete test suite, the adversarial gate, and
348
+ the build in GitHub Actions.
273
349
 
274
- ## Documentation
350
+ ## Project documentation
275
351
 
276
- - [`ARCHITECTURE.md`](./ARCHITECTURE.md) — system design, execution model, layer responsibilities
277
- - [`CHANGELOG.md`](./CHANGELOG.md) — release history
278
- - [`CONTRIBUTING.md`](./CONTRIBUTING.md) — contributor workflow and expectations
279
- - [`SECURITY.md`](./SECURITY.md) — vulnerability reporting and data-handling notes
280
- - [`SUPPORT.md`](./SUPPORT.md) — where to ask for help
281
- - [`docs/RELEASE.md`](./docs/RELEASE.md) — release checklist
352
+ - [Architecture](https://github.com/alpertarhan/pi-smart-compact/blob/main/ARCHITECTURE.md)
353
+ - [Changelog](https://github.com/alpertarhan/pi-smart-compact/blob/main/CHANGELOG.md)
354
+ - [Contributing](https://github.com/alpertarhan/pi-smart-compact/blob/main/CONTRIBUTING.md)
355
+ - [Security](https://github.com/alpertarhan/pi-smart-compact/blob/main/SECURITY.md)
356
+ - [Support](https://github.com/alpertarhan/pi-smart-compact/blob/main/SUPPORT.md)
357
+ - [Release checklist](https://github.com/alpertarhan/pi-smart-compact/blob/main/docs/RELEASE.md)
282
358
 
283
359
  ## License
284
360
 
@@ -38,6 +38,7 @@ import type { CompressionProfile, LlmMessage, StructuredExtraction, ExplorationR
38
38
  import type { PendingSlot } from "./pending-slot.ts";
39
39
  import type { PruningResult } from "../utils/pruning.ts";
40
40
  import type { CompactionTier } from "../utils/helpers.ts";
41
+ import type { TokenEstimator } from "../utils/tokens.ts";
41
42
  import type { SmartCompactServices } from "../infra/services.ts";
42
43
  export type Notifier = (msg: string, type?: "info" | "success" | "warning" | "error") => void;
43
44
  export interface CancellationToken {
@@ -76,6 +77,8 @@ export interface RcBase {
76
77
  isRunning: Cell<boolean>;
77
78
  flags: RunFlags;
78
79
  userNote?: string;
80
+ focus?: string;
81
+ maxLlmCalls?: number;
79
82
  timeoutMs: number;
80
83
  phaseTimings: PipelinePhaseTiming[];
81
84
  pipelineStart: number;
@@ -91,6 +94,8 @@ export interface PreparedExt {
91
94
  config: CompactConfig;
92
95
  profileCfg: ProfileConfig;
93
96
  providerCaps: ProviderCapabilities;
97
+ estimator: TokenEstimator;
98
+ adapted: boolean;
94
99
  summaryAuth: ResolvedAuth;
95
100
  segAuth: ResolvedAuth;
96
101
  }
@@ -157,6 +162,7 @@ export interface VerifiedExt extends SynthesizedExt {
157
162
  readonly _verified: true;
158
163
  verificationScore: number;
159
164
  verificationGaps: string[];
165
+ verificationProvenance: import("../types.ts").VerificationProvenance;
160
166
  verified: boolean;
161
167
  }
162
168
  export type VerifiedRc = RcBase & VerifiedExt;