pi-smart-compact 9.7.1 → 10.0.1

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 (206) hide show
  1. package/ARCHITECTURE.md +973 -372
  2. package/CHANGELOG.md +721 -0
  3. package/LICENSE +8 -0
  4. package/README.md +128 -640
  5. package/SECURITY.md +34 -12
  6. package/SUPPORT.md +26 -9
  7. package/assets/DejaVu-LICENSE.txt +187 -0
  8. package/assets/DejaVuSansMono.ttf +0 -0
  9. package/assets/README.md +26 -0
  10. package/assets/skills/context-management/SKILL.md +34 -0
  11. package/dist/app/anchor-cache.d.ts +36 -0
  12. package/dist/app/anchor-cache.d.ts.map +1 -0
  13. package/dist/app/artifact-storage.d.ts +47 -0
  14. package/dist/app/artifact-storage.d.ts.map +1 -0
  15. package/dist/app/background-preparation.d.ts +39 -0
  16. package/dist/app/background-preparation.d.ts.map +1 -0
  17. package/dist/app/compaction-commit-store.d.ts +5 -1
  18. package/dist/app/compaction-commit-store.d.ts.map +1 -1
  19. package/dist/app/context-evidence.d.ts +57 -0
  20. package/dist/app/context-evidence.d.ts.map +1 -0
  21. package/dist/app/context-guide.d.ts +3 -0
  22. package/dist/app/context-guide.d.ts.map +1 -0
  23. package/dist/app/context-operations.d.ts +106 -0
  24. package/dist/app/context-operations.d.ts.map +1 -0
  25. package/dist/app/effective-state.d.ts +23 -0
  26. package/dist/app/effective-state.d.ts.map +1 -0
  27. package/dist/app/global-settings-runtime.d.ts +3 -3
  28. package/dist/app/global-settings-runtime.d.ts.map +1 -1
  29. package/dist/app/hindsight-memory.d.ts +100 -0
  30. package/dist/app/hindsight-memory.d.ts.map +1 -0
  31. package/dist/app/host-cache-ledger.d.ts +68 -0
  32. package/dist/app/host-cache-ledger.d.ts.map +1 -0
  33. package/dist/app/lazy-tools.d.ts +36 -0
  34. package/dist/app/lazy-tools.d.ts.map +1 -0
  35. package/dist/app/memory-backend.d.ts +58 -0
  36. package/dist/app/memory-backend.d.ts.map +1 -0
  37. package/dist/app/mnemopi-memory.d.ts +13 -0
  38. package/dist/app/mnemopi-memory.d.ts.map +1 -0
  39. package/dist/app/mnemopi-protocol.d.ts +78 -0
  40. package/dist/app/mnemopi-protocol.d.ts.map +1 -0
  41. package/dist/app/mnemopi-worker.d.ts +2 -0
  42. package/dist/app/mnemopi-worker.d.ts.map +1 -0
  43. package/dist/app/model-feasibility.d.ts +20 -0
  44. package/dist/app/model-feasibility.d.ts.map +1 -0
  45. package/dist/app/native-compaction.d.ts +88 -0
  46. package/dist/app/native-compaction.d.ts.map +1 -0
  47. package/dist/app/native-continuity-bridge.d.ts.map +1 -1
  48. package/dist/app/navigation-data.d.ts +28 -0
  49. package/dist/app/navigation-data.d.ts.map +1 -0
  50. package/dist/app/navigation-types.d.ts +60 -0
  51. package/dist/app/navigation-types.d.ts.map +1 -0
  52. package/dist/app/pending-slot.d.ts +11 -1
  53. package/dist/app/pending-slot.d.ts.map +1 -1
  54. package/dist/app/preflight.d.ts.map +1 -1
  55. package/dist/app/register-context-tools.d.ts +16 -3
  56. package/dist/app/register-context-tools.d.ts.map +1 -1
  57. package/dist/app/register-navigation.d.ts +20 -0
  58. package/dist/app/register-navigation.d.ts.map +1 -0
  59. package/dist/app/register-smart-compact-command.d.ts +17 -2
  60. package/dist/app/register-smart-compact-command.d.ts.map +1 -1
  61. package/dist/app/register-smart-compact-tool.d.ts.map +1 -1
  62. package/dist/app/register-smart-context-tool.d.ts +55 -0
  63. package/dist/app/register-smart-context-tool.d.ts.map +1 -0
  64. package/dist/app/run-context.d.ts +1 -0
  65. package/dist/app/run-context.d.ts.map +1 -1
  66. package/dist/app/run-smart-compact.d.ts +3 -3
  67. package/dist/app/run-smart-compact.d.ts.map +1 -1
  68. package/dist/app/session-handoff.d.ts +64 -0
  69. package/dist/app/session-handoff.d.ts.map +1 -0
  70. package/dist/app/session-lineage.d.ts +17 -0
  71. package/dist/app/session-lineage.d.ts.map +1 -0
  72. package/dist/app/session-run-lock.d.ts +0 -2
  73. package/dist/app/session-run-lock.d.ts.map +1 -1
  74. package/dist/app/settled-auto-trigger.d.ts +2 -0
  75. package/dist/app/settled-auto-trigger.d.ts.map +1 -1
  76. package/dist/app/smart-compact-input.d.ts +1 -1
  77. package/dist/app/smart-compact-input.d.ts.map +1 -1
  78. package/dist/app/smart-compact-policy.d.ts +1 -1
  79. package/dist/app/smart-compact-policy.d.ts.map +1 -1
  80. package/dist/app/steps/extract.d.ts +45 -1
  81. package/dist/app/steps/extract.d.ts.map +1 -1
  82. package/dist/app/steps/metrics.d.ts +1 -0
  83. package/dist/app/steps/metrics.d.ts.map +1 -1
  84. package/dist/app/steps/persist.d.ts.map +1 -1
  85. package/dist/app/steps/prepare.d.ts.map +1 -1
  86. package/dist/app/steps/recover.d.ts +9 -0
  87. package/dist/app/steps/recover.d.ts.map +1 -1
  88. package/dist/app/steps/synthesize.d.ts.map +1 -1
  89. package/dist/app/steps/tier.d.ts.map +1 -1
  90. package/dist/app/steps/verify.d.ts.map +1 -1
  91. package/dist/app/steps/visual.d.ts +4 -0
  92. package/dist/app/steps/visual.d.ts.map +1 -0
  93. package/dist/app/steps/window.d.ts.map +1 -1
  94. package/dist/app/tool-artifacts.d.ts +27 -0
  95. package/dist/app/tool-artifacts.d.ts.map +1 -0
  96. package/dist/app/visual-archive.d.ts +29 -0
  97. package/dist/app/visual-archive.d.ts.map +1 -0
  98. package/dist/constants.d.ts +96 -1
  99. package/dist/constants.d.ts.map +1 -1
  100. package/dist/domain/compaction-usage.d.ts +16 -0
  101. package/dist/domain/compaction-usage.d.ts.map +1 -0
  102. package/dist/domain/model-capacity.d.ts +12 -0
  103. package/dist/domain/model-capacity.d.ts.map +1 -0
  104. package/dist/domain/provider-evaluation.d.ts +7 -0
  105. package/dist/domain/provider-evaluation.d.ts.map +1 -1
  106. package/dist/domain/telemetry.d.ts +43 -2
  107. package/dist/domain/telemetry.d.ts.map +1 -1
  108. package/dist/domain/tool-semantics.d.ts +23 -0
  109. package/dist/domain/tool-semantics.d.ts.map +1 -1
  110. package/dist/index.d.ts.map +1 -1
  111. package/dist/index.js +15757 -6942
  112. package/dist/infra/ai-messages.d.ts +1 -1
  113. package/dist/infra/ai-messages.d.ts.map +1 -1
  114. package/dist/infra/context-graph.d.ts +38 -7
  115. package/dist/infra/context-graph.d.ts.map +1 -1
  116. package/dist/infra/fs.d.ts.map +1 -1
  117. package/dist/infra/hindsight-client.d.ts +73 -0
  118. package/dist/infra/hindsight-client.d.ts.map +1 -0
  119. package/dist/infra/hindsight-receipts.d.ts +68 -0
  120. package/dist/infra/hindsight-receipts.d.ts.map +1 -0
  121. package/dist/infra/llm-client.d.ts +26 -23
  122. package/dist/infra/llm-client.d.ts.map +1 -1
  123. package/dist/infra/memory-ref.d.ts +27 -0
  124. package/dist/infra/memory-ref.d.ts.map +1 -0
  125. package/dist/infra/native-protocol.d.ts +54 -0
  126. package/dist/infra/native-protocol.d.ts.map +1 -0
  127. package/dist/infra/optional-components.d.ts +15 -0
  128. package/dist/infra/optional-components.d.ts.map +1 -0
  129. package/dist/infra/paths.d.ts +2 -0
  130. package/dist/infra/paths.d.ts.map +1 -1
  131. package/dist/infra/services.d.ts +15 -5
  132. package/dist/infra/services.d.ts.map +1 -1
  133. package/dist/infra/visual-renderer.d.ts +16 -0
  134. package/dist/infra/visual-renderer.d.ts.map +1 -0
  135. package/dist/mnemopi-worker.js +213 -0
  136. package/dist/phases/explore.d.ts +12 -9
  137. package/dist/phases/explore.d.ts.map +1 -1
  138. package/dist/phases/synthesize.d.ts +18 -3
  139. package/dist/phases/synthesize.d.ts.map +1 -1
  140. package/dist/phases/verify.d.ts +5 -1
  141. package/dist/phases/verify.d.ts.map +1 -1
  142. package/dist/rtk.d.ts +7 -0
  143. package/dist/rtk.d.ts.map +1 -0
  144. package/dist/rtk.js +767 -0
  145. package/dist/types.d.ts +128 -4
  146. package/dist/types.d.ts.map +1 -1
  147. package/dist/ui/dashboard-format.d.ts +2 -1
  148. package/dist/ui/dashboard-format.d.ts.map +1 -1
  149. package/dist/ui/dashboard-insights.d.ts +9 -1
  150. package/dist/ui/dashboard-insights.d.ts.map +1 -1
  151. package/dist/ui/error-format.d.ts +7 -2
  152. package/dist/ui/error-format.d.ts.map +1 -1
  153. package/dist/ui/handoff-overlay.d.ts +26 -0
  154. package/dist/ui/handoff-overlay.d.ts.map +1 -0
  155. package/dist/ui/home-overlay.d.ts +54 -0
  156. package/dist/ui/home-overlay.d.ts.map +1 -0
  157. package/dist/ui/metrics-dashboard-overlay.d.ts.map +1 -1
  158. package/dist/ui/metrics-report.d.ts.map +1 -1
  159. package/dist/ui/navigation-overlay.d.ts +92 -0
  160. package/dist/ui/navigation-overlay.d.ts.map +1 -0
  161. package/dist/ui/overlays.d.ts +12 -2
  162. package/dist/ui/overlays.d.ts.map +1 -1
  163. package/dist/ui/profiles.d.ts +51 -0
  164. package/dist/ui/profiles.d.ts.map +1 -0
  165. package/dist/ui/settings-complex.d.ts +49 -3
  166. package/dist/ui/settings-complex.d.ts.map +1 -1
  167. package/dist/ui/settings-list.d.ts +28 -0
  168. package/dist/ui/settings-list.d.ts.map +1 -0
  169. package/dist/ui/settings-overlay.d.ts +13 -6
  170. package/dist/ui/settings-overlay.d.ts.map +1 -1
  171. package/dist/ui/storage-report.d.ts +4 -0
  172. package/dist/ui/storage-report.d.ts.map +1 -0
  173. package/dist/utils/backups.d.ts.map +1 -1
  174. package/dist/utils/cache.d.ts +6 -2
  175. package/dist/utils/cache.d.ts.map +1 -1
  176. package/dist/utils/config.d.ts +12 -0
  177. package/dist/utils/config.d.ts.map +1 -1
  178. package/dist/utils/helpers.d.ts.map +1 -1
  179. package/dist/utils/id-fingerprint.d.ts +3 -1
  180. package/dist/utils/id-fingerprint.d.ts.map +1 -1
  181. package/dist/utils/issues.d.ts +61 -0
  182. package/dist/utils/issues.d.ts.map +1 -0
  183. package/dist/utils/pruning.d.ts.map +1 -1
  184. package/dist/utils/session-log.d.ts +0 -2
  185. package/dist/utils/session-log.d.ts.map +1 -1
  186. package/dist/utils/state.d.ts +3 -1
  187. package/dist/utils/state.d.ts.map +1 -1
  188. package/dist/utils/tokens.d.ts +10 -2
  189. package/dist/utils/tokens.d.ts.map +1 -1
  190. package/docs/MIGRATING_TO_V8.md +7 -1
  191. package/docs/README.md +69 -0
  192. package/docs/RELEASE.md +173 -56
  193. package/docs/assets/banner.png +0 -0
  194. package/docs/assets/banner.svg +1158 -70
  195. package/docs/assets/pi-smart-compact.png +0 -0
  196. package/docs/assets/pi-smart-compact.svg +24 -0
  197. package/docs/configuration.md +637 -0
  198. package/docs/evaluation.md +408 -0
  199. package/docs/guide.md +860 -0
  200. package/docs/hindsight-memory.md +314 -0
  201. package/docs/identity.md +124 -0
  202. package/package.json +44 -11
  203. package/dist/provider-eval.js +0 -2122
  204. package/dist/provider-scenario-eval.js +0 -2900
  205. package/dist/telemetry-report.js +0 -1973
  206. package/docs/provider-evaluation-2026-08-06.md +0 -63
package/docs/guide.md ADDED
@@ -0,0 +1,860 @@
1
+ # Pi Continuity user guide
2
+
3
+ Pi Continuity keeps a long Pi Coding Agent session usable: it keeps the working
4
+ context small, keeps removed evidence retrievable, and carries goals, decisions,
5
+ errors and next steps across compaction. Compaction and project memory are the
6
+ mechanisms; context hygiene and session continuity are the goal.
7
+
8
+ Pi Continuity is the product name. Everything you type or configure keeps the
9
+ existing technical names: the npm package `pi-smart-compact`, the
10
+ `/smart-compact` command, the `smart_*` agent tools and the `smartCompact`
11
+ settings key. The UI title still reads "Smart Compact".
12
+
13
+ This guide is task oriented. For every setting, default and range, see the
14
+ [configuration reference](./configuration.md). For measurements, pilots and
15
+ release evidence, see [evaluation](./evaluation.md).
16
+
17
+ > [!NOTE]
18
+ > **Which version this describes.** This guide targets Pi Continuity `10.0.1`,
19
+ > the stable release of the context-hygiene and continuity rework. The earlier
20
+ > `9.8.0-canary.*` entries in the changelog are historical local candidates,
21
+ > not npm releases. See [upgrade notes](#upgrade-from-9x) when coming from 9.x
22
+ > and [the changelog](../CHANGELOG.md) for the release scope and evidence limits.
23
+
24
+ ## Contents
25
+
26
+ - [How it works in one minute](#how-it-works-in-one-minute)
27
+ - [Install and first run](#install-and-first-run)
28
+ - [Upgrade from 9.x](#upgrade-from-9x)
29
+ - [The Home screen](#the-home-screen)
30
+ - [Clean up tool output](#clean-up-tool-output)
31
+ - [Compact now](#compact-now)
32
+ - [Let it run automatically](#let-it-run-automatically)
33
+ - [Retrieve archived output](#retrieve-archived-output)
34
+ - [Checkpoint and rewind](#checkpoint-and-rewind)
35
+ - [Session navigation](#session-navigation)
36
+ - [Agent tools](#agent-tools)
37
+ - [Memory: what is stored where](#memory-what-is-stored-where)
38
+ - [Pi host integration](#pi-host-integration)
39
+ - [Experimental features](#experimental-features)
40
+ - [Recovery](#recovery)
41
+ - [Storage and privacy](#storage-and-privacy)
42
+ - [Troubleshooting](#troubleshooting)
43
+ - [Command reference](#command-reference)
44
+
45
+ ## How it works in one minute
46
+
47
+ Pi Continuity works in four layers. Prefer the cheaper, recoverable ones
48
+ before a lossy compaction when they fit the task; each can be used on its own.
49
+
50
+ | Layer | What you use | Model call? |
51
+ | --- | --- | --- |
52
+ | 1. Context hygiene | [Clean up tool output](#clean-up-tool-output), [offload of huge outputs](#automatic-offload-of-large-outputs), the [RTK companion](#rtk-companion-optional-experimental) | No |
53
+ | 2. Recoverable continuity | [Retrieve archived output](#retrieve-archived-output), [checkpoint and rewind](#checkpoint-and-rewind), [session navigation](#session-navigation), [hand-off](#hand-off-to-a-new-session) | No |
54
+ | 3. Verified compaction | [Compact now](#compact-now) or [automatic compaction](#let-it-run-automatically): older history becomes a verified summary; recent turns stay raw | Usually (Fast may use none) |
55
+ | 4. Cross-session memory | [Project memory](#memory-what-is-stored-where): facts `smart_recall` finds in later sessions | No (a Hindsight server runs its own models) |
56
+
57
+ Layers 1 and 2 are recoverable: the original output stays in Pi's session file
58
+ or in a private artifact file, and the agent can search and read it back.
59
+ Layer 3 replaces history with a summary. The summary is checked against facts
60
+ extracted from the conversation first, but it is still a summary: some
61
+ incidental details are not kept. A backup of the replaced text is written by
62
+ default.
63
+
64
+ ### What is on by default
65
+
66
+ | Status | Features |
67
+ | --- | --- |
68
+ | On by default | Replacing Pi's summary when Pi compacts, **Compact now**, `/smart-compact trim`, session navigation, agent tools on demand, local project memory, backups, secret scrubbing |
69
+ | Optional, off until selected | **Automatic cleanup**, **Offload huge outputs**, the `When idle` and `Prepare in background` strategies, the Hindsight and Mnemopi memory stores, personal-data scrubbing |
70
+ | Experimental | [Provider compaction, image snapshots](#summary-format-provider-compaction-and-images) and the [RTK companion](#rtk-companion-optional-experimental) |
71
+
72
+ Settings and defaults are listed in the
73
+ [configuration reference](./configuration.md#all-settings).
74
+
75
+ ## Install and first run
76
+
77
+ Requirements: Pi Coding Agent 0.87.1 or newer, Node.js 22.19 or newer.
78
+
79
+ ```bash
80
+ pi install npm:pi-smart-compact
81
+ ```
82
+
83
+ Then, inside Pi:
84
+
85
+ ```text
86
+ /smart-compact
87
+ ```
88
+
89
+ Opening Home changes nothing. With the built-in defaults, automatic compaction
90
+ depends on Pi starting it. Automatic local cleanup, early output offload and
91
+ speculative background preparation are off until selected.
92
+
93
+ ## Upgrade from 9.x
94
+
95
+ 10.0.0 is the Pi Continuity product and workflow rework. The npm package,
96
+ `/smart-compact` commands, `smart_*` tools, `smartCompact` settings namespace
97
+ and stored paths keep their names; do not rename existing data directories.
98
+
99
+ 1. Update Pi to **0.87.1+** and use **Node.js 22.19+**. Install the release with
100
+ `pi install npm:pi-smart-compact@10.0.1`, then reload or restart Pi.
101
+ 2. Open `/smart-compact` in the TUI. The bare command now opens Home; **Compact
102
+ now** starts the interactive compaction flow. Print/RPC/SDK use still runs
103
+ compaction directly. Review requires **A** to apply, not Enter.
104
+ 3. Expect the agent to see `smart_tools` first. It loads navigation, history,
105
+ memory and compaction tools on demand. Choose **Always available** only if
106
+ you want all permitted tools exposed from the start.
107
+ 4. Review **Memory store** if you use project memory. Exactly one backend is
108
+ used, with no silent fallback. Mnemopi and image snapshots now require
109
+ [separately installed optional components](../README.md#optional-components);
110
+ the default local memory store does not.
111
+
112
+ Automatic cleanup, early offload, background preparation, provider-native
113
+ compaction and image snapshots remain opt-in. Existing compaction permissions
114
+ are preserved. Claude subscription routes still need the compatible separate
115
+ adapter described under [provider compaction](#summary-format-provider-compaction-and-images).
116
+
117
+ ## The Home screen
118
+
119
+ A bare `/smart-compact` in the TUI opens Home. Without a UI (print, RPC, SDK) it
120
+ instead runs one compaction with your configured defaults.
121
+
122
+ The header shows `Context:` (current usage or why compaction is blocked) and
123
+ `Automatic: off | follows Pi | when idle | prepare in background · Agent: allowed | off`.
124
+
125
+ | Row | What it does |
126
+ | --- | --- |
127
+ | **Compact now** | Opens the compact picker to choose a mode and summary model. Shows `unavailable` with a reason when blocked. |
128
+ | **Clean up tool output** | Queues local cleanup (`no model call`). Applies at the next completed turn. Shows `held for a cold cache` with the reason when automatic cleanup is holding a batch; selecting it applies that batch at the next completed turn instead. |
129
+ | **Settings** | `How it runs`, `Summary format`, `Models`, `Memory`, `Agent tools & navigation`, `Advanced settings`. |
130
+ | **History & recovery** | `Session navigation`, `Hand off to a new session`, `Restore a backup`, `Unfinished tasks`, `Storage`, `Forget local project memory`. |
131
+ | **Status & help** | `Readiness & details`, `Which action should I use?`, `Metrics` (`Report`, `Dashboard`). |
132
+
133
+ Keys on every list: `↑`/`↓` choose, `Enter` select, `Esc` back (from Home,
134
+ back to chat). Long help and result screens also scroll with `PgUp`/`PgDn` and
135
+ `Home`/`End`. When a label or value is truncated, the selected row shows it in
136
+ full below the list. In settings lists, `r` resets the selected row to its
137
+ default (or to `global` on the branch page); `r` typed into an open text field
138
+ is just text.
139
+
140
+ `Readiness & details` uses local evidence only. "local checks pass" means no
141
+ local blocker was found. It does not mean a provider accepted a request,
142
+ credentials were valid, or billing was checked.
143
+
144
+ ## Clean up tool output
145
+
146
+ Use this when the context is filling with old tool output but you do not want a
147
+ summary yet.
148
+
149
+ ```text
150
+ /smart-compact trim
151
+ ```
152
+
153
+ Or Home → **Clean up tool output**. Either one:
154
+
155
+ - makes no model call and does not force a new turn;
156
+ - is queued, not applied: **the first next provider request is still sent
157
+ untrimmed**, and the edit applies at the next natural completed-turn boundary;
158
+ - replaces old successful text results of at least 4,096 characters with a
159
+ digest marker, up to 32 outputs per boundary: read-only tools, shell
160
+ (`bash`) output and `smart_context` `read` pages;
161
+ - keeps the latest four assistant turns, an active checkpoint's prefix, errors,
162
+ every tool call (including shell commands), writes, unknown tools, turns
163
+ that mix shell or read-only calls with any other tool, instruction/skill-file
164
+ reads, `smart_context` results other than `read`, and another extension's
165
+ explicit context edits;
166
+ - is cancelled with a visible notice if a return to an anchor is pending or a
167
+ newer boundary change arrives.
168
+
169
+ Trimmed output stays retrievable with
170
+ [`smart_context`](#retrieve-archived-output). Trimming is not secure deletion:
171
+ the raw history remains in Pi's session JSONL.
172
+
173
+ A digest marker has at most 6 lines and 400 characters and is derived only
174
+ from the recorded call and output:
175
+
176
+ ```text
177
+ [Archived bash output, 18088 chars. Retrieve with smart_context action=read id=3f9a1c2e.]
178
+ $ bun test
179
+ > bun test v1.4.2
180
+ ! error: expect(received).toBe(expected)
181
+ ! warning: snapshot obsolete
182
+ ```
183
+
184
+ Line 1 names the tool, size and retrieval ID. Then, when known: the subject
185
+ (`path:` for reads, `$ ` and the first command line for shell, the pattern or
186
+ path for searches), the first non-empty output line (`> `), and up to three
187
+ lines matching error, failure, warning, exception, traceback, panic, exit-code,
188
+ `command not found`, `permission denied`, `ENOENT` or `EACCES` (`! `). Each
189
+ line is whitespace-normalized and cut to 100 characters; lines past the
190
+ limit are dropped from the end. Shell calls are never removed, only their old
191
+ output; errored shell results stay whole. An archived `smart_context` `read`
192
+ page points back at the source it paged
193
+ (`[Archived smart_context read of id=<source-id>, …]`), so the agent re-reads
194
+ the source instead of the copy.
195
+
196
+ Superseded output goes first. A read-only result whose path a later call
197
+ writes, edits or deletes (`write`, `edit`, path-carrying mutating tools, or a
198
+ literal `bash` target such as `sed -i`, `>` or `rm`), or reads again in full
199
+ (a plain `read` without `offset`/`limit`; searches, listings, symbol reads and
200
+ ranged reads never count), is archived before other outputs, edited ones
201
+ before re-read ones, each in session order; the 32-output cap then keeps
202
+ them. The marker's subject line says why, e.g.
203
+ `path: src/a.ts (superseded: edited later)` or
204
+ `(superseded: read again in full later)`. Paths match only as written after
205
+ normalization (`./src/a.ts` = `src/a.ts`, but not `/repo/src/a.ts`). This
206
+ changes only the order and the note, never which outputs are eligible.
207
+
208
+ ### Automatic cleanup (optional)
209
+
210
+ Automatic trimming is separate and off by default: turn on
211
+ **Automatic cleanup** (`contextHygieneEnabled`), or pick the `Cleanup only` or
212
+ `Fully automatic` preset. It uses the same eligibility rules as the manual
213
+ command and needs `smart_context` reachable by the model, since the digest
214
+ points it there (any **Agent tools** choice except **Off**).
215
+
216
+ A batch needs at least 16,384 characters of net savings and eight assistant
217
+ turns after the last trim, rewind or compaction. It then commits at the turn
218
+ boundary for one of three causes, recorded on the trim entry:
219
+
220
+ - `pressure`: context usage reached the early pressure gate.
221
+ - `break-even`: the model's catalog prices say the trim pays back its prompt
222
+ cache rewrite within 24 further requests.
223
+ - `cold`: otherwise the batch is held back until the cache has expired (5
224
+ minutes after the last response, 1 hour when the last response that wrote
225
+ cache reported 1h retention). A refresh from Pi's cache warming keeps the
226
+ entry alive, so the batch also waits one lifetime past the latest refresh.
227
+ The first request after that already sends the trimmed context, every later
228
+ request keeps sending it, and the edits commit at the next completed turn
229
+ that nothing else claims.
230
+
231
+ While a batch is held, Pi Continuity stops Pi's cache warming once another
232
+ refresh no longer pays for itself, because the held batch will rewrite that
233
+ cache anyway. Home notes the stop on **Clean up tool output**, and Pi's
234
+ `/session` shows warming as stopped by an extension.
235
+
236
+ The timing uses the model's catalog price ratios and estimated token counts,
237
+ not measured cache behavior. The formulas are in
238
+ [configuration](./configuration.md#automatic-trim-timing).
239
+
240
+ ## Compact now
241
+
242
+ Use this for a deliberate compaction with a preview, even below the automatic
243
+ threshold.
244
+
245
+ 1. Home → **Compact now** (or `/smart-compact balanced`, see
246
+ [command reference](#command-reference)).
247
+ 2. The compact picker compares `Fast`, `Balanced` and `Thorough` by estimated
248
+ saving and highlights a recommendation.
249
+ 3. Review the summary and choose **Apply** or **Cancel**.
250
+
251
+ Compact picker keys:
252
+
253
+ | Key | Action |
254
+ | --- | --- |
255
+ | `↑` / `↓` | Choose `Fast`, `Balanced` or `Thorough`; the plan is recalculated |
256
+ | `Enter` | Compact with the selected mode; only viable plans run |
257
+ | `M` | Choose the summary model and replan (the hint appears when the current model does not fit) |
258
+ | `D` | Show or hide technical details: estimator, targets, routes, boundaries, recommendation reason |
259
+ | `S` | Show the effective state, then return to the picker |
260
+ | `PgUp` / `PgDn` | Page the details on short terminals |
261
+ | `Esc` | Back to Home; nothing changes |
262
+
263
+ Review keys: `A` applies. `C` or `Esc` cancels. `Enter` never applies. `D`
264
+ toggles details; arrows, `PgUp`/`PgDn` and `Home`/`End` scroll. The review is
265
+ on by default (`requireApproval: true`). Review time does not count against the
266
+ run time limit.
267
+
268
+ What to expect:
269
+
270
+ - The conversation is unchanged until you apply and Pi confirms the matching
271
+ compaction. Backups, continuity state and project memory are written only
272
+ after that confirmation.
273
+ - `100/100` is labelled **verification coverage**. The source score and
274
+ whether the text came from the model, deterministic repair or the fallback
275
+ stay visible.
276
+ - A plan projected below 10% net savings does not start. A finished summary
277
+ that misses its mode target or savings floor is rejected before apply.
278
+ - A manual timeout or failure leaves the conversation unchanged and does not
279
+ start Pi's own compactor.
280
+ - Models too small for the planned requests are shown as unavailable with a
281
+ reason. Choosing a summary model never switches your chat model.
282
+
283
+ Use `--focus=<topic or path>` to give that topic more room in the summary. It
284
+ does not keep non-adjacent messages raw.
285
+
286
+ ## Let it run automatically
287
+
288
+ Settings → **How it runs** offers presets. Each one is a single atomic change
289
+ to existing settings.
290
+
291
+ | Preset | Automatic compaction | Automatic cleanup | Agent can call `smart_compact` |
292
+ | --- | --- | --- | --- |
293
+ | `With Pi (default)` | Only when Pi's own auto-compaction fires | Off | Follows Pi's tool settings |
294
+ | `Manual only` | Off | Off | No |
295
+ | `Manual + agent` | Off | Off | Yes |
296
+ | `Cleanup only` | Off | On | No |
297
+ | `Fully automatic` | Starts itself when idle (`settled`) | On | No |
298
+
299
+ Two points matter most:
300
+
301
+ - **`With Pi (default)` is passive.** It replaces the summary only when Pi
302
+ starts a compaction. If Pi's auto-compaction is off, nothing compacts
303
+ automatically. Extensions cannot read Pi's setting, so readiness reports it
304
+ as `unknown`.
305
+ - **`Fully automatic` works with Pi's auto-compaction off.** It asks Pi to
306
+ compact at the next idle, queue-empty boundary once context reaches
307
+ `Start at context %`, with a 10-minute cooldown after a compaction.
308
+
309
+ `Start at context %` counts against the model's full window. On a large-window
310
+ model (Home warns above 400k tokens), set `Context cap for start % (tokens)`
311
+ (`maxContextTokens`) to measure it against a smaller window instead; requests
312
+ and safety headroom still use the real window.
313
+
314
+ Turning `Automatic compaction` off disables both Smart Compact strategies. It
315
+ does not turn off Pi's own compactor. Automatic runs are capped at 60 seconds
316
+ and four model calls, whatever the configured limits are. When they fail, Pi
317
+ may still use its own compactor. See
318
+ [automatic strategies](./configuration.md#automatic-strategies) for the
319
+ background strategy and the gate arithmetic.
320
+
321
+ ## Retrieve archived output
322
+
323
+ The agent retrieves trimmed, rewound, offloaded or image-archived output with
324
+ `smart_context`. You normally do not call it yourself; you can ask the agent to.
325
+
326
+ Each line below is a separate example tool input, not one JSON document or a
327
+ batch of calls. Replace `<source-id>` with an ID returned by `status` or `search`.
328
+
329
+ ```jsonl
330
+ {"action":"status"}
331
+ {"action":"search","query":"AUTH_EXPIRED","limit":3}
332
+ {"action":"read","id":"<source-id>","line":120,"limit":20}
333
+ {"action":"read","id":"<source-id>","offset":0,"limit":2048}
334
+ {"action":"search","query":"AUTH_EXPIRED","scope":"lineage"}
335
+ ```
336
+
337
+ | Action | Behavior |
338
+ | --- | --- |
339
+ | `status` | Checkpoint validity and archived source IDs, newest first. Default 8, maximum 32 per page; continue with `offset` / `nextOffset`. |
340
+ | `search` | Literal, case-sensitive text or source-label match; first match per source with excerpt, line and offset. Default 5 hits, maximum 10; scans at most 32 sources or 4 Mi characters per request. `nextOffset` is a source cursor. No regex or embeddings. |
341
+ | `read` | By character `offset` with `limit` characters (default 2,048), or by 1-based `line` with `limit` lines (default 40, maximum 200). At most 4,096 characters per call. |
342
+
343
+ By default (`"scope":"session"`), retrieval only returns output this extension
344
+ archived on the active branch and reads no other session file. Text is
345
+ scrubbed again with the current privacy settings before search or paging. You
346
+ get the originally recorded tool output, not bytes the tool had already
347
+ truncated before Pi recorded it. Each archive records a SHA-256 of the
348
+ archived text; `read` and `search` refuse text that no longer matches (for
349
+ example after a hand-edited session file), and a rewind leaves such outputs
350
+ out of recovery. Archives from earlier versions have no hash and are read as
351
+ before.
352
+
353
+ With `"scope":"lineage"`, `status`, `search` and `read` also reach the sessions
354
+ this one was handed off or forked from, following each session's recorded
355
+ parent up to 3 levels (files over 64 MiB, missing files and cycles end the
356
+ walk). Parent files are read, never opened through Pi or written. Their
357
+ sources come after the active branch's and carry `session` and `depth`;
358
+ `status` adds a `lineage` count per parent, and `read` of a parent source says
359
+ which session it came from. Each parent's own archive records authorize and
360
+ verify its outputs; checkpoints, rewind and trim stay on the active branch.
361
+
362
+ ### Automatic offload of large outputs
363
+
364
+ Optional and off by default. With **Offload huge outputs**
365
+ (`artifactOffloadEnabled`) on and `smart_context` reachable by the model (any
366
+ **Agent tools** choice except **Off**, and not hidden with `/tools`),
367
+ successful, known read-only text results of at least 16,384 characters are
368
+ saved before their first model request. The model sees the tool/source label,
369
+ size, an `artifact-<hash>` ID and short first/last excerpts.
370
+
371
+ - Not offloaded: errors, images, shell commands, writes, unknown tools,
372
+ `read`/`read_symbol`/`read_enclosing` deliveries, instruction/skill-file
373
+ reads and `smart_context` itself. File reads stay inline on first delivery,
374
+ so read-before-edit guards see what was actually read.
375
+ - This is not a summary. The agent has to search or read the omitted parts
376
+ when it needs them. Total savings depend on how much it reads back.
377
+ - Each file is at most 2 MiB. A session holds at most 256 files or 32 MiB; at
378
+ the limit, new offloads stop instead of evicting older evidence.
379
+ - A storage failure, cancellation, unsafe path or quota limit leaves the
380
+ original result unchanged.
381
+
382
+ ## Checkpoint and rewind
383
+
384
+ Use this for bounded research: set a checkpoint, explore, then replace the
385
+ exploration with a short report.
386
+
387
+ Example inputs (one JSON object per call; explore between checkpoint and rewind):
388
+
389
+ ```jsonl
390
+ {"action":"checkpoint","label":"Investigate auth expiry"}
391
+ {"action":"rewind","report":"Expiry must use <=. Keep async API. Failed approach: local-time parsing. Next: patch and test."}
392
+ {"action":"plan"}
393
+ {"action":"trim"}
394
+ ```
395
+
396
+ - `checkpoint`, `rewind` and `trim` return **queued**. Pi commits them at the
397
+ end of the current tool batch.
398
+ - One checkpoint is active at a time; a new one replaces it. It survives reload.
399
+ - New user instructions, a compaction, branch changes or edits to the context
400
+ before the checkpoint invalidate rewind. It does not silently drop new
401
+ requirements.
402
+ - Rewind removes successful read-only tool exchanges as complete call/result
403
+ pairs. Errors, instruction reads, incomplete exchanges, images, shell
404
+ commands, writes and unknown tools stay.
405
+ - **Files, processes, Git state and external effects are never rolled back.**
406
+ - The report (maximum 8,000 characters) is written by the agent and is not
407
+ verified. It should include findings, constraints, failed attempts and the
408
+ next step. More than 512 eligible messages requires a normal compaction.
409
+ - `plan` previews how many outputs a trim would remove and the characters
410
+ saved, without queuing anything.
411
+
412
+ ## Session navigation
413
+
414
+ An anchor is a named point in this conversation with a summary of what was
415
+ true there: the goal, decisions and the state of the work. Anchors are stored
416
+ as messages in the session, so the agent sees them too. Use them to find the
417
+ way back after a long detour.
418
+
419
+ Home → **History & recovery** → **Session navigation**, or `/smart-compact context`:
420
+
421
+ | Row | What it does |
422
+ | --- | --- |
423
+ | **Anchors in this session** | Browse and filter anchors. Open one to read its summary before returning to it. |
424
+ | **Mark this point** | Save an anchor here: a short name, then a summary written in Pi's editor. |
425
+ | **Search other sessions** | Read-only search of anchors saved by earlier sessions of this project (or all projects). Results are history to check, not instructions. Use Pi's `/resume` to open another session; archived tool output of a session this one was handed off or forked from is readable from here with `smart_context` `"scope":"lineage"`. |
426
+ | **How navigation works** | Opens the navigation guide. It is read only when you open it. |
427
+
428
+ Returning to an anchor:
429
+
430
+ - Open the anchor, choose **Return to this anchor**, write what to carry over
431
+ (required), optionally the next message, then confirm. Nothing changes until
432
+ you confirm; `Esc` goes back one step.
433
+ - The conversation continues from the anchor on a new branch. The carryover is
434
+ recorded as Pi's branch summary; the anchor and its summary stay visible to
435
+ the model. The conversation since then stays saved on its own branch.
436
+ - **Only the conversation moves.** Files, running processes, Git state and
437
+ anything else changed since the anchor are not rolled back.
438
+ - While a return is queued or running, automatic cleanup, compaction and
439
+ `smart_context` changes pause. Typing a new message cancels a queued return
440
+ requested by the agent.
441
+
442
+ Settings → **Agent tools & navigation** has the switches: **Session
443
+ navigation** (off hides the panel and the agent tool; recorded anchors and the
444
+ other switches are kept), **Search other sessions**, **Return to an anchor**,
445
+ **Anchor prompt cache** (Anthropic models: keeps a prompt-cache marker on the
446
+ newest anchor, so the context before it is read from cache while later turns
447
+ change), **Anchor status** (footer, display only) and **Navigation guide**.
448
+
449
+ Legacy `context` tool anchors recorded in earlier sessions stay readable in
450
+ browse and search.
451
+
452
+ ### Hand off to a new session
453
+
454
+ ```text
455
+ /smart-compact handoff [dry-run] [-- note]
456
+ ```
457
+
458
+ Opens a new Pi session seeded with one handoff message assembled from what
459
+ this session already recorded, in this order: your note, the latest anchor on
460
+ the branch, the continuity ledger (from the last Continuity compaction, else
461
+ the saved state for this branch), always-kept files (`pinPaths`), a memory
462
+ recall through the selected store (up to 5 results; the query is the note,
463
+ else the anchor, else the ledger goal), and pointers back to this session. No
464
+ model writes it. It is scrubbed and capped at 16,000 characters; recall is cut
465
+ first, then always-kept files, the ledger, the anchor and the note, each marked
466
+ `[truncated]`.
467
+
468
+ The message is saved as an anchor named `handoff-<first 8 characters of this
469
+ session id>`, so navigation lists it and cleanup keeps it. The new session
470
+ records this one as its parent; this session is not modified. With no anchor,
471
+ ledger or note, nothing opens. From the new session, `smart_context` with
472
+ `"scope":"lineage"` searches and reads this session's archived output.
473
+
474
+ From Home → **History & recovery** → **Hand off to a new session**: write an
475
+ optional note (`Enter` continues, empty skips), then review the seed: its
476
+ size and sources, **Read the full seed**, and **Open the new session**. The
477
+ selection starts on **Go back**; `Esc` goes back one step, and on the note
478
+ field closes. Nothing opens until you confirm.
479
+
480
+ `dry-run` only shows the seed and opens nothing: in the TUI as the same
481
+ read-only preview, in other UI modes as a message. Without a UI it warns and
482
+ does nothing.
483
+
484
+ ## Agent tools
485
+
486
+ Settings → **Agent tools & navigation** → **Agent tools** (`toolLoading`)
487
+ decides what the agent sees:
488
+
489
+ | Choice | What the agent sees |
490
+ | --- | --- |
491
+ | **On demand** (default) | One small loader, `smart_tools`. The agent loads a group when it needs it: `navigation`, `history`, `memory` or `compaction`. Loaded groups are forgotten at the next session start, branch change or compaction. |
492
+ | **Always available** | Every permitted tool from the start. |
493
+ | **Off** | No context tools. The human UI keeps working. |
494
+
495
+ `smart_tools` also answers `status`, `unload` and `guide`. The guide is the
496
+ context workflow text; it is returned only when asked for and is never added
497
+ to the system prompt. Loading a group adds only that group's tool declarations.
498
+ Each group still needs its own permission: `compaction` follows **Agent can
499
+ compact**, `memory` needs project memory or a Hindsight/Mnemopi backend, and
500
+ `navigation` needs **Session navigation**. Choices you make with `/tools` win
501
+ over the loader. Pi may keep previously loaded declarations in cached history;
502
+ turning a group off stops it from being called but does not promise that
503
+ earlier request bytes disappear.
504
+
505
+ | Tool | Group | What it does | When it takes effect |
506
+ | --- | --- | --- | --- |
507
+ | `smart_navigation` | `navigation` | View or search anchors, record an anchor, return to one with required carryover | A return ends the turn and is revalidated by the host after the tool batch settles |
508
+ | `smart_context` | `history` | Status, search, read, plan, trim, checkpoint, rewind | Queued edits apply at the end of the current tool batch |
509
+ | `smart_recall` | `memory` | Searches this project's memory in the selected store | Immediately; read-only |
510
+ | `smart_save_memory` | `memory` | Saves or resolves one durable fact | Only after **you** approve the host confirmation dialog |
511
+ | `smart_compact` | `compaction` | Prepares a verified summary and stages it | Never mid-turn. Staged for 5 minutes; applied by the next `/compact` or a compaction Pi starts. |
512
+
513
+ Approval and gates:
514
+
515
+ - `smart_compact` refuses below `Start at context %` (default 60%) or below
516
+ 5,000 tokens. `tool=XX%` in Pi's footer is the tool-output share, not
517
+ context fullness. If a summary is already staged, it reports that and makes
518
+ no calls. With automatic compaction off, nothing consumes the staged summary
519
+ unless you run `/compact`.
520
+ - `smart_save_memory` always opens a confirmation showing the scrubbed kind,
521
+ title, content, paths and the exact destination. Without an interactive UI
522
+ it changes nothing. The agent cannot approve on your behalf.
523
+ - Recall results are untrusted history: the agent is told not to follow
524
+ instructions inside them.
525
+
526
+ ## Memory: what is stored where
527
+
528
+ Pi Continuity keeps several kinds of state. Only one of them is cross-session
529
+ project memory.
530
+
531
+ | State | Purpose | Scope | Removed by |
532
+ | --- | --- | --- | --- |
533
+ | Continuity state | Goals, decisions, constraints, errors and open loops carried between compactions | Project, session and branch | Bounded retention; not affected by `forget` |
534
+ | Project memory | Facts `smart_recall` can find in later sessions | Project, in the selected store only | Resolve; `forget` (local store only) |
535
+ | Backups | Pre-compaction text for restore | Per compaction | Bounded retention |
536
+ | Artifacts | Archived tool output for retrieval | Per origin session | Only you, by hand |
537
+
538
+ A project is the Git root, or the working directory when there is no Git root.
539
+ Your home directory and the filesystem root are never projects; memory tools
540
+ fail there.
541
+
542
+ ### Memory store (`memoryBackend`)
543
+
544
+ Exactly one store is active. It is the only store read or written. There is
545
+ **no fallback**: if the selected store fails, the failure is reported and no
546
+ other store is used. Stores you switch away from are left untouched, not
547
+ migrated or cleared.
548
+
549
+ | `Memory store` | Where facts go | Recall | `scope: "session"` |
550
+ | --- | --- | --- | --- |
551
+ | `This machine` (`local`, default) | Local SQLite context graph: facts you confirm plus verified state from applied compactions | Full-text plus one-hop file links | Supported |
552
+ | `Hindsight server` | Your existing Hindsight server and bank only; confirmed saves only, never transcripts | Strict project-tag-scoped section of that bank | **Not supported**: reads nothing |
553
+ | `Mnemopi (local SQLite)` | A separate SQLite database per project | Bounded full-text search, no embeddings | **Not supported**: skipped, nothing else is read |
554
+
555
+ - Hindsight: Pi Continuity never installs, starts or configures a server. See
556
+ [Hindsight memory backend](./hindsight-memory.md).
557
+ - Mnemopi runs in a bounded `bun --no-install` worker. The engine
558
+ (`@oh-my-pi/pi-mnemopi` 18.3.1) is an optional component you install into
559
+ Pi's package directory; the worker runs on a Bun 1.3.14 or newer from `PATH`,
560
+ or on the optional `bun` (1.4.2) component installed the same way. Nothing is
561
+ downloaded with the extension; **Readiness & details** shows the install
562
+ command (see [Optional components](../README.md#optional-components)).
563
+ Missing pieces fail before any request is sent. Embeddings, model calls,
564
+ automatic consolidation and model downloads are off. It never opens the
565
+ shared OMP/Mnemopi default bank.
566
+ - Each project can hold at most 500 active manually saved facts in the local
567
+ store.
568
+
569
+ ### Refs and resolving facts
570
+
571
+ Every save and recall returns a stable `Ref`. To retire a fact, the agent calls
572
+ `smart_save_memory` with `status: "resolved"` and that `ref`; copied preview
573
+ text does not work. A ref is bound to its project, store and storage target.
574
+ Changing the selected store never redirects a ref. To resolve an old ref,
575
+ restore the original target configuration first.
576
+
577
+ | Store | Effect of resolve |
578
+ | --- | --- |
579
+ | Local | Soft-closes the fact and its links; not a physical deletion |
580
+ | Mnemopi | Deletes that one fact from its original database |
581
+ | Hindsight | Deletes the named remote document and reports the receipt state |
582
+
583
+ ### Forget local project memory
584
+
585
+ `/smart-compact forget` (or History & recovery → **Forget local project
586
+ memory**) needs the TUI and applies only to the local store. It offers:
587
+
588
+ - **Learned from compactions only**: deletes compaction-derived items and keeps
589
+ confirmed facts and legacy items without provenance;
590
+ - **Everything in the local project graph**.
591
+
592
+ It shows counts and asks for confirmation. Mnemopi, Hindsight, continuity
593
+ state, backups and artifacts are not affected.
594
+
595
+ ## Pi host integration
596
+
597
+ ### Pi compaction lifecycle
598
+
599
+ Pi applies one compaction per request: the last extension to answer
600
+ `session_before_compact` wins, and with no answer Pi's built-in summarizer
601
+ runs. When something other than Pi Continuity applies the compaction:
602
+
603
+ - A summary Pi Continuity had already prepared for that session is discarded
604
+ and recorded in `/smart-compact metrics` as `discarded` with reason
605
+ `native-apply:foreign`; its continuity state is not saved. A notice names
606
+ the winner and the model calls that were wasted.
607
+ - Another extension's compaction shows a once-per-session notice even when
608
+ nothing was prepared, because Pi Continuity recorded no state or metrics
609
+ for it.
610
+ - Pi's built-in compaction shows a notice only while automatic compaction is
611
+ on (nothing was ready when Pi asked); earlier continuity state still carries
612
+ over through the capsule.
613
+
614
+ Provider usage of the summary Pi Continuity applies (its own explore,
615
+ synthesize and verify calls, or the provider-native compaction request) is
616
+ returned to Pi with the compaction, so Pi's session totals and cost include
617
+ that work at the route model's catalog rates. Runs that reused a cached
618
+ summary report no usage; work whose usage a provider did not report is left
619
+ out rather than estimated. Discarded preparations are only in
620
+ `/smart-compact metrics`, never in Pi's totals.
621
+
622
+ ### Host prompt-cache ledger
623
+
624
+ For each assistant response in the current session, Pi Continuity records the
625
+ prompt usage the provider reported for Pi's own request: uncached input, cache
626
+ reads and cache writes. Nothing is estimated; responses without reported
627
+ usage, or with zero prompt tokens (aborted or failed requests), are skipped.
628
+
629
+ A request counts as a cache rebuild when it is not the session's first and
630
+ its uncached tokens (input + cache writes) are at least 16,384 and at least
631
+ half of its prompt tokens. Each rebuild gets one cause, checked in this order:
632
+
633
+ - **continuity**: a Continuity edit reached the branch since the previous
634
+ request (an output trim or checkpoint rewind, a navigation pivot, or a Pi
635
+ Continuity compaction). Edits that were queued but not committed do not
636
+ count.
637
+ - **idle-expiry**: the gap since the previous request, or since Pi's latest
638
+ cache-warming refresh after it, exceeded the cache lifetime, 5 minutes, or
639
+ 1 hour while the cached prefix was written with 1-hour retention (only
640
+ Anthropic reports that split).
641
+ - **foreign**: neither. Something else changed the prompt prefix, for
642
+ example another extension, a model or tool change, Pi's built-in
643
+ compaction, or eviction by the provider.
644
+
645
+ Home › Readiness & details lists the request count, the share of prompt
646
+ tokens read from cache, rebuilds by cause with their uncached tokens, and the
647
+ cost Pi priced from that usage when the model has catalog prices. The third
648
+ foreign rebuild in a session shows one notice with the count and uncached
649
+ tokens. The ledger is session-local: it resets on a new or switched session,
650
+ is not persisted, and covers only Pi's own requests; Pi Continuity's summary
651
+ calls are in `/smart-compact metrics` instead.
652
+
653
+ ## Experimental features
654
+
655
+ These features are off by default and are not part of the default workflow.
656
+ Each one has narrow support and known costs; read its limits before turning it
657
+ on.
658
+
659
+ ### RTK companion (optional, experimental)
660
+
661
+ RTK is not a dependency and is never loaded automatically. Install RTK 0.50 or
662
+ newer yourself, then load the companion explicitly:
663
+
664
+ ```bash
665
+ # From a source checkout
666
+ bun run build
667
+ pi -e ./dist/rtk.js
668
+ ```
669
+
670
+ The published subpath is `pi-smart-compact/rtk`; Pi can also load the installed
671
+ package's `dist/rtk.js` by file path. Keep the core extension loaded as well.
672
+
673
+ - Only bare `git status`, `cargo test` and `bun test` are rewritten. Commands
674
+ with arguments, pipes, redirections or substitutions pass unchanged.
675
+ - Load it **before** permission or command-policy hooks, and do not load it
676
+ together with the upstream RTK Pi hook.
677
+ - A failed filtered command is never retried as the original. `RTK_DISABLED=1`
678
+ disables it; `command git status` bypasses it for one call.
679
+ - RTK's own recall store is separate: Pi Continuity neither reads nor scrubs it.
680
+
681
+ ### Summary format: provider compaction and images
682
+
683
+ Settings → **Summary format**:
684
+
685
+ | Choice | Effect |
686
+ | --- | --- |
687
+ | `Verified text` (default) | Checked text summary |
688
+ | `Text + images` | Adds PNG snapshots of old read-only output when the chat model passes the image-cost check; otherwise text only |
689
+ | `Provider (experimental)` | Tries your provider's own compaction first, then verified text. Needs a second `Enter` to confirm. |
690
+
691
+ Provider (native) compaction:
692
+
693
+ - Supported routes: Anthropic Messages (API key or Claude subscription),
694
+ OpenAI Codex subscription and the OpenAI Responses API with an API key.
695
+ Other routes are skipped with a notice.
696
+ - The provider state is opaque and **not verified** by Pi Continuity. It is
697
+ replayed only to the same provider and model. With another model, or when
698
+ replay is not possible, the model reads the text summary instead; on OpenAI
699
+ routes that is only the retained user messages.
700
+ - Claude subscription requests that Pi Continuity makes itself (summaries and
701
+ provider compaction) go through Pi's model runtime, so a provider registered
702
+ by the separate `pi-claude-oauth-adapter` package handles their transport.
703
+ The published adapter `0.2.2` rewrites the request body only inside Pi's
704
+ `before_provider_request` hook, which Pi does not run for these requests; a
705
+ build that normalizes the final payload inside its provider is required for
706
+ full parity ([upstream PR #10](https://github.com/minzique/pi-claude-oauth-adapter/pull/10)).
707
+ Anthropic may bill the compaction as extra usage.
708
+ - A native boundary changes the request prefix, so the provider's prompt cache
709
+ is not reused across it.
710
+ - In sessions smaller than Pi's `compaction.keepRecentTokens`, Pi refuses to
711
+ apply the result; the conversation stays unchanged.
712
+
713
+ Image snapshots:
714
+
715
+ - Experimental and off by default. They add image tokens; they are not a
716
+ cheaper replacement for the text summary. A synthetic pilot used more input
717
+ tokens than the same excerpts as text (see [evaluation](./evaluation.md)).
718
+ - A cost rule is validated only for direct Anthropic `claude-sonnet-5`; other
719
+ models stay text only. Snapshots need the optional `@resvg/resvg-js`
720
+ component, which is not installed with the extension (**Readiness & details**
721
+ shows the install command); when it is missing, output falls back to text.
722
+ - Limits: 2 pages, 8 excerpts of up to 3,000 characters, 1 MB of PNG, and only
723
+ Latin/Turkish text. Errors, writes and edited-away messages are never
724
+ rendered.
725
+
726
+ ## Recovery
727
+
728
+ | Need | Use |
729
+ | --- | --- |
730
+ | Get back the conversation from before a compaction | `/smart-compact restore` → pick a backup → `View content` or `Restore into a new session` |
731
+ | Review tasks carried across compactions | `/smart-compact loops`: resolve/reopen, set priority, pin/unpin |
732
+ | See what artifact storage holds | `/smart-compact storage` (read-only) |
733
+ | Continue in a fresh session with the recorded state | `/smart-compact handoff [-- note]` (see [Hand off to a new session](#hand-off-to-a-new-session)) |
734
+ | See what went wrong recently | `/smart-compact metrics`: effective state, then the last 20 issues |
735
+
736
+ `Restore into a new session` first tries to fork at the exact pre-compaction
737
+ branch point. If that entry no longer exists, it opens a new session with the
738
+ backup injected as context for the next turn. Restore is refused when the
739
+ backup is above 90% of the current model's window; you can still view it. Your
740
+ current session is not modified. Backups contain text, not binary attachments.
741
+
742
+ ## Storage and privacy
743
+
744
+ ### Where files live
745
+
746
+ Everything is under `~/.pi/agent/`. Directories Pi Continuity creates are `0700`
747
+ and its files are `0600`; a custom backup folder gets the same protection.
748
+
749
+ | Path | Contents | Growth |
750
+ | --- | --- | --- |
751
+ | `settings.json` | Pi's settings; Pi Continuity only edits its `smartCompact` section | Host-owned |
752
+ | `compact-backups/` | Scrubbed pre-compaction text backups | Retention-pruned |
753
+ | `smart-compact-artifacts/<session-hash>/` | Archived tool output | **No automatic expiry** |
754
+ | `smart-compact-memory/mnemopi/<projectId>/memory.sqlite` | Mnemopi facts (only when selected) | Until resolved |
755
+ | `.cache/compact-extraction-<session>.json` | Incremental extraction cache | Cache |
756
+ | `.cache/compact-metrics.jsonl` | Local metrics | 5 MiB cap |
757
+ | `.cache/smart-compact-report.html` | Local dashboard | Overwritten |
758
+ | `.cache/smart-compact/projects/` | Project fingerprints | Small |
759
+ | `.cache/smart-compact/states/` | Continuity state and loop overrides | Per branch |
760
+ | `.cache/smart-compact/run-locks/` | Cross-process run leases | Transient |
761
+ | `.cache/smart-compact/native-continuity/` | One-shot handoffs | Transient |
762
+ | `.cache/smart-compact/context-graph.sqlite` | Local project memory | Bounded per project |
763
+ | `.cache/smart-compact/hindsight-receipts.json` | Hindsight submission receipts (only when selected) | Small |
764
+ | `.cache/smart-compact/damage-reports.jsonl` | Post-compaction damage reports | 5 MiB cap |
765
+ | `.cache/smart-compact/remediation-<projectId>.json` | Files to preserve after damage | Small |
766
+
767
+ ### Artifacts have no garbage collection
768
+
769
+ There is deliberately no `--clean` and no automatic artifact deletion. Total
770
+ disk use can grow across sessions. `/smart-compact storage` reports totals,
771
+ per-session status (`in use`, `not referenced in scan`, `unknown`) and scan
772
+ coverage, but "not referenced in scan" does **not** mean "safe to delete":
773
+ sessions can live outside Pi's sessions folder, and a running session can add
774
+ references at any time. Delete an origin directory by hand only when that
775
+ session **and all its forks** are no longer needed. Missing or modified files
776
+ are reported, never replaced with current data.
777
+
778
+ ### Scrubbing
779
+
780
+ High-confidence secret scrubbing (`Scrub secrets`, on by default) runs before
781
+ provider requests, extraction cache, backups, state, project memory and staged
782
+ summaries. It covers common API keys and tokens, JWTs, bearer tokens, private
783
+ keys, credential assignments and passwords in connection URIs. `Scrub personal
784
+ data` (off by default) adds email, phone and card-shaped values. Scrubbing is
785
+ defense in depth, not a DLP system; see the [security policy](../SECURITY.md).
786
+
787
+ What is not covered:
788
+
789
+ - Raw history stays in Pi's session JSONL; trimming and rewind do not delete it.
790
+ - `DEBUG=smart-compact` logs can contain private conversation text.
791
+ - The RTK recall store is outside Pi Continuity.
792
+
793
+ ## Troubleshooting
794
+
795
+ | Symptom | Cause and action |
796
+ | --- | --- |
797
+ | Agent reports "Compaction skipped: context 38% (…) below the 60% agent-tool threshold" | `smart_compact` waits for `Start at context %` of the **active model's** window (`tool=XX%` in the footer is the tool-output share, not context fullness). Use **Compact now** for early compaction. |
798
+ | Nothing compacts automatically | With the default `With Pi`, Pi's auto-compaction must be on (readiness shows `unknown`). Choose `Fully automatic` to start without it. Check `Automatic compaction` and `This branch only`. On a large-window model, see `Context cap for start % (tokens)` in [Let it run automatically](#let-it-run-automatically). |
799
+ | Cleanup did nothing on the next reply | Expected: the next request is sent untrimmed; cleanup applies at the next completed turn. |
800
+ | **Clean up tool output** shows `held for a cold cache` | Expected with **Automatic cleanup**: the batch waits for the prompt cache to expire; see [automatic cleanup](#automatic-cleanup-optional). Select the row to apply it at the next completed turn instead. |
801
+ | Automatic cleanup or offload never happens | Both need `smart_context` reachable: **Agent tools** must not be **Off**, and `smart_context` must not be hidden with `/tools`. Offload also needs **Offload huge outputs** on and applies only to read-only text results of 16,384+ characters. |
802
+ | Agent says a summary is staged, but context did not shrink | Run `/compact` within 5 minutes. With automatic compaction off, nothing else consumes it. |
803
+ | `smart_context`, `smart_recall`, `smart_save_memory` or `smart_navigation` missing | With **On demand**, the agent loads a group through `smart_tools`; with **Off**, no context tool is shown; see [agent tools](#agent-tools). Check `/tools`. |
804
+ | Memory tools say they "must run from a project directory" | Start Pi from inside a project, not from your home directory or `/`. |
805
+ | Recall with `scope: "session"` returns nothing | Not supported on Hindsight or Mnemopi; use project scope. |
806
+ | Hindsight save refused, `FAILED` or "outcome unknown" | See [Hindsight troubleshooting](./hindsight-memory.md#troubleshooting). No other store is used as a fallback. |
807
+ | Mnemopi lock error | Another writer is active. Retry later. Remove `memory.sqlite.lock` only after confirming no process writes that database. |
808
+ | Settings do not save; `settings.json.lock` exists | A Pi process died while writing. Verify no Pi process is writing settings, then remove the lock directory by hand. |
809
+ | Edited `settings.json` by hand, tool list or footer not updated | External edits are read on the next operation; tool and footer state refresh on `/reload` or session restore. |
810
+ | Warning line at the top of Settings | Some `settings.json` values were invalid or converted and are being ignored; the line names them. |
811
+ | Provider compaction was skipped | The chat model's API is not a supported native route; verified text was used. In sessions smaller than Pi's `compaction.keepRecentTokens`, Pi refuses the result and the conversation stays unchanged. |
812
+ | `Text + images` produced text only | Expected unless the chat model is direct Anthropic `claude-sonnet-5` and the optional `@resvg/resvg-js` component is installed; see [image snapshots](#summary-format-provider-compaction-and-images). |
813
+ | Timeout or verification failure | A single `Smart Compact: ...` line explains the effect and next step. Details: `/smart-compact metrics`. Stack traces: `DEBUG=smart-compact`. |
814
+
815
+ Without a UI, warnings and errors go to stderr.
816
+
817
+ ## Command reference
818
+
819
+ ```text
820
+ /smart-compact Home (TUI); without a UI, compact with defaults
821
+ /smart-compact trim queue local cleanup; no model call
822
+ /smart-compact storage read-only artifact inventory
823
+ /smart-compact settings categorized settings (TUI only)
824
+ /smart-compact context session navigation: anchors, search, return (TUI only)
825
+ /smart-compact metrics effective state, recent issues, metrics report
826
+ /smart-compact dashboard interactive metrics dashboard (TUI only)
827
+ /smart-compact restore browse and restore backups
828
+ /smart-compact loops manage open loops
829
+ /smart-compact forget forget local project memory (TUI only)
830
+ /smart-compact handoff [-- note] new session seeded with anchor, ledger, pinned files, recall
831
+ /smart-compact handoff dry-run [-- note] preview the seed; opens nothing
832
+ ```
833
+
834
+ Direct compaction takes, in any order at the start: a model
835
+ (`provider/model`), a mode (`auto`, `fast`, `balanced`, `thorough`),
836
+ `dry-run`, and `verbose` (or `debug`). Options:
837
+
838
+ | Option | Range | Effect |
839
+ | --- | --- | --- |
840
+ | `--focus=<text>` | | Give a topic or path more room |
841
+ | `--max-calls=<n>` | 1–100 | Model call budget for this run |
842
+ | `--max-input-tokens=<n>` | 10000–1000000 | Aggregate prompt-token budget for this run |
843
+ | `--max-latency=<ms>` | 5000–600000 | Cancellation deadline; review time excluded |
844
+ | `--note=<text>` or `-- <text>` | | Steering note for the summary |
845
+
846
+ ```bash
847
+ /smart-compact balanced --focus=src/auth.ts
848
+ /smart-compact anthropic/claude-sonnet-4 fast --max-calls=3
849
+ /smart-compact --note="keep the balanced and fast terminology"
850
+ /smart-compact -- fast is part of this note, not a mode
851
+ ```
852
+
853
+ Controls are read only from the left. Once note text starts, words like `fast`
854
+ or paths are part of the note. Unknown `--` options and out-of-range budgets
855
+ return an error instead of silently using defaults. Call and input budget
856
+ exhaustion falls back to a deterministic summary. A timeout or cancellation
857
+ stops the run with no staged summary.
858
+
859
+ Legacy mode words are still accepted: `aggressive` means `fast`; `slow` and
860
+ `light` mean `thorough`.