Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion bun.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

22 changes: 21 additions & 1 deletion devlog/131_opencode-go-metadata-drift/00_plan.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,26 @@ models. The root cause is that OpenCode Go's `/v1/models` endpoint only exposes
`id/object/created/owned_by`, while the exact `context/output/modalities` values live in
OpenCode's official `/data/...` catalog pages.

## Retry Update: Web SOT Split

The first upstream GJC PR (#914) was closed after review because it treated every tracked
OpenCode Go id as `/v1/chat/completions` and reused generic data-page prices for rows where
the Go product page publishes a different contract. The retry uses a split source of truth:

- `https://opencode.ai/docs/go/#endpoints` is authoritative for the OpenCode Go gateway
endpoint/API SDK path.
- `https://opencode.ai/docs/go/#usage-limits` is authoritative for current Go product
prices when the row appears in that table.
- `https://opencode.ai/data/...` pages remain authoritative for context/output/modalities.
- `https://opencode.ai/zen/go/v1/models` is existence-only for this work because it returns
model ids without context/output/pricing metadata.

This means MiniMax M2.5/M2.7/M3 and Qwen3.6/3.7 Plus/Max must route to
`anthropic-messages` on `https://opencode.ai/zen/go`, while GLM/Kimi/DeepSeek/MiMo rows in
the endpoint table route to `openai-completions` on `https://opencode.ai/zen/go/v1`.
Qwen Plus rows have tiered prices in the Go usage table; generated rows advertise a 1M
context window, so the retry encodes the `> 256K tokens` tier.

## Official Source Values

These are the Phase 131 source-of-truth values verified from official OpenCode data pages on
Expand Down Expand Up @@ -45,6 +65,7 @@ These are the Phase 131 source-of-truth values verified from official OpenCode d

Official evidence pages:

- `https://opencode.ai/docs/go/`
- `https://opencode.ai/data/deepseek/deepseek-v4-flash`
- `https://opencode.ai/data/zhipu/glm-5-2`
- `https://opencode.ai/data/moonshot/kimi-k2-7-code`
Expand Down Expand Up @@ -111,4 +132,3 @@ Plan:
`max_context_window`, and `auto_compact_token_limit`.
- No token values are printed.
- No unrelated dirty worktree changes are reverted.

189 changes: 112 additions & 77 deletions devlog/131_opencode-go-metadata-drift/10_verification.md
Original file line number Diff line number Diff line change
@@ -1,117 +1,152 @@
# 131.10 — Verification: OpenCode Go Metadata Drift Closure
# 131.10 — Verification: OpenCode Go Metadata Drift Retry

## Scope

Phase 131 closes the OpenCode Go metadata drift across three repositories:
Phase 131 retry replaces the closed GJC PR #914 assumptions with the current official
OpenCode Go web contract.

- GJC upstream clone on `dev`: `/Users/jun/Developer/new/700_projects/jawcode/devlog/_upstream_gjc`
- jawcode on `dev`: `/Users/jun/Developer/new/700_projects/jawcode`
- opencodex on `dev`: `/Users/jun/Developer/new/700_projects/opencodex`
Source-of-truth split:

The source-of-truth values are recorded in `00_plan.md`. The generated model contracts still
support only `text` and `image` inputs, so official `video`, `audio`, and `pdf` support remains
recorded as source evidence but is not emitted into generated rows.
- `https://opencode.ai/docs/go/#endpoints`: OpenCode Go endpoint/API SDK routing.
- `https://opencode.ai/docs/go/#usage-limits`: current Go product prices for rows present
in the usage table.
- `https://opencode.ai/data/...`: context window, output limit, and modality facts.
- `https://opencode.ai/zen/go/v1/models`: existence-only; the endpoint does not expose
context/output/pricing metadata.

## Official Routing Contract

Routes encoded in GJC and jawcode:

- `openai-completions` on `https://opencode.ai/zen/go/v1`: `deepseek-v4-flash`,
`deepseek-v4-pro`, `glm-5.1`, `glm-5.2`, `kimi-k2.6`, `kimi-k2.7-code`, `mimo-v2.5`,
`mimo-v2.5-pro`.
- `anthropic-messages` on `https://opencode.ai/zen/go`: `minimax-m2.5`, `minimax-m2.7`,
`minimax-m3`, `qwen3.6-plus`, `qwen3.7-max`, `qwen3.7-plus`.

Rows present in the data catalog but absent from the current Go endpoint table retain data-page
metadata and are not used to infer undocumented endpoint overrides.

## GJC

Repository:

- `/Users/jun/Developer/new/700_projects/jawcode/devlog/_upstream_gjc`

Branch:

- `codex/opencode-go-contract`, based on `origin/dev`.

Modified:

- `/Users/jun/Developer/new/700_projects/jawcode/devlog/_upstream_gjc/packages/ai/src/provider-models/openai-compat.ts`
- `/Users/jun/Developer/new/700_projects/jawcode/devlog/_upstream_gjc/packages/ai/test/issue-887-repro.test.ts`
- `/Users/jun/Developer/new/700_projects/jawcode/devlog/_upstream_gjc/packages/ai/src/model-thinking.ts`
- `/Users/jun/Developer/new/700_projects/jawcode/devlog/_upstream_gjc/packages/ai/src/models.json`

Verification:

- `bun test packages/ai/test/issue-887-repro.test.ts` passed: 10 tests, 0 failures.
- `bun test packages/ai/test/issue-887-repro.test.ts` passed: 17 tests, 0 failures,
32 assertions.
- `bun --cwd=packages/ai run generate-models` produced `opencode-go: 20 models`.
- Generated contract check passed: `checked=8 bad=0` for routing, base URL, context,
output, and price samples.
- `bun --cwd=packages/ai run check` passed.
- Custom 20-row comparison against generated `opencode-go` rows returned `bad=0`.
- GJC PR #914 (`Yeachan-Heo/gajae-code`, base `dev`) CI passed all checks:
`gh pr checks 914 --repo Yeachan-Heo/gajae-code` returned 12 passing checks.

GJC needed one extra guard in `model-thinking.ts`: the global `minimax-m3` 1M policy now excludes
`provider === "opencode-go"`, because OpenCode Go's official `minimax-m3` context is 512000.

## jawcode

Repository:

- `/Users/jun/Developer/new/700_projects/jawcode/devlog/_worktrees/opencode-go-contract`

Branch:

- `codex/opencode-go-contract`, based on `origin/dev` in a separate worktree to preserve
unrelated dirty files in `/Users/jun/Developer/new/700_projects/jawcode`.

Modified:

- `/Users/jun/Developer/new/700_projects/jawcode/packages/ai/src/provider-models/openai-compat.ts`
- `/Users/jun/Developer/new/700_projects/jawcode/packages/ai/test/issue-887-repro.test.ts`
- `/Users/jun/Developer/new/700_projects/jawcode/packages/ai/src/models.json`
- `/Users/jun/Developer/new/700_projects/jawcode/devlog/_worktrees/opencode-go-contract/packages/ai/src/provider-models/openai-compat.ts`
- `/Users/jun/Developer/new/700_projects/jawcode/devlog/_worktrees/opencode-go-contract/packages/ai/test/issue-887-repro.test.ts`
- `/Users/jun/Developer/new/700_projects/jawcode/devlog/_worktrees/opencode-go-contract/packages/ai/src/models.json`

Verification:

- `bun test packages/ai/test/issue-887-repro.test.ts` passed: 10 tests, 0 failures, 19 assertions.
- `bun test packages/ai/test/issue-887-repro.test.ts` passed: 17 tests, 0 failures,
32 assertions.
- `bun --cwd=packages/ai run generate-models` produced `opencode-go: 20 models`.
- `bun --cwd=packages/ai run check` passed.
- Custom 20-row comparison against generated `opencode-go` rows returned `bad=0`.

Commit:

- `80395c9c fix(ai): sync opencode go model metadata`
- Generated contract check passed: `checked=8 bad=0` for routing, base URL, context,
output, and price samples.
- `bun --cwd=packages/ai run check` passed after temporarily linking the existing parent
repo `node_modules` into the worktree for type resolution; the symlink was removed and not
staged.

Existing jawcode dirty files were preserved and not staged:
Existing dirty files preserved outside the worktree:

- `/Users/jun/Developer/new/700_projects/jawcode/AGENTS.md`
- `/Users/jun/Developer/new/700_projects/jawcode/.agents/`
- `/Users/jun/Developer/new/700_projects/jawcode/.claude/`

## opencodex

Modified:
Repository:

- `/Users/jun/Developer/new/700_projects/opencodex`

Branch:

- `codex/opencode-go-contract`

Implementation result:

- `/Users/jun/Developer/new/700_projects/opencodex/src/generated/jawcode-model-metadata.ts`
- `/Users/jun/Developer/new/700_projects/opencodex/scripts/generate-jawcode-metadata.ts`
- `/Users/jun/Developer/new/700_projects/opencodex/src/codex-catalog.ts`
- `/Users/jun/Developer/new/700_projects/opencodex/tests/codex-catalog.test.ts`
- `/Users/jun/Developer/new/700_projects/opencodex/devlog/131_opencode-go-metadata-drift/10_verification.md`
- `JAWCODE_MODELS_JSON=/Users/jun/Developer/new/700_projects/jawcode/devlog/_worktrees/opencode-go-contract/packages/ai/src/models.json bun run generate:jawcode-metadata`
was executed and verified. It introduced no `opencode-go` metadata delta because opencodex
stores context/output/modalities only; endpoint and price changes live in GJC/jawcode.
- The generated-file diff was intentionally reduced back to zero to avoid unrelated dynamic
`openrouter` metadata churn from the jawcode worktree.
- The no-code-runtime rationale is recorded in `20_opencodex-integration.md`.

Verification:

- `bun run generate:jawcode-metadata` regenerated from
`/Users/jun/Developer/new/700_projects/jawcode/packages/ai/src/models.json`.
- `bun test tests/codex-catalog.test.ts` passed: 12 tests, 0 failures, 90 assertions.
- `bun test tests/provider-registry-parity.test.ts` passed: 8 tests, 0 failures, 23 assertions.
- `bun test tests` passed: 65 tests, 0 failures, 234 assertions.
- `bun test tests/codex-catalog.test.ts` passed: 13 tests, 0 failures, 98 assertions.
- `bun test tests/provider-registry-parity.test.ts` passed: 8 tests, 0 failures,
23 assertions.
- OpenCode Go generated metadata sample check passed: `metadata_checked=5 bad=0`.
- `bun test tests` passed: 88 tests, 0 failures, 287 assertions.
- `bun x tsc --noEmit` passed.
- Generated metadata 20-row comparison for `opencode-go` returned `bad=0`.

Real `ocx` verification found one extra runtime gap after the first commit:

- `ocx` is correctly symlinked to the local repository:
`/Users/jun/.local/bin/ocx` -> `/Users/jun/Developer/new/700_projects/opencodex/dist/bin/ocx`
-> `/Users/jun/Developer/new/700_projects/opencodex/src/cli.ts`.
- `ocx sync` originally still omitted official rows absent from the live provider `/v1/models`
response unless they were manually configured.
- The runtime catalog path now augments configured `opencode-go` with generated jawcode metadata
rows before disabled-model filtering.
- Current user config intentionally disables `opencode-go/qwen3.5-plus` and
`opencode-go/hy3-preview`, so they remain absent from the live catalog by configuration.

Post-patch local `ocx` smoke:

- `ocx stop; ocx start` started the proxy on `http://localhost:10100`.
- `GET /healthz` returned status `ok`.
- `GET /v1/models?client_version=0.141.0` returned HTTP 200.
- `opencode-go/glm-5.2` returned `context_window=1000000`,
`auto_compact_token_limit=900000`, `input_modalities=["text"]`, `supports_websockets=true`.
- `opencode-go/kimi-k2.7-code` returned `context_window=262144`,
`auto_compact_token_limit=235929`, `input_modalities=["text","image"]`, `supports_websockets=true`.
- `opencode-go/minimax-m3` returned `context_window=512000`,
`auto_compact_token_limit=460800`, `input_modalities=["text","image"]`, `supports_websockets=true`.

The catalog regression test now locks high-risk OpenCode Go rows through the full opencodex path:

- `glm-5.2`: `context_window=1000000`, `auto_compact_token_limit=900000`, `input_modalities=["text"]`
- `qwen3.5-plus`: `context_window=1000000`, `auto_compact_token_limit=900000`, `input_modalities=["text","image"]`
- `kimi-k2.7-code`: `context_window=262144`, `auto_compact_token_limit=235929`, `input_modalities=["text","image"]`
- `minimax-m3`: `context_window=512000`, `auto_compact_token_limit=460800`, `input_modalities=["text","image"]`
- `hy3-preview`: `context_window=256000`, `auto_compact_token_limit=230400`, `input_modalities=["text"]`

## Result

The OpenCode Go metadata drift is closed at source generation, jawcode consumption, and opencodex
catalog export. Codex routed catalog entries now receive corrected context limits and compaction
thresholds for the tracked OpenCode Go models.
- local `ocx` catalog smoke passed and the proxy was stopped afterward.

Runtime `ocx` smoke:

- `ocx start` started the proxy on `http://localhost:10100`.
- `GET http://127.0.0.1:10100/healthz` returned `health ok`.
- `GET http://127.0.0.1:10100/v1/models?client_version=0.141.0` returned Codex catalog
rows with corrected OpenCode Go limits:
- `opencode-go/glm-5.2`: `context_window=1000000`,
`max_context_window=1000000`, `auto_compact_token_limit=900000`,
`input_modalities=["text"]`.
- `opencode-go/kimi-k2.7-code`: `context_window=262144`,
`max_context_window=262144`, `auto_compact_token_limit=235929`,
`input_modalities=["text","image"]`.
- `opencode-go/minimax-m3`: `context_window=512000`,
`max_context_window=512000`, `auto_compact_token_limit=460800`,
`input_modalities=["text","image"]`.
- `opencode-go/qwen3.7-plus`: `context_window=1000000`,
`max_context_window=1000000`, `auto_compact_token_limit=900000`,
`input_modalities=["text","image"]`.
- Final state confirmed with `ocx stop`: no running proxy found and opencodex was removed
from Codex config.

## PR / CI

Opened PRs:

- GJC upstream: `https://github.com/Yeachan-Heo/gajae-code/pull/915`
- jawcode: `https://github.com/lidge-jun/jawcode/pull/1`
- opencodex: `https://github.com/lidge-jun/opencodex/pull/1`

Initial CI status after PR creation:

- GJC PR #915: checks pending (`Affected path validation / plan`, `gjc-state-gates / integrity`,
`gjc-state-gates / read`, `gjc-state-gates / runtime`, `gjc-state-gates / static`).
- jawcode PR #1: checks pending (`Affected path validation`, `jwc-state-gates`).
- opencodex PR #1: no checks reported on the branch at creation time.
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
# 131.20 — opencodex Integration Note

## Why There Is No opencodex Runtime Code Patch

Phase 131 retry changes two upstream jawcode/GJC surfaces:

- OpenCode Go endpoint routing: `/v1/chat/completions` versus `/v1/messages`.
- OpenCode Go product pricing from `https://opencode.ai/docs/go/#usage-limits`.

opencodex does not consume either field. Its Codex catalog integration consumes only the
generated jawcode metadata fields represented in
`src/generated/jawcode-model-metadata.ts`:

- `contextWindow`
- `maxTokens`
- `input`
- `reasoning`
- optional `wireModelId`

Those are the fields Codex needs for `context_window`, `max_context_window`,
`auto_compact_token_limit`, and `input_modalities`.

## Existing Guards

The opencodex-side regression surface is already covered by
`tests/codex-catalog.test.ts`:

- `opencode-go high-risk models use official jawcode metadata in the Codex catalog`
locks `glm-5.2`, `qwen3.5-plus`, `kimi-k2.7-code`, `minimax-m3`, and `hy3-preview`.
- `opencode-go catalog sync appends official rows missing from /v1/models` verifies that
generated jawcode rows are appended for configured `opencode-go`, even when the live
provider `/v1/models` endpoint omits them.

The runtime smoke in `10_verification.md` then verifies the same path through real `ocx start`
and `GET /v1/models?client_version=0.141.0`.

## Generated Metadata Result

Regenerating opencodex metadata from the patched jawcode worktree was tested with:

`JAWCODE_MODELS_JSON=/Users/jun/Developer/new/700_projects/jawcode/devlog/_worktrees/opencode-go-contract/packages/ai/src/models.json bun run generate:jawcode-metadata`

The relevant `opencode-go` context/output/modalities rows did not change compared with the
existing committed snapshot. The retry's meaningful payload therefore lives in jawcode/GJC,
while opencodex records the source-of-truth split and verifies the live catalog behavior.

To avoid unrelated dynamic provider churn, no generated metadata diff is committed in
opencodex for this retry.
2 changes: 1 addition & 1 deletion docs-site/src/content/docs/reference/cli.md
Original file line number Diff line number Diff line change
Expand Up @@ -93,7 +93,7 @@ ocx service uninstall
### `ocx update`

Self-update opencodex to the latest version published on npm, using the package manager it was
installed with (`bun add -g @bitkyc08/opencodex@latest` or `npm install -g @bitkyc08/opencodex@latest`). It detects a
installed with (`bun install -g @bitkyc08/opencodex@latest` or `npm install -g @bitkyc08/opencodex@latest`). It detects a
source checkout and tells you to `git pull && bun install` instead, and is a no-op if you're already
on the newest version. Restart the proxy afterward (`ocx stop && ocx start`) to run the new build.

Expand Down
2 changes: 1 addition & 1 deletion scripts/install.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ $bunVer = & bun --version
Write-Host "Using Bun v$bunVer"

# Install opencodex globally
& bun add -g @bitkyc08/opencodex
& bun install -g @bitkyc08/opencodex

Write-Host ""
Write-Host "opencodex installed! Run 'ocx init' to set up." -ForegroundColor Green
2 changes: 1 addition & 1 deletion scripts/install.sh
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ BUN_VER=$(bun --version)
echo "Using Bun v$BUN_VER"

# Install opencodex globally
bun add -g @bitkyc08/opencodex
bun install -g @bitkyc08/opencodex

echo ""
echo "✅ opencodex installed! Run 'ocx init' to set up."
2 changes: 1 addition & 1 deletion scripts/postinstall.mjs
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#!/usr/bin/env node
/**
* postinstall — one-time GitHub-star prompt during `npm install -g opencx`.
* postinstall — one-time GitHub-star prompt during `npm install -g @bitkyc08/opencodex`.
*
* Behavior:
* - TTY-only (skips CI / piped installs)
Expand Down