@astrosheep/pi-context 0.10.0 → 0.10.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.
package/README.md CHANGED
@@ -43,7 +43,7 @@ The margin is measured in **remaining context tokens** added on top of Pi's `com
43
43
 
44
44
  - `reminder = reserveTokens + reminderMarginTokens` (default margin `24576`)
45
45
 
46
- Put the key in the global settings (`~/.pi/agent/settings.json`) or the project settings (`<cwd>/.pi/settings.json`); project values win per key, mirroring Pi's own settings merge. With Pi's default `reserveTokens: 16384` the default gives reminder `40960`, leaving 24,576 tokens of working room above Pi's reset line no matter how you set `reserveTokens`. The borrowed fallback turn needs no threshold of its own: it is driven by Pi's automatic `threshold`/`overflow` compaction request, so `before_agent_start`/`turn_end` send nothing and no `fallbackMarginTokens` setting exists.
46
+ Put the key in the global settings (`~/.pi/agent/settings.json`) or the project settings (`<cwd>/.pi/settings.json`); project values win per key, mirroring Pi's own settings merge. With Pi's default `reserveTokens: 16384` the default gives reminder `40960`, leaving 24,576 tokens of working room above Pi's reset line no matter how you set `reserveTokens`. The reminder is an early warning; once fallback guidance has been persisted in the current window, no later early reminder is appended. This also applies after session reload. The borrowed fallback turn needs no threshold of its own: it is driven by Pi's automatic `threshold`/`overflow` compaction request, so `before_agent_start`/`turn_end` send nothing and no `fallbackMarginTokens` setting exists.
47
47
 
48
48
  Pi's `reserveTokens` and the `pi-context` reminder margin are re-read from disk at every `session_start` and cached for that session. An invalid margin — not a positive integer — is ignored with one TUI warning naming the key and the default used instead; session handling never throws.
49
49
 
@@ -97,4 +97,4 @@ npm run typecheck
97
97
  npm test
98
98
  ```
99
99
 
100
- The integration harness uses the installed Pi `SessionManager` and `SettingsManager` (global and project settings fixtures in temp directories, so the real `~/.pi` is never touched), including an on-disk JSONL reload. It verifies note persistence/Unicode/path rules, the boot block contents and extension-minted window ids on reset and root paths, that the `context` hook never injects, provider context exclusion after the real `firstKeptEntryId` boundary while history remains searchable, completed tool-result boundary placement, settings-derived reminder threshold resolution and margin validation, that the removed `before_agent_start`/`turn_end` fallback is gone, one early reminder per window, one continuation only, the two-phase automatic ordering (one cancel, one steer, one real reset, re-armed per window, `ctx.compact()` for both threshold and overflow, idle crossings and manual/`new_context` resets bypassing the borrow), and cancellation/failure/no-double-retry behavior. Additional lifecycle tests cover duplicate callbacks, stale callback identity, shutdown/tree/toggle changes, user abort, synchronous errors, native retry ownership, and queued prompts. SDK tests run the real Pi agent loop, extension hooks, manual compaction, and continuation with scripted provider responses: explicit and fallback resets each produce one boundary, exclude old provider context, and preserve durable history. A real uncompactable-session case verifies no automatic retry and recovery on the next user prompt. Further SDK cases verify steering/follow-up delivery before reset without replay, consecutive distinct windows, and user cancellation without automatic continuation. Persisted-data tests verify boot/reminder deduplication after JSONL reload and branch navigation, and reject malformed note timestamps without overwriting valid notes. These tests use temporary settings and fake credentials and make no model or network call.
100
+ The integration harness uses the installed Pi `SessionManager` and `SettingsManager` (global and project settings fixtures in temp directories, so the real `~/.pi` is never touched), including an on-disk JSONL reload. It verifies note persistence/Unicode/path rules, the boot block contents and extension-minted window ids on reset and root paths, that the `context` hook never injects, provider context exclusion after the real `firstKeptEntryId` boundary while history remains searchable, completed tool-result boundary placement, settings-derived reminder threshold resolution and margin validation, that the removed `before_agent_start`/`turn_end` fallback is gone, one early reminder per window, one continuation only, the two-phase automatic ordering (one cancel, one steer, one real reset, re-armed per window, `ctx.compact()` for both threshold and overflow, idle crossings and manual/`new_context` resets bypassing the borrow), and cancellation/failure/no-double-retry behavior. Additional lifecycle tests cover duplicate callbacks, stale callback identity, shutdown/tree/toggle changes, user abort, synchronous errors, native retry ownership, and queued prompts. SDK tests run the real Pi agent loop, extension hooks, manual compaction, and continuation with scripted provider responses: explicit and fallback resets each produce one boundary, exclude old provider context, and preserve durable history. A real uncompactable-session case verifies no automatic retry and recovery on the next user prompt. Further SDK cases verify fallback note-writing while usage remains above the reserve line, with no obsolete early reminder before reset; steering/follow-up delivery before reset without replay; consecutive distinct windows; and user cancellation without automatic continuation. Persisted-data tests verify boot/reminder deduplication after JSONL reload and branch navigation, and reject malformed note timestamps without overwriting valid notes. These tests use temporary settings and fake credentials and make no model or network call.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@astrosheep/pi-context",
3
- "version": "0.10.0",
3
+ "version": "0.10.1",
4
4
  "type": "module",
5
5
  "description": "Codex-style context windows for Pi: reset-style compaction, durable session history tools, and persistent notes.",
6
6
  "license": "MIT",
package/src/budget.ts CHANGED
@@ -1,6 +1,6 @@
1
1
  import { Type } from "@earendil-works/pi-ai";
2
2
  import { defineTool, SettingsManager, type ExtensionAPI, type ExtensionContext } from "@earendil-works/pi-coding-agent";
3
- import { PI_CONTEXT_SETTINGS_KEY, DEFAULT_RESERVE_TOKENS, DEFAULT_REMINDER_MARGIN_TOKENS, GUIDANCE_TYPE } from "./protocol.js";
3
+ import { PI_CONTEXT_SETTINGS_KEY, DEFAULT_RESERVE_TOKENS, DEFAULT_REMINDER_MARGIN_TOKENS, GUIDANCE_TYPE, FALLBACK_TYPE } from "./protocol.js";
4
4
  import { currentWindowId, hasWindowMessage } from "./history.js";
5
5
  import { tokenBudgetGuidance } from "./prompts.js";
6
6
  import { output } from "./tool-output.js";
@@ -82,7 +82,7 @@ export function registerBudget(pi: ExtensionAPI, isEnabled: () => boolean) {
82
82
  pi.on("session_start", (_event, ctx) => { thresholds = undefined; guidancePersistedInWindow = undefined; resolveThresholds(ctx); });
83
83
  pi.on("session_tree", () => { guidancePersistedInWindow = undefined; });
84
84
  pi.on("context", (_event, ctx) => {
85
- if (!isEnabled()) return undefined;
85
+ if (!isEnabled() || hasWindowMessage(ctx, FALLBACK_TYPE)) return undefined;
86
86
  // This hook does exactly one thing: persist the once-per-window low-budget
87
87
  // reminder the first time remaining context crosses the reminder threshold.
88
88
  // It never injects messages into the request.