Skip to content
This repository was archived by the owner on Oct 11, 2026. It is now read-only.
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
3 changes: 2 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@

## 0.6.2

- Document Claude Sonnet 5.5 and add it to cache validation. No model behavior changes.
- Add GPT-6.1 Sol (`gpt-6.1-sol`) to the OpenAI profiles, with `low` through `max` efforts (`none` is not supported).
- Document Claude Sonnet 5.5 and add it to cache validation.

## 0.6.1

Expand Down
6 changes: 4 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -145,15 +145,17 @@ cost, but have no manual effort variants.
| `jev-router/gpt-6-astra` | `low`, `medium`, `high`, `xhigh`, `max` |
| `jev-router/gpt-6-luna` | `none`, `low`, `medium`, `high`, `xhigh`, `max` |
| `jev-router/gpt-6-sol` | `none`, `low`, `medium`, `high`, `xhigh`, `max` |
| `jev-router/gpt-6.1-sol` | `low`, `medium`, `high`, `xhigh`, `max` |
| `jev-router/claude-fable-5-1` | `low`, `medium`, `high`, `xhigh`, `max` |
| `jev-router/claude-mythos-5-1` | `low`, `medium`, `high`, `xhigh`, `max` |
| `jev-router/claude-opus-5-5` | `low`, `medium`, `high`, `xhigh`, `max` |
| `jev-router/claude-opus-5` | `low`, `medium`, `high`, `xhigh`, `max` |
| `jev-router/claude-sonnet-5-5` | `low`, `medium`, `high`, `xhigh`, `max` |

See OpenAI's [Astra](https://developers.openai.com/api/docs/models/gpt-6-astra),
[Luna](https://developers.openai.com/api/docs/models/gpt-6-luna), and
[Sol](https://developers.openai.com/api/docs/models/gpt-6-sol) pages to choose
[Luna](https://developers.openai.com/api/docs/models/gpt-6-luna),
[Sol](https://developers.openai.com/api/docs/models/gpt-6-sol), and
[6.1 Sol](https://developers.openai.com/api/docs/models/gpt-6.1-sol) pages to choose
between them. Your endpoint must grant access to the model you select.

For GPT-6, only standard, single-agent mode is supported: pro models, other
Expand Down
2 changes: 1 addition & 1 deletion docs/behavior.md
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ Reference for the wire behavior shared by the OpenCode plugin and the standalone
drop injected history). Conflicting caller updates at an insertion boundary
receive a local `400`. No item fields are silently stripped to make these
combinations work.
- Exact registered OpenAI IDs are `gpt-6-astra`, `gpt-6-luna`, and `gpt-6-sol`;
- Exact registered OpenAI IDs are `gpt-6-astra`, `gpt-6-luna`, `gpt-6-sol`, and `gpt-6.1-sol`;
Comment thread
robertn702 marked this conversation as resolved.
Anthropic `/v1/messages` accepts `claude-fable-5-1`, `claude-mythos-5-1`,
`claude-opus-5-5`, `claude-opus-5`, and `claude-sonnet-5-5`. Model/route mismatches are local `400`s.
Missing, malformed, unknown, and pro IDs fail locally before classification.
Expand Down
1 change: 1 addition & 0 deletions src/models.ts
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ export const MODELS: readonly ModelProfile[] = Object.freeze([
profile("gpt-6-astra", "GPT-6 Astra", ["low", "medium", "high", "xhigh", "max"]),
profile("gpt-6-luna", "GPT-6 Luna", ["none", "low", "medium", "high", "xhigh", "max"]),
profile("gpt-6-sol", "GPT-6 Sol", ["none", "low", "medium", "high", "xhigh", "max"]),
profile("gpt-6.1-sol", "GPT-6.1 Sol", ["low", "medium", "high", "xhigh", "max"]),
profile("claude-fable-5-1", "Claude Fable 5.1", ["low", "medium", "high", "xhigh", "max"], "anthropic", "high"),
profile("claude-mythos-5-1", "Claude Mythos 5.1", ["low", "medium", "high", "xhigh", "max"], "anthropic", "high"),
profile("claude-opus-5-5", "Claude Opus 5.5", ["low", "medium", "high", "xhigh", "max"], "anthropic"),
Expand Down
2 changes: 1 addition & 1 deletion test/models.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ describe("registered model isolation", () => {
}
});
it("registers only supported Anthropic profiles with model-specific base efforts", () => {
expect(modelsFor("openai").map((model) => model.id)).toEqual(["gpt-6-astra", "gpt-6-luna", "gpt-6-sol"]);
expect(modelsFor("openai").map((model) => model.id)).toEqual(["gpt-6-astra", "gpt-6-luna", "gpt-6-sol", "gpt-6.1-sol"]);
expect(modelsFor("anthropic").map((model) => [model.id, model.defaultBaseEffort])).toEqual([
["claude-fable-5-1", "high"], ["claude-mythos-5-1", "high"], ["claude-opus-5-5", "medium"], ["claude-opus-5", "high"], ["claude-sonnet-5-5", "medium"],
]);
Expand Down
9 changes: 5 additions & 4 deletions test/plugin-v2.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import type { ModelEditor } from "@opencode/plugin/promise/model";
import type { SessionHttpRequest, SessionHttpResponse } from "@opencode/plugin/promise/session";

import plugin from "../src/plugin.js";
import { MODELS } from "../src/models.js";

const originalFetch = globalThis.fetch;
const OPENAI = "@opencode/ai/providers/openai/responses";
Expand All @@ -22,7 +23,7 @@ const sources = () => new Map([
]);

async function host(options: Record<string, unknown> = base, source = sources(), credentials: Record<string, unknown> = {}) {
const registrations: unknown[] = [];
const registrations: Parameters<ProviderEditor["add"]>[0][] = [];
const aliases = new Map<string, Record<string, unknown>>();
const hooks = new Map<string, (event: any) => Promise<void> | void>();
let providerTransform!: (editor: ProviderEditor) => void;
Expand All @@ -37,7 +38,7 @@ async function host(options: Record<string, unknown> = base, source = sources(),
const cleanup = await plugin.setup(ctx);
const providerPass = () => {
aliases.clear();
providerTransform({ add(registration: any) { registrations.push(registration); for (const model of registration.models) aliases.set(model.id, { ...model }); } } as ProviderEditor);
providerTransform({ add(registration) { registrations.push(registration); for (const model of registration.models) aliases.set(model.id, { ...model }); } } as ProviderEditor);
};
const modelPass = () => {
modelTransform({
Expand Down Expand Up @@ -89,8 +90,8 @@ describe("V2 wrap aliases", () => {

it("registers placeholders, copies late source metadata, removes unused aliases and survives reload", async () => {
const h = await host();
expect((h.registrations[0] as any).info).toMatchObject({ id: "jev-router", settings: { transport: "http" } });
expect((h.registrations[0] as any).models).toHaveLength(8);
expect(h.registrations[0]?.info).toMatchObject({ id: "jev-router", settings: { transport: "http" } });
expect(h.registrations[0]?.models.map((model) => model.id)).toEqual(MODELS.map((model) => model.id));
expect([...h.aliases.keys()].sort()).toEqual(["claude-opus-5-5", "gpt-6-astra"]);
expect(h.aliases.get("gpt-6-astra")).toMatchObject({ name: "GPT-6 Astra", modelID: "gpt-6-astra", limit: { context: 123 }, cost: [1], variants: [], settings: { baseURL: "https://a.test/v1", apiKey: "config-key", extra: 1 }, headers: { "x-source": "provider", "x-model": "yes" }, body: { top: true, model: true } });
expect(h.aliases.get("gpt-6-astra")).toMatchObject({ transport: "http" });
Expand Down
Loading