mirror of
https://github.com/anomalyco/opencode.git
synced 2026-10-26 20:49:57 +00:00
fix(ai): map unknown OpenAI Chat finish reasons to unknown (#58608)
This commit is contained in:
parent
7d59b05429
commit
dbd99a940b
3 changed files with 7 additions and 53 deletions
|
|
@ -858,12 +858,7 @@ const mapFinishReason = Effect.fnUntraced(function* (event: OpenAIChatEvent, rea
|
|||
case "tool_calls":
|
||||
return "tool-calls" as const
|
||||
default:
|
||||
return yield* new AIError({
|
||||
reason: new UnknownProviderError({
|
||||
message: `Provider finish_reason: ${reason}`,
|
||||
body: ProviderShared.encodeJson(event),
|
||||
}),
|
||||
})
|
||||
return "unknown" as const
|
||||
}
|
||||
})
|
||||
|
||||
|
|
|
|||
|
|
@ -2072,47 +2072,14 @@ describe("OpenAI Chat route", () => {
|
|||
}),
|
||||
)
|
||||
|
||||
it.effect("rejects unknown finish reasons without finalizing streamed tool calls", () =>
|
||||
it.effect("maps unknown finish reasons to unknown and keeps the raw value", () =>
|
||||
Effect.gen(function* () {
|
||||
const body = sseEvents(
|
||||
deltaChunk({
|
||||
tool_calls: [{ index: 0, id: "call_1", function: { name: "lookup", arguments: '{"query":"weather"' } }],
|
||||
}),
|
||||
deltaChunk({}, "future_reason"),
|
||||
)
|
||||
const events = yield* Ref.make<ReadonlyArray<LLMEvent>>([])
|
||||
const error = yield* LLMClient.stream(
|
||||
LLMRequest.update(request, {
|
||||
tools: [ToolDefinition.make({ name: "lookup", description: "Lookup data", inputSchema: { type: "object" } })],
|
||||
}),
|
||||
).pipe(
|
||||
Stream.tap((event) => Ref.update(events, (current) => [...current, event])),
|
||||
Stream.runDrain,
|
||||
Effect.provide(fixedResponse(body)),
|
||||
Effect.flip,
|
||||
const response = yield* LLMClient.generate(request).pipe(
|
||||
Effect.provide(fixedResponse(sseEvents(deltaChunk({ content: "Hello" }), deltaChunk({}, "future_reason")))),
|
||||
)
|
||||
|
||||
expect(error).toMatchObject({
|
||||
reason: { _tag: "UnknownProvider" },
|
||||
message: "Provider finish_reason: future_reason",
|
||||
})
|
||||
expect(yield* Ref.get(events)).toEqual([
|
||||
{ type: "step-start", index: 0 },
|
||||
{
|
||||
type: "tool-input-start",
|
||||
id: "call_1",
|
||||
name: "lookup",
|
||||
providerExecuted: undefined,
|
||||
providerMetadata: undefined,
|
||||
},
|
||||
{
|
||||
type: "tool-input-delta",
|
||||
id: "call_1",
|
||||
name: "lookup",
|
||||
text: '{"query":"weather"',
|
||||
input: { query: "weather" },
|
||||
},
|
||||
])
|
||||
expect(response.text).toBe("Hello")
|
||||
expect(response.finishReason).toEqual({ normalized: "unknown", raw: "future_reason" })
|
||||
}),
|
||||
)
|
||||
|
||||
|
|
|
|||
|
|
@ -572,16 +572,8 @@ describe("OpenAI-compatible Chat route", () => {
|
|||
|
||||
const unknown = yield* LLMClient.generate(request).pipe(
|
||||
Effect.provide(fixedResponse(sseEvents(deltaChunk({}, "future_reason")))),
|
||||
Effect.flip,
|
||||
)
|
||||
expect(unknown).toMatchObject({
|
||||
reason: { _tag: "UnknownProvider" },
|
||||
message: "Provider finish_reason: future_reason",
|
||||
})
|
||||
expect(decodeJson(unknown.reason.body ?? "")).toMatchObject({
|
||||
id: "chatcmpl_fixture",
|
||||
choices: [{ finish_reason: "future_reason" }],
|
||||
})
|
||||
expect(unknown.finishReason).toEqual({ normalized: "unknown", raw: "future_reason" })
|
||||
}),
|
||||
)
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue