# 接手摘要 · v0.3.2(第三轮:第二个朗读引擎) > **用途**:开新会话时,连同 [`交接摘要.md`](交接摘要.md) 一起贴给 AI。 > 本文只讲**上一轮干了什么**、**现在接着干什么**;项目全貌看 `交接摘要.md`。 --- ## 1. 一句话状态 **v0.3.2 已发布**(tag 已推、GitHub Release 已建、7 个附件齐全且与本机逐字节一致)。 工作区干净,`HEAD = origin/main = 3eb8caf`。 **只差一件事**:Release 正文缺三块(见 §3)。 --- ## 2. 上一轮做完的(不用再动) | # | 内容 | 提交 | | --- | --- | --- | | 1 | **新增第二个朗读引擎 MOSS-TTS-Nano**(CPU 就能跑):`lib/server/moss-tts-transport.js` + 配置 `engine`/`sovitsBase`/`mossBase` + `buildTtsTransport()` 分派 + 自检引擎感知 | `5b91b65` | | 2 | **MOSS 一键安装**:`tools/install-moss.ps1` + `tools/moss-tts-server/server.py` + `verify.py` + `docs/install-moss.md` | `5b91b65` | | 3 | **设置面板重做**:先配置后验证的顺序、改名、自检明细折叠、引擎优缺点对照卡、「复制安装说明」按钮、拆掉顶部大红框 | `5b91b65` | | 4 | **修两个 bug**:「重新自检」重置表单 / 自检不跟引擎走;并加了 **10 个回归测试**(`test/moss-tts.test.js`,全绿) | `5b91b65` | | 5 | **参考音频位置**定为 `~/.dsh/fairy-voice/reference/`,插件启动时自动建目录 + 写 `README.txt`;旧位置保留兼容回退 | `5b91b65` | | 6 | **文档拆分**:README 的「本地改动」97 行挪进 `docs\本地改动.md`,README 只留引用 | `20367f0` | | 7 | **新增 `docs\Release正文模板.md`**(起因:v0.3.1 和 v0.3.2 连着两次正文都没贴全) | 本轮 | | 8 | 用户自己改的:README 标题点出"可以不依赖显卡"、版本号 0.3.2 | `f5c8871` `9855232` | --- ## 3. ⚠️ 唯一未完成的事:Release 正文缺三块 **现状**:Release v0.3.2 正文只有 **1215 字符**,缺「📦 下载哪个?」「🚀 装完做什么」「🔐 SHA256」。 **精确步骤**(只能人工做,本机没有 `gh`、也没有 GitHub token): 1. 打开 2. 打开 `release\RELEASE-BODY-v0.3.2-补充.md`(**这个文件在 `release\` 里,不进 git**),全选复制 3. 粘到正文**最末尾**(已有内容不用动) 4. 点「**Update release**」 5. **附件一个都不用动**(已核对:7 个齐全、字节与 SHA 与本机一致) > 以后发版照 [`Release正文模板.md`](Release正文模板.md) 填,并过一遍它的「提交前自检」。 --- ## 4. 这一轮新学到的(重要,别再踩) ### 4.1 🔴 用户数据绝不能放进插件目录 起因:看到参考音频默认在 `~/.dsh/fairy-voice/reference/`,而插件装在 `~/.dsh/plugins/Fairy-DSH/fairy-voice/dsh-fairy-voice/`,**第一反应是"路径写错了"** —— 于是把默认位置往顶层挪了一次,后来发现 `~/.dsh/fairy-voice/` **本来就存在**(是插件的数据目录),又挪回来。 **真相**:两个路径**故意不同、也必须不同**。`dsh plugin add ` 会把包解进 **profile 下的 `node_modules`** —— 那是 **pnpm 随时会清掉/重建/按版本重装**的目录。 把音色、API Key 放进去 = 放在定时炸弹上,升一次版本就没了。 **规矩**:用户数据一律 `~/.dsh/fairy-voice/`。判据一句话: **任何会被 `pnpm install` / 插件重装影响到的目录,都不许放用户数据。** (已写进 `AGENTS.md` §5.4.1、`交接摘要.md` §9 坑 16、README「你的东西放在哪」) ### 4.2 MOSS 相关的坑(4 个,实测) | 坑 | 真相 | | --- | --- | | 官方 README 说"ONNX 版推理期不要 PyTorch" | **只对命令行成立**。`onnx_tts_runtime.py` 顶层硬 `import torch`;HTTP 服务还额外要 `transformers` | | `huggingface_hub` 装成最新的 1.x | **跑不了**:它传的 `local_dir_use_symlinks` 在 1.0 已被移除。**必须 `<1`** | | 用 `hf-mirror.com` 加速下载 | 证书**可能过期**。走**官方 + 梯子**(`HTTP(S)_PROXY`)更稳 | | 官方 `app_onnx.py` 在 Windows 上起不来 | 它预热时**强制**加载 WeTextProcessing,而 **`pynini` 在 PyPI 上没有任何 Windows 轮子**(实测 0 个 `win` 文件)。所以本仓库自带 `server.py` 绕开它 | ### 4.3 两个工具层面的教训 - **`$ErrorActionPreference='Stop'` + 原生命令**:git/uv/python 往 stderr 写进度是正常的, 但在 Stop 模式下会被当成**终止错误**、脚本当场退出(`install-moss.ps1` 第一版就死在这)。 改用 `Continue` + 每步显式 `$LASTEXITCODE` 判断。 - **`edit` 工具改嵌套 JSX 时,`old_string` 要卡在成对的边界上**: 这次我删多了,把「保存设置」按钮那段的开头一起替换掉,导致结构断裂 —— 靠 **`node --check` 立刻抓到**。改完必跑。 --- ## 5. 常用命令 ```powershell cd C:\Users\1\.dsh\plugins\Fairy-DSH # 改了 lib\settings-merge.ps1 之后必做(两个 client.js 都是生成物) . .\lib\settings-merge.ps1 Set-SettingsMerge -Root (Get-Location) -Mode merged -Snapshot -Force node --check .\fairy-visual\dsh-fairy-visual\lib\client.js node --check .\fairy-voice\dsh-fairy-voice\lib\client.js # 改了 .ps1 之后(edit 工具会丢 BOM) $p='lib\settings-merge.ps1' $t=[IO.File]::ReadAllText($p,[Text.UTF8Encoding]::new($false)) [IO.File]::WriteAllText($p,$t,(New-Object Text.UTF8Encoding($true))) $e=$null;[void][System.Management.Automation.Language.Parser]::ParseFile((Resolve-Path $p).Path,[ref]$null,[ref]$e);$e.Count # 跑测试(⚠️ 只跑新加的那个快的;全套含 performance 会跑很久) cd fairy-voice\dsh-fairy-voice node --test test\moss-tts.test.js # 打包 + 取 SHA cd ..\..\ ; .\pack.ps1 Get-Content .\release\SHA256SUMS.txt # MOSS 服务 & E:\MOSS-TTS-nano\start-moss.cmd # 启动(双击也行) & E:\MOSS-TTS-nano\venv\Scripts\python.exe E:\MOSS-TTS-nano\verify.py # 验证 Get-NetTCPConnection -LocalPort 18083 -State Listen # 看谁占着 # 推送(代理不通时直连反而能成功) git push origin main ``` --- ## 6. 环境事实(本机) | 项 | 值 | | --- | --- | | DSH | `0.1.2-rc.1`,GUI 在 `127.0.0.1:3080` | | live profile | `dsh-fairy-visual` / `dsh-fairy-voice` / `dsh-balance-meter` 以 **`link:`** 装入 | | **插件改动要重启 DSH 才生效** | `link:` 装法下改仓库文件不影响正在跑的实例 | | MOSS 安装位置 | `E:\MOSS-TTS-nano`(`venv\` + `repo\` + `server.py` + `verify.py` + `start-moss.cmd`) | | MOSS 服务 | `127.0.0.1:18083`。**本次会话启动的进程可能已不在** —— 用 `start-moss.cmd` 重起 | | 参考音频 | `~\.dsh\fairy-voice\reference\fairy_ref.wav`(+ `.txt` + `README.txt`) | | 当前引擎 | `moss-nano`(写在 `~\.dsh\fairy-voice\runtime\config.json`,有 `.bak`~`.bak4` 备份) | | 代理 | 梯子端口 `127.0.0.1:7897`;git 亦配了 `http.https://github.com.proxy` | --- ## 7. 已知欠债(都不急) | # | 事项 | 说明 | | --- | --- | --- | | 1 | **Release 正文补三块** | 见 §3,唯一"该做没做"的 | | 2 | **4 个上游陈旧测试一直红** | `test/index.test.js` 等,是**上游 2026-08-29 的原版**,从没跟着 v0.2.3 的重构更新过。它们断言的是旧写法(如 `const localTtsTransport = createLocalTtsTransport(`)。**修复它们 = 让测试套件重新有绿灯信号** | | 3 | MOSS 真流式 | 现在整句返回;要接它的 4 个 `generate-stream` 端点 | | 4 | 语音兜底引擎 | 浏览器 `speechSynthesis` + 自动降级(§6 中期目标) | | 5 | SoVITS 一键盘 | 与 MOSS 一键安装同思路,但 SoVITS 要显卡、6–9 GB | | 6 | `tag v0.3.2` 与 `main` 差 4 个提交 | 全是**纯文档**提交,不影响发布产物。**不建议 `git tag -f` 挪** —— 已发布的 Release 会跟着动 | --- ## 8. 交接时的一句提醒 `docs\交接摘要.md` 是**全量档案**(状态 / 待办 / 全部踩坑),本文只是**这一轮的增量**。 两者一起看,但**冲突时以本文为准**(它更新)。