大模型对话前端第一版:先跑通流式响应和取消
大模型对话前端第一版先跑通流式响应和取消第一版大模型对话界面先验证一条主链路接收流式响应、正确解码、可取消地渲染并在异常时给出可恢复的提示。本文以流式 Markdown 的前端实现为例讨论这条链路的最小边界。fetch与TextDecoder足以搭起原型但还要处理不完整的 UTF-8 字节、被截断的事件以及高频更新带来的重复渲染。状态机、Worker 等机制应由测得的瓶颈决定而不是一开始全部引入。MVP 核心链路拆解在第一版交付中前端最核心的链路只有一条接收服务端 Server-Sent Events (SSE) 字节流逐块解码后通过平滑打字机队列推入状态同时控制 Markdown DOM 树的渲染频率。flowchart TD A[SSEResponse 字节流] -- B(ReadableStream DefaultReader) B -- C{TextDecoder Chunk 解码} C -- D[打字机缓冲区队列 Queue] D -- E{requestAnimationFrame 调度器} E -- F[更新 React/Vue State] F -- G[DOM 增量渲染与自动滚动] G -- H{用户触发 AbortController?} H -- 是 -- I[CancelToken 中断底层 HTTP 链接] H -- 否 -- J[流传输结束释放 Worker/Timer]整个链路涉及三个主要瓶颈点网络层EventSourceAPI 不支持 POST 请求与自定义 Header必须改用原生fetch结合ReadableStream。缓冲层后端返回的 Chunk 尺寸不均单次推送可能包含半个 UTF-8 字符或 incomplete JSON直接赋值给 UI 会导致乱码闪烁。渲染层高频setState触发 React Re-render导致 CPU 占用率飙升至 100%。关键代码取舍与实现为了在最小代码量下解决高频渲染卡顿第一版不需要引入复杂的 Web Worker而是采用基于requestAnimationFrame的缓冲队列Buffer Queue。// sse_client.ts export interface SSEOptions { url: string; headers: Recordstring, string; body: object; onChunk: (text: string) void; onError: (err: Error) void; signal?: AbortSignal; } export async function fetchSSEResponse(options: SSEOptions): Promisevoid { const { url, headers, body, onChunk, onError, signal } options; try { const response await fetch(url, { method: POST, headers: { Content-Type: application/json, ...headers, }, body: JSON.stringify(body), signal, }); if (!response.ok || !response.body) { throw new Error(HTTP 异常: ${response.status} ${response.statusText}); } const reader response.body.getReader(); const decoder new TextDecoder(utf-8); let buffer ; while (true) { const { done, value } await reader.read(); if (done) break; buffer decoder.decode(value, { stream: true }); const lines buffer.split(\n); // 保留未完成的最后一行 buffer lines.pop() || ; for (const line of lines) { const trimmed line.trim(); if (!trimmed || trimmed.startsWith(:)) continue; if (trimmed data: [DONE]) return; if (trimmed.startsWith(data: )) { try { const parsed JSON.parse(trimmed.slice(6)); const delta parsed.choices?.[0]?.delta?.content || ; if (delta) onChunk(delta); } catch (e) { // 避免单个解析失败阻断后续流处理 console.warn(Chunk 解析不完整:, trimmed); } } } } } catch (err: any) { if (err.name AbortError) { console.log(请求已被用户主动中断); } else { onError(err); } } }在 UI 层直接将onChunk的回调关联到组件 State 是灾难性的。按照 50ms 一次 Chunk 的频率一秒钟触发 20 次组件树重绘。我们可以通过平滑渲染器截断频率。// useSmoothStream.ts import { useState, useRef, useEffect } from react; export function useSmoothStream() { const [displayText, setDisplayText] useState(); const queueRef useRefstring[]([]); const frameRef useRefnumber | null(null); const pushChunk (chunk: string) { queueRef.current.push(...chunk.split()); if (!frameRef.current) { scheduleFlush(); } }; const scheduleFlush () { frameRef.current requestAnimationFrame(() { if (queueRef.current.length 0) { // 每次渲染取出最多 3 个字符保持流畅打字感 const batch queueRef.current.splice(0, 3).join(); setDisplayText((prev) prev batch); scheduleFlush(); } else { frameRef.current null; } }); }; const reset () { if (frameRef.current) cancelAnimationFrame(frameRef.current); frameRef.current null; queueRef.current []; setDisplayText(); }; return { displayText, pushChunk, reset }; }第一版中果断放弃的技术点离线 VectorDB 本地检索完全在服务端处理前端只负责呈现。自定义 Markdown AST 增量解析引擎直接选用轻量marked或markdown-it加防抖不写自定义 Parser。复杂的多会话并行 WorkerMVP 阶段单次窗口仅支持单条活跃 Request。现场诊断与优化验证线上验证时不能凭感觉判断“卡不卡”。用 Chrome DevTools 的 Performance 面板录制流式输出过程中的 CPU Profile 才是标准动作。打开 Chrome DevTools切到Performance标签页点击 Record开始一次 1000 字的大模型文本生成录制 15 秒后停止。在没有优化前Profile 显示大量的Recalculate Style和Layout频次高达 45 次/秒Task列表中长任务Long Task 50ms占比超过 35%。使用requestAnimationFrame批处理后Layout频次降至 16 次/秒以内。JS 执行线程的火焰图中setDisplayText导致的重绘耗时从 320ms 降至 42ms。内存占用在整个流式传输期间稳定在 38MB 左右没有任何内存泄漏曲线。做 MVP 的核心思维是给网络层加终止器AbortController给渲染层加缓冲闸门rAF给异常加降级保护。三者具备第一版就立住了。

相关新闻

PostgreSQL动态分区裁剪技术:查询性能优化解析

PostgreSQL动态分区裁剪技术:查询性能优化解析

摘要在海量时序数据、业务流水日志、订单交易记录等大表业务场景中,PostgreSQL分区表是解决单表数据量过大、查询延迟攀升、运维成本过高的核心方案。分区裁剪作为分区表查询的核心优化技术,可精准过滤无关分区、避免全分区扫描,大幅缩减IO开…

2026/8/11 15:32:49 阅读更多 →
UTS集群调度系统架构与数据库任务优化实践

UTS集群调度系统架构与数据库任务优化实践

1. UTS集群调度系统的架构演进 UTS(Unified Task Scheduler)作为新一代分布式任务调度平台,其核心架构经历了三次重大迭代。最新版本采用混合调度策略,将中心化调度与分布式调度有机结合,形成了独特的双层调度体系。 …

2026/8/11 15:32:49 阅读更多 →
Unity3D RPG开发实战:从Dungeon Breaker Starter Kit学习商业级游戏架构

Unity3D RPG开发实战:从Dungeon Breaker Starter Kit学习商业级游戏架构

1. 项目概述与核心价值如果你正在寻找一个能让你快速上手Unity3D RPG游戏开发,并且希望深入理解一个商业级项目是如何从零到一构建起来的,那么Dungeon Breaker Starter Kit(以下简称DBSK)绝对是一个不可多得的宝藏。这不仅仅是一套…

2026/8/11 15:31:49 阅读更多 →

最新新闻

土耳其跨境网络钓鱼治理困境与公众扫码防护体系构建研究

土耳其跨境网络钓鱼治理困境与公众扫码防护体系构建研究

摘要 移动数字支付、跨境线上服务普及推动土耳其境内二维码钓鱼(Quishing)案件逐年攀升,跨境黑产依托域名境外注册、短链接多层跳转、实体二维码篡改手段,突破单一国家网络安全监管边界,形成跨国流转的新型电信诈骗链条…

2026/8/11 16:18:06 阅读更多 →
天玑9300+与骁龙8s Gen3深度对比:性能释放四层模型与真实场景选择指南

天玑9300+与骁龙8s Gen3深度对比:性能释放四层模型与真实场景选择指南

去年这个时候,我还在为一个项目选型发愁。团队需要一批性能稳定、成本可控的测试机,用来跑自动化脚本和压力测试。当时市面上几款热门机型,参数表都写得天花乱坠,但真用起来,不是调度策略太激进导致发热降频&#xff0…

2026/8/11 16:18:06 阅读更多 →
UNC6671 语音 - AiTM 复合勒索攻击链路、产业化运营与企业全域防护研究

UNC6671 语音 - AiTM 复合勒索攻击链路、产业化运营与企业全域防护研究

摘要 2026 年谷歌威胁情报组 GTIG 披露威胁团伙 UNC6671 构建 “语音钓鱼社工诱导 AiTM 中间人凭证劫持 云 SaaS 批量数据窃取 多品牌数据泄露站勒索变现” 完整犯罪闭环,区别于单一网页钓鱼或勒索软件攻击,该团伙依托电话渠道突破企业办公网络边界管…

2026/8/11 16:18:06 阅读更多 →
9B模型与27B模型,能力差异体现在哪里?

9B模型与27B模型,能力差异体现在哪里?

9B和27B模型在网页分析和编程上的能力差异,核心体现在27B模型上限更高、思考更透彻,但代价是速度慢且对硬件要求极高。而9B模型则是在效率、稳定性和性价比上做到了极致平衡。 下面这张表格可以让你更直观地看到它们的核心差异: 对比维度Qw…

2026/8/11 16:18:06 阅读更多 →
2026 苹果录音转文字软件怎么选?多轮筛选后不踩雷只留这一款

2026 苹果录音转文字软件怎么选?多轮筛选后不踩雷只留这一款

2026年苹果生态下选择录音转文字软件,核心逻辑是匹配自身使用场景,而非盲目追求头部品牌。本次针对5款主流工具从产品功能到成本完成多轮筛选,不同需求对应不同适配选项,如果你需要转写AI整理一体化的工具,不需要绑定大…

2026/8/11 16:18:06 阅读更多 →
深度学习训练代码的基本执行流程

深度学习训练代码的基本执行流程

刚接触深度学习代码的同学,常被一堆 Dataset、DataLoader、optimizer.zero_grad()、loss.backward() 搞晕,觉得每个项目的训练脚本都长得不一样。其实拆开来看,绝大多数训练代码都是同一套骨架,换的只是数据、模型和损失函数。 把…

2026/8/11 16:17:06 阅读更多 →

日新闻

如何用Video2X实现专业级视频画质提升:AI视频增强完整指南

如何用Video2X实现专业级视频画质提升:AI视频增强完整指南

如何用Video2X实现专业级视频画质提升:AI视频增强完整指南 【免费下载链接】video2x A machine learning-based video super resolution and frame interpolation framework. Est. Hack the Valley II, 2018. 项目地址: https://gitcode.com/GitHub_Trending/vi/v…

2026/8/11 0:00:02 阅读更多 →
前后端分离项目中控制台与接口工具数据差异排查指南

前后端分离项目中控制台与接口工具数据差异排查指南

1. 问题现象解析:控制台与Apifox的数据差异 最近在调试一个前后端分离项目时,遇到了一个典型问题:后端服务在本地开发环境控制台能正常输出查询数据,但通过Apifox测试时却返回空结果。这种"控制台有数据,接口工具…

2026/8/11 0:00:03 阅读更多 →
AI编程实战:从Claude Code踩坑到游戏开发入门

AI编程实战:从Claude Code踩坑到游戏开发入门

1. 从“AI能帮我做游戏”到“AI让我重新学编程”最近身边不少朋友,尤其是一些非技术背景、但对游戏开发有浓厚兴趣的朋友,都在问我同一个问题:“听说现在用Claude Code这种AI编程工具,小白也能做游戏了,是真的吗&#…

2026/8/11 0:00:03 阅读更多 →

周新闻

5分钟告别提取码焦虑:baidupankey如何智能破解百度网盘资源锁

5分钟告别提取码焦虑:baidupankey如何智能破解百度网盘资源锁

5分钟告别提取码焦虑:baidupankey如何智能破解百度网盘资源锁 【免费下载链接】baidupankey 在线查询网盘提取码(维护中 rm repo) 项目地址: https://gitcode.com/gh_mirrors/ba/baidupankey 你是否曾经在深夜寻找一份重要资料&#x…

2026/8/11 1:08:05 阅读更多 →
如何快速生成中国车牌图片:Python开源工具完整指南

如何快速生成中国车牌图片:Python开源工具完整指南

如何快速生成中国车牌图片:Python开源工具完整指南 【免费下载链接】chinese_license_plate_generator 中国车牌生成器 项目地址: https://gitcode.com/gh_mirrors/ch/chinese_license_plate_generator 中国车牌生成器是一个基于Python的开源项目&#xff0c…

2026/8/11 1:08:05 阅读更多 →
收藏!小白程序员轻松入门大模型,从Harness工程开始实践

收藏!小白程序员轻松入门大模型,从Harness工程开始实践

文章强调学习大模型不应只关注模型本身,而应重视模型外的系统搭建,即Harness。提出AgentModelHarness的实用公式,详细介绍Harness的四个层次:持久化层、执行层、控制层和观察与验证层。文章还探讨了上下文工程、工具设计、AGENTS.…

2026/8/11 1:08:05 阅读更多 →

月新闻

免费解锁百度网盘SVIP加速:macOS用户必备的下载提速终极指南

免费解锁百度网盘SVIP加速:macOS用户必备的下载提速终极指南

免费解锁百度网盘SVIP加速:macOS用户必备的下载提速终极指南 【免费下载链接】BaiduNetdiskPlugin-macOS For macOS.百度网盘 破解SVIP、下载速度限制~ 项目地址: https://gitcode.com/gh_mirrors/ba/BaiduNetdiskPlugin-macOS 还在为百度网盘macOS版的龟速下…

2026/8/10 17:07:33 阅读更多 →
终极ncmdump指南:3分钟实现网易云NCM音乐解密与格式转换

终极ncmdump指南:3分钟实现网易云NCM音乐解密与格式转换

终极ncmdump指南:3分钟实现网易云NCM音乐解密与格式转换 【免费下载链接】ncmdump 项目地址: https://gitcode.com/gh_mirrors/ncmd/ncmdump 还在为网易云音乐下载的NCM格式文件无法在其他播放器播放而烦恼吗?ncmdump解密工具帮你轻松解决这个困…

2026/8/11 1:08:06 阅读更多 →
HarmonyOS 应用开发《掌上英语》第81篇: 智能体卡片:为英语学习 App 打造桌面级学习助手

HarmonyOS 应用开发《掌上英语》第81篇: 智能体卡片:为英语学习 App 打造桌面级学习助手

AgentCard 智能体卡片:为英语学习 App 打造桌面级学习助手适用平台:HarmonyOS 7.0 (API 26 Beta)一、引言 HarmonyOS 7.0(API 26 Beta)新增了 AgentCard 智能体卡片能力,这是继 HMAF(鸿蒙智能体框架&#x…

2026/8/10 17:07:33 阅读更多 →