Files
CamTalk/CamTalk-演讲稿.md
cfy666 fd5c7712f8 feat: 引入 Eino 框架并实现 AI 编排层基础设施与节点
- 引入 cloudwego/eino v0.9.9 和 eino-ext/components/model/openai v0.1.13
- 新增 internal/eino/ 包:
  - types.go: PipelineInput/Output、STTOutput、TokenUsage 类型定义
  - state.go: PipelineState 跨节点状态收集(线程安全)
  - callback.go: ChatModel OnEndWithStreamOutput 回调,逐 token 推送 llm_chunk
  - nodes_stt.go: STT Lambda,支持文本/语音输入模式
  - nodes_history.go: 历史组装 Lambda,含多模态图片支持
  - nodes_splitter.go: 句子分割 Transform Lambda
  - nodes_tts.go: TTS Lambda,逐句合成推送音频
  - nodes_done.go: Done Lambda,发送 llm_done 并追加历史

Co-Authored-By: Claude <noreply@anthropic.com>
2026-06-19 21:49:28 +08:00

9.0 KiB
Raw Blame History

CamTalk — 多模态实时 AI 视觉对话助手 · 演讲稿

面向面试官,预计 10-15 分钟。建议配合架构图或项目文档做演示。


开场(约 1 分钟)

各位好,今天我想和大家分享一个我主导设计和开发的项目——CamTalk,一个多模态实时 AI 视觉对话助手。

简单来说用户打开浏览器对着摄像头用语音提问AI 就能同时"看到"画面、"听到"语音,然后用文字和语音自然地回应。整个过程不需要打字,就像一个面对面的助手。

做这个项目的初衷其实很直接——现在的大模型已经具备多模态能力,但大多数产品还是"上传一张图、输入一段文字"的交互方式。我认为真正的多模态交互应该是无感的——用户只需要说话AI 自己去理解视觉场景,就像两个人面对面聊天一样。


系统架构(约 3 分钟)

CamTalk 采用三层架构:前端做轻量预处理,后端做智能编排,云端 AI 服务按需调用

前端是 React 18 加 TypeScript跑在浏览器里。它负责三件事摄像头和麦克风的采集边缘侧的预处理——比如语音活动检测和关键帧过滤以及 UI 渲染。通过 WebSocket 与后端通信。

后端是 Go 写的网关服务,用 Gin 框架做 HTTP 路由gorilla/websocket 处理长连接。它是整个系统的"大脑"负责会话管理、AI 编排,以及和各家 AI 服务的对接。每个 WebSocket 连接对应一个 goroutine天然适合这种长连接场景。

AI 服务层是可插拔的。LLM 默认用 GPT-4o通过 OpenAI 兼容接口可以随时切换成通义千问等国产模型。语音识别默认 Deepgram语音合成默认 OpenAI TTS同时也支持小米的 MiMo 系列作为备选。

有人可能会问:为什么不直接让前端调用 AI API这里有三点考虑。第一是安全性API Key 不应该暴露在客户端。第二是统一管控,速率限制、成本监控、模型路由这些逻辑集中在网关层更好维护。第三是可扩展性,未来加缓存、做负载均衡、多实例部署,都在网关层解决。

部署方面,我们设计了 Nginx 做同源反向代理,前端静态资源和后端 API 在同一个域名下天然解决跨域问题。Go 网关可以水平扩展,通过 Redis 共享会话状态。目前也已经配置好了 Docker Compose 一键部署方案,包含前端、后端和 PostgreSQL 三个容器。


核心交互流程(约 3 分钟)

我想重点讲一下一次完整的交互流程,因为它串起了整个系统最核心的技术挑战。

用户对着摄像头说了一句话,比如"这是什么花"。首先是前端的 VAD——语音活动检测模块——在浏览器端实时检测用户何时开始说话、何时说完。这一步完全在端侧完成用的是 @ricky0123/vad-web基于 WebRTC VAD 算法。好处是:用户不说话时不需要上传任何音频,节省约 70% 的无效带宽。

VAD 检测到语音结束后,前端会同时做两件事:把音频编码成 PCM 格式,以及从摄像头捕获当前画面,一起通过 WebSocket 发给后端。

后端收到后,启动一个 AI 编排管道(我们叫它 Orchestrator。第一步把音频发给 STT 服务做语音识别,拿到文字结果。第二步,把识别出的文字、摄像头画面以及对话历史,一起打包发给多模态 LLM 做推理。LLM 以流式方式逐 token 输出。第三步,也是最关键的优化——我们不等待 LLM 输出完再调用 TTS而是做句子级切分LLM 每输出一个完整句子,就立即送入 TTS 合成并推送给客户端。

所以客户端的体验是这样的:文字一个 token 一个 token 地出现,几乎同时语音就开始播放了。用户先看到文字、紧接着听到语音,感知延迟可以控制在 0.5 秒以内。整个端到端的目标延迟是 1.5 到 2 秒。

这个"LLM 文本流和 TTS 音频流并行推送"的设计,是我们降低感知延迟最关键的手段。


成本控制(约 2 分钟)

做实时多模态应用,成本是最容易失控的地方。我在设计之初就把成本控制作为架构级别的考量。

最直观的例子是视觉链路:如果按 1fps 全量发送画面给 LLM一个用户每天用 10 分钟,一天就是 60 万帧的 token 消耗1000 个用户时成本完全不可控。

我们的核心策略叫端云协同——把适合的计算前置到客户端。

在视觉侧,我们做了三个优化:一是降低采样频率,空闲时 5 秒一帧,用户说话时 1 秒一帧;二是关键帧过滤,通过 Canvas 像素比较计算帧间相似度,画面没有显著变化就不发送;三是只在用户提问时捕获画面,而不是持续上传视频流。

在语音侧VAD 在浏览器端检测,只上传有效语音片段,环境噪音和静默时段完全不消耗带宽。

在推理侧,我们规划了模型分级策略——简单识别类问题走 GPT-4o-mini深度分析走 GPT-4o复杂推理走 o1。同时对话历史做了裁剪前端保留最近 10 轮,后端保留 20 轮,限制每轮的固定 token 开销。

这些策略综合下来,预估月成本可以从无优化的约 5000 美元降到 300 到 500 美元,降幅大约 90%。


工程设计与取舍(约 2 分钟)

除了技术实现,我想分享几个设计上的取舍。

存储方案的分阶段设计。MVP 阶段我们用进程内存存会话状态,快速验证核心功能。但代码层面我们已经通过 Repository 接口模式做了抽象——HistoryRepository、UsageRepository 这些接口定义好了,底层实现可以是 Memory、Redis 或 PostgreSQL通过配置切换。目前 Redis 实现已经就绪PostgreSQL 的 schema 也设计好了,包括 sessions、messages、usage_daily 三张表。这种渐进式设计让我们既能快速交付,又为后续扩展留好了空间。

文档驱动开发。项目里有一套完整的设计文档,涵盖架构、接口协议、技术选型、成本控制等。我们遵循"文档优先"原则——实现功能前先写设计文档,实现和文档不一致时优先更新文档。这在团队协作中特别重要,接口契约清晰,前后端可以并行开发。

WebSocket 协议的可靠性设计。客户端每 30 秒发心跳,服务端 60 秒没收到心跳就断开。断线后用指数退避加抖动重连——1 秒、2 秒、4 秒、8 秒,最大 30 秒。消息用统一信封格式,所有消息都带 type 字段做类型分发。


用户故事与产品规划(约 2 分钟)

最后讲一下产品层面的思考。用户故事我按 P0 到 P2 分了三个优先级。

P0 是 MVP 必做的四个场景AI 识别画面中的物体、语音对话无需打字、AI 能看到摄像头画面、AI 用语音回答。这四个跑通了,核心价值就成立了。

P1 是体验增强AI 主动观察画面变化并提示重要事件、识别画面中的文字做 OCR、以及多轮对话的上下文记忆。

P2 是进阶探索比如视障用户的无障碍辅助——AI 实时描述周围环境并提示障碍物,画面中外语内容的实时翻译,以及"观察模式"和"对话模式"的切换。

优先级判断用两个维度交叉评估用户价值和实现成本。P0 是高价值且成本合理的P1 是高价值但成本较高的P2 是探索性的,验证后再投入。

目前还有几个功能创意在规划中,包括视频录制、对话翻译、对话总结、手动对话输入,以及对话情景选择——比如面试官模式、英语老师模式、辩论赛模式等。


总结(约 1 分钟)

总结一下CamTalk 这个项目有几个我比较满意的设计点。

第一是架构清晰三层分离每层职责明确前端做轻量预处理后端做智能编排AI 服务可插拔。

第二是体验导向:从用户感知延迟倒推技术方案,流式并行推送、句子级切分、端侧 VAD 这些手段都是围绕"让对话像真人一样自然"这个目标设计的。

第三是成本意识:从架构层面就融入了成本控制,端云协同、智能采样、模型分级,不是等功能做完再去优化成本。

第四是工程成熟度:接口抽象、文档驱动、渐进式存储升级,为项目的长期演进留好了空间。

以上就是 CamTalk 项目的整体介绍。谢谢大家,有什么问题我们可以一起讨论。


附:讲解提示

  • 如果面试官追问技术深度,可以展开讲 Orchestrator 的管道实现细节goroutine 并发、context 取消、句子切分算法)或 VAD 参数调优。
  • 如果追问产品思维,可以展开讲用户故事的优先级判断逻辑,以及观察模式和对话模式的差异设计。
  • 如果追问可扩展性,可以讲 Redis 共享会话、多 Gateway 水平扩展、模型路由器的规划。
  • 如果追问成本数据,可以给出具体的 token 消耗计算过程和各种优化手段的量化效果。