По сути, я создаю потоковую передачу нескольких сообщений на простом JS (без фреймворков), где мне нужно передавать несколько ответов OpenAI один за другим. на локальном хосте выглядит нормально, но в рабочей среде (узел 18), когда два потока перекрываются даже на несколько мс, все это начинает смешивать фрагменты между потоками, как будто они используют один и тот же модуль чтения или что-то в этом роде. такое ощущение, что какой-то асинхронный итератор теряет состояние?? не знаю
Я использую официальный SDK узла openai (новый) и функцию .response.body.getReader(). иногда фрагменты приходят дублированными, иногда не по порядку, иногда фрагмент из потока A буквально появляется внутри потока B. Непонятно, почему. нет общих переменных, нет глобального состояния, ничего.
Я предполагаю, что что-то в читателе или полифиле WebStream внутри узла не работает, когда вы запускаете несколько одновременных чтений? или может я что-то не так делаю с циклом. но это происходит только на prod-сервере при реальном трафике, что усложняет отладку.
есть идеи, каков «правильный» способ обработки 2–3 параллельных потоковых завершений без утечки фрагментов? есть ли известная проблема с SDK или потоками узлов?
вот урезанная версия кода, которая по-прежнему случайным образом ломается:
Код: Выделить всё
import OpenAI from "openai";
const client = new OpenAI({ apiKey: process.env.OPENAI_KEY });
async function runStream(prompt) {
const res = await client.chat.completions.create({
model: "gpt-4.1",
messages: [{ role: "user", content: prompt }],
stream: true,
});
const reader = res.response.body.getReader();
let buffer = "";
while (true) {
const { done, value } = await reader.read();
if (done) break;
const chunk = new TextDecoder().decode(value);
// this is where random corruption happens:
// sometimes chunk contains leftover bytes from another stream??
buffer += chunk;
}
return buffer;
}
// simulate parallel calls
Promise.all([
runStream("msg A"),
runStream("msg B"),
runStream("msg C"),
]).then(console.log);
Подробнее здесь: https://stackoverflow.com/questions/798 ... across-res
Мобильная версия