@sidshaytay/pi-context-management
Trim old tool results with exact recall and preserve verbatim user messages beside pi's compaction summaries.
Package details
Install @sidshaytay/pi-context-management from npm and Pi will load the resources declared by the package manifest.
$ pi install npm:@sidshaytay/pi-context-management- Package
@sidshaytay/pi-context-management- Version
0.1.2- Published
- Nov 3, 2026
- Downloads
- 409/mo · 230/wk
- Author
- sidshaytay
- License
- MIT
- Types
- extension
- Size
- 53.7 KB
- Dependencies
- 0 dependencies · 1 peer
Pi manifest JSON
{
"extensions": [
"./extensions/index.ts"
]
}Security note
Pi packages can execute code and influence agent behavior. Review the source before installing third-party packages.
README
pi-context-management
Keep long pi sessions useful: replace old tool output with recoverable notes, and keep your exact words beside compaction summaries. Pi still decides when to compact. The extension makes no model calls.
Quick start
Tested with pi 1.2.0, 1.3.0, and 1.5.0, which load the TypeScript source directly. Current pi requires Node.js 22.19 or later.
pi install npm:@sidshaytay/pi-context-management
Run /reload in an existing pi session, or start a new one. Both features are enabled by default. Continue working normally: when eligible old output fills enough context, subsequent requests replace it with notes pointing to saved copies. After compaction, requests also include exact historical user text within the configured budget.
To update an unpinned npm installation, run pi update --extensions and /reload. Updating this package does not change its saved copies or your configuration.
To try it for one invocation from this repository's root:
pi -e ./packages/pi-context-management/extensions/index.ts
To install from this repository's root instead, run pi install ./packages/pi-context-management. Use either the npm or local installation to avoid loading two copies. To remove the npm installation, run pi remove npm:@sidshaytay/pi-context-management and /reload. For a local installation, give pi remove its absolute package path instead.
Using pi-multi-account? First set "contextGuard": false in ~/.pi/agent/provider-failover.json and reload. Its guard also trims context and can initiate compaction. A detected active guard blocks new trimming by this package and produces a warning; this package never changes that setting.
Retrieve trimmed output
When context usage reaches 50% of the model's window, the extension replaces whole eligible results, oldest first, until estimated usage reaches 35% or there are no more eligible results. For a 200K window, this means starting at 100K and aiming to leave 70K. The newest 40K tokens stay protected. Protection can prevent reaching the target.
For example, if two eligible old results save about 20K and 12K after note costs, both are replaced to bring 100K down to roughly 68K. A result is never partially shortened.
Each replacement looks like:
[Trimmed 14,200 tokens of bash output. Full text: /path/to/session/trimmed/tool-id.txt. Use read to see it again.]
Ask the agent to read the path in the note, for example: “Read the saved output at /path/to/session/trimmed/tool-id.txt and check the failure.” Use the actual path from your session. The normal read tool retrieves the copy; larger copies may need an offset. Reads from this package's copy directories are protected from trimming. Copies contain visible text blocks joined with one newline, preserving each block's text exactly. They exclude hidden details and structured payloads. Pi may already have truncated the original output: the copy preserves that visible output, including any link to pi's own larger bash-output file.
The transcript on disk retains its original tool results. Notes and history sections affect outgoing requests only. Copies live at <session-file-without-.jsonl>/trimmed/<safe-tool-call-id>.txt, with private directories (0700) and files (0600). Unsafe IDs are encoded. Copies remain until the session's associated directory is deleted. Forks retain inherited parent-owned paths; deleting the parent can make those copies unavailable.
Trimming needs a successful response to establish which notes the provider's usage count already includes. Missing or invalid bookkeeping postpones new batches until a fresh response. Valid existing notes continue to replay with identical text, including after reload. In-memory sessions cannot create saved copies and skip new trims.
Keep your words after compaction
The outgoing summary keeps pi's existing text and file lists, followed by historical user messages quoted newest first. Whole messages must fit within a 5K approximate-token budget, including labels and the closing sentence. Oversized messages are skipped so smaller older messages can still fit. Text, whitespace, and Unicode stay unchanged; images are omitted.
The closing sentence is:
Re-read any instruction files listed above that apply to the current task.
The section uses active-branch history, including earlier compactions, respects content edits/removals, and excludes the live retained suffix. It does not accumulate on repeated requests. Stored summaries stay unchanged, and other extensions can continue generating summaries.
Configure or disable either feature
Add any overrides under contextManagement in personal ~/.pi/agent/settings.json (or the directory selected by PI_CODING_AGENT_DIR), then /reload. Project settings are not used for these controls. This is the complete default configuration:
{
"contextManagement": {
"trimming": {
"enabled": true,
"triggerTrimAtWindow": 0.5,
"freeUptoWindow": 0.35,
"keepRecentTokens": 40000,
"minResultTokens": 2000,
"tools": ["read", "bash", "grep", "find", "ls", "subagent", "fetch_content", "get_search_content", "web_search"],
"trimMarkdownGlobs": []
},
"verbatimUserMessages": {
"enabled": true,
"budgetTokens": 5000,
"skipPrefixes": ["[failover]", "Provider failover activated"]
}
}
}
Each enabled switch works independently. Set trimming.enabled to false to send original results; set verbatimUserMessages.enabled to false to send only the base summary. Disabling both produces no extension-owned session writes. Existing copies and metadata remain available for re-enabling.
| Setting | Meaning |
|---|---|
triggerTrimAtWindow |
Fraction of the full model window at which a batch starts. |
freeUptoWindow |
Fraction of the full window to leave after the batch; must be positive and below the trigger, which is at most 1. |
keepRecentTokens |
Recent contiguous suffix protected from trimming; nonnegative integer. Any whole message touching it is protected. |
minResultTokens |
Minimum eligible result size; positive integer. |
tools |
Exact eligible tool names; replaces defaults. [] permits no tools. |
trimMarkdownGlobs |
Exceptions allowing specified Markdown reads; [] protects every Markdown read. |
budgetTokens |
Total approximate budget for the added history section; nonnegative integer. Zero inserts nothing. |
skipPrefixes |
Exact case-sensitive starts-with filters for user text; replaces defaults. [] skips no prefixes. |
Markdown exceptions support *, **, and ? against normalized forward-slash paths. Relative patterns match cwd-relative paths; absolute patterns match absolute paths. There is no negation or shell expansion. For example, "trimMarkdownGlobs": ["logs/**/*.md"] permits Markdown logs while leaving other Markdown reads protected.
Invalid settings disable the affected feature and produce a concise diagnostic. Malformed settings JSON disables both. Size estimates use rounded-up JavaScript string length divided by four for text; these are approximate budgets, not provider token counts.
Protections and limits
- Unknown tools, image-bearing results, ambiguous
readpaths, small results, and recent messages stay intact. Markdown extension checks are case-insensitive. Markdown returned throughbash/grep, and non-Markdown instructions, cannot be identified by these protections. - A failed copy write or metadata write keeps original output. Missing copies can be rebuilt from verified source text; corrupt or unsafe copies are left alone and their notes are not replayed.
- User-role history includes stored steering/follow-ups and pasted text. Slash commands appear only if pi stores them. The role does not prove human authorship: prefix filters skip known injected messages but cannot identify every injection.
- With pi-secret-safe active, actual tool-result/message-end processing redacts text before copies or historical quotes are made. Offline tests verify both extension load orders. This package has no independent secret detector; old unredacted logs retain that risk.
- Batching is intended to avoid repeated prefix-cache changes. Default thresholds and actual cache savings still need real-provider measurement; tests establish correctness, not performance gains.
Troubleshooting
No output is being trimmed. Trimming starts at 50% by default and needs a successful response for usage tracking. Recent results, Markdown reads, small results, and image-bearing output are protected. An in-memory session cannot save copies; use a persisted pi session.
A configuration warning appears. Fix the named setting in personal settings.json and run /reload. Invalid settings disable the affected feature. Check provider-failover.json for an enabled pi-multi-account context guard as described above.
“Could not save a tool-output copy” appears. The original output stays in context and no successful trim record is written. The warning includes a reason, once per reason/code per session:
source-missing/source-text-mismatch: the outgoing result no longer matches the session projection, for example after another context hook changes it. Keep the original; report the reason and extension load order if this recurs. Do not disable redaction to make a copy succeed.session-unavailable/owner-validation: a persisted session is unavailable or its identity/path cannot be verified. Check that the session still exists in its original location.path-invalid/encoding-invalid/record-invalid: the filename, UTF-8 text, or note cannot be represented safely. Ordinary Unicode and emoji are supported.unsafe-copy-directory/unsafe-copy-file/existing-copy-mismatch: a copy location fails the directory, ownership, link, or content checks. Leave existing data alone and inspect the local copy location before making changes.filesystem-errorwith an OS code: inspect permissions forEACCES, available storage forENOSPC, or a file where a directory is expected forENOTDIR. Other codes identify the OS failure without revealing paths or output.
Warnings omit session/tool identifiers, paths, output, and raw exception messages. When reporting a problem, share the reason/code and versions, not private logs. These diagnostics do not identify the cause of a warning emitted by an older release.
A saved copy is missing. The original result remains in the source transcript. Copies may be rebuilt from verified source text, but deleting a parent session's associated directory can break paths inherited by a fork.
Links
Development and tests · Design and verification evidence · MIT license