如何实现SSE流式推送与并行抓取?TinyFish Cookbook之game-buying-guide完整深度解析
如何实现SSE流式推送与并行抓取TinyFish Cookbook之game-buying-guide完整深度解析【免费下载链接】tinyfish-cookbookA collection of sample apps and recipes built with the TinyFish web agent. Open-source examples for you to learn build!项目地址: https://gitcode.com/gh_mirrors/ti/tinyfish-cookbook本文带你完整拆解 TinyFish Cookbook 中的开源示例game-buying-guide它是一个 AI 游戏比价助手通过SSE 流式推送11 路并行抓取让 10 个浏览器 Agent 同时访问 Steam、Epic、GOG 等游戏商店并实时回传价格分析结果。下面从架构、并发、流式协议到客户端解析一次讲透它的代码设计。一、它是什么一个能同时逛 11 个商店的 AI 比价工具game-buying-guide 的目标很直接输入一个游戏名它立刻派出 11 个 TinyFish 浏览器 Agent并行执行10 个商店 AgentSteam、Epic Games、GOG、PlayStation、Xbox、Nintendo eShop、Humble Bundle、Green Man Gaming、Fanatical、CDKeys1 个 SteamDB Agent专门抓取该游戏的历史最低价格判断现在是买还是等每个 Agent 返回结构化 JSON现价、折扣、评分、buy_now / wait / consider建议最先完成的平台最先显示在页面上——这正是 SSE 流式推送的价值所在。二、总体架构三个 API 路由组成流水线项目结构见 game-buying-guide/README.md核心只有 3 个 API 路由路由职责是否流式discover-platforms/route.ts返回 10 个商店的搜索 URL硬编码模板无需 LLM❌ 普通 JSONanalyze-platform/route.ts单个商店的 Agent 分析✅ SSE 流式steamdb-price-history/route.tsSteamDB 历史最低价分析✅ SSE 流式设计亮点平台发现用硬编码 URL 模板route.ts#L4-L55省掉一次 LLM 调用的等待只有真正需要看网页的环节才交给浏览器 Agent。整个项目无数据库、无缓存纯内存实时抓取。三、并行抓取核心Promise.allSettled 同时发起 11 个任务客户端状态全部集中在 hooks/use-game-search.ts 这个自定义 Hook 里。search函数是并行抓取的入口// 所有平台 Agent SteamDB 并行执行 await Promise.allSettled([ ...platforms.map((platform) analyzePlatform(platform, gameTitle)), analyzeSteamDB(gameTitle), ]);见 use-game-search.ts#L186-L189。这里有两个关键选择Promise.allSettled而非Promise.all任何一个商店 Agent 超时或失败都不会拖垮其余 10 个任务失败的那张卡片单独显示错误状态。每个任务独立持有AbortController见 use-game-search.ts#L22-L23用户重新搜索或点击重置时可以精确中止某一路 SSE 连接避免旧请求污染新结果。四、SSE 服务端实现ReadableStream 四行事件头analyze-platform路由的精髓只有几十行。它用ReadableStream构造响应体把 Agent 事件逐条编码为 SSE 格式data: {JSON}\n\n写入const stream new ReadableStream({ async start(controller) { const send (payload) controller.enqueue(encoder.encode(sseData(payload))); // 把 TinyFish 事件流逐条转成 SSE 帧发送…… }, });完整实现见 route.ts#L70-L118。响应头中有 4 个保证流式体验的关键设置Content-Type: text/event-stream Cache-Control: no-cache, no-transform Connection: keep-alive X-Accel-Buffering: no ← 禁止 Nginx 类代理缓冲数据即刻下发另外注意 route.ts#L4-L5 的maxDuration 300浏览器 Agent 爬取慢必须把云函数超时时间拉长到 5 分钟否则流会在中途被掐断。三种 SSE 事件类型客户端只会收到 4 种帧全部由服务端事件映射而来SSE 帧类型来源TinyFish SDK 事件用途STREAMING_URLEventType.STREAMING_URL拿到 Agent 浏览器的实时画面地址STATUSEventType.PROGRESS更新卡片上的正在做什么文案COMPLETEEventType.COMPLETERunStatus.COMPLETED返回解析后的价格分析 JSONERROR异常分支携带错误信息前端标记卡片为失败五、最大亮点STREAMING_URL 驱动的实时浏览器预览STREAMING_URL事件是这套架构最出彩的部分TinyFish 会把 Agent 浏览器的实时画面地址流式推给前端前端直接用iframe加载用户就能亲眼看到 AI 正在哪个商店页面上翻找价格。卡片内嵌预览components/agent-card.tsx 中运行中的卡片带一块 128px 高的实时窗口点击可放大为悬浮窗components/live-browser-preview.tsx 用 Framer Motion 实现展开/收起上图是同一 Cookbook 仓库中 fast-qa 示例应用的截图——同样基于 TinyFish Agent 流式回传能看到边执行、边更新的交互质感game-buying-guide 的每张卡片都是这种体验。六、客户端 SSE 解析手写 30 行解析器前端没有用EventSource它不支持 POST而是手写了一个极简解析器核心逻辑在 use-game-search.ts#L40-L74response.body.getReader()按块读取响应体用TextDecoder解码buffer 保留最后一个不完整行SSE 帧可能被网络拆包按\n切行只处理以data:开头的帧JSON.parse后按type字段分发到对应的状态更新。解析失败直接catch跳过坏块保证流不被一条脏数据中断。所有数据结构定义在 lib/types.tsAgentStatus每路任务状态机pending → running → complete/error与PlatformAnalysis比价结果字段。七、一个容易被忽略的细节COMPLETED ≠ 任务成功服务端对结果做了双重校验见 route.ts#L85-L96状态校验RunStatus.COMPLETED只代表浏览器没崩不代表真的取到了价格内容校验Agent 可能返回带 json 围栏的字符串需先清洗再JSON.parse解析不出来时回退到兜底对象recommendation: consider前端永远不会白屏。这是所有 Agent 应用的通用经验永远校验内容而不只是状态。八、本地运行这份示例git clone https://gitcode.com/gh_mirrors/ti/tinyfish-cookbook cd tinyfish-cookbook/game-buying-guide # 需要 Node.js 22.x npm install # 创建 .env.local填入 TINYFISH_API_KEY npm run dev打开 http://localhost:3000输入任意游戏名即可看到 11 张卡片从运行中逐步变为完成实时画面、进度文案、比价结果依次流式呈现。总结这套架构最值得抄的 4 个点⚡并行用allSettledN 路任务互不牵连失败只影响单卡SSE 用ReadableStream手写POST 场景下比EventSource更灵活客户端解析器仅需 30 行️STREAMING_URL事件转发 iframe把AI 在干活变成可视过程体验远超转圈 loading✅COMPLETED 后仍校验内容Agent 结果永远需要清洗 兜底完整源码可直接参考 game-buying-guide/ 目录更多基于 TinyFish 的实战示例都在 Cookbook 仓库的 README.md 中有索引。【免费下载链接】tinyfish-cookbookA collection of sample apps and recipes built with the TinyFish web agent. Open-source examples for you to learn build!项目地址: https://gitcode.com/gh_mirrors/ti/tinyfish-cookbook创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

相关新闻

linux部署jdk+tomcat 启动服务

linux部署jdk+tomcat 启动服务

linux部署jdktomcat 启动服务 在麒麟 ARM 离线环境里:JDK 选 aarch64 版本、Tomcat 用官方 tar.gz、通过 setenv.sh 指向 JDK。 1,安装 jdk 1.1 下载jdk # 在离线服务器上执行,确认架构 uname -m # 输出应为 aarch64浏览器根据服务器架构…

2026/10/12 12:47:49 阅读更多 →
Unity网络通信最稳方案:从零手写异步TCP客户端与粘包拆包处理

Unity网络通信最稳方案:从零手写异步TCP客户端与粘包拆包处理

做Unity客户端的朋友,早期应该都踩过这样的坑:需要跟服务器通信,于是直接在Update里写了个Socket.Receive,结果网络一抖动,整个游戏画面就像PPT一样卡。或者网上找教程,用协程把接收包循环包起来&#xff0…

2026/10/12 21:42:43 阅读更多 →
Unity内嵌浏览器ZFBrowser实战指南:数字孪生与网页交互

Unity内嵌浏览器ZFBrowser实战指南:数字孪生与网页交互

做数字孪生项目时我遇到一个很典型的需求:要在Unity场景里嵌入一个实时网页仪表盘,用户可以一边看3D设备状态,一边滚动查看网页上的数据图表。一开始我走的是UITexture加浏览器截图的野路子,结果延迟高、不能点击、页面一滚动就卡…

2026/10/16 15:02:27 阅读更多 →

最新新闻

Agentic Workflow 实战:从问答到任务执行闭环的AI应用改造

Agentic Workflow 实战:从问答到任务执行闭环的AI应用改造

过去一年我一直在做 AI Native 类产品,听得最多的反馈不是“这个 AI 回答得不准确”,而是“它回答得很好,但它没有帮我把事情办完”。这句话其实点中了现在大量 AI 应用的通病:交互逻辑还停留在“问答”上,没有进入“任…

2026/10/19 2:45:51 阅读更多 →
RockyLinux 8.6安装实战与Linux核心命令入门

RockyLinux 8.6安装实战与Linux核心命令入门

1. 为什么我建议学习从 RockyLinux 8.6 开始这几年 Linux 发行版市场的变动,其实比很多人想象中要大。CentOS 8 停止维护之后,大量服务器运维人员、实验室管理员和自学入门的开发者都面临一个现实问题:生产环境到底用什么系统?我自…

2026/10/19 2:45:51 阅读更多 →
AI Agent驱动游戏NPC:从脚本到自主人格的工程实践指南

AI Agent驱动游戏NPC:从脚本到自主人格的工程实践指南

1. 为什么要让NPC长“脑子”:先聊聊这件事的价值过去几年我一直在琢磨一件事:游戏里的NPC,到底能不能从“台词播放器”变成“活人”?很多从业者其实都清楚,传统NPC的核心是状态机行为树对话脚本。状态机管状态切换&…

2026/10/19 2:45:51 阅读更多 →
Vibe Coding被打断后,如何快速恢复编程上下文?

Vibe Coding被打断后,如何快速恢复编程上下文?

1. 被拉出Vibe Coding时,到底丢掉了什么1.1 Vibe Coding是三件事同时在线,不是“感觉好”Vibe Coding这个词,这两年听得多了,但很多人的理解还停留在“写代码写得很有感觉”。实际上,它不是一个虚无缥缈的玄学状态&…

2026/10/19 2:45:51 阅读更多 →
AI辅助论文写作的六大绝技:从选题扫描到仿真评审的全流程实操指南

AI辅助论文写作的六大绝技:从选题扫描到仿真评审的全流程实操指南

写论文这件事,十个人里有九个半卡住的都不是"打字速度",而是"找不到一个笃定的方向"和"不知道写到什么程度算合格"。我在帮学生改论文的这些年里,见过太多人把三周时间耗在选题上,再用两周时间把综…

2026/10/19 2:45:51 阅读更多 →
局域网设备互联:mDNS与DNS-SD的区别及服务发现排错指南

局域网设备互联:mDNS与DNS-SD的区别及服务发现排错指南

很多人在局域网里折腾设备互联时,都会被同一个问题卡住:手机上的服务发现工具能搜到隔壁房间的投影仪和网络打印机,电脑上却怎么都看不到;或者设备明明已经在列表里,点击连接却提示“服务不可用”。去查资料&#xff0…

2026/10/19 2:44:50 阅读更多 →

日新闻

频率跟踪型PWM电源设计:臭氧发生器谐振点漂移与软开关实现

频率跟踪型PWM电源设计:臭氧发生器谐振点漂移与软开关实现

简介:本资源为电源技术方向的学术研究文档,聚焦介质阻挡放电型臭氧发生器电源的频率跟踪型PWM控制策略,面向电力电子、高压电源及臭氧应用领域的科研人员与工程技术人员。针对负载呈容性、等效电容随外加电压升高而增大、谐振频率随之漂移的难…

2026/10/19 0:00:47 阅读更多 →
Vibe Coding 遇上 TaoToken:把开发者思维圣殿的灵感流接入统一 Key 通道

Vibe Coding 遇上 TaoToken:把开发者思维圣殿的灵感流接入统一 Key 通道

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/19 0:00:47 阅读更多 →
HundredCV-Chat话题建模实战教程:利用4,871个内置话题标签构建主题分析系统

HundredCV-Chat话题建模实战教程:利用4,871个内置话题标签构建主题分析系统

【免费下载链接】HundredCV-Chat 项目地址: https://ai.gitcode.com/hf_mirrors/Jax-dan/HundredCV-Chat 点击查看 免费下载 HundredCV-Chat 是一个由 100 位青年简历数据开发而来的中文多轮对话数据集,共包含 24,750 组日常闲聊对话和 4,871 个话题标签…

2026/10/19 0:00:47 阅读更多 →

周新闻

基于GMM的语音识别系统原理与MATLAB实现详解

基于GMM的语音识别系统原理与MATLAB实现详解

说到基于高斯混合模型(GMM)的语音识别系统,很多人第一反应就是一堆数学公式,觉得门槛很高。但如果你真的在MATLAB里把它落地跑通,会发现核心其实就是三件事:把声音变成特征向量,用GMM给每个类别…

2026/10/18 0:00:55 阅读更多 →
数字图像处理入门:反白、灰度化、调色板修改与导出txt实践

数字图像处理入门:反白、灰度化、调色板修改与导出txt实践

数字图像处理这四个字听起来挺唬人,但落到具体操作上,无非就是让计算机按你的想法“摆弄”像素。我在一个模拟项目X里用了一套特别经典的基础处理流程:对图像做反白、改调色板、彩色转灰度,最后把像素数据导出成txt文件。单看每一…

2026/10/18 0:00:55 阅读更多 →
机器人大脑技术盘点:具身智能的感知、决策与数据闭环

机器人大脑技术盘点:具身智能的感知、决策与数据闭环

如果你的信息流最近也天天刷到“机器人大脑”这个词,你会发现一个很有意思的现象:每个人说的“大脑”根本不是同一个东西。有人指的是大语言模型,有人指的是运动控制系统,还有人指的是能理解物理世界的端到端模型。在2026年这个时…

2026/10/19 1:30:52 阅读更多 →

月新闻

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/18 0:55:02 阅读更多 →
Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/17 17:22:31 阅读更多 →
黑夜航拍船只数据集训练YOLOV5模型全流程解析

黑夜航拍船只数据集训练YOLOV5模型全流程解析

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/18 12:16:16 阅读更多 →