npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@timmyjl12/pi-context

v0.1.0

Published

Configurable, cheap smart context management for the Pi coding agent

Readme

@timmyjl12/pi-context

A configurable Pi context extension combining pre-compaction shake, pi-vcc-style compaction and recall, and optional JEV relevance decisions.

pi install npm:@timmyjl12/pi-context

Try it for one run without installing: pi -e npm:@timmyjl12/pi-context. Requires pi 1.0 or newer. If you use pi-vcc, read Migrating from pi-vcc first. The extension never activates, uninstalls or replaces other extensions on its own.

How it works

  • Shake at 60%, 70%, 80%: each rung once per cycle. Old tool/MCP results become bounded previews with recall references; current/protected turns are retained. Old or superseded skill loads become re-read markers, so skills do not monopolize context.
  • Cache-aware timing (default): a rewrite invalidates the provider prompt cache from the earliest edited message onward. While the cache is warm, a due rung rewrites only if it pays back that one-time cost before the next compaction (break-even requests from the model's cost prices, measured prompt growth and the compaction point; model after billion-context-pi's compression-economics write-up). Otherwise it waits and is applied when the next prompt arrives after the model's cache lifetime (promptCache, else shake.cacheTiming.idleTtlMs, 5 min), when the rewrite costs no extra cache miss. All rungs already reached are applied as one rewrite. After a model switch or on a provider that never reports cache reads, rungs rewrite at the turn boundary. shake.cacheTiming.mode: "boundary" restores immediate rewrites. When the judge narrows a plan, the judged plan is priced again before it is applied: if it removes less or now starts earlier in history and no longer pays back while warm, it waits for a cold prompt like any other deferred rung.
  • Compact at 95%: structured-free first, optional configured cheap summarizer second, native Pi fallback. Pi's own trigger (contextWindow − reserveTokens, 16,384 by default) runs first on windows under ~328K tokens unless you raise it, and goes through the same session_before_compact path, so pi-context writes the summary either way. Recommended: keep Pi's compaction enabled (compaction.enabled: false also turns off Pi's overflow recovery) and make it a backup behind pi-context's 95% by lowering Pi's reserve below 5% of the window, e.g. "compaction": { "reserveTokens": 4096 } in ~/.pi/agent/settings.json (98% of 200K; use compaction.modelOverrides for per-model control). Overflow recovery does not depend on the reserve. pi-context reads Pi's settings (global, trusted project, model overrides) so its shake cost estimates use Pi's actual trigger, and /pi-context doctor reports whether Pi's trigger is a backup. A confirmed compaction (Pi's session_compact, or pi-context's own boundary compaction once committed) permits a new cycle after usage drops below 55%; if the kept tail stays above 55%, the ladder restarts from the post-compaction usage. A shake-induced dip alone does not replay completed rungs. Boundary compaction keeps at most 30% of the window verbatim.
  • Compaction builds on shake and JEV: both compaction paths summarize the shaken view, and Pi re-applies shake edits to the kept tail. Every pi-context summary (structured-free or cheap-model) ends its sections with Recoverable Tool Output: up to 24 recall pointers (pi_context_recall id=…) for tool results leaving context, ranked JEV load-bearing > error > edit > other > shaken, with one-line previews for load-bearing and error results. The list and the read/modified file lists carry forward through each compaction's details (Pi itself does not carry file lists from extension compactions). The section stays inside compaction.maxSummaryChars. Only when pi-context owns compaction: with pi-vcc owning it (compaction.owner: "auto" while pi-vcc is loaded with overrideDefaultCompaction), pi-context only shakes and this section is not produced; set compaction.owner: "pi-context" or remove pi-vcc to enable it.
  • Recover originals: shake appends context edits rather than overwriting raw entries. Recall reads the current session's original entries, including text omitted from live context by shake or compaction.
  • JEV (on when available): hosted TypeSafe JEV is used when a key is available — the environment variable named by judge.typeSafe.apiKeyEnv (TYPESAFE_API_KEY) first, then judge.typeSafe.apiKey in the owner-restricted config — or through Pi's native TypeSafe classifier (Pi 0.99+). Local Laya via explicit compatibility transport. shake.judge.mode is off, ambiguous or all; all judges every eligible result. For each result the judge sees the tool, a head preview, the call's arguments and any later calls on the same file (for example a later edit or re-read, which usually makes the old result stale). Set judge.typeSafe.enabled: false to turn it off. No available judge means deterministic reduction, not unverified pair pruning.

Automation thresholds support percentages or absolute token counts and exact provider/model overrides. Overriding a default threshold without specifying extras drops the inherited default ladder for that stage.

Commands and tools

| Surface | Purpose | | ---------------------------------------- | --------------------------------------------------------------------------------------------------------------- | | /pi-context | Context controls, status, settings and diagnostics | | /pi-context pause / resume | Pause/resume automation for this session | | /shake | Manual shake while idle | | /pi-context-compact | Request manual/native compaction | | /pi-context-recall <query> [scope:all] | Display recalled history and supply it as context, without starting a model turn | | pi_context_recall | Ranked keyword/regex search, pagination, exact id/index expansion, historical file drill-down and touched files | | pi_context_find_skill | Optional skill discovery | | pi_context_review | Optional JEV/Laya anti-slop review |

Recall defaults to the active lineage. scope: "all" reaches other branches of the same session, never earlier sessions. Stable #N references are numbered before lineage filtering; Pi's prompt/tool loadout records keep their number but are never listed. expand: [N] and id recover full original text in bounded output pages; #N:path drills into historical tool payloads, not a live file. mode: "touched" lists identifiable file operations with provenance. Regex runs in a terminable worker, with cancellation/deadline and explicit fallback rather than blocking Pi's event loop. In-memory sessions remain supported through the raw session manager.

Configuration

User (optional): <agent-dir>/extensions/timmyjl12/pi-context/config.json (normally ~/.pi/agent/extensions/timmyjl12/pi-context/config.json). No file means built-in defaults; nothing is written on load. Saves from /pi-context store only what differs from the defaults (a stage's threshold and extra rungs together), so the file stays small and later default changes still reach you; it resolves back to exactly what you saved. The folder is created owner-private and an existing file must verify as private before it is used. The verdict cache lives in the same folder (cache/). Older ~/.pi/agent/pi-context/config.json and ~/.pi/agent/pi-context.json are no longer read. Trusted project: <cwd>/.pi/pi-context.json. Model overrides use exact provider/model keys and do not get persisted into user defaults. Prefer environment variables for keys; the one stored secret supported is judge.typeSafe.apiKey (owner-restricted file, never displayed — the settings editor shows a placeholder and keeps the stored key unless you replace it, and doctor names only the source); native Pi provider credentials are used only on the registered classifier's HTTPS origin. A custom judge origin requires an explicit request/environment key. Invalid/inaccessible settings retain the prior valid configuration and report safe guidance; existing unsafe permissions are rejected, not repaired.

{
  "version": 1,
  "shake": {
    "judge": { "mode": "all" },
    "elideSkills": true,
    "cacheTiming": { "mode": "cold", "idleTtlMs": 300000 }
  },
  "judge": {
    "typeSafe": { "enabled": true, "apiKeyEnv": "TYPESAFE_API_KEY" },
    "laya": { "mode": "off" },
    "cache": { "persist": true, "maxEntries": 512, "ttlMs": 86400000 }
  },
  "recall": {
    "enabled": true,
    "maxSearchResults": 5,
    "maxEntryChars": 500,
    "maxOutputChars": 20000,
    "regexTimeoutMs": 500
  }
}

maxEntryChars bounds previews, not stored originals. Recall output limits do not rewrite session history. judge.cache.persist: false disables disk persistence; in-memory verdict reuse remains available. Published schema: schema/pi-context.schema.json.

Two different caches

Judge verdict cache: byte-identical judge-visible inputs reuse relevance verdicts. Entries are session-scoped and expire; resume can reload them when session identity and judge configuration match. Persistence contains hashes, numeric verdicts and counters only—no prompts, raw payloads, free-text choices or credentials. Same configuration does not unnecessarily clear hits. Private storage: owner/mode checks on POSIX and owner-SID/DACL checks on Windows verify directories and existing files before reads, restrict empty temporary files before bytes, and verify the final atomic replacement. Broad or reparse/symlink paths are rejected without repairing existing permissions. If private persistence cannot be verified, use judge.cache.persist: false; numeric in-memory reuse remains available.

Provider prompt cache: status uses actual main-assistant input, cacheRead and cacheWrite usage, separately from judge hits. Capped shake favors newer eligible edit groups and keeps the unchanged prefix verbatim. Reached rungs commit as one batch, and cache-aware timing only rewrites a warm cache when the rewrite pays back before compaction; otherwise it waits for a prompt that already misses the cache. While such a rung waits, pi-context answers Pi's cache_warming_decision with stop when idle, so no money is spent warming a prefix about to be rewritten. Changing historical messages can invalidate the suffix of the provider cache; unchanged hit rate is not guaranteed. The rewrite frontier, real usage and /pi-context's cache misses by cause (pi-context shake, compaction, model switch, idle expiry, Pi loadout change, unexplained; plus the cached share of the first request after the last rewrite) expose that tradeoff. No extra warming/model calls are made.

Safety and coexistence

  • compaction.owner: auto (default), pi-context or defer. auto detects pi-vcc's commands/tool and follows pi-vcc's own settings (PI_VCC_CONFIG_PATH or ~/.pi/agent/pi-vcc-config.json): with overrideDefaultCompaction on (pi-vcc's default) pi-vcc compacts and pi-context only shakes; with it off pi-vcc only handles /pi-vcc, so pi-context compacts; for a provider in pi-vcc's skipForProviders, neither compacts (that provider's own compactor was chosen). Explicit pi-vcc __pi_vcc__ compactions are never overridden, and status names the compactor from the committed entry (details.compactor).
  • shake.prunePair requires a configured judge strongly rejecting every result in the call group and separately judging that nobody needs to know each call happened (both >= strongPruneScore). The call-record question is asked in the same judge request, so it adds no requests. Otherwise calls remain paired with marker results. Signed/thinking assistant blocks are not rewritten.
  • shake.longText is opt-in. Tool-call blocks and protected current/recent turns remain intact.
  • Skill filtering is optional and sticky per session; a judge outage reuses the already-filtered list instead of restoring every skill. Tool routing changes only configured namespaces; other extensions' tools remain untouched. With tools.sticky (default) a selected namespace stays active until the next compaction and an outage keeps the current loadout, because Pi records every loadout change in the transcript. MCP-adapter-managed names are excluded by default; /pi-context doctor flags configured tools that are not registered (Pi 0.99.2 renamed MCP tools from - to _).
  • Supported session identity transitions reset policy, pause, rollback and reports, cancel old work, and suppress stale tool writes. Arbitrary concurrent SDK hosting is not a replacement-readiness claim.
  • Laya is off by default: no manager, process or health probes. Even when configured, local setup occurs only if its judge profile is attempted; successful hosted JEV does not require local Laya. Managed shutdown kills the process tree with a bounded wait and host-exit fallback. Setup/install is explicit.
  • Boundaries do not invoke the aborting manual compaction API. In-flight guards, cancellation, deadlines and handled asynchronous errors keep operations from overlapping or wedging the terminal.

Migrating from pi-vcc

  1. Try coexistence with compaction.owner: "auto"; pi-vcc remains the compactor while pi-context supplies shake.
  2. When satisfied, disable pi-vcc yourself and reload Pi. With no detected pi-vcc, auto lets pi-context own compaction.
  3. Replace vcc_recall / /pi-vcc-recall usage with pi_context_recall / /pi-context-recall. Verify resume, recall of shaken/compacted originals and real provider cache usage before making the cutover permanent.
  4. Exercise representative sessions with switches and interrupts and inspect actual provider-cache usage. Automated deadlines/tree tests and synthetic live/terminal evidence are safeguards, not universal guarantees. Laya is optional/off by default; enabling a real managed installation requires its own installation-specific soak.

Trial and rollback

To try only this extension for one invocation, with no change to your package settings:

pi --no-extensions -e npm:@timmyjl12/pi-context

Omit --no-extensions to test coexistence with your configured extensions. Before a permanent switch, record your current package/resource selections with pi list and pi config. If satisfied, run pi install npm:@timmyjl12/pi-context, disable pi-vcc through pi config, and restart Pi. Do not load a second pi-context source alongside this one.

Rollback: exit the trial invocation, or run pi remove npm:@timmyjl12/pi-context and restore your recorded pi-vcc/resource selections. Keep raw sessions and legacy settings; no cache or history deletion is required.

The extension never removes another package or changes global Pi configuration on your behalf.

Development

npm install
npm run check          # typecheck, lint, tests, import guard
npm run format:check

The suite runs against the Pi SDK, including a real AgentSession contract for cache-cold shake timing and native classifier compatibility.