Skip to content

fix(opencode): support OpenCode 2 plugin API (V1/V2 dual export) - #1171

Open
Scratchydisk wants to merge 7 commits into
mksglu:mainfrom
Scratchydisk:fix/opencode-v2-plugin-compat
Open

Scratchydisk wants to merge 7 commits into
mksglu:mainfrom
Scratchydisk:fix/opencode-v2-plugin-compat

Conversation

@Scratchydisk

Copy link
Copy Markdown

Supersedes #1169 (closed to allow further local testing — same branch, force-pushed since to rebase onto current main, which is why GitHub wouldn't let me reopen it directly).

Summary

OpenCode 2's plugin loader ignores the V1 { id, server } shape this package's src/adapters/opencode/plugin.ts exports — per OpenCode's own migration guide (opencode.ai/v2/docs/migrate-v1): "V1 plugin implementations do not run in V2." It only recognizes a default export produced by Plugin.define({ id, setup }) from the new @opencode/plugin package.

Repro against the currently-published package (verified against a real opencode@2.0.3/2.0.4 install)

// opencode.jsonc
{ "plugins": ["context-mode"] }
level=WARN message="failed to load plugin" target=context-mode
cause="Cause([Fail(PluginModule.LoadError: Plugin must export a default
definition with an id and an effect or setup function. (cause:
SchemaError(Missing key at ["default"]["effect"] Missing key at
["default"]["setup"])))])"

ctx_* tools never register, no hooks fire, and opencode plugin list silently shows nothing for it — worse than a crash, since there's no indication anything is wrong until a user notices the tools are gone.

Fix

Adds a V2 setup() entrypoint alongside the existing V1 server(), following OpenCode's own documented "support V1 and V2 from one package" pattern (opencode.ai/v2/docs/build/plugins#support-v1): spread Plugin.define({ id, setup }) into the same default-export object that already carries server. OpenCode 1.x and KiloCode keep calling server() — completely unchanged — while OpenCode 2 reads id/setup() off the same object and ignores server().

The V2 setup() re-implements all five hooks using OpenCode 2's documented mapping (opencode.ai/v2/docs/build/plugins/migrate-v1):

V1 hook V2 API
tool.execute.before ctx.tool.hook("execute.before", ...)
tool.execute.after ctx.tool.hook("execute.after", ...)
event (message.updated) ctx.event.subscribe()
chat.message ctx.session.hook("prompt", ...)
experimental.session.compacting ctx.session.hook("compaction", ...)
experimental.chat.system.transform ctx.session.hook("context", ...)
tool map ctx.tool.transform(editor => editor.add(...))

The custom ctx_* tools now declare JSON Schema (required by V2) instead of a Zod shape, reusing the existing zod3ShapeToV4 conversion (added for #574) plus Zod v4's own toJSONSchema().

@opencode/plugin is imported dynamically (await import(...) inside a try/catch), not as a static top-level import, so a stale/partial install missing that dependency degrades to V1-only instead of breaking the whole module for existing OpenCode 1.x/KiloCode users.

Verification

This branch has now been tested two ways:

  1. Sandboxed, against the real binary: patched a real opencode@2.0.3 package cache and confirmed the unmodified published package fails with the exact error above while this branch's build loads with no error.
  2. Live production install: patched ~/.cache/opencode/.../node_modules/context-mode on a machine actually running this plugin day-to-day (real opencode.json with "plugins": ["context-mode", ...], real provider credentials), restarted the OpenCode background service (which picked it up along with an unrelated OpenCode 2.0.3→2.0.4 self-update), and confirmed:
    • Every plugin load since the restart is clean — zero "failed to load plugin" entries for context-mode in the service log (previously, every single load attempt failed with the schema error above).
    • Ran a live session that explicitly invoked the ctx_stats tool and got back a fully-formed real report pulled from the actual session database (event counts, per-tool capture stats, lifetime cost) — end-to-end proof that Plugin.define/setup() → ctx.tool.transform → tool execution → session DB all work correctly under a real OpenCode 2 session.

All 122 pre-existing opencode-plugin/adapters/opencode/parse-opencode-usage tests pass unchanged — zero behavior change to the V1/KiloCode path. Plus 2 new tests locking in the dual-export shape. npm run typecheck and npm run build both clean.

Known gap for maintainer review

The exact field names on OpenCode 2's ToolExecuteBefore/ToolExecuteCompleted/ToolExecuteFailed event types aren't spelled out in the public docs beyond short examples (event.tool, event.input, event.status, event.result, event.error). I inferred event.sessionID by analogy with every other hook interface OpenCode documents (SessionRequestHook, SessionRetryHook, PermissionEvaluation, etc. all expose it), and defensively no-op when it's absent. The routing-enforcement path (tool.execute.before/after → session event capture) hasn't yet been exercised against a live agent turn that actually triggers a blocked/modified tool call — worth a maintainer smoke test before release, though the ctx_* tool-execution path itself (registration, JSON Schema conversion, execute, result handling) is now confirmed working live.

Test plan

  • npm run typecheck
  • npm run build
  • npx vitest run tests/opencode-plugin.test.ts tests/adapters/opencode.test.ts tests/session/parse-opencode-usage.test.ts (122 passed)
  • Live OpenCode 2 session: plugin loads cleanly, ctx_stats tool call succeeds end-to-end against a real session DB
  • Maintainer: exercise tool.execute.before/after (routing enforcement + session capture) against a live OpenCode 2 session with a real blocked/modified tool call

Scratchydisk and others added 4 commits September 16, 2026 14:00
OpenCode 2's plugin loader ignores the V1 `{ id, server }` shape entirely
(opencode.ai/v2/docs/migrate-v1: "V1 plugin implementations do not run in
V2") — it only recognizes a default export produced by
`Plugin.define({ id, setup })` from `@opencode/plugin`. Verified against a
real opencode@2.0.3 install: pointing `"plugins": ["context-mode"]` at the
currently-published package fails immediately with
`PluginModule.LoadError: Plugin must export a default definition with an
id and an effect or setup function.` The same repro against this fix's
build loads cleanly.

Adds a V2 `setup()` entrypoint alongside the untouched V1 `server()`,
following OpenCode's own documented "support V1 and V2 from one package"
pattern — both are spread into one default export, so OpenCode 1.x and
KiloCode keep calling `server()` unchanged while OpenCode 2 reads `id`/
`setup()` and ignores `server()`. Hook-for-hook mapping (per OpenCode's
migration guide, e.g. tool.execute.before -> ctx.tool.hook("execute.before"),
chat.message -> ctx.session.hook("prompt"), the tool map ->
ctx.tool.transform) is documented inline above `setupContextModePluginV2`.

`@opencode/plugin` is imported dynamically (not statically) so a stale
install missing that dependency degrades to V1-only instead of breaking
the whole module for existing users. Zero changes to V1 behavior — all
120 existing opencode-plugin/adapter tests still pass unchanged, plus 2
new tests locking in the dual-export shape.
…ed names

OpenCode 2's editor.add() defaults tools to codemode: true, which keeps them
out of the model's direct tool list -- they are only reachable by writing code
against the execute tool's catalog. Routing enforcement, meanwhile, tells the
model to call context-mode_ctx_execute / ctx_fetch_and_index / ctx_search
directly, and the V2 registration used the bare ctx_* names, so the redirect
pointed at tools that did not exist.

Register the V2 tools with codemode: false and under createToolNamer(platform)
names, the same names the routing block and execute.before redirects use.
Observed on OpenCode 2.0.7: before, the model's direct tool list had no ctx_*
tools while curl was redirected to context-mode_ctx_execute; after, all ctx_*
tools are direct and the redirect names match.

Adds a test that runs the real V2 setup() against a fake OpenCode 2 context
and asserts codemode: false plus routed names (red without the fix).
…option

OpenCode 2 composes the model-visible tool name as <namespace>_<name>. Instead
of baking the routed prefix into the name, split toolNamer(name) into
{ name, namespace } (v2ToolIdentity) so the tools use the host's native
namespace field while the visible names stay exactly what the router tells the
model to call. Any namer shape other than a clean <prefix>_<tool> (bare names,
mcp__x__tool) is registered verbatim with no namespace.

Verified on OpenCode 2.0.7: the model sees context-mode_ctx_execute etc., and
context-mode_ctx_execute runs.

Tests: v2ToolIdentity unit cases; the setup() test now asserts, per tool, that
the host-composed visible name equals namer(name) (no prefix-startsWith
tautology), awaits the transform callback, and removes its abort listener.
hooks/core/routing.mjs only redirects curl/wget and large-output commands when
isMCPReady() finds a live readiness sentinel, which the stdio MCP server writes
from its main(). With native V2 tools there is no MCP server, so the redirects
silently depended on an unrelated context-mode MCP process (e.g. another
client's) being alive: on a host with none, curl ran straight through.

The V2 setup() now writes the same sentinel for its own process (PID contents,
30s refresh against the reader's 90s freshness window, unref'd timer) and
removes it on dispose. Observed on OpenCode 2.0.7: curl was redirected on a
machine where a Claude Code context-mode MCP happened to be running and not on
one without; with this change it is redirected on both.

The V1 native-tool path looks to share this dependency; left untouched here as
it was not tested against a live OpenCode 1.x host.
@qoole

qoole commented Sep 18, 2026

Copy link
Copy Markdown

Thanks for this port. I ran it against a live OpenCode 2.0.7 server, and it loads and hooks fine. Three things stopped it being automatic there, though, and I've put fixes for them in a PR against your branch, so they can go into this PR: Scratchydisk#1

In short:

  • editor.add() defaults to codemode: true, so the ctx_* tools weren't directly callable.
  • The registered names didn't match the context-mode_ctx_* names that the routing redirects tell the model to call.
  • curl/wget redirects only happened when some other context-mode MCP server's readiness sentinel happened to exist, because the plugin never writes one itself.

Each fix has a test that fails without it, and all three are verified live on 2.0.7. Details are in the linked PR.

@Scratchydisk

Copy link
Copy Markdown
Author

Huge thanks to @qoole for the three follow-up commits — they've now been folded into this branch (fast-forward ad55440..86c15ef), so #1171 carries the complete fix:

  • 4b91426 — V2 ctx_* tools registered as direct tools (codemode: false) under the routed names
  • 468b7eb — registration via OpenCode 2's native namespace option (v2ToolIdentity), visible names match the router
  • 86c15ef — V2 setup() writes its own readiness sentinel, so curl/wget redirects no longer depend on a stray MCP process

Verified live against opencode v2.0.9: tests/opencode-plugin.test.ts 63 passed, tsc --noEmit clean, plus a live backend check — own-PID sentinel written by setup(), and curl -s https://example.com | head -c 80 via a model shell tool returns the redirect (hooks/core/routing.mjs:819) with zero MCP processes running.

@qoole — grateful for the live-host testing on 2.0.7 that surfaced all three; the index.js local-install note is recorded but intentionally left out of this PR as it's docs, not code.

@imyu37

imyu37 commented Sep 21, 2026 •

Copy link
Copy Markdown

Reproduced on opencode 2.0.10, the newest release — same load error as described in the PR body.

Environment

  • opencode 2.0.10, standalone Windows x64 binary
  • context-mode 1.0.169, installed via opencode plugin add context-mode@1.0.169
  • Declared under the V2 config key plugins in opencode.json

Repro

Fails on every session start, not intermittently. Two consecutive starts produced the same rejection:

level=WARN message="failed to load plugin" target=context-mode@1.0.169

with the cause reducing to:

PluginModule.LoadError: Plugin must export a default definition
with an id and an effect or setup function.

followed by a SchemaError naming the two missing keys under the default export: setup and the effect key.

Static confirmation

The entry declared in package.json is build/adapters/opencode/plugin.js. It ends with:

export default { id: "context-mode", server: createContextModePlugin };
export { createContextModePlugin as ContextModePlugin };

Checks against that file: Plugin.define absent, setup absent, @opencode/plugin not imported. So the default export carries only the V1 server key, which V2 ignores.

On the failure mode

The only signal is a WARN in the background service log. opencode plugin list does not list the plugin either, so there is no in-product indication that anything is wrong. All 11 ctx_* tools and every hook are simply absent until someone reads the log.

Version coverage

The PR describes live verification against 2.0.3 / 2.0.4 / 2.0.7. The same load error reproduces on 2.0.10, so the V2 API surface the fix targets has not drifted in a way that would break the approach.

Scratchydisk added a commit to Scratchydisk/context-mode that referenced this pull request Sep 21, 2026
…2 export shape

Plugin.define() in @opencode/plugin is the identity function, so the
dynamic import that built the V2 default-export shape added no
behavior — only a dependency that isn't guaranteed to resolve on
every host. When it failed to resolve, the code silently fell back to
a V1-only shape missing `setup`, which OpenCode 2 rejects outright.

Reported on upstream mksglu#1171 by imyu37: opencode 2.0.10 standalone
Windows binary, installed via `opencode plugin add`, failed to load
with "Plugin must export a default definition with an id and an
effect or setup function." Reproduced live against the real opencode
2.0.10 CLI (Linux) by hiding @opencode/plugin from node_modules at
runtime — got the identical LoadError — then confirmed the fix loads
clean under the same conditions. Windows itself is unverified; no
Windows box to run the actual installer end-to-end on.
…2 export shape

Plugin.define() in @opencode/plugin is the identity function, so the
dynamic import that built the V2 default-export shape added no
behavior — only a dependency that isn't guaranteed to resolve on
every host. When it failed to resolve, the code silently fell back to
a V1-only shape missing `setup`, which OpenCode 2 rejects outright.

Reported on upstream mksglu#1171 by imyu37: opencode 2.0.10 standalone
Windows binary, installed via `opencode plugin add`, failed to load
with "Plugin must export a default definition with an id and an
effect or setup function." Reproduced live against the real opencode
2.0.10 CLI (Linux) by hiding @opencode/plugin from node_modules at
runtime — got the identical LoadError — then confirmed the fix loads
clean under the same conditions. Windows itself is unverified; no
Windows box to run the actual installer end-to-end on.
@Scratchydisk

Copy link
Copy Markdown
Author

Pushed a fix for @imyu37's report above (312e50a).

Root cause: the V2 default-export shape was built via await import("@opencode/plugin") → Plugin.define({ id, setup }). Plugin.define() in that package is just the identity function, so the import added no behavior — only a dependency that isn't guaranteed to resolve on every host. When it failed, the code silently fell back to a V1-only shape missing setup, which is exactly what OpenCode 2 rejected in your log (Missing key at ["default"]["setup"]).

Fix: build the V2 shape inline, no import — { id: "context-mode", setup: setupContextModePluginV2 }. Removes the failure mode entirely rather than papering over it.

Reproduced and verified live, not just in unit tests: built the pre-fix code, hid @opencode/plugin from node_modules at runtime (simulating a host where it doesn't resolve), and loaded it through the real opencode 2.0.10 CLI — got your exact error, PluginModule.LoadError: Plugin must export a default definition with an id and an effect or setup function. Rebuilt with the fix under the same hidden-dependency condition and it loaded clean, no warnings. Also added a regression test (tests/opencode-plugin.test.ts) that mocks @opencode/plugin to fail resolution and asserts setup is still present.

Caveat: I don't have a Windows machine, so I can't run the actual opencode plugin add installer end-to-end on Windows the way you did. The reproduction above matches your reported failure exactly (same error, same missing keys), so I'm confident in the fix, but the real Windows install path itself is still unverified by me — appreciate it if you're able to re-test once this lands.

nathanpride added a commit to nathanpride/context-mode that referenced this pull request Sep 22, 2026
… failure

Adds a regression test proving the merged default export still exposes a
working v2 setup() even when @opencode/plugin cannot be resolved on the
host (the mksglu#1171 failure mode: opencode plugin add skipping full dependency
resolution). Our default export is a plain object literal that never
depends on that import, so the test passes by construction — but it locks
the invariant against a future reintroduction of a dynamic-import-with-
fallback that would silently drop setup and make OpenCode 2 reject the
whole plugin.

Verified the guard is real by temporarily swapping in the buggy
await-import + fallback pattern: the test fails with
"expected 'undefined' to be 'function'", then reverted.

typecheck EXIT 0; v2 suite 57 pass.
nathanpride added a commit to nathanpride/context-mode that referenced this pull request Sep 22, 2026
… failure

Adds a regression test proving the merged default export still exposes a
working v2 setup() even when @opencode/plugin cannot be resolved on the
host (the mksglu#1171 failure mode: opencode plugin add skipping full dependency
resolution). Our default export is a plain object literal that never
depends on that import, so the test passes by construction — but it locks
the invariant against a future reintroduction of a dynamic-import-with-
fallback that would silently drop setup and make OpenCode 2 reject the
whole plugin.

Verified the guard is real by temporarily swapping in the buggy
await-import + fallback pattern: the test fails with
"expected 'undefined' to be 'function'", then reverted.

typecheck EXIT 0; v2 suite 57 pass.
@imyu37

imyu37 commented Sep 24, 2026

Copy link
Copy Markdown

Thanks for the quick turnaround — I can see 312e50a on the branch.

One factual clarification from my side, about the exact artifact my log came from. My report was against the published npm context-mode@1.0.169, installed via opencode plugin add context-mode@1.0.169 (Windows x64, opencode 2.0.10). I re-checked that installed package statically:

  • No file in the package contains the string @opencode/plugin, and package.json does not list it under dependencies either — so on the published build there is no dynamic import of that package at all, hence no fallback path.
  • The entry build/adapters/opencode/plugin.js (28,879 bytes) contains no occurrence of setup anywhere, no Plugin.define, and ends with:
export default { id: "context-mode", server: createContextModePlugin };

So on the published package the missing default.setup key is not a silent fallback — that build never had any V2 attempt to fall back from. Your dynamic-import diagnosis matches the pre-fix PR branch code (which does build the V2 shape via await import("@opencode/plugin")), and removing that dependency-soundness issue is worthwhile hardening on its own — but my log came from a build that ships no V2 code whatsoever.

Both cases happen to produce the identical PluginModule.LoadError, which is presumably why your repro matched mine exactly. Possibly worth keeping distinct in the regression-test framing: the published-package case is "V2 export entirely absent", while the branch case was "V2 export silently dropped when the dep fails to resolve". For users on the published package, the fix is simply this PR merging and being released.

Environment facts unchanged from my earlier comment: opencode 2.0.10, Windows x64 standalone, installed with opencode plugin add, declared under the plugins key in opencode.json.

Scratchydisk added a commit to Scratchydisk/context-mode that referenced this pull request Sep 24, 2026
…s in mksglu#1171 regression framing

imyu37 clarification 2026-09-24: published 1.0.169 never had V2 code (no setup, no @opencode/plugin ref) — fix is merge+release. Pre-fix branch separately had silent fallback when dynamic import failed — hardened by inline {id, setup}. No logic change, comment-only.
…s in mksglu#1171 regression framing

imyu37 clarification 2026-09-24: published 1.0.169 never had V2 code (no setup, no @opencode/plugin ref) — fix is merge+release. Pre-fix branch separately had silent fallback when dynamic import failed — hardened by inline {id, setup}. No logic change, comment-only.
@Scratchydisk

Copy link
Copy Markdown
Author

You're right, thanks for re-checking the installed artifact — correction accepted.

To keep the two cases distinct:

  • Published 1.0.169: V2 export entirely absent ({id, server}, no setup, no @opencode/plugin reference). Fix is simply this PR merging + release.
  • Pre-fix branch: V2 shape built via dynamic import("@opencode/plugin") → Plugin.define({ id, setup }). Since Plugin.define() is the identity function, the import added no behavior, only a resolution failure mode that silently fell back to V1-only. Hardened by 312e50a building {id, setup} inline with no import.

Same PluginModule.LoadError in both, different cause. The inline shape covers both. Pushed bad09fd to update the regression-test comment to keep that distinction (no logic change).

Still unverified on my side: actual opencode plugin add on Windows (no Windows box — my 2.0.10 repro was Linux CLI with the dep hidden). Appreciate a re-test from you once this lands.

@jfayad

jfayad commented Sep 24, 2026 •

Copy link
Copy Markdown

Hello,

Just confirming this patch fixes context-mode on opencode 2.0.16

tried it via the TUI and also via Openchamber v2

Thanks!

A small quirk though:

PR #1171 fixes loading under OpenCode 2.0.16 and ctx_doctor/ctx_stats become available. However, ctx_doctor selects Gemini CLI when ~/.gemini exists, and ctx_stats reports OpenCode as “Skipped … no real chat activity.” This suggests V2 tool registration works, but platform detection and/or OpenCode activity capture may not.

@Scratchydisk

Copy link
Copy Markdown
Author

Thank you @jfayad — both for confirming the load fix on 2.0.16 and for the sharp follow-up. The quirk you found is real, and I dug into both halves:

Doctor picking Gemini CLI: root cause is in detectPlatform(), not the V2 registration. Inside the OpenCode 2 server process none of the OPENCODE_* env markers are set, so detection falls through to config-dir fallbacks (~/.claude, then ~/.gemini) — anyone with a ~/.gemini gets misdetected. Fixed on my side by pinning CONTEXT_MODE_PLATFORM to the plugin's known platform around ctx_* handler execution (the override already exists in detectPlatform(), the plugin path just never set it).

Stats showing OpenCode as "Skipped": I verified every V2 hook payload field name against the published @opencode/plugin@2.0.16 + @opencode/schema@2.0.16 types — the 2.0.4→2.0.16 diff is purely additive, so no shape drift explains it. But that check surfaced something else: message.updated does not exist anywhere in the v2 event bus schema, so the ctx.event.subscribe usage capture on this branch (which filters on exactly that name) can never fire on OpenCode 2. My fork captures usage via session.step.started/ended correlation instead, and I've confirmed StepEnded rows landing in the session DB on live 2.0.12 and 2.0.16 sessions.

One thing I couldn't explain from here: "Skipped" means zero captured events of any type, and the tool.execute.after / prompt hooks should still have captured tool and prompt activity on your machine. If you have a moment, the details that would pin it down: which branch/build you tested, the exact stats output, and whether the session DB for that project (~/.config/opencode/context-mode/sessions/…) has any rows for the session. Happy to chase it further with that in hand.

… hooks

Follow-up to jfayad's mksglu#1171 report (opencode 2.0.16):

- withPinnedPlatform(): inside the OpenCode 2 server process no OPENCODE_*
  markers are set, so detectPlatform() fell through to ~/.claude / ~/.gemini
  fallbacks and ctx_doctor misreported the platform. Pin
  CONTEXT_MODE_PLATFORM to the plugin's known platform around ctx_*
  handler execution (V1 bridge + V2 registration); explicit user override
  wins, value restored afterwards.
- Usage capture via session.step.started/ended correlation
  (parseOpencodeV2StepUsage): message.updated does not exist on the v2 bus
  schema (verified against @opencode/plugin@2.0.16 types), so the old filter
  could never fire. Model correlated by assistantMessageID, reasoning folded
  into output, native USD cost verbatim; message.updated kept as fallback.
- Collect every hook/transform Registration dispose; release on cleanup and
  tear down partial registrations if setup fails mid-way.

Tests: 13 new (pin unit x3, lifecycle x2, V1/V2 doctor wiring with gemini
decoy, step correlation e2e, parser x5). Targeted suites 140 passed,
typecheck clean. Live on 2.0.16 scrubbed-env standalone: zero load errors,
ctx_doctor resolves the OpenCode adapter, ctx_stats reports real totals.
@Scratchydisk

Copy link
Copy Markdown
Author

Code update pushed to this branch (5bf8ab5) covering the jfayad follow-ups discussed above:

  • Platform pin: withPinnedPlatform() pins CONTEXT_MODE_PLATFORM to the plugin's known platform around ctx_* handler execution (V1 bridge + V2 registration), so ctx_doctor no longer falls through to the ~/.claude / ~/.gemini fallbacks inside the server process. Explicit user override wins; restored afterwards.
  • Usage capture: session.step.started/ended correlation (parseOpencodeV2StepUsage, field names verified against the 2.0.16 SDK types), since message.updated doesn't exist on the v2 bus. message.updated kept as fallback.
  • Lifecycle: every hook/transform Registration dispose is collected and released on cleanup, with teardown of partial registrations if setup fails mid-way.

Verification: 13 new tests (targeted suites 140 passed, typecheck clean) plus a live scrubbed-env standalone run on opencode 2.0.16 — zero load errors, ctx_doctor resolves the OpenCode adapter, ctx_stats reports real totals (32.4K events / 218 projects on my machine).

@jfayad

jfayad commented Sep 25, 2026

Copy link
Copy Markdown

One thing I couldn't explain from here: "Skipped" means zero captured events of any type, and the tool.execute.after / prompt hooks should still have captured tool and prompt activity on your machine. If you have a moment, the details that would pin it down: which branch/build you tested, the exact stats output, and whether the session DB for that project (~/.config/opencode/context-mode/sessions/…) has any rows for the session. Happy to chase it further with that in hand.

I might have an error in my install ?

I re-ran the command and here's the new output:

context-mode 37 min 4 calls

10.7 KB entered context | 0 tokens saved

Persistent memory ✓ preserved across compact, restart & upgrade
23.8K events · 278 sessions · ~$30.41 saved lifetime

Skipped (4): Gemini CLI, Antigravity, Antigravity CLI, OpenCode
These adapters have DBs on disk but only test fixtures, dev skeletons,
or detection probes — no real chat activity.

─────────────────────────────────────────────────────────────────
Your AI talks less, remembers more, costs less.
$0.00 this session · $0.00 lifetime
─────────────────────────────────────────────────────────────────

v1.0.169

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants