Repository navigation
fix(opencode): alias over-length tool names (>64 chars) for OpenCode Zen/Go - #16531
Merged
diegosouzapw merged 6 commits intoOct 17, 2026
Merged
Conversation
…Zen/Go
OpenCode chat-completions upstreams reject tool names longer than 64
characters ("name must be at most 64 characters, got 68"), which Claude
Code MCP tool names routinely exceed. The registry-scoped length alias
only ran in DefaultExecutor; OpencodeExecutor extends BaseExecutor, so
names reached opencode.ai unchanged.
- Extract the DefaultExecutor alias block into a reusable
open-sse/executors/toolNameLengthAlias.ts (applyToolNameLengthAliases
with a pluggable normalizer, applyRegistryToolNameLengthAliases, and
mergeToolNameAliases for the non-enumerable _toolNameMap side channel).
DefaultExecutor now calls it; behavior unchanged.
- OpencodeExecutor applies it last in transformRequest, only on the
chat-completions surface; Claude/Responses surfaces are untouched.
- Declare toolNameMaxLength: 64 on opencode, opencode-zen, opencode-go.
Aliases reuse normalizeOpenAIToolNames (prefix + sha256-12, collision
safe) and are restored in responses through the existing _toolNameMap
consumer in chatCore.
Co-authored-by: MakdumIbrohim <makdumibrohim3@gmail.com>
Inspired-by: decolua/9router#3637
Contributor
CI Coverage Report
Coverage artifact was not available for this run. |
6 of 7 tasks
…Alias to keep opencode.ts under its frozen size
diegosouzapw
added a commit
that referenced
this pull request
Oct 17, 2026
Brings in #16531 (OpenCode tool-name aliasing), #16960 (Parallel provider) and #16965 (migration 206). Count-only conflicts take the tip's numbers (re-measured in the next commit); the OpenCode Free registry stays deleted; QUICK-START mirrors keep this branch's retranslation (the tip's still listed OpenCode Free); .i18n-state.json takes the tip (this branch's mirrors are re-adopted next).
diegosouzapw
added a commit
that referenced
this pull request
Oct 17, 2026
…e-measure counts The release tip now ships 206_codex_wakeup_tasks.sql, so this branch's migration moves to 207 (no gap); REMOVED_PROVIDERS (source + 66 mirrors), the changelog fragment and the migration test follow. Counts re-measured on the merged tree: 374 providers (375 on the tip minus OpenCode Free), 204 migrations, 34 recurring pools, 52 free-forever providers; count-only edits in AGENTS.md, llm.txt (+ mirrors via sync-llm-mirrors) and the omni-auth/omni-providers skills. PROVIDER_REFERENCE regenerated. #16531's tool-name-length test now covers the keyed Zen/Go entries only — the keyless `opencode` registry it also listed is removed by this PR. i18n: re-adopt the eight docs whose mirrors this branch retranslated or edited, and re-hash the README/PROVIDER_REFERENCE mirror targets after the count-only edits; the drift gate now reports exactly the tip's inherited source drift.
diegosouzapw
added a commit
that referenced
this pull request
Oct 17, 2026
) Merged via /merge-batch (2026-10-17 wave, owner-approved rework incl. count-only edits to protected surfaces). Reconciled on release/v3.8.52 @ 5413a24 (after #16531, #16960, #16965, #16924): - Migration renumbered 208 -> 207 (`207_remove_opencode_free_provider.sql`; tip ships 206_codex_wakeup_tasks, no gap); test, REMOVED_PROVIDERS (+66 mirrors) and changelog fragment follow. - #16531: the keyless `opencode` registry stays deleted; its tool-name-length test now covers the keyed Zen/Go entries only (10/10). - Counts re-measured on the merged tree: 374 providers (375 - OpenCode Free), 204 migrations, 34 recurring pools, 52 free-forever. AGENTS.md, llm.txt (+66 mirrors), skills omni-auth/omni-providers differ from the tip only in digits (verified). - FREE_TIERS mirrors: tip's #16924 refresh kept, OpenCode Free rows/section removed and pool count 35->34 applied mechanically (66/66); QUICK-START, TROUBLESHOOTING, FREE-TIERS-GUIDE, PROVIDERS-GUIDE, REMOVED_PROVIDERS mirrors retranslated with targeted `i18n:run --files` (330/330, table row counts equal to the source). i18n drift gate reports exactly the tip's inherited 21 drifted sources, 0 drifted targets. - CodeQL: chat-noauth-model-cooldown test compares the exact upstream hostname instead of a URL substring. Validation: focused node tests 1737/1737 (PR tests, migrations, blocklist, opencode*, tool-name-length, noauth cooldown) + 1052/1053 across every other test referencing opencode (1 env-only: opencode-ai postinstall binary absent locally); vitest 61/61 + 18/18; typecheck:core, api-typecheck, open-sse typecheck OK; complexity/cognitive/file-size/dead-code within baseline; boundary 774/774; changelog-integrity, docs-sync, docs-counts (strict) OK; provider-consistency OK (374); agent-skills Generated 0; eslint + prettier on changed files clean. CI runs for this head were queued (account runner backlog) and never started; remaining tip reds are the inherited base-red #15306.
6 of 7 tasks
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
name must be at most 64 characters, got 68), which Claude Code MCP tool names routinely exceed. The registry-scoped tool-name alias only ran inDefaultExecutor;OpencodeExecutorextendsBaseExecutor, so long names reached opencode.ai unchanged and the request failed with 400.opencode,opencode-zen,opencode-gonow declaretoolNameMaxLength: 64). Aliases are restored in responses through the existing_toolNameMappath.Attribution
Thanks to @MakdumIbrohim for the original implementation.
Changes
open-sse/executors/toolNameLengthAlias.ts(new):applyToolNameLengthAliases(body, maxLength, normalize?)(pluggable normalizer, defaulting to the existingnormalizeOpenAIToolNames; a missing or non-positive-integer limit is a no-op),applyRegistryToolNameLengthAliases(provider, body), andmergeToolNameAliases(copies any existing_toolNameMap, merges the new aliases, and keeps the map non-enumerable). It accepts other normalizers, so a surface with a different tool shape (for example a Responses-API 128-char cap) can reuse it.open-sse/executors/default.ts: the inline alias block is replaced byapplyRegistryToolNameLengthAliases(this.provider, withDefaults). Outputs are unchanged; the NVIDIA suite passes as before.open-sse/executors/opencode.ts:transformRequestapplies the helper as its last step, and only on the chat-completions surface. Claude and Responses surfaces are left alone.open-sse/config/providers/registry/opencode/{index,zen/index,go/index}.ts:toolNameMaxLength: 64.normalizeOpenAIToolNames(prefix +_+ sha256-12, safe against collisions, consistent acrosstools,tool_choice, historytool_callsandrole:"tool"names).Test plan
tests/unit/opencode-tool-name-length.test.ts(TDD). Against the pre-port opencode executor and registry, 4 tests failed (registry flag, distinct aliases for two 68-char names sharing a 64-char prefix, consistent history/tool_choice aliasing, response restore). After the port:node --import tsx/esm --test tests/unit/opencode-tool-name-length.test.ts→ℹ tests 10 ℹ pass 10 ℹ fail 0node --import tsx/esm --test tests/unit/nvidia-tool-compatibility-2840.test.ts→ℹ tests 7 ℹ pass 7 ℹ fail 0executors/opencode.ts,executors/default.ts,registry/opencode,toolNameMaxLength,normalizeOpenAIToolNames):ℹ tests 1375 ℹ pass 1374 ℹ fail 1. The one failure was a concurrency-timing assertion inopencode-transient-rotation.test.ts("both requests must be in flight simultaneously") that showed up under box load. Rerun in isolation:ℹ tests 11 ℹ pass 11 ℹ fail 0.npm run typecheck:core→ exit 0npx eslint --suppressions-location config/quality/eslint-suppressions.json <changed files>→ exit 0;npx prettier --check <changed files>→ cleannode scripts/check/check-pr-test-policy.mjs→Result: PASS;GITHUB_BASE_REF=release/v3.8.52 npm run check:test-masking→OK — 0 modificado(s) … sem enfraquecimento