pi-opencode-direct0.1.9
Keyless OpenCode Zen free models for Pi, using native HTTP APIs
Untested on omp
This is a pi package. No one has reported whether it works on omp yet. If you try it, add your result below.
Reports 0
No reports yet.
Readme
pi-opencode-direct
Free OpenCode Zen models in Pi through native HTTP requests. No OpenCode installation, login, API key, server, container, or LiteLLM is required.
Install
Requires Pi 0.85.1 or newer (tested with 1.3.0) and Node 22.19 or newer.
pi install npm:pi-opencode-direct
For development, run npm ci --ignore-scripts followed by pi install .
from a checkout of this repository. Install through npm or Pi so that peer
packages needed by the native transport imports are available.
Restart Pi or use /reload, then select OpenCode Zen Free in /model.
pi --provider opencode-zen-free --model muse-spark-1.3-contributor-free --thinking xhigh
Muse Spark supports native images, reasoning, and tool calls. Pi's thinking
selector exposes minimal, low, medium, high, and xhigh. An explicit Pi
thinking setting wins; requests without one default to xhigh for Muse Spark.
The provider also registers the other known free models supported by Pi's
Chat Completions transport. Their capabilities and limits come from Pi's
built-in OpenCode catalogue rather than guessed defaults.
How it works
The extension adds a separate opencode-zen-free provider. It uses Pi's native
Responses transport for Muse Spark and native Chat Completions for the other
supported free models. Native Pi streaming handles text, thinking, tool-call
arguments, usage, aborts, and tool-result replay. Tools execute through Pi.
Requests are anonymous by default: without any configured key the literal
public bearer is used and no credentials are sent. If the anonymous tier
rejects you (FreeTierError ... within OpenCode on every request, even tiny
ones — upstream gates anonymous access by more than headers, e.g. egress IP
reputation), attach a Zen key instead: /login opencode-zen-free, or set
OPENCODE_API_KEY. Priority is stored credential, then OPENCODE_API_KEY,
then anonymous; an explicitly passed --api-key is honored the same way.
Anonymous summarization additionally sends OpenCode's byte-identical compaction system prompt instead of Pi's: Zen gates anonymous free tier on that developer content (identical requests with Pi's text 403, with OpenCode's text pass). Only short standalone summarization prompts are rewritten, never conversation content or keyed requests.
Anonymous quota is shared per egress IP (server-side trial bucket counting input +
output + reasoning tokens), so heavy anonymous traffic from one IP — large Hermes
reviews, compactions, or many clients behind one NAT/egress proxy — can exhaust
it for everyone behind that IP with FreeTierError, while the genuine CLI from
a fresh IP keeps working. If anonymous fails everywhere at once, wait for the
window to reset and move heavy background work to a keyed model; light chat
spends little. Set PI_OPENCODE_DIRECT_DEBUG=1 to log outbound identity.
A generated OpenCode session id (timestamp-based ses_ id, cached per Pi
session) supplies x-opencode-session and the full correlation set
(x-opencode-session-id / x-session-affinity / X-Session-Id), keeping
routing affinity stable across turns and distinct between sessions. Auxiliary
calls use the active Pi session when no explicit session ID is available.
A bounded public-catalogue refresh intersects the currently listed IDs with
Pi's known zero-cost models. Paid models are not registered; unknown
free-looking IDs get conservative synthetic entries (Chat Completions
transport) until official metadata arrives via pi update --models.
Pi's model cache is used offline, with the bundled catalogue as the initial
fallback. Update Pi for newly added model metadata. Free-model availability
and limits can change upstream; there is no automatic paid fallback.
Requests use Pi's native retry handling (two retries by default) and a
180-second per-request timeout. Caller overrides and cancellation are honored.
Muse Spark currently accepts only tool_choice: auto; normal Pi tool use does
not require forced tool choice.
Memory extensions (pi-hermes-memory)
Background-review direct transport (pi-ai/compat completeSimple) bypasses
the stream() wrapper, so this extension patches the global compat registry
at load: opencode-zen-free models get the full dynamic identity there too
(Bearer public, OpenCode User-Agent / x-opencode-client / project /
per-session correlation headers, plus the
encrypted-content retry), while other providers pass through untouched. No
memory config needed for the default direct transport — and compat omission
stays off, preserving Hermes llmThinkingOverride: off (no forced xhigh
on this path).
As a last resort, a fetch guard scoped strictly to https://opencode.ai/inference/v1
adds the same identity at the network edge for any other in-process path
(Pi core flows such as compaction, present or future) — other hosts pass
through untouched, and a valid upstream session / existing Authorization are
preserved. node:http/https callers (axios / node-fetch style, any extension
or in-process MCP tool) get the same treatment. Separate processes, direct
undici imports, and WebSocket are the only gaps — Zen transports are
fetch/SSE, so those don't apply in practice.
The pi -p --no-session subprocess transport is a separate process, so no
in-process patch can cover it: it loads --no-extensions + Hermes only and
cannot see opencode-zen-free on its own. That path only runs when direct
fails (or reviewTransport is forced to subprocess), so with direct fixed
no config is needed. If you force subprocess, expose this package to the
child with an absolute file path:
{
"childExtensionPaths": ["/path/to/pi-opencode-direct/src/index.ts"]
}
Development
npm ci --ignore-scripts
npm run verify
# Optional: sends real requests to Zen
npm run test:live
npm test uses in-memory HTTP fixtures, with no network or model calls.
test:live is opt-in and sends two small free-tier requests to verify images,
xhigh reasoning, native streaming tool calls, and replay of a tool result.
Use the free tier lightly and follow the provider's data-use policies.
Validated with Pi 1.3.0 and OpenCode CLI 2.0.30: twenty-one automated tests; live chat with a
native tool-call/result round trip; and a Pi CLI session that used read on a
PNG and correctly described it while OpenCode was absent from PATH.
npm run verify runs type checking, fixture tests, and an npm package dry run.
CI runs these checks on Node 22, 24, and 26. See PUBLISHING.md
for release steps and CHANGELOG.md for changes.
License
MIT. This is an independent extension, not an official OpenCode or Pi package.