ابتدا نتیجه را بگویم: لگ در رندر کردن کلمهبهکلمه در فرانتاند، در نود درصد موارد مشکل شبکه نیست، بلکه لایه گیتوی مدل استراتژی یکسانسازی پروتکل SSE را انجام نداده و استراتژی تکهبندی استریم مدلهای بزرگ مختلف مستقیماً به مرورگر منتقل میشود. این مشکل را در یک پروژه پاسخگویی هوشمند تجربه کردیم و سه روز کامل آن را بررسی کردیم.
به زبان ساده، SSE (Server-Sent Events) مکانیزمی است که سرور همزمان با تولید، داده را به سمت کلاینت هدایت میکند. دادههای استریم بازگشتی از API مدلهای بزرگ در اصل رشتهای از رویدادهای SSE هستند. مشکل اینجاست که تعریف هر ارائهدهنده از «چه زمانی هدایت کند و چه اندازهای هدایت کند» کاملاً متفاوت است. API مدل GPT-4o تمایل دارد به صورت دستهای بر اساس Token هدایت کند و هر بار چند Token بیرون بدهد؛ API مدل Claude قبل از اولین Token یک دوره سکوت دارد که در موارد طولانی به دو تا سه ثانیه میرسد؛ دانهبندی تکهبندی API مدل Qwen و API مدل DeepSeek نیز هر کدام متفاوت است. اگر فرانتاند مستقیماً این فرمتهای خام را مصرف کند، ریتم رندر طبیعتاً کند و تند میشود.
گام اول عیبیابی: ابتدا لایه شبکه را حذف کنید
در ابتدا شک داشتیم لرزش لینک باشد، دو روز تأخیر رفت و برگشت TCP و نرخ از دست رفتن بسته را ثبت کردیم، دادهها بسیار تمیز بودند. با curl مستقیماً به یکی از مدلها متصل شدیم و برچسب زمانی پاسخ را چاپ کردیم، متوجه شدیم در همان بخش پاسخ، فاصله سه رویداد اول 800 میلیثانیه است و بعد ناگهان به هر 20 میلیثانیه یک رویداد متراکم میشود. این با شبکه قابل توضیح نیست، خود استراتژی هدایت سمت سرور ناهموار است.
گام دوم عیبیابی: تفاوت استراتژی تکهبندی SSE را مکانیابی کنید
استریم خام پنج مدل را گرفتیم و مقایسه کردیم، تفاوتها بسیار واضح بودند. مدلی که بر اساس کاراکتر هدایت میکند، یک کاراکتر چینی یک رویداد، تعداد رویدادها منفجر میشود؛ مدلی که بر اساس Token به صورت دستهای هدایت میکند، هر بار چهار پنج Token جمع میکند و بعد میفرستد؛و همچنین برخی مدلها قبل از اولین Token دوره سکوت طولانی دارند، فرانتاند هیچ دادهای دریافت نمیکند، کاربر مکاننما را بیحرکت میبیند و فکر میکند قفل شده. سه استراتژی مخلوط در یک سیستم پاسخگویی هوشمند، فرانتاند اصلاً نمیتواند با ریتم یکسان رندر کند.
گام سوم عیبیابی: لایه گیتوی ترجمه پروتکل را کم داشت
ریشه اینجاست. گیتوی مدل ما در آن زمان فقط ارسال درخواست و مدیریت API Key را انجام میداد و یکسانسازی پروتکل سمت پاسخ را انجام نمیداد، فرمت خام SSE هر مدل مستقیماً به فرانتاند میرفت. این مثل این است که پنج نفر با گویشهای مختلف همزمان به شما گزارش دهند، اگر ترجمه نکنید، شنونده طبیعتاً گیج میشود.
بعداً به پلتفرم تجمیع API مدلهای بزرگ token8341 به عنوان خروجی یکپارچه متصل شدیم، رابط سازگار با OpenAI آن در یکسانسازی پروتکل سه کار انجام داده که ارزش بسط دادن دارد.
اول، یکسانسازی فرمت رویداد SSE. مهم نیست در زیرساخت کدام مدل فراخوانی میشود، خروجی همیشه فرمت استاندارد OpenAI است: data: {...} به همراه پایان data: [DONE]. فرانتاند فقط یک پروتکل را میشناسد و نیازی نیست برای هر مدل یک منطق تجزیه بنویسد. ارزش اتصال یکپارچه چندمدلی، بیشترش اینجا نمایان میشود.
دوم، پشتیبانی اجباری در تایماوت اولین Token. سمت گیتوی آستانه انتظار اولین Token تعیین کرده، اگر از آستانه بگذرد ابتدا یک رویداد ضربان قلب هدایت میکند تا از خالی ماندن طولانی فرانتاند جلوگیری شود. این اقدام کوچک است، اما در سناریوی پاسخگویی هوشمند تفاوت درک کاربر بسیار زیاد است.
سوم، استراتژی بافر تکهبندی. برای مدلهایی که بر اساس کاراکتر هدایت میکنند دستهبندی و برای مدلهایی که دستهای هدایت میکنند شکستن فریم انجام میشود تا فاصله رویدادها تا حد امکان به یک بازه پایدار صاف شود. در آزمون واقعی، ریتم رندر کلمهبهکلمه فرانتاند به وضوح یکنواختتر شد و دیگر حالت تکهتکه پیش نمیآید.
اینجا یک مقایسه داده اضافه کنم: قبل از بازسازی، فرانتاند برای مصرف استریم خام پنج مدل باید پنج شاخه تجزیه SSE نگه میداشت، حجم کد حدود 400 خط بود. بعد از بازسازی با رابط سازگار با OpenAI پلتفرم تجمیع API مدلهای بزرگ token8341، شاخههای تجزیه به یک مجموعه کاهش یافت و کد به حدود 80 خط رسید. هزینه نگهداری حدود هشتاد درصد کاهش یافت.
هشدار برای جلوگیری از اشتباه: در لایه گیتوی فقط ارسال انجام ندهید و پردازش سمت پاسخ را نادیده نگیرید. بسیاری از تیمها فکر میکنند با تغییر base_url کار تمام است، در نتیجه همه مشکلات تجربه استریم در فرانتاند باقی میماند. یکسانسازی پروتکل باید در گیتوی انجام شود، نمیتوان به پشتیبانی سمت کلاینت امیدوار بود.
برگردیم به همان سیستم پاسخگویی هوشمند ابتدای بحث، پس از حل مشکل یک دور دیگر تست فشار انجام دادیم. پلتفرم تجمیع API مدلهای بزرگ token8341 از یک Key برای فراخوانی مدلهای اصلی مانند GPT-4o، Claude، Gemini، DeepSeek، Qwen، ERNIE، Doubao و غیره پشتیبانی میکند، هنگام تعویض مدل کد فرانتاند بدون تغییر است، این برای تیمهایی که نیاز به مسیریابی مدل و تست A/B دارند نسبتاً راحت است. در مدل پرداخت به میزان مصرف، صورتحسابها را مقایسه کردیم، هزینه کمی کمتر از اتصال مستقیم به هر ارائهدهنده است.
اگر شما هم در حال ساخت تجمیع API هوش مصنوعی یا گیتوی مدل اختصاصی هستید، پیشنهاد میکنم یکسانسازی SSE را به عنوان اولویت اول طراحی در نظر بگیرید، نه اینکه صبر کنید تا فرانتاند لگ بزند و بعد برگردید و جبران کنید.
نویسنده: ژائو چیمینگ
تاریخ انتشار: 29 اکتبر 2026