@thanh01.pmt/curriculum-kit 1.4.32 → 1.4.34

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/ai/index.cjs CHANGED
@@ -933,6 +933,52 @@ async function runCurriculumAIInference(messages, projectContext, options = {},
933
933
  }
934
934
 
935
935
  // src/ai/provider-factory.ts
936
+ function cleanNonStreamingFetch() {
937
+ return async (input, init) => {
938
+ const res = await fetch(input, init);
939
+ let wantsStream = false;
940
+ try {
941
+ const body = init?.body;
942
+ if (typeof body === "string") wantsStream = /"stream"\s*:\s*true/.test(body);
943
+ } catch {
944
+ }
945
+ if (wantsStream) return res;
946
+ const contentType = res.headers.get("content-type") || "";
947
+ if (!contentType.includes("text/event-stream") && !contentType.includes("application/json")) return res;
948
+ const text = await res.text();
949
+ const trimmed = text.trim();
950
+ if (trimmed.startsWith("data:")) {
951
+ let content = "";
952
+ let lastChunk = null;
953
+ for (const line of trimmed.split("\n")) {
954
+ const l = line.trim();
955
+ if (!l || !l.startsWith("data:")) continue;
956
+ const jsonStr = l.slice(5).trim();
957
+ if (jsonStr === "[DONE]") continue;
958
+ try {
959
+ const chunk = JSON.parse(jsonStr);
960
+ lastChunk = chunk;
961
+ content += chunk.choices?.[0]?.delta?.content || "";
962
+ } catch {
963
+ }
964
+ }
965
+ const assembled = {
966
+ id: lastChunk?.id || "chatcmpl-" + Date.now(),
967
+ object: "chat.completion",
968
+ created: lastChunk?.created || Math.floor(Date.now() / 1e3),
969
+ model: lastChunk?.model || "9router",
970
+ choices: [{ index: 0, message: { role: "assistant", content }, finish_reason: "stop" }],
971
+ usage: lastChunk?.usage || void 0
972
+ };
973
+ const headers = new Headers(res.headers);
974
+ headers.set("content-type", "application/json");
975
+ return new Response(JSON.stringify(assembled), { status: res.status, statusText: res.statusText, headers });
976
+ }
977
+ const doneIndex = text.indexOf("data: [DONE]");
978
+ if (doneIndex === -1) return res;
979
+ return new Response(text.slice(0, doneIndex).trim(), { status: res.status, statusText: res.statusText, headers: res.headers });
980
+ };
981
+ }
936
982
  var DEFAULT_MODELS = {
937
983
  "9router": "fast-reasoning",
938
984
  ninerouter: "fast-reasoning",
@@ -972,7 +1018,8 @@ function getAIModel(options = {}) {
972
1018
  const rawUrl = options.baseURL || resolveApiKey("NINEROUTER_BASE_URL") || resolveApiKey("NINE_ROUTER_BASE_URL") || "https://ai-router.orchable.app/v1";
973
1019
  const ninerouter = openai.createOpenAI({
974
1020
  apiKey,
975
- baseURL: rawUrl.replace(/^["']|["']$/g, "").trim()
1021
+ baseURL: rawUrl.replace(/^["']|["']$/g, "").trim(),
1022
+ fetch: cleanNonStreamingFetch()
976
1023
  });
977
1024
  return ninerouter.chat(resolvedModelName || "fast-reasoning");
978
1025
  }