docs(05): 锚点补记三十五 —— 模拟器已切真后端(含全角冒号坑与「未知错误」根因);主人报的标签解析 bug 定位到后端畸形 markup <p><p>正文</p> 并已容错修复 + 真机验收;W54A/C/D + W55 + W56 五支合并推送(112/1361 绿);模拟器卡的原因诊断
This commit is contained in:
1 parent
a60e3abc12
commit
5f7489d70e
1 file changed
+77
@@ -1816,3 +1816,80 @@ adb shell dumpsys activity services top.yeij.cyrene | grep -E "KeepAliveService|
|
|||||||
- 模拟器 `emulator-5554` 在跑;App pid **25584**、`KeepAliveService` 在、App 在**后台**(前台是 launcher)。
|
- 模拟器 `emulator-5554` 在跑;App pid **25584**、`KeepAliveService` 在、App 在**后台**(前台是 launcher)。
|
||||||
- 假后端 `127.0.0.1:18090` 活着(**store 已清空**:`sessions[].messages = 0`,说明它重启过,App 会自愈重连,对保活判定无影响);真后端 `10942` 活着、**没碰**。
|
- 假后端 `127.0.0.1:18090` 活着(**store 已清空**:`sessions[].messages = 0`,说明它重启过,App 会自愈重连,对保活判定无影响);真后端 `10942` 活着、**没碰**。
|
||||||
- ⚠️ **22:13 长跑复查之前不要操作 App 前台**(一操作就把「后台存活」的基线破坏了)。S4 对照组同理,**排到长跑之后**。
|
- ⚠️ **22:13 长跑复查之前不要操作 App 前台**(一操作就把「后台存活」的基线破坏了)。S4 对照组同理,**排到长跑之后**。
|
||||||
|
|
||||||
|
## ★★ 锚点补记三十五 · 切真后端 + 标签解析 bug(已修已验)+ W54/W55/W56 五支落地(2026-10-06 21:45)
|
||||||
|
|
||||||
|
> 本节是三十四之后的实况:**模拟器现在连的是真后端**,主人报的「标签解析小问题」已定位到根因并修完验完。
|
||||||
|
|
||||||
|
### 1. 五支全部合并推送(`a60e3ab` = `origin/android`)
|
||||||
|
|
||||||
|
| 支 | 内容 | 提交 |
|
||||||
|
|---|---|---|
|
||||||
|
| **W54A** | 通知「一事一条」:通知 id 与 `PendingIntent` requestCode 按消息**稳定派生**(`proactiveNotificationId(key)`,先展宽 Long 再 `%` 落到 `[1000, 2e9+999]`,避开保活的 1 / 0) | `53339b3` |
|
||||||
|
| **W54C** | 转屏不再静默丢掉「已取走的分享」:面板状态与描述移进 `ChatUiState.shareConfirm`(`ShareConfirmDraft` + 纯函数 `shareConfirmClaim`),**`take()` 仍只发生一次** | `1142bf5` |
|
||||||
|
| **W54D** | 分享面板正文预览:3 行高度上限 + **内部滚动**(`cap` 由 `TextLayoutResult` 量出,非写死 dp) | `ec89d82` |
|
||||||
|
| **W55** | **解析器剥掉落单标签**(本节的 bug①) | `464e916` |
|
||||||
|
| **W56** | 分享面板预览加**展开/收起**(主人拍板「可以滚动 可以展开」的后半) | `14955ef` |
|
||||||
|
|
||||||
|
- 合并后主树全量真跑:**112 suites / 1361 tests / 0 failures / 0 errors**。
|
||||||
|
- worktree / 分支 / 构建锁**全清**(`git worktree list` 只剩主树)。
|
||||||
|
- ⚠️ **worktree 目录删除在 Windows 上会因长路径失败**(`git worktree remove` 报 `Filename too long`,`cmd rmdir`、`robocopy /MIR`、`Remove-Item` 都不行)。**可用的招**:`find <dir> -depth -delete`。注册表用 `git worktree prune` 清。
|
||||||
|
|
||||||
|
### 2. 模拟器已切到真后端(主人 2026-10-06 晚要求)
|
||||||
|
|
||||||
|
**怎么切的**(App 设置页里**没有**「服务器地址」栏,改地址只能走登出):
|
||||||
|
|
||||||
|
1. 抽屉 →「App 设置」→ 滚到底 →「退出登录」→ 确认框点「退出登录」;
|
||||||
|
2. 登录页填地址 / 用户名 / 密码 → 登录。
|
||||||
|
|
||||||
|
**⚠️ 踩到的坑(下次照抄结论)**:`adb shell input text "localhost:10942"` 里的 `:` 会被**中文输入法转成全角 `:`(U+FF1A)**,于是地址成了 `localhost:10942` → URL 非法 → Retrofit 抛 `IllegalArgumentException` → `mapException` 的 `else` 分支 → 界面显示**「发生未知错误」**(`CyreneError.LocalKind.Unknown`)。
|
||||||
|
**排查凭证**:`uiautomator dump` 读出 EditText 的真实值 = `localhost\uff1a10942`(转义后一眼看到全角)。
|
||||||
|
**绕法(已采用)**:把 `tcp:80` 直接转发到真后端,地址只填 `localhost`(纯 ASCII,无冒号):
|
||||||
|
```
|
||||||
|
adb reverse --remove tcp:80 && adb reverse tcp:80 tcp:10942
|
||||||
|
```
|
||||||
|
**当前转发**:`tcp:80 → tcp:10942`(真后端)、`tcp:10942 → tcp:10942`。⚠️ **假后端 18090 因此失去了 `tcp:80` 映射**,要回去用假后端得把这条改回来。
|
||||||
|
|
||||||
|
**当前登录态**:真后端、账号 `yeij0942`(`role=owner`),主会话 `web`。宿主机直连验证:`POST http://127.0.0.1:10942/api/v1/auth/login` → **200** `{token,expiresAt,role:owner,refreshToken}`。
|
||||||
|
|
||||||
|
### 3. bug① 「标签解析」——根因、证据、修复、验收(**这是主人报的那条**)
|
||||||
|
|
||||||
|
**现象**:气泡正文里**字面显示** `<p>那现在——想让人家陪你看会儿晚霞,还是安静坐着发会儿呆?`。
|
||||||
|
|
||||||
|
**根因(服务端产出的 markup 畸形)**:从真后端拉到的那条消息 `content` 逐字节是
|
||||||
|
```
|
||||||
|
<p><action>满意地点点头</action></p>\n<p>真乖♪ …放心的一句。</p>\n<p><p>那现在——…发会儿呆?</p>
|
||||||
|
```
|
||||||
|
第三段 = **`<p><p>` 两个开标签、一个 `</p>`**。客户端 `ChatContentParser.kt:70` 的 `P_BLOCK_RE` 是**非贪婪**的,必然把内层裸 `<p>` 收进本段正文,于是标签被当正文渲染。
|
||||||
|
|
||||||
|
**修(客户端容错,`464e916`)**:只剥**完整匹配标签正则**的落单 `<p>` / `<p 属性>` / `</p>`(有完整块时也剥块外未认领的旁白标签);`1 < 2`、`<3`、`a<b`、`<p2>`、`<P>`(大写,有既有反契约)、残缺 `<p` 一律**原样保留**。17 条新单测。
|
||||||
|
- **流式那条**:`stablePrefixEnd()` **一行未改**,理由写进了 KDoc(前缀里每个开标签都已配对 ⇒ 中间态不存在「还没定死的落单标签」;而 `<p><p>…` 这种扣留点是 0,中间态压根不产帧,谈不上跳动)。子代理**评估并否决**了「放宽扣留让正文更早流出」的方案(会引入字面标签闪现)。
|
||||||
|
|
||||||
|
**真机验收(`emulator-5554` + 真后端)**:装新 APK 后打开主会话,那条消息现在渲染成
|
||||||
|
`那现在——想让人家陪你看会儿晚霞,还是安静坐着发会儿呆?`(干净无标签),旁边那条旁白/两段仍各就各位。
|
||||||
|
|
||||||
|
**已登记给后端**(`devdocs/02`,本节末尾:**「客户端登记(2026-10-06 晚 · 在途消息出现 markup 畸形…)」**,含逐字节凭证、为什么「任何按契约实现的消费方都会踩」、我们已容错不需要他们动作、以及问他们**两件事**:① 是拼接 bug 还是有意形状?② 若是 bug 能否修在产出侧?)。
|
||||||
|
⚠️ **这一节我没有提交**:`devdocs/02` 工作区里压着**后端会话的在途改动**(8 个 hunk,最后一支延伸到文件末尾),提交会跟它打架。内容已写入磁盘文件,提交留给掌握该文件的会话。
|
||||||
|
|
||||||
|
### 4. bug②(顺带诊断)模拟器为什么卡 —— 不是分配少了
|
||||||
|
|
||||||
|
**证据(宿主 `Get-Process` 按累计 CPU 排序)**:同时跑着 `cs2`(游戏,34837 s)、`llama-server`(本地模型,53186 s)、com.docker.backend、GameViewer、加速器,**并且当前是 RDP 会话**(`query session` → `rdp-tcp#1` 为当前;`emulator.exe` / `qemu-system-x86_64.exe` 都跑在 RDP 会话里)。
|
||||||
|
- AVD 配置本身不寒酸:`hw.ramSize=8192`、`hw.cpu.ncore=5`、`hw.lcd=1080x2340@440`;模拟器内 `top` 显示 idle 仍有 **398%**(CPU 不是瓶颈)。
|
||||||
|
- `emulator -accel-check` → **WHPX 可用**(硬件加速正常)。
|
||||||
|
- **主因判断**:RDP 会话下 GPU 加速路径退化 + 宿主的游戏/模型/Docker 抢资源;我这边并行跑的 Gradle 构建也在抢。
|
||||||
|
- **已做(无损)**:`settings put global {window,transition,animator}_animation_scale 0`(关动画,UI 立刻跟手,不改分辨率所以坐标不变)。
|
||||||
|
- **没做(要重启模拟器,得主人点头)**:换 `-gpu angle_indirect`、或降 `hw.lcd` 分辨率/密度。⚠️ 重启模拟器**必然杀 App**。
|
||||||
|
|
||||||
|
### 5. 环境现状(动手前照核)
|
||||||
|
- HEAD = **`a60e3ab`** = `origin/android`;主仓唯一脏 = `devdocs/02`(**后端在途 + 我这一节的登记**)。
|
||||||
|
- 模拟器 `emulator-5554` 前台是 App;App 已装**合并后**的 APK(`adb install -r` 会杀进程,**不是 bug**)。
|
||||||
|
- ⚠️ **保活长跑基线(20:13:35 / pid 25584)已被打断两次**:主人自己把 App 切到前台;以及我 `adb install`。那个 22:13 的复查任务结果**只能当「装包后重启的 App 能不能重新连上」看**,不能再当「后台存活」的证据。
|
||||||
|
- 假后端 18090 进程仍在,但**已不在 App 的路径上**。
|
||||||
|
|
||||||
|
### 6. 待办(更新后)
|
||||||
|
1. **等主人真机验收**(他自己看,我不截图代替):分享面板「3 行窗口 + 内部滚动 + 展开/收起」(W54D + W56);退出登录确认框;保活文案。
|
||||||
|
2. **等后端回执**:`.end` 的 `resultSummary`、`channel_persisted` 是否带 `proactive`、实时帧 id 与落库 id 同源、**以及本节 3 的两问(markup 畸形)**。
|
||||||
|
3. **W56 留下的已知取舍**:分享面板的**展开态不跨转屏**(状态在 `remember(preview.text)`;跨转屏要么进 `ChatUiState`(红线)要么 `rememberSaveable`(本仓零先例)→ **待主人定要不要做**);展开态上限 240dp **没在真机上量过**。
|
||||||
|
4. **批 2(未开)**:订阅提到进程级(Activity 被划掉后收不到帧)。W54A 已合入,`AppContainer.kt` 的冲突面解除,可以开了。
|
||||||
|
5. **S4 回收对照组**(设备侧,随时可做,长跑已无基线可言)。
|
||||||
|
6. **推送**:主人继续研究,等他。
|
||||||
Reference in new issue
Block a user