docs: 固化抓包对照结论 —— 「走不动」在客户端物理层,不是服务端回弹

用新增的出站包抓取(1.8.0)做了三组对照 + 四方向逐包序列,结论与 TODO 原有框架相反,
先写进 TODO.md 免得下一个接手的人继续沿错误方向排查。

手动按住方向键 3 秒的实测(任务未启动、机器人空闲):
- 入站位置包 0 个 —— 服务端全程没插手,根本没有「回弹」
- 客户端自己的坐标与朝向一字未变;moveDiag.velocity 恒为 (0, -0.078, 0)
- 而 player_input 位标志是 backward: true —— 控制键确实按下去了
- 四方向位移 forward 0.02 / back 0.00 / left 1.22 / right 1.40(正常应约 12 格)

推论:
- 是客户端物理引擎没有把按键积分成位移(prismarine-physics 的 applyHeading
  没有产生水平速度),下一步要加 physicsDiag 直接看 physicsEnabled /
  physicsTick 计数 / simulate 前后 onGround / world.getBlock 命中 / control 快照;
- 服务端回弹只在「任务驱动移动」时出现(任务中入站 6/秒、出站 position_look 25/秒),
  是伴生现象而非病因,这与「两套地面修正开关对位移毫无影响」的实测一致;
- 原记的「手动按键移动完全正常(forward 2 秒 4~8 格)」已不成立,该基准需重建。

顺带记下两条协议事实:flags.hasHorizontalCollision 恒为 0(mineflayer 写成 undefined),
teleport_confirm.teleportId 是该服务端自定义的大负数。
这个提交包含在:
lyizai
2026-09-29 22:08:50 +08:00
父节点 8ab2d59eb0
当前提交 0c6700642e
+44 -2
查看文件
@@ -141,9 +141,51 @@ ls -1d /opt/autostore-bot/backup-* 2>/dev/null | tail -3
--- ---
## 1. 🟡 「机器人走不动」:本轮已实现两套修正 + 备选执行器,**待线上实测确认** ## 1. 🔴 「机器人走不动」:**已实测定位到客户端物理层**(不是服务端回弹,见本节开头的实测补充)
### 现象回顾 ### ⚠️ 线上实测补充(2026-09-29,**先读这段:它推翻了下面原有的框架**)
用新增的**出站包抓取**(`POST/GET /api/bots/:id/capture`,见 CHANGELOG [1.8.0])做了对照,
结论是:**「走不动」不是服务端回弹造成的,是客户端物理引擎没有把按键积分成位移。**
手动按住一个方向键 3 秒的逐包实测(任务未启动、机器人空闲):
| 项 | 实测 |
| --- | --- |
| 入站位置包(服务端回弹) | **0 个** —— 服务端全程没插手 |
| 出站位置包 | 5 个,全是 1 秒一次的空闲包(**不是**每 tick 一个) |
| 客户端自己的坐标 | **完全没变**(`6752.3000, 146, 11922.3000` → 一字不差) |
| 朝向 | 完全没变(`-0.20876`) |
| `moveDiag.velocity` | 恒为 `(0, -0.078, 0)`,`speed = 0.078` |
| `player_input` 位标志 | `backward: true` ✅ —— 控制键确实按下去了 |
四方向各按 3 秒的位移:`forward 0.02 / back 0.00 / left 1.22 / right 1.40`(正常应约 12 格)。
**推论:**
1. `player_input` 如实上报了输入、`bot.getControlState()` 也是 true,
但 `prismarine-physics` 的 `applyHeading` 没有产生任何水平速度 ——
要么物理引擎拿到的 `control` 快照里 `forward/back` 是 0,
要么 `moveEntity` 把位移全吃掉了。**下一步要加 `physicsDiag` 直接看**:
`bot.physicsEnabled`、每 tick 的 `physicsTick` 计数、simulate 前后 `onGround`、
`world.getBlock(脚下)` 是否命中、以及 PlayerState 里读到的 `control` 快照。
2. **「服务端回弹」只在寻路任务运行时出现**(实测任务中入站 6/秒、出站 `position_look` 25/秒),
手动移动时入站为 **0** —— 回弹是「任务驱动移动」的伴生现象,**不是走不动的原因**。
这也解释了为什么下面两套针对回弹的修正(方案 A/B)开关对位移毫无影响
(实测:修正开 0.4~6.4 格 / 修正关 0.4~2.4 格,同量级)。
3. 原先记的「手动按键移动完全正常(forward 2 秒 4~8 格)」**已不成立**,
该基准需要重建 —— 基于它的推理(「规划问题 vs 协议问题」二分)也就全部偏了。
**顺带确认(1.21.4 协议):**
- `flags.hasHorizontalCollision` 恒为 `null`(= 0):mineflayer 在 `physics.js` 里
把它写成 `undefined`,而原版客户端会在水平碰撞时置位;实测 62/62 个位置包都是 0。
- `teleport_confirm.teleportId` 是大负数(如 `-1884468723`):该服务端用的是随机大整数,
不是原版的自增小整数,属于它自己的实现,不是 bug,但排查时别按原版预期去读。
- 包类型分布对照(5 秒):空闲 `player_input/tick_end/pong ≈ 100` 且 `position=5`;
手动按键与空闲同构(**没有** `position_look`);寻路中才有 `position_look=126`。
### 现象回顾(历史记录;其中「手动移动正常」已被上面的实测推翻)
- **手动按键移动完全正常**:通过控制台「移动测试」按 forward 2 秒,实测位移 4~8 格,位置保持。 - **手动按键移动完全正常**:通过控制台「移动测试」按 forward 2 秒,实测位移 4~8 格,位置保持。
- **寻路器驱动的移动被回弹**:一旦 `bot.pathfinder.setGoal()` 开始执行, - **寻路器驱动的移动被回弹**:一旦 `bot.pathfinder.setGoal()` 开始执行,