项目叫喵艺。地址:github.com/Yizhimao626…
先说实话:这不是一个"重新定义 AI 陪伴"的东西,也不是什么颠覆性产品。它就是一个我自己写着写着越写越大的聊天应用,前后端、安卓包、语音、记忆全都自己搭的。写完觉得还行,就开源了。
它和普通聊天框的区别
普通聊天机器人有个共同毛病:你说十句,它回十句,但你明天再来,它什么都不记得,语气也没变过。
喵艺在这几个地方做了点不一样的事:
情绪是四个维度,而且会衰减。 joy、arousal、intimacy、trust,各自有独立的变化速率。你夸它一句,joy 上去;冷落它半天,会慢慢回落;吵一架,亲密度真的会掉,之后几轮回复明显更冷。这些值会写进系统提示词,直接影响它说话的长短和语气。
记忆不是存了就完。 每条记忆带情绪标签和时间,检索时同时看语义相似度和当时的情绪强度。记忆会以卡片形式推回前端,你能看见它"想起了什么"。
它会主动找你,但有纪律。 沉默超过一段时间会触发,不过加了硬限制:任何一小时内最多两条,23 点到早 8 点不发,攒到早上合成一条早安。不这么限,半夜能被它刷屏。
语音是一条降级链。 CosyVoice2 → GPT-SoVITS → Edge TTS → 百度 → 本地 → gTTS,哪一级没配 key 或挂了就自动往下走,不会出现"通话连上了但没声"。
再加上表情包、语音通话、成长等级、关系阶段这些,整体是个能过日子的东西,而不是一个 demo。
技术上是怎么搭的
后端是 FastAPI,前端 React 19 + TypeScript + Zustand,安卓用 Capacitor 打包,数据默认 SQLite、生产可切 MySQL。
模型这块做成了供应商池:智谱、DashScope、DeepSeek、Moonshot 四家写进配置,按顺序故障转移,某个供应商 429 或超时就进 60 秒冷却,自动切下一家。没配 key 的条目启动时直接跳过,所以只配一家也能跑。
同一个池子还按"角色"分工,一共八个:
| 角色 | 干什么 |
|---|---|
| chat | 说话主力,流式输出 |
| light | 寒暄、意图分类,用便宜快的模型 |
| inner | 内心独白,先想后说 |
| think | 深度推理 |
| emotion | 情绪识别,返回结构化 JSON |
| tool | 决定要不要查天气/搜索 |
| memory | 记忆质量门 |
| proactive | 主动消息 |
换模型只改一行配置,不用碰业务代码。
还有一个零成本体验模式:MIAOYI_MOCK_LLM=1。不配任何 API key 也能启动,全流程都能走通,只是回复是模板。想先看看界面长什么样,用这个就够了。
踩过的坑,都是真的
写的过程中修了不少东西,挑几个有代表性的:
两个标签页互相踢。 早期 WebSocket 一个账号只允许一个连接,开第二个标签就把第一个踢掉,前端立刻重连,再被踢,形成每秒一轮的乒乓。服务器日志像卡带一样刷屏。后来改成同账号多连接并存,加了 10 条上限。
图片上传一直 500。 接口返回里写了个不存在的变量 file_size,文件其实已经存进磁盘了,但接口报错,用户以为发失败。这个 bug 活了很久,因为没人真的去测返回值。
记忆淘汰功能从来没生效。 整理记忆的函数里把 uid 写成了 user_id,NameError 被外层 except 吞掉,existing_facts 永远是空字典。也就是说"旧记忆被新对话推翻就淘汰"这条逻辑,从写出来那天起就没跑过,而且一声不响。
后两个是跑 ruff 才发现的。所以现在 CI 里加了静态检查,专门拦"未定义变量"这类会导致运行时崩溃的问题。
App 登录点了没反应。 请求到后端了,token 也签发了,日志显示登录成功,但前端毫无反应。原因是 Capacitor WebView 的 Origin 是 http://localhost,服务端 CORS 没放行这批 Origin,响应被浏览器拦掉了。
误提交了数据库文件。 SQLite 的 WAL 文件跟着进了 git,里面可能有聊天记录。已经重写了一遍历史,也在给 GitHub 提工单清缓存对象。这事挺丢人,但既然开源了,说清楚比藏着好。
怎么跑起来
git clone https://github.com/Yizhimao626/miaoyi.git
cd miaoyi
pip install -r requirements.txt
MIAOYI_MOCK_LLM=1 python server.py
浏览器打开 http://127.0.0.1:8001,注册个账号就能聊。想用真模型,把 .env 里的 key 填上就行,配置说明在 docs/CONFIGURATION.zh-CN.md,接口说明在 docs/API.zh-CN.md。
它现在还不行的部分
- 没有在线试玩。境内公网跑生成式 AI 服务要备案,个人项目搞这个不划算,所以只能本地跑。
- mock 模式看不出猫娘味。回复是模板,情绪和记忆的联动也得接真模型才有感觉。
server.py是个 200KB 的单文件。这是历史包袱,我知道不专业,重构要动的东西太多,暂时没做。别学。- 测试覆盖不够。现在 CI 里跑三十来项,集中在关键回归路径,情感和记忆的深层逻辑还没覆盖。