UNPKG

@inductiv/node-red-openai-api

Version:

Enhance your Node-RED projects with advanced AI capabilities.

193 lines (172 loc) 5.37 kB
"use strict"; // This file keeps the newer gpt-5.4 mini/nano slug contract honest. // It proves the node forwards the new v6.32.0 model ids unchanged and keeps the example payload importable. const assert = require("node:assert/strict"); const fs = require("node:fs"); const path = require("node:path"); const test = require("node:test"); function withMockedOpenAI(FakeOpenAI, callback) { const openaiModule = require("openai"); const originalDescriptor = Object.getOwnPropertyDescriptor(openaiModule, "OpenAI"); Object.defineProperty(openaiModule, "OpenAI", { value: FakeOpenAI, configurable: true, enumerable: true, writable: true, }); const run = async () => { try { return await callback(); } finally { if (originalDescriptor) { Object.defineProperty(openaiModule, "OpenAI", originalDescriptor); } } }; return run(); } const responsesWebsocketExample = JSON.parse( fs.readFileSync( path.join(__dirname, "..", "examples", "responses", "websocket.json"), "utf8" ) ); test("responses and chat methods forward gpt-5.4 mini/nano slugs unchanged", async () => { const calls = []; const models = [ "gpt-5.4-mini", "gpt-5.4-nano", "gpt-5.4-mini-2026-03-17", "gpt-5.4-nano-2026-03-17", ]; class FakeOpenAI { constructor(clientParams) { calls.push({ method: "ctor", clientParams }); this.responses = { create: async (payload) => { calls.push({ method: "responses.create", payload }); return { id: `resp_${payload.model}` }; }, }; this.chat = { completions: { create: async (payload) => { calls.push({ method: "chat.completions.create", payload }); return { id: `chat_${payload.model}` }; }, }, }; } } await withMockedOpenAI(FakeOpenAI, async () => { const responsesModulePath = require.resolve("../src/responses/methods.js"); const chatModulePath = require.resolve("../src/chat/methods.js"); delete require.cache[responsesModulePath]; delete require.cache[chatModulePath]; const responsesMethods = require("../src/responses/methods.js"); const chatMethods = require("../src/chat/methods.js"); const clientContext = { clientParams: { apiKey: "sk-test", baseURL: "https://api.example.com/v1", }, }; for (const model of models) { const response = await responsesMethods.createModelResponse.call(clientContext, { payload: { model, input: "Summarize the rollout status in one sentence.", }, }); assert.deepEqual(response, { id: `resp_${model}` }); } for (const model of models) { const response = await chatMethods.createChatCompletion.call(clientContext, { payload: { model, messages: [{ role: "user", content: "Say hello." }], }, }); assert.deepEqual(response, { id: `chat_${model}` }); } delete require.cache[responsesModulePath]; delete require.cache[chatModulePath]; }); assert.deepEqual( calls.filter((entry) => entry.method !== "ctor"), [ { method: "responses.create", payload: { model: "gpt-5.4-mini", input: "Summarize the rollout status in one sentence.", }, }, { method: "responses.create", payload: { model: "gpt-5.4-nano", input: "Summarize the rollout status in one sentence.", }, }, { method: "responses.create", payload: { model: "gpt-5.4-mini-2026-03-17", input: "Summarize the rollout status in one sentence.", }, }, { method: "responses.create", payload: { model: "gpt-5.4-nano-2026-03-17", input: "Summarize the rollout status in one sentence.", }, }, { method: "chat.completions.create", payload: { model: "gpt-5.4-mini", messages: [{ role: "user", content: "Say hello." }], }, }, { method: "chat.completions.create", payload: { model: "gpt-5.4-nano", messages: [{ role: "user", content: "Say hello." }], }, }, { method: "chat.completions.create", payload: { model: "gpt-5.4-mini-2026-03-17", messages: [{ role: "user", content: "Say hello." }], }, }, { method: "chat.completions.create", payload: { model: "gpt-5.4-nano-2026-03-17", messages: [{ role: "user", content: "Say hello." }], }, }, ] ); }); test("Responses websocket example keeps the current model payload importable", () => { const websocketInjectNode = responsesWebsocketExample.find( (node) => node.name === "Send response.create Event" ); assert.ok(websocketInjectNode); const websocketEventProperty = websocketInjectNode.props.find( (prop) => prop.p === "ai.event" ); assert.ok(websocketEventProperty); const websocketEvent = JSON.parse(websocketEventProperty.v); assert.deepEqual(websocketEvent, { type: "response.create", model: "gpt-5.4-nano-2026-03-17", input: "Say hello from Responses websocket mode in one sentence.", }); });