# 项目状态报告 _最后更新:2026-04-06_ --- ## 一、当前部署架构 ``` ┌─────────────────────────────────────────────────────┐ │ MacBook Pro (本地) │ │ │ │ ┌─ xiaozhi-esp32-server (Docker) ─────────────┐ │ │ │ 端口: 8000 (WS) / 8003 (HTTP) │ │ │ │ config: /opt/xiaozhi-esp32-server/data/ │ │ │ │ │ │ │ │ ⚠️ 当前: manager-api → xinnan-tech 云端 │ │ │ │ 云端配置覆盖本地 .config.yaml │ │ │ │ 导致 LLM 型号: glm-4-flash (应为MiniMax) │ │ │ └──────────────────────────────────────────────┘ │ │ │ │ ┌─ xiaozhi_cli_client.py ──────────────────────┐ │ │ │ WebSocket CLI 调试工具 │ │ │ │ ✅ WebSocket 认证问题已修复 │ │ │ │ ⚠️ TTS 音频跳过(无播放),文本回复正常 │ │ │ └──────────────────────────────────────────────┘ │ │ │ │ ┌─ child-psycho-companion ─────────────────────┐ │ │ │ psycho-screener MCP 工具 │ │ │ │ ✅ 已注册到 xiaozhi-server │ │ │ │ ✅ psycho_screen 工具在工具列表中 │ │ │ └──────────────────────────────────────────────┘ │ └─────────────────────────────────────────────────────┘ ``` --- ## 二、问题排查记录 ### 2.1 WebSocket 连接 ✅ 已解决 | 项目 | 详情 | |------|------| | **症状** | 连接成功但 `device-id` 为 None | | **根因** | 服务端从 HTTP header 读 `device-id`,客户端从 URL query param 传 | | **文件** | `xiaozhi_cli_client.py` | | **修复** | `additional_headers={"Device-ID": DEVICE_ID, "Client-ID": DEVICE_ID}` | ### 2.2 MCP Endpoint Token ✅ 已解决 | 项目 | 详情 | |------|------| | **症状** | `ERROR: token解密失败 1008` | | **根因** | URL 中 `+` 被解码为空格,base64 解析失败 | | **文件** | `xiaozhi-server/data/.config.yaml` | | **修复** | `+` → `%2B`,`=` → `%3D` | ### 2.3 MiniMax LLM 401 ❌ 未解决(根因已定位) | 项目 | 详情 | |------|------| | **症状** | LLM 返回 401 "令牌已过期或验证不正确" | | **根因** | `config_loader.py` 优先从 manager-api 获取配置,云端返回 `glm-4-flash`,覆盖本地 MiniMax 配置 | | **证据** | 请求日志中 `model: "glm-4-flash"`(而非 MiniMax-M2.5) | | **解法** | 升级到全模块安装,在智控台配置 MiniMax | --- ## 三、MiniMax LLM 401 深度分析 ### 当前配置加载逻辑 ``` 1. load_config() 读取 .config.yaml 2. 检测到 manager-api 有配置(url + secret) 3. 调用 get_server_config() 从 xinnan-tech API 获取设备配置 4. API 返回配置的 model: "glm-4-flash" 5. 覆盖本地 LLM 配置 6. xiaozhi-server 用 glm-4-flash + GLM API key 调 LLM → 401 ``` ### MiniMax API 验证结果 | 端点 | 状态 | 备注 | |------|------|------| | `api.minimaxi.com/v1/chat/completions` | ✅ 200 | MiniMax key 有效 | | `api.minimaxi.com/anthropic` | ✅ 200 | MiniMax Token Plan | | 容器内 urllib 直接调用 | ✅ 成功 | key 和网络均正常 | | 容器内 httpx 直接调用 | ✅ 成功 | key 和网络均正常 | | xiaozhi-server openai 库调用 | ❌ 401 | 因用的是 glm-4-flash 模型 | --- ## 四、下一步计划 ### 方案:升级到 xiaozhi-esp32-server 全模块安装(智控台) #### 为什么选这个方案 1. **路径最短**:当前已是最简化安装,升级到全模块架构改动最小 2. **MiniMax 原生支持**:智控台有原生日志配置页,TTS 有 `MinimaxTTS` 选项 3. **社区最大**:8k ⭐,文档完善,有中文社区支持 4. **功能完整**:智控台提供完整 Web UI,设备管理、模型配置、OTA 升级等 #### 部署要求 | 项目 | 最低配置 | 推荐配置 | |------|---------|---------| | CPU | 2核 | 4核 | | 内存 | 4GB | 8GB | | Docker | ✅ | ✅ | | 数据库 | 自动拉起 MySQL + Redis | 同左 | #### 部署步骤 1. 下载 `docker-compose_all.yml` 和 `config_from_api.yaml` 2. 配置 MySQL + Redis 容器 3. 启动 xiaozhi-esp32-server-web(智控台,端口 8002) 4. 访问 `http://:8002` 注册超级管理员 5. 从智控台复制 `server.secret` 到本地 `.config.yaml` 6. **在智控台配置 MiniMax API Key**(LLM + TTS) 7. 重启容器验证 #### MiniMax 集成方式 **LLM**:智控台 → 模型配置 → 新增 ```yaml type: openai model_name: MiniMax-M2.5 url: https://api.minimaxi.com/v1 api_key: sk-cp-Sd2G0paJUZWdQhKrISIICVqQnuiE4qvT-yMszahI7s0Sau02Pa1XZCXNsj2Z91n-xNV8hIG-xL8lENaEgFNQBZr7S6Y8_R7OASOScenpJIxxWOb6vc7sF38 ``` **TTS**:智控台 → 模型配置 → 语音合成 → 选择 `MinimaxTTS` --- ## 五、备选方案(备查) | 方案 | 特点 | MiniMax 难度 | 备注 | |------|------|------------|------| | **xinnan-tech 官方全模块** | 8k⭐,功能最全 | ⭐ 极易 | **推荐首选** | | **joey-zhou Java 版** | Web UI 最完整,716⭐ | ⭐⭐⭐ 中等 | 3 容器,Java 技术栈 | | **MiniMax-OpenPlatform 版** | MiniMax 官方深度定制 | ⭐ 零配置 | 强耦合 MiniMax,灵活性差 | --- ## 六、依赖信息 ### Docker 容器 ``` xiaozhi-esp32-server ghcr.nju.edu.cn/xinnan-tech/xiaozhi-esp32-server:server_latest ``` ### MiniMax API - Key 类型:Token Plan(sk-cp- 开头) - LLM 端点:`https://api.minimaxi.com/v1` - Anthropic 端点:`https://api.minimaxi.com/anthropic` ### mcp-endpoint-server - 端口:8004 - Token(已 URL 编码):`usxQ%2BQ7GkvPsndgGVZDZBCE1%2Bcp6w1dJKkmoj7EJCqM%3D`