126 lines
4.4 KiB
TypeScript
126 lines
4.4 KiB
TypeScript
import { afterEach, describe, expect, it, vi } from "vitest";
|
|
import { OpenAIResponsesClient } from "../src/services/openaiResponsesClient";
|
|
|
|
describe("openai local responses fallback", () => {
|
|
const originalFetch = global.fetch;
|
|
|
|
afterEach(() => {
|
|
vi.restoreAllMocks();
|
|
global.fetch = originalFetch;
|
|
});
|
|
|
|
it("falls back to /chat/completions when /responses payload is parseable JSON but has no output_text", async () => {
|
|
const fetchMock = vi
|
|
.fn()
|
|
.mockResolvedValueOnce(
|
|
new Response(JSON.stringify({ id: "resp-1", output: [], usage: { prompt_tokens: 4, completion_tokens: 3 } }), {
|
|
status: 200,
|
|
headers: { "content-type": "application/json" }
|
|
})
|
|
)
|
|
.mockResolvedValueOnce(
|
|
new Response(
|
|
JSON.stringify({
|
|
id: "chat-1",
|
|
choices: [{ message: { content: "{\"schema_version\":\"normalized_query_v2_0_2\"}" } }],
|
|
usage: { prompt_tokens: 7, completion_tokens: 5, total_tokens: 12 }
|
|
}),
|
|
{
|
|
status: 200,
|
|
headers: { "content-type": "application/json" }
|
|
}
|
|
)
|
|
);
|
|
|
|
global.fetch = fetchMock as unknown as typeof fetch;
|
|
|
|
const client = new OpenAIResponsesClient();
|
|
const response = await client.normalize(
|
|
{
|
|
llmProvider: "local",
|
|
apiKey: "",
|
|
model: "qwen2.5-14b-instruct-1m",
|
|
baseUrl: "http://127.0.0.1:1234",
|
|
temperature: 0
|
|
},
|
|
{
|
|
systemPrompt: "system",
|
|
developerPrompt: "developer",
|
|
domainPrompt: "domain",
|
|
userQuestion: "question",
|
|
schemaVersion: "v2_0_2"
|
|
}
|
|
);
|
|
|
|
expect(response.outputText).toContain("\"schema_version\":\"normalized_query_v2_0_2\"");
|
|
expect(response.usage.total_tokens).toBe(12);
|
|
expect(fetchMock).toHaveBeenCalledTimes(2);
|
|
expect(String(fetchMock.mock.calls[0]?.[0] ?? "")).toContain("/responses");
|
|
expect(String(fetchMock.mock.calls[1]?.[0] ?? "")).toContain("/chat/completions");
|
|
});
|
|
|
|
it("retries alternative local base when endpoint mismatch payload is returned for chat completions", async () => {
|
|
const fetchMock = vi
|
|
.fn()
|
|
.mockResolvedValueOnce(
|
|
new Response(JSON.stringify({ error: { message: "Unexpected endpoint or method. (POST /responses)" } }), {
|
|
status: 404,
|
|
headers: { "content-type": "application/json" }
|
|
})
|
|
)
|
|
.mockResolvedValueOnce(
|
|
new Response(JSON.stringify({ error: { message: "Unexpected endpoint or method. (POST /responses)" } }), {
|
|
status: 404,
|
|
headers: { "content-type": "application/json" }
|
|
})
|
|
)
|
|
.mockResolvedValueOnce(
|
|
new Response(JSON.stringify({ error: "Unexpected endpoint or method. (POST /chat/completions)" }), {
|
|
status: 200,
|
|
headers: { "content-type": "application/json" }
|
|
})
|
|
)
|
|
.mockResolvedValueOnce(
|
|
new Response(
|
|
JSON.stringify({
|
|
id: "chat-v1",
|
|
choices: [{ message: { content: "{\"schema_version\":\"normalized_query_v2_0_2\"}" } }],
|
|
usage: { prompt_tokens: 10, completion_tokens: 7, total_tokens: 17 }
|
|
}),
|
|
{
|
|
status: 200,
|
|
headers: { "content-type": "application/json" }
|
|
}
|
|
)
|
|
);
|
|
|
|
global.fetch = fetchMock as unknown as typeof fetch;
|
|
|
|
const client = new OpenAIResponsesClient();
|
|
const response = await client.normalize(
|
|
{
|
|
llmProvider: "local",
|
|
apiKey: "",
|
|
model: "qwen2.5-14b-instruct-1m",
|
|
baseUrl: "http://127.0.0.1:1234",
|
|
temperature: 0
|
|
},
|
|
{
|
|
systemPrompt: "system",
|
|
developerPrompt: "developer",
|
|
domainPrompt: "domain",
|
|
userQuestion: "question",
|
|
schemaVersion: "v2_0_2"
|
|
}
|
|
);
|
|
|
|
expect(response.outputText).toContain("\"schema_version\":\"normalized_query_v2_0_2\"");
|
|
expect(response.usage.total_tokens).toBe(17);
|
|
expect(fetchMock).toHaveBeenCalledTimes(4);
|
|
expect(String(fetchMock.mock.calls[0]?.[0] ?? "")).toBe("http://127.0.0.1:1234/responses");
|
|
expect(String(fetchMock.mock.calls[1]?.[0] ?? "")).toBe("http://127.0.0.1:1234/v1/responses");
|
|
expect(String(fetchMock.mock.calls[2]?.[0] ?? "")).toBe("http://127.0.0.1:1234/chat/completions");
|
|
expect(String(fetchMock.mock.calls[3]?.[0] ?? "")).toBe("http://127.0.0.1:1234/v1/chat/completions");
|
|
});
|
|
});
|