g1t/services/models/src/openai.test.ts
Pick any line to see why it is the way it is: the commit, the pull request and issue it came from, and what the agent was thinking.
| Models per workspace: several providers, routed by kind of work | 1 | import assert from "node:assert/strict"; |
| 2 | import { test } from "node:test"; | |
| 3 | ||
| A catalogue of model providers, and settings that feel like settings | 4 | import { StreamTranslator, carryId, errorFromChat, fromChat, toChat, uncarryId } from "./openai.ts"; |
| Models per workspace: several providers, routed by kind of work | 5 | |
| 6 | test("a conversation with tool calls becomes a chat completion", () => { | |
| 7 | const body = toChat( | |
| 8 | { | |
| 9 | system: [{ type: "text", text: "You are a coding agent." }], | |
| 10 | max_tokens: 4096, | |
| 11 | temperature: 0.2, | |
| 12 | stream: true, | |
| 13 | tools: [ | |
| 14 | { name: "Bash", description: "Run a command", input_schema: { type: "object", properties: { command: { type: "string" } } } }, | |
| 15 | { name: "web_search", type: "web_search_20250305" }, | |
| 16 | ], | |
| 17 | messages: [ | |
| 18 | { role: "user", content: "Fix the test." }, | |
| 19 | { | |
| 20 | role: "assistant", | |
| 21 | content: [ | |
| 22 | { type: "text", text: "Running it." }, | |
| 23 | { type: "tool_use", id: "toolu_1", name: "Bash", input: { command: "cargo test" } }, | |
| 24 | ], | |
| 25 | }, | |
| 26 | { | |
| 27 | role: "user", | |
| 28 | content: [ | |
| 29 | { type: "tool_result", tool_use_id: "toolu_1", content: [{ type: "text", text: "1 failed" }] }, | |
| 30 | { type: "text", text: "Keep going." }, | |
| 31 | ], | |
| 32 | }, | |
| 33 | ], | |
| 34 | }, | |
| 35 | "gpt-5", | |
| 36 | { official: true }, | |
| 37 | ); | |
| 38 | assert.deepEqual(body.messages, [ | |
| 39 | { role: "system", content: "You are a coding agent." }, | |
| 40 | { role: "user", content: "Fix the test." }, | |
| 41 | { | |
| 42 | role: "assistant", | |
| 43 | content: "Running it.", | |
| 44 | tool_calls: [{ id: "toolu_1", type: "function", function: { name: "Bash", arguments: '{"command":"cargo test"}' } }], | |
| 45 | }, | |
| 46 | { role: "tool", tool_call_id: "toolu_1", content: "1 failed" }, | |
| 47 | { role: "user", content: "Keep going." }, | |
| 48 | ]); | |
| 49 | assert.equal(body.model, "gpt-5"); | |
| 50 | assert.equal(body.max_completion_tokens, 4096); | |
| 51 | assert.equal(body.temperature, undefined); | |
| 52 | assert.deepEqual(body.stream_options, { include_usage: true }); | |
| 53 | // Only functions cross over; Anthropic's server tools do not. | |
| 54 | assert.equal((body.tools as unknown[]).length, 1); | |
| 55 | }); | |
| 56 | ||
| 57 | test("a compatible endpoint gets max_tokens and temperature", () => { | |
| 58 | const body = toChat({ messages: [{ role: "user", content: "hi" }], max_tokens: 10, temperature: 0.5 }, "llama", { official: false }); | |
| 59 | assert.equal(body.max_tokens, 10); | |
| 60 | assert.equal(body.temperature, 0.5); | |
| 61 | }); | |
| 62 | ||
| 63 | test("a completion comes back as an Anthropic message", () => { | |
| 64 | const message = fromChat( | |
| 65 | { | |
| 66 | id: "chatcmpl-1", | |
| 67 | choices: [ | |
| 68 | { | |
| 69 | finish_reason: "tool_calls", | |
| 70 | message: { | |
| 71 | content: "Let me look.", | |
| 72 | tool_calls: [{ id: "call_1", type: "function", function: { name: "Read", arguments: '{"file_path":"a.rs"}' } }], | |
| 73 | }, | |
| 74 | }, | |
| 75 | ], | |
| 76 | usage: { prompt_tokens: 10, completion_tokens: 5 }, | |
| 77 | }, | |
| 78 | "gpt-5", | |
| 79 | ); | |
| 80 | assert.deepEqual(message.content, [ | |
| 81 | { type: "text", text: "Let me look." }, | |
| 82 | { type: "tool_use", id: "call_1", name: "Read", input: { file_path: "a.rs" } }, | |
| 83 | ]); | |
| 84 | assert.equal(message.stop_reason, "tool_use"); | |
| 85 | assert.deepEqual(message.usage, { input_tokens: 10, output_tokens: 5 }); | |
| 86 | }); | |
| 87 | ||
| 88 | function events(sse: string): { type: string; [key: string]: unknown }[] { | |
| 89 | return sse | |
| 90 | .split("\n\n") | |
| 91 | .filter(Boolean) | |
| 92 | .map((block) => JSON.parse(block.split("\n")[1].slice(6))); | |
| 93 | } | |
| 94 | ||
| 95 | test("a streamed answer becomes Anthropic's stream, text then a tool call", () => { | |
| 96 | const translator = new StreamTranslator("gpt-5"); | |
| 97 | const chunks = [ | |
| 98 | { id: "c1", choices: [{ delta: { role: "assistant", content: "On it" } }] }, | |
| 99 | { id: "c1", choices: [{ delta: { content: "." } }] }, | |
| 100 | { id: "c1", choices: [{ delta: { tool_calls: [{ index: 0, id: "call_9", function: { name: "Bash", arguments: '{"comm' } }] } }] }, | |
| 101 | { id: "c1", choices: [{ delta: { tool_calls: [{ index: 0, function: { arguments: 'and":"ls"}' } }] } }] }, | |
| 102 | { id: "c1", choices: [{ delta: {}, finish_reason: "tool_calls" }] }, | |
| 103 | { id: "c1", choices: [], usage: { prompt_tokens: 12, completion_tokens: 7 } }, | |
| 104 | ]; | |
| 105 | // Delivered in awkward pieces, as networks do. | |
| 106 | const raw = chunks.map((c) => `data: ${JSON.stringify(c)}\n\n`).join("") + "data: [DONE]\n\n"; | |
| 107 | let out = ""; | |
| 108 | for (let at = 0; at < raw.length; at += 17) out += translator.push(raw.slice(at, at + 17)); | |
| 109 | out += translator.finish(); | |
| 110 | const seen = events(out); | |
| 111 | assert.deepEqual( | |
| 112 | seen.map((e) => e.type), | |
| 113 | [ | |
| 114 | "message_start", | |
| 115 | "content_block_start", | |
| 116 | "content_block_delta", | |
| 117 | "content_block_delta", | |
| 118 | "content_block_stop", | |
| 119 | "content_block_start", | |
| 120 | "content_block_delta", | |
| 121 | "content_block_delta", | |
| 122 | "content_block_stop", | |
| 123 | "message_delta", | |
| 124 | "message_stop", | |
| 125 | ], | |
| 126 | ); | |
| 127 | assert.deepEqual(seen[5].content_block, { type: "tool_use", id: "call_9", name: "Bash", input: {} }); | |
| 128 | const json = seen | |
| 129 | .filter((e) => (e.delta as { type?: string } | undefined)?.type === "input_json_delta") | |
| 130 | .map((e) => (e.delta as { partial_json: string }).partial_json) | |
| 131 | .join(""); | |
| 132 | assert.deepEqual(JSON.parse(json), { command: "ls" }); | |
| 133 | assert.deepEqual(seen[9].delta, { stop_reason: "tool_use", stop_sequence: null }); | |
| 134 | assert.deepEqual(seen[9].usage, { input_tokens: 12, output_tokens: 7 }); | |
| 135 | }); | |
| 136 | ||
| 137 | test("a provider's error keeps its status and says what it said", () => { | |
| 138 | const error = errorFromChat(429, JSON.stringify({ error: { message: "Rate limit reached" } })); | |
| 139 | assert.deepEqual(error, { type: "error", error: { type: "rate_limit_error", message: "The provider said: Rate limit reached" } }); | |
| 140 | }); | |
| A catalogue of model providers, and settings that feel like settings | 141 | |
| 142 | test("each provider's quirks are met", () => { | |
| 143 | const ask = { messages: [{ role: "user" as const, content: "hi" }], max_tokens: 32000, stream: true, tool_choice: { type: "any" as const }, tools: [{ name: "Bash", input_schema: { type: "object" } }] }; | |
| 144 | const deepseek = toChat(ask, "deepseek-chat", { official: false, provider: "deepseek" }); | |
| 145 | assert.equal(deepseek.max_tokens, 8192); | |
| 146 | assert.equal(deepseek.tool_choice, "required"); | |
| 147 | const mistral = toChat(ask, "mistral-large-latest", { official: false, provider: "mistral" }); | |
| 148 | assert.equal(mistral.tool_choice, "any"); | |
| 149 | assert.equal(mistral.stream_options, undefined); | |
| 150 | }); | |
| 151 | ||
| 152 | test("what a provider attaches to a tool call comes back with it", () => { | |
| 153 | const signature = { google: { thought_signature: "c2lnbmF0dXJl+/==" } }; | |
| 154 | const id = carryId("call_1", signature); | |
| 155 | assert.match(id, /^call_1__g1t_[A-Za-z0-9_-]+$/); | |
| 156 | assert.deepEqual(uncarryId(id), { id: "call_1", extra: signature }); | |
| 157 | assert.deepEqual(uncarryId("toolu_plain"), { id: "toolu_plain", extra: undefined }); | |
| 158 | ||
| 159 | const body = toChat( | |
| 160 | { | |
| 161 | messages: [ | |
| 162 | { role: "user", content: "go" }, | |
| 163 | { role: "assistant", content: [{ type: "tool_use", id, name: "Bash", input: {} }] }, | |
| 164 | { role: "user", content: [{ type: "tool_result", tool_use_id: id, content: "ok" }] }, | |
| 165 | ], | |
| 166 | }, | |
| 167 | "gemini-3-pro", | |
| 168 | { official: false, provider: "gemini" }, | |
| 169 | ); | |
| 170 | const messages = body.messages as Record<string, unknown>[]; | |
| 171 | assert.deepEqual((messages[1].tool_calls as Record<string, unknown>[])[0].extra_content, signature); | |
| 172 | assert.equal((messages[1].tool_calls as Record<string, unknown>[])[0].id, "call_1"); | |
| 173 | assert.equal(messages[2].tool_call_id, "call_1"); | |
| 174 | }); |