您好!
欢迎来到京东云开发者社区
登录
首页
博文
课程
大赛
工具
用户中心
开源
首页
博文
课程
大赛
工具
开源
更多
用户中心
开发者社区
>
博文
>
【全栈实践】第一个 AI Agent 项目:从零搭建 AI 音频创作助手【最终版】
分享
打开微信扫码分享
点击前往QQ分享
点击前往微博分享
点击复制链接
【全栈实践】第一个 AI Agent 项目:从零搭建 AI 音频创作助手【最终版】
jd****
2026-07-29
IP归属:北京
6浏览
# 从零到一,全栈手搓 AI 智能播客平台——我的完整开发手记 ## 引言:这个项目是做什么的? **Smart Podcast Platform** 是一个端到端的智能播客制作平台。它的核心能力很简单:**用户上传一段视频或音频,AI 自动理解内容、设计音色、生成播客,全程无需人工干预。** 传统的 AI 音频工具通常停留在"生成文字脚本"的层面——用户拿到脚本后,还需要自己找配音、做剪辑、调音效,整个流程割裂且低效。这个项目试图把整个链条打通:从**内容理解**到**音色设计**,从**语音合成**到**专业混音**,全部由 AI Agent 自动完成。 这是我个人独立开发的全栈项目,从后端 Python 到前端 Vue 3,从 LangGraph Agent 编排到 pydub 音频处理,完整覆盖了一个 AI 音频应用的方方面面。 代码库地址:[https://github.com/XingtongCai/podcast_agent](https://github.com/XingtongCai/podcast_agent) --- ## 0、相关细节说明文章 以下三篇是关于这个Agent更详细说明: 1.[http://sd.jd.com/article/66149?shareId=56999&isHideShareButton=1](第一个 AI Agent 项目:从零搭建 AI 音频创作助手) : 这个是第一版本,里面主要进行初期框架搭建,包含Vue3 + ai-elements-vue 搭前端界面,LangChain 1.0 × AG-UI 协议 × Qwen TTS 驱动后端,支持定制音色,复刻音色和配音功能。 2.[http://sd.jd.com/article/70053?shareId=56999&isHideShareButton=1](第一个 AI Agent 项目:从零搭建 AI 音频创作助手(进阶篇)) : 这个是第二版本,新增了完整的播客后期制作能力,包括音频拼接、智能BGM选择、音轨混音三大核心功能,同时新增了音频资源管理API和语音输入功能,实现了从前端上传、语音输入到后端处理的全链路闭环。 3.[http://sd.jd.com/article/71346?shareId=56999&isHideShareButton=1](第一个 AI Agent 项目:从零搭建 AI 音频创作助手(高级篇)) : 这个是第三版本,新增了音频、视频识别能力、临时-永久双层存储架构、定时清理机制和更智能的提示词系统,让播客 Agent 从单纯的"语音合成工具"升级为"全链路音频内容创作平台"。 ## 一、项目架构总览 ### 1.1 技术栈一览 | 层级 | 技术选型 | 核心作用 | |------|---------|---------| | **前端框架** | Vue 3 + TypeScript + Vite | 提供流式对话界面与播客管理 | | **UI 组件** | shadcn-vue + Tailwind CSS | 深色主题的现代化交互体验 | | **AI 框架** | LangChain + LangGraph | Agent 编排与多轮对话记忆 | | **后端服务** | FastAPI + Uvicorn | REST API + SSE 流式响应 | | **通信协议** | AG-UI Protocol | 前后端 Agent 事件标准化通信 | | **语音引擎** | 阿里云 DashScope (Qwen-TTS) | 音色设计、语音克隆、语音合成 | | **语音识别** | 阿里云 DashScope (Qwen-ASR) | 高精度语音转文字,支持 ITN 标准化 | | **多模态模型** | qwen3.5-omni-plus | 图片/视频/音频统一理解 | | **音频处理** | pydub + FFmpeg | 音频拼接、混音、后期制作 | ### 1.2 系统架构图 ```mermaid graph TB A[用户浏览器] --> B[Vue 3 前端] B --> C[FastAPI 后端] C --> D[LangGraph Agent] D --> E[LLM 推理引擎] D --> F[工具调用层] F --> G1[Qwen-TTS 音色设计] F --> G2[Qwen-TTS 语音克隆] F --> G3[Qwen-ASR 语音识别] F --> G4[Qwen-Omni 多模态理解] F --> G5[音频拼接与混音] C --> H[存储层] H --> H1[音频文件存储] H --> H2[音色索引管理] H --> H3[配置持久化] B --> I[AG-UI 协议] I --> C ``` --- ## 二、核心技术深度解析 ### 2.1 Agent 智能体:不只是"调用 API" 传统的 AI 应用通常是"用户输入 → 调用 API → 返回结果"的线性流程。但在播客制作场景中,这个流程要复杂得多: - 用户可能上传**视频**(需要多模态理解) - 用户可能上传**音频**(需要语音识别) - 用户可能要求**特定音色**(需要音色设计) - 最终需要**混音输出**(需要音频后期处理) 我们的 Agent 系统通过 **LangGraph** 实现了智能编排: ```python # backend/app/services/agent_service.py agent = create_agent( name="tts_agent", model=model, # LLM 推理引擎 tools=tools, # 注册 9 个专业工具 system_prompt=full_prompt, # 播客专家角色定义 checkpointer=InMemorySaver() # 多轮对话记忆 ) ``` **核心设计理念:** 1. **自主决策**:Agent 根据用户输入自动判断需要调用哪些工具,无需预设固定流程 2. **链式调用**:复杂任务自动编排多步骤工具调用(理解内容 → 设计音色 → 合成语音 → 混音输出) 3. **上下文感知**:自动从对话历史中提取信息,避免重复询问用户 4. **记忆持久化**:基于 `InMemorySaver` 实现多轮对话状态保持 ### 2.2 流式通信:AG-UI 协议的妙用 我们采用了 **AG-UI 协议**(Agent-User Interaction Protocol),将 Agent 的各种行为标准化为事件流: ```python # backend/app/services/stream_processor.py class StreamProcessor: async def process_stream(self, agent, messages): # 1. 发送运行开始事件 yield RunStartedEvent(...) # 2. 流式处理 Agent 输出 async for chunk in agent.astream(...): if isinstance(chunk, AIMessage): # 文本内容 → TextMessageContentEvent yield TextMessageContentEvent(delta=content) elif hasattr(chunk, 'tool_calls'): # 工具调用 → ToolCallStartEvent + ToolCallArgsEvent yield ToolCallStartEvent(tool_call_name=name) ``` **协议事件类型:** | 事件 | 含义 | 前端展示 | |------|------|---------| | `RUN_STARTED` | Agent 开始运行 | 加载动画 | | `TEXT_MESSAGE_START/CONTENT/END` | 文本流式输出 | 打字机效果 | | `TOOL_CALL_START/ARGS/END` | 工具调用过程 | 工具卡片展开 | | `TOOL_CALL_RESULT` | 工具返回结果 | 结果展示 | 前端通过 `ai-elements-vue` 组件库,将这些事件渲染为丰富的交互界面:思维链展示、工具调用卡片、代码块高亮等。 ### 2.3 音色设计:让 AI "开口说话" 这是整个系统最核心的功能模块。我们基于阿里云 DashScope 的 Qwen-TTS 引擎,实现了两种音色生成方式: #### 方式一:文本描述生成音色(Voice Design) 用户只需用文字描述想要的音色特征: ```python # backend/app/tools/qwen_tts.py @tool("qwen_voice_design", args_schema=VoiceDesignInput) def qwen_voice_design_tool( voice_description: str, # 如:"沉稳的中年男性,音色低沉浑厚,富有磁性" text: str, # 测试文本 language: str = "zh" ) -> str: # 调用 DashScope API,传入音色描述文本 # API 返回 voice_id 和预览音频 ... ``` **技术亮点**:音色描述直接作为 API 参数,无需训练或微调,零样本生成。 #### 方式二:参考音频复刻(Voice Cloning) 上传一段参考音频,AI 自动复刻其音色特征: ```python @tool("qwen_voice_cloning", args_schema=VoiceCloningInput) def qwen_voice_cloning_tool( voice_id: str = "", # 已设计的音色ID local_path: str = "", # 本地音频路径 reference_audio: str = "", # 上传的参考音频 text: str = "" ) -> str: # 优先级:voice_id > local_path > reference_audio # 1. 注册音色 → 2. 合成语音 → 3. 保存本地 ... ``` **参数优先级设计**:`voice_id` > `local_path` > `reference_audio`,确保已设计的音色可以复用,避免重复注册。 ### 2.4 多模态理解:让 AI "看懂"和"听懂" 播客内容的来源不限于文字——用户可能上传视频、音频、图片等各种格式。我们集成了 `qwen3.5-omni-plus` 模型,提供统一的多模态理解能力: ```python # backend/app/tools/qwen_multimodal.py @tool("qwen_multimodal_tool") def qwen_multimodal_tool(media: str, prompt: str) -> str: # 1. 智能解析媒体来源(URL / 本地路径 / base64) media_content = _resolve_media_source(media) # 2. 大视频自动分割(>21MB 自动切片) if isinstance(media_content, list): # 对每个片段分别调用 API,合并结果 # 3. 调用多模态 API response = _call_multimodal_api(messages) return _extract_text_from_response(response) ``` **关键设计决策:** 1. **大视频分割策略**:当文件超过 21MB 时,自动使用 `moviepy` 分割为多个片段,每段约 10MB,确保 base64 编码后不超过 API 限制 2. **统一媒体抽象**:`_resolve_media_source()` 函数将 URL、本地路径、base64 统一转换为 API 所需的格式 3. **格式智能识别**:根据文件扩展名自动选择 `image_url` / `video_url` / `input_audio` 类型 #### 音频理解:不只是"听",而是"懂" 除了视频和图片,多模态模型同样支持**音频内容理解**。用户上传一段音频,模型可以直接分析其中的语义内容、情感色彩、甚至识别说话人的语气和节奏——这对于播客内容创作尤为重要,因为很多用户会直接上传录音素材作为播客的原始材料。 ```python # 音频理解调用示例 messages = [ {"role": "user", "content": [ {"input_audio": "https://example.com/podcast-raw.mp3"}, {"text": "请分析这段音频的主要内容和情感基调"} ]} ] response = client.chat.completions.create( model="qwen3.5-omni-plus", messages=messages ) # 返回:内容摘要 + 情感分析 + 关键信息提取 ``` ### 2.5 音频后期制作:从"语音片段"到"专业播客" 生成语音只是第一步,真正的播客需要专业的后期处理。我们基于 `pydub` 实现了完整的音频处理管线: ```python # backend/app/tools/audio_mixing.py # 工具1:音频拼接 @tool("concatenate_audio") def concatenate_audio_tool( audio_files: List[str], crossfade_duration: int = 200, # 交叉淡入淡出 silence_duration: int = 1200 # 片段间静音 ) -> str: # 按顺序拼接多个音频片段 ... # 工具2:智能BGM选择 @tool("select_background_music") def select_bgm_tool( scene_description: str, # 如"欢快的开场" duration_seconds: float = None ) -> str: # 基于文件名关键词匹配 BGM # 自动循环/裁剪以匹配时长 ... # 工具3:专业混音 @tool("mix_audio_with_bgm") def mix_audio_with_bgm_tool( voice_audio: str, bgm_audio: str, bgm_volume: float = -26, # BGM 约 5% 音量 intro_duration: float = 3.0 # 开场原声时长 ) -> str: # BGM 开场(原音量)→ 过渡(渐变)→ 背景(5%音量) ... ``` **混音策略设计:** ``` BGM 音量曲线: 100% ┤ ┌────── 开场(原声 BGM) │ │ 5% ┤─────┼──────────────────── 背景(-26dB) │ │ └─────┴────────────────────→ 时间 0s 3s 淡入过渡 2s ``` 这种设计模拟了专业播客的听觉体验:开场时 BGM 烘托氛围,过渡后降低为背景音,确保人声清晰。 ### 2.6 配置管理:多层级优先级策略 项目采用 **配置文件 > 环境变量 > 默认值** 的三级配置优先级: ```python # backend/app/utils/config_manager.py def get_config_value(key: str, env_key: str, default: str = "") -> str: # 1. 先读 config.json(前端可视化配置) config = load_config() value = config.get("llm", {}).get("openai_api_key") # 2. 再读环境变量 if not value: value = os.getenv("OPENAI_API_KEY") # 3. 最后用默认值 return value or default ``` **设计意图**:用户可以通过前端界面(`VisualConfig.vue`)直接修改配置,无需手动编辑 `.env` 文件。配置自动持久化到 `storage/config.json`,降低使用门槛。 ### 2.7 音频索引系统:轻量级的资源管理 我们没有引入数据库,而是用 JSON 文件实现了轻量级的音频资源索引: ```json // storage/voice_index.json [ { "id": "uuid", "local_path": "storage/audios/xxx.wav", "voice_id": "voice-xxx", "model_name": "cosyvoice-v3.5-plus", "path": "audios", "createTime": "2026-07-10 14:30:00" } ] ``` **关键设计:** - **文件锁并发控制**:使用 `fcntl.flock` 保证多请求并发写入安全 - **path 字段分类**:`audios`(定制音色)/ `bgm`(背景音乐)/ `podcasts`(播客成品),便于前端分类展示 - **临时文件自动清理**:`storage/temp/` 目录下的文件定期清理,避免磁盘堆积 --- ## 三、前端交互设计 ### 3.1 深色主题的沉浸式体验 前端采用深蓝紫的色调主题,深空背景 + 蓝紫光晕 + 亮蓝高亮,配置提取`style.css`中: ```css /* —— 光晕装饰色 —— */ --brand-glow-blue: #3a5cff; --brand-glow-purple: #7c3aed; --brand-glow-deep-blue: #1e40ff; /* —— 品牌高亮蓝 —— */ --brand-blue: #4f7cff; --brand-blue-light: #4f9dff; --brand-blue-strong: #2b6ef7; --brand-blue-soft: #7ea3ff; --brand-blue-pale: #9ec2ff; /* —— 卡片封面渐变 —— */ --brand-cover-from: #1e3a8a; --brand-cover-via: #2a1e5f; --brand-cover-to: #0d0524; ``` ### 3.2 流式对话体验 基于 `ai-elements-vue` 组件库,前端实现了丰富的 Agent 交互界面: - **思维链展示**:Agent 的推理步骤以可折叠卡片形式展示 - **工具调用可视化**:每个工具调用显示名称、参数、结果 - **音频播放器**:生成的音频直接在对话中嵌入播放 - **文件上传**:支持拖拽上传音频/视频文件 ### 3.3 四个核心页面 | 页面 | 功能 | 路由 | 效果描述 | |------|------|------|---------| | **ChatAgent** | 流式对话 Agent,核心创作入口 | `/` | 深色主题对话界面,Agent 逐步展示思考过程、工具调用和生成结果,支持音频播放和文件拖拽上传 | | **PodcastList** | 播客成品列表,展示和管理作品 | `/podcasts` | 卡片网格布局展示所有已生成的播客作品,每个卡片包含封面、标题、时长信息,悬停有微动效 | | **ResourceLibrary** | 资源库管理,管理音色/BGM/素材 | `/resources` | 分类管理音色、BGM、播客素材,支持上传、预览、删除操作,左侧分类导航 + 右侧内容列表 | | **VisualConfig** | 可视化配置 API Key 和模型参数 | `/config` | 表单式配置界面,分为"对话模型"和"语音播客"两个区块,支持密码可见性切换和自动持久化 | --- ## 四、工程实践与经验 ### 4.1 工具设计的"单一职责"原则 我们将音频处理拆分为 9 个独立工具,每个工具只做一件事: | 工具 | 职责 | 输入 | 输出 | |------|------|------|------| | `qwen_multimodal_tool` | 多模态内容理解 | 媒体文件 | 文本描述 | | `qwen_asr_tool` | 语音识别 | 音频文件 | 文字转录 | | `qwen_voice_design` | 音色设计 | 文本描述 | 音色ID+音频 | | `qwen_voice_cloning` | 语音合成 | 音色ID+文本 | 音频文件 | | `save_voice` | 音色保存 | 音频路径 | 永久存储 | | `concatenate_audio` | 音频拼接 | 音频列表 | 拼接文件 | | `select_background_music` | BGM 选择 | 场景描述 | BGM 路径 | | `mix_audio_with_bgm` | 专业混音 | 人声+BGM | 最终播客 | 这种设计让 Agent 可以灵活组合工具,而不是被预设的"大而全"工具束缚。 ### 4.2 临时文件与永久存储的分离 - **临时目录**(`storage/temp/`):工具生成的中间产物,10 分钟自动清理 - **永久目录**(`storage/audios/`):用户确认保存的音色,持久化存储 - **成品目录**(`storage/podcasts/`):混音后的最终播客 这个设计避免了磁盘空间浪费,同时保证了用户主动保存的内容不会丢失。 ### 4.3 流式输出的"真"流式 我们使用 `stream_mode="messages"` 模式,确保 Agent 的输出是**逐 token 流式**的,而非"生成完再发送"的伪流式: ```python async for chunk in agent.astream( {"messages": langchain_messages}, {"configurable": {"thread_id": self.thread_id}}, stream_mode="messages" # 关键:逐消息流式输出 ): async for event in self._handle_chunk(chunk): yield event # 立即发送,不等待 ``` ### 4.4 配置可视化:降低技术门槛 传统 AI 项目需要用户手动编辑 `.env` 文件,对非技术用户极不友好。我们通过 `VisualConfig.vue` 页面,将配置项以表单形式呈现: - API Key 输入框(支持密码可见性切换) - 模型选择下拉框 - 配置自动持久化到 `config.json` - 前后端通过 `/api/config` 接口同步 --- ## 五.结果展示     *** ## 六、总结 这个项目展示了 **AI Agent 在垂直内容创作领域** 的完整实践: 1. **端到端自动化**:从内容理解到播客输出,全流程 AI 驱动 2. **多模态融合**:文字、图片、音频、视频统一处理 3. **专业级音频质量**:音色设计 + 智能混音,输出广播级品质 4. **低门槛使用**:可视化配置 + 自然语言交互,无需技术背景 --- ## 附录:快速开始 ```bash # 1. 克隆项目 git clone <repo-url> # 2. 启动后端 cd backend python -m venv venv source venv/bin/activate pip install -r requirements.txt cp .env.example .env # 填写 API Key python main.py # 3. 启动前端 cd fronted npm install npm run dev # 4. 访问 http://localhost:3000 ``` ---
上一篇:三十分钟入门基础Go——Java小子版
下一篇:大模型是怎样炼成的:从会背书到能办案
jd****
文章数
2
阅读量
2062
作者其他文章
01
【MCP】同时支持stdio,streamableHttpless和sse三种协议的MCP服务框架
项目说明这是一个同时支持stdio,streamableHttpless和sse三种协议的MCP-Server的框架(ts语言)。 为什么我想做这个框架呢?因为随着AI发展,现在越来越多业务需要和AI相结合。而我在做AI应用中发现,MCP服务在AI方向的业务使用频率很高,但随着业务的加深,发现存在以下痛点:针对不同业务,对于mcp-server需要的类型不同,有的就需要stdio,有的需要网络请求
01
【全栈实践】第一个 AI Agent 项目:从零搭建 AI 音频创作助手【最终版】
从零到一,全栈手搓 AI 智能播客平台——我的完整开发手记引言:这个项目是做什么的?Smart Podcast Platform 是一个端到端的智能播客制作平台。它的核心能力很简单:用户上传一段视频或音频,AI 自动理解内容、设计音色、生成播客,全程无需人工干预。传统的 AI 音频工具通常停留在”生成文字脚本”的层面——用户拿到脚本后,还需要自己找配音、做剪辑、调音效,整个流程割裂且低效。这个项目
jd****
文章数
2
阅读量
2062
作者其他文章
01
【MCP】同时支持stdio,streamableHttpless和sse三种协议的MCP服务框架
添加企业微信
获取1V1专业服务
扫码关注
京东云开发者公众号