docs(07-08): revise test route to teleport (2,0) and register self-target defect

This commit is contained in:
unanmed 2026-09-15 21:57:44 +08:00
parent 123493ccb4
commit 4a25e2e794

View File

@ -18,7 +18,7 @@ estimate:
must_haves:
truths:
- "core.ts 已提供 useMapState(this.maps) 与 usePassPredicate(new DefaultPassPredicateImpl(this.maps)),且 useMapLayer(null) 为有意设计(勇士初始不在任何楼层,待切层时再设置)"
- "测试在楼层激活后把 map.eventLayer 绑定到 finder顶层录像瞬移可解析出路径并到达 (1,0)(不再告警 173、不再下发 2005"
- "测试在楼层激活后把 map.eventLayer 绑定到 finder顶层录像瞬移可解析出路径并到达 (2,0)(不再告警 173、不再下发 2005"
- "重命名后的用例不再以 it.skip 存在wireFinder=true 的既有兄弟用例一字未改"
- "pnpm test:ci 全绿,且本计划不新增任何 it.skip"
- "AI 未修改任何生产源码;楼层切换重注入缺口作为用户负责项在 SUMMARY 登记,本阶段不修复"
@ -35,6 +35,7 @@ must_haves:
- "FIX-01 探针未分类:本计划以显式假设承接,即 FIX-01 = 「登记缺陷的正确预期 skip 用例转绿且不新增跳过」"
- "core.ts:238 useMapLayer(null) 属有意设计(源码注释:初始状态下勇士不在任何楼层,切换楼层后再具体设置);本计划保持 core.ts 原样,由测试侧显式绑定事件层来验证真实装配"
- "楼层切换时事件层会变化gameMap.ts:43 的 eventLayer仓库内除测试外没有任何生产调用点重新调用 useMapLayer。该重注入缺口是已登记的用户负责后续项不在本阶段AI 不实现、不评价其设计)"
- "路由修订用户裁决D-09 首跑证实接线有效(不再告警 173`finder.find``startIndex === targetIndex` 早退返回空数组(`finder.ts:150`)、`teleportTo` 据此返回 null 并下发 2005致使 sandbox 挂起;故把瞬移目标由 `(1,0)` 改为 `(2,0)`,断言随之改为 `x=2`/`y=0`。该自目标空路径行为属未登记缺陷,用户裁决「仅登记不修」"
prohibitions:
- "AI 不修改 packages-user/data-state/src/core.ts 或任何生产源码;接线已是用户产出(提交 1ff22dd本计划不追加、不调整、不重注入"
- "不新增测试用例D-10本次只取消一条既有 skip 并重命名,且只允许对 createSmallMapScene 做「返回 map」的加法式变更"
@ -95,7 +96,7 @@ Output: 接线事实与「layer 有意为 null」的确认 + 测试侧绑定 `ma
② 由此的必然结果:`finder.find` 在 `layer``null` 时进入 `finder.ts:212-215` 的告警 173 早退分支并返回空数组,顶层录像瞬移随之下发 2005——仅取消 skip、不绑定事件层仍会红。
③ 用户已确认的处置方式(本计划据此执行):**保持 `core.ts` 原样**;在**测试侧**于楼层激活后调用 `state.pathfinding.finder.useMapLayer(map.eventLayer)`,并把用例从 `plays a teleport step without manual finder wiring` **重命名为** `plays a teleport step after the event layer is bound on floor activation`(名字须反映其不再宣称「无需手动接线」)。
④ 需要登记的用户负责项(本阶段**不修复**`core.ts:238` 的 `useMapLayer(null)` 是一次性注入,楼层切换时事件层会变化(`gameMap.ts:43`),仓库内除测试外没有任何生产调用点在切层时重新注入;该缺口归用户所有,在 SUMMARY 登记为后续项,且不新建账本条目。
⑤ 验证方式:取消 skip 后运行该文件确认转绿;断言一字不改(`x` 为 1、`y` 为 0
⑤ 验证方式与路由修订D-09 首跑已证实):接线有效(绑层后不再告警 173但原路由 `[Right, Teleport(1,0)]` 的瞬移目标与 `Right` 后勇士所在格 `(1,0)` 相同,`finder.find((1,0),(1,0))` 因 `startIndex === targetIndex` 早退返回空数组(`finder.ts:150``teleportTo` 据空路径返回 null`system.ts:96-98`)→ 2005 → `ReplaySandbox.step` 返回 false、`ending` 未置位、`waitForEnded` 抛 `replay sandbox did not end`。故按用户裁决**改瞬移目标为 `(2,0)`**,断言改为 `x` 为 2、`y` 为 0
⑥ 失败纪律若绑定事件层后用例仍红AI 必须**退出本计划**、如实汇报观测到的告警码与路径结果,并等待用户修订接线或修订本计划;**不得**自行修改 `core.ts`、不得改断言D-07/D-09
⑦ 账本事实:`#06-07-1` 在 WINDOWS.md 中无对应条目D-14 的 waive 没有可 waive 的对象;按用户确认不新建条目(避免抬高 `open_count` 门禁),改为在本计划 SUMMARY 记录用户负责项与验证结果。请用户确认。
</action>
@ -152,12 +153,13 @@ Output: 接线事实与「layer 有意为 null」的确认 + 测试侧绑定 `ma
- packages-user/data-system/src/path/finder.ts:121-123 useMapLayer 接受 IMapLayer | null、:209-215 layer 为 null 时告警 173 并返回空数组)
</read_first>
<action>
仅改 `replayPlayback.test.ts` 一个文件,做处加法式/最小变更,不动生产源码(`core.ts` 为用户产出,保持原样):
仅改 `replayPlayback.test.ts` 一个文件,做处加法式/最小变更,不动生产源码(`core.ts` 为用户产出,保持原样。注意D-09 首跑已证实——绑层后告警 173 消失(接线有效),但原路由 `[Right, Teleport(1,0)]` 的瞬移目标与 `Right` 后勇士所在格 `(1,0)` 相同,`finder.find((1,0),(1,0))` 因 `startIndex === targetIndex` 早退返回空数组(`finder.ts:150``teleportTo` 据空路径返回 null 并下发 2005`sandbox.step()` 返回 false 致 `ended` 永假、`waitForEnded` 抛 `replay sandbox did not end`。故按用户裁决**改瞬移目标**(见 (b2)
(a) 让 `createSmallMapScene`:85**返回 `map`**:在函数体末尾(`resetHero(state)` 之后,且仍在 `if (!map || !map.eventLayer) throw` 造成的非空收窄范围内)加 `return map;`。既有调用方 :287/:302/:320 忽略返回值,不受影响;`withReplayDisabled`:71-78返回 `action()` 的返回值,故返回值可穿透该包装器。
(b) 在目标用例中捕获该 map 并在**楼层激活后**显式绑定事件层:把 `withReplayDisabled(state, () => createSmallMapScene(state, false));` 改为捕获返回值的形式(`const map = withReplayDisabled(state, () => createSmallMapScene(state, false));`),随后在 `runHeroStep`/`replay.record`/`playRoute` **之前**调用 `state.pathfinding.finder.useMapLayer(map.eventLayer);`。`wireFinder = false` 保持不变——该用例刻意不依赖 createSmallMapScene 内部的手动注入,只补上事件层。
(b2) 修正路由使瞬移目标 ≠ 勇士当前格:前置 `runHeroStep(state, FaceDirection.Right)` 后勇士位于 `(1,0)`,故把 `replay.record(ReplayCommandCode.Teleport, 1, 0)` 的目标改为 `(2,0)`(第二参数写 2并把断言 `expect(state.hero.location.x).toBe(1)` 改为 `toBe(2)``y` 仍为 0。这是用户裁决的「改瞬移目标」方案用于规避 `finder.find``startIndex === targetIndex` 空路径早退(非 #06-07-1属未登记的自目标行为
(c) 取消 skip 并重命名:`it.skip('plays a teleport step without manual finder wiring', ...)` 改为 `it('plays a teleport step after the event layer is bound on floor activation', ...)`;同步把 :360-361 的中文注释从「疑似缺陷 #06-07-1 …… 修复后取消 skip」改为中性描述说明本用例在楼层激活后由测试侧绑定事件层、验证顶层录像瞬移仍可解析并到达目标不得再出现「疑似 bug / 待修复」措辞。
断言保持一字不改(`expect(state.hero.location.x).toBe(1)``expect(state.hero.location.y).toBe(0)`);不改 :108-114 的 `wireFinder` 分支;不改该文件任何其它用例;不新增用例;不改任何生产源码;不引入新依赖、不新建文件。
断言随路由修订为 `expect(state.hero.location.x).toBe(2)``expect(state.hero.location.y).toBe(0)`(用户已授权「改瞬移目标」,用于规避自目标空路径;除此之外断言不再另改);不改 :108-114 的 `wireFinder` 分支;不改该文件任何其它用例;不新增用例;不改任何生产源码;不引入新依赖、不新建文件。
若用例仍红:立即停止并按 Task 0 的第 ⑥ 条退出汇报(记录实际告警码、找到的路径与首个分歧),不得改断言、不得改 `core.ts`
@ -171,7 +173,8 @@ Output: 接线事实与「layer 有意为 null」的确认 + 测试侧绑定 `ma
- `replayPlayback.test.ts``plays a teleport step without manual finder wiring` 已不存在;`it('plays a teleport step after the event layer is bound on floor activation', ...)` 不以 `.skip` 存在(源码断言:该行不含 `.skip`
- `createSmallMapScene` 返回 `map`,且目标用例在 `playRoute` 之前调用 `state.pathfinding.finder.useMapLayer(map.eventLayer)`
- `core.ts` 保持原样(`:236` 提供 `useMapState`、`:239-240` 提供 `usePassPredicate`、`:238` 的 `useMapLayer(null)` 不变)
- `pnpm exec vitest run packages-user/data-state/test/replayPlayback.test.ts` 全绿,且断言未被改写
- 目标用例的瞬移目标为 `(2,0)``replay.record(ReplayCommandCode.Teleport, 2, 0)`),断言为 `x=2`/`y=0`
- `pnpm exec vitest run packages-user/data-state/test/replayPlayback.test.ts` 全绿
- 本计划未修改任何生产源码(以本计划提交 sha 核验:`git show --name-only <本计划提交 sha>` 仅含该测试文件与 .planning 文档)
</acceptance_criteria>
<done>用例已重命名并在测试侧绑定事件层后转绿,三个 `wireFinder=true` 兄弟用例未改动,且未触碰任何生产源码;已一个原子提交入库</done>
@ -193,8 +196,9 @@ Output: 接线事实与「layer 有意为 null」的确认 + 测试侧绑定 `ma
在 SUMMARY 中记录以下四类内容:
① 已确认的接线事实(源码逐字):`core.ts:236 pathfinding.finder.useMapState(this.maps)`、`:238 pathfinding.finder.useMapLayer(null)`(含中文注释原意:初始状态下勇士不在任何楼层,切换楼层后再具体设置)、`:239-240 usePassPredicate(new DefaultPassPredicateImpl(this.maps))`;用户接线提交 `1ff22dd`
`core.ts``layer``null` 是**有意设计**(非遗漏),因此单纯取消 skip 仍会命中 `finder.ts:212-215` 的告警 173 → 空路径 → 2005。
③ 本计划的测试侧处置:`createSmallMapScene` 返回 `map`(加法式);目标用例在楼层激活后调用 `state.pathfinding.finder.useMapLayer(map.eventLayer)`;用例由 `plays a teleport step without manual finder wiring` 重命名为 `plays a teleport step after the event layer is bound on floor activation`断言未改
③ 本计划的测试侧处置:`createSmallMapScene` 返回 `map`(加法式);目标用例在楼层激活后调用 `state.pathfinding.finder.useMapLayer(map.eventLayer)`;用例由 `plays a teleport step without manual finder wiring` 重命名为 `plays a teleport step after the event layer is bound on floor activation`瞬移目标由 `(1,0)` 改为 `(2,0)`、断言改为 `x=2`/`y=0`(用户裁决的「改瞬移目标」)
④ 剩余的用户负责缺口(本阶段**不修复**`core.ts:238` 的一次性 `useMapLayer(null)` 在楼层切换(`gameMap.ts:43` 的 `eventLayer` 变化时不会被重新注入仓库内无对应生产调用点登记为用户负责后续项D-14 账本无 `#06-07-1` 条目、不新建。
⑤ 未登记缺陷登记(本阶段**不修复**仅登记D-09 首跑发现 `PathfindingSystem.teleportTo` 对「空路径 / 瞬移目标等于勇士当前格」返回 null`system.ts:96-98`,源于 `finder.find``startIndex === targetIndex` 早退,`finder.ts:150`),进而下发 2005并使 `ReplaySandbox.step` 返回 false、`ending` 未置位、`waitForEnded` 抛 `replay sandbox did not end`。该行为属未登记缺陷、超出 `#06-07-1` 范围,用户裁决为「仅登记不修」,登记于 SUMMARY。
</action>
<verify>
<automated>pnpm test:ci</automated>
@ -204,7 +208,7 @@ Output: 接线事实与「layer 有意为 null」的确认 + 测试侧绑定 `ma
- `pnpm exec eslint` 对该文件 0 错误
- `pnpm exec vue-tsc --noEmit` 按该文件路径过滤后无命中
- `pnpm test:ci` 全绿,且本计划未新增 `it.skip`
- SUMMARY 含①接线事实(`1ff22dd` 与三处实参、②layer 有意为 null、③测试侧绑定与重命名、④楼层切换重注入的用户负责缺口登记
- SUMMARY 含①接线事实(`1ff22dd` 与三处实参、②layer 有意为 null、③测试侧绑定 `(2,0)` 目标与重命名、④楼层切换重注入的用户负责缺口登记、⑤`teleportTo` 自目标空路径缺陷登记(不修)
</acceptance_criteria>
<done>D-44 三步全过、全量套件绿、四类登记内容均写入 SUMMARY提交粒度按 D-13 一个缺陷一个原子提交)</done>
</task>
@ -232,6 +236,7 @@ Output: 接线事实与「layer 有意为 null」的确认 + 测试侧绑定 `ma
- `core.ts` 中存在 `useMapState``:236`/`useMapLayer(null)``:238`/`usePassPredicate``:239-240`)三处注入(用户产出,本计划只读)
- `replayPlayback.test.ts` 的目标用例已重命名为 `plays a teleport step after the event layer is bound on floor activation` 且不以 `it.skip` 存在
- `createSmallMapScene` 返回 `map`;该用例在 `playRoute` 之前调用 `state.pathfinding.finder.useMapLayer(map.eventLayer)`
- 目标用例的瞬移目标为 `(2,0)`、断言为 `x=2`/`y=0`SUMMARY 登记 `teleportTo` 自目标空路径缺陷(不修)
- 改动文件仅 `replayPlayback.test.ts`AI 未触碰生产源码;`git show --name-only <本计划提交 sha>` 可核验)
- `pnpm exec vitest run packages-user/data-state/test/replayPlayback.test.ts` 全绿
- `pnpm test:ci` 全绿且本计划不新增 `it.skip`
@ -239,9 +244,10 @@ Output: 接线事实与「layer 有意为 null」的确认 + 测试侧绑定 `ma
<success_criteria>
1. 确认 `core.ts` 的三处 finder 注入已由用户落地D-07`useMapLayer(null)` 为有意设计
2. 测试侧在楼层激活后绑定 `map.eventLayer``#06-07-1` 用例重命名、取消 skip 后转绿
2. 测试侧在楼层激活后绑定 `map.eventLayer`瞬移目标改为 `(2,0)``#06-07-1` 用例重命名、取消 skip 后转绿
3. AI 未修改任何生产源码;失败时按 D-09 退出并汇报
4. 用户负责的楼层切换重注入缺口与账本处置(不新建条目)在 SUMMARY 登记
5. `teleportTo` 自目标空路径导致的 2005 / sandbox 挂起缺陷登记于 SUMMARY本阶段不修
</success_criteria>
## Artifacts this phase produces