agentleFS
Ex-imanityEx-imanity/SkillCollections/skills/whitebox-op-combo/SKILL.md

whitebox-op-combo

Skill1 starsChanged 17 days agoMITView on GitHub

白盒操作组合分析:在能看到源码(服务端和/或客户端)的前提下,把一个功能的用户操作拆成原子动作, 按读写集排列组合出正向与异常的操作顺序,映射到代码执行路径,提前定位缺陷位置、判定服务端/客户端归属, 并产出可执行的测试用例。当用户提到白盒测试、对照代码看看会发生什么、代码走查找 bug、操作顺序/操作组合、 多个操作之间的相互影响、先 A 再 B 会怎样、退出重进/切后台/杀进程后状态对不对、重新生成/编辑/撤销后字段没更新、 异步落库/缓存/多存储不一致、多端(Android/iOS/Web/服务端)行为不一致、流式输出中途中断时,都应使用本 skill, 即使用户没有说"白盒"或"原子动作"。不适用于:只有需求文档没有代码的用例生成(用 case-lite), 或只需要覆盖度评审策略(用 case-design-strategy-skill)。

The file

Files
SKILL.md

whitebox-op-combo:白盒操作组合分析

这个 skill 解决什么问题

单个操作的缺陷通常在开发自测时就暴露了。线上漏出去的,大多是操作之间的相互影响: 点赞后重新生成,赞还在;重新生成后退出重进,错题本存的是旧答案;流式输出到一半退出,重进后卡片丢失。 这类缺陷在需求文档里看不出来,黑盒测试靠运气碰。

白盒的优势是可以把"操作之间有没有影响"变成可计算的问题:两个操作只有在读写了同一份状态时才会相互影响。 所以方法是:

  1. 静态:找出这个功能的所有状态读写点(字段 × 存储层 × 同步/异步)。
  2. 原子化:把用户动作按"读写了哪些状态"归类成原子动作。
  3. 动态:只对存在读写依赖(同一字段上的先写后读/写写,或替换后读旧字段)的原子组合做代码路径推演,其余机械剪枝。
  4. 收敛:每个可疑组合要么被代码证实,要么被排除,要么标为需实测的潜在问题;最后产出用例。

整个过程最难、也最容易被做成拍脑袋的是第 2 步——原子由谁拆、拆得全不全。 本 skill 的回答是:agent 从代码穷举,人只审一次;覆盖度由 scripts/op_matrix.py 计算出的缺口来闭环, 而不是靠头脑风暴。要注意脚本能证明的范围:它只能在已声明的读写点和原子上检查缺口, 读写点本身找没找全、同一写入集下的不同产品语义要不要拆开,仍要靠需求映射和人工审阅。详见 references/atomization.md §4。

何时读哪个参考文件

文件什么时候读
references/atomization.md阶段 1–2 之前必读:原子定义、范围锚点、四个来源、覆盖闭环、atoms.json 结构
references/defect-patterns.md阶段 4 对每个候选组合做推演时:8 类缺陷模式和"排除"检查
references/verification.md阶段 5:状态标记、复现方法、定级、服务端/客户端归属、快速指纹
references/output-templates.md写 atoms.md / analysis.md / cases.md 时
examples/ai-search-answer-card/想看一个真实功能的 atoms.json 与脚本输出长什么样时

产物目录

默认 whitebox-output/{slug}/(用户指定则用用户的)。每个阶段的产物都落盘,便于中断后续做和人审阅:

baseline.md  atoms.json  atoms.md  pairs.md  analysis.md  cases.md

工作流

阶段 0:基线与范围

  • 确认范围对象:一个被多个动作共享的对象("一张 AI 回答卡片"、"一个订单"、"一条批改记录")。 范围对象定不下来,后面的读写点就没有边界。见 atomization.md §2。
  • 确认代码基线:涉及哪些仓库、以哪个远程分支为准、记录最新提交号。本地工作区常常不是最新的, 用 git fetch 后 git show "origin/<branch>:<path>" 读文件,必要时导出到 /tmp 再 grep。
  • 确认配置/开关:实验开关、TTL、特性开关的实际取值来源;拿不到的记为盲区。
  • 写 baseline.md:范围对象、仓库/分支/提交表、配置来源、盲区(看不到代码的服务、黑盒依赖)。

阶段 1:状态模型与读写点

先找写入点,再找读取点——写入点是覆盖度的硬约束(每个写入点都必须被某个原子触达)。

  • 从范围对象的数据结构出发,列出它的字段,以及每个字段存在哪些层(DB、缓存、内存、端本地、下游服务)。
  • grep 所有写这些字段的地方(setter、put、save、update、序列化构造),逐个记为写入点: 字段 × 层 × sync/async × 代码位置。同一路径双写多层的,用 layers 同时声明。
  • 再 grep 读取点:展示、回填、作为下游请求参数、作为判断条件。
  • 三端都有代码时,端本地状态(内存、持久化缓存)同样是层;端之间实现不同的,分别记。

阶段 2:原子动作与覆盖检查

  • 按 atomization.md 的四个来源拆原子:代码自底向上为主(入口 → 触达的写入点/读取点), 需求/设计稿自顶向下补漏,隐式动作清单逐项作答,最后留给人补代码之外的动作。
  • 写 atoms.json,运行:

    python3 <skill_dir>/scripts/op_matrix.py whitebox-output/{slug}/atoms.json --out whitebox-output/{slug}/pairs.md

    脚本返回 1 表示引用错误(原子引用了不存在的读写点),先修。

  • 处理 pairs.md 第 1 节的每一条覆盖缺口:孤儿写入点要么补原子、要么说明它不由用户触发; "替换型原子漏写的字段"是最强的缺陷信号,直接进入阶段 4 的候选清单。 迭代到缺口全部有结论。
  • 写 atoms.md(模板见 output-templates.md)。

⏸ 人工检查点(唯一必做):把 atoms.md 交给用户审,请用户回答三个问题: ① 有没有代码之外的动作(后台操作、客服、其他系统、另一个角色)? ② 有没有用户实际上不会做的原子?(降级处理,不删除——它仍可能被自动化或异常路径触发) ③ 有没有应该拆开的变体? 用户确认前不进入阶段 3。原子表错了,后面的组合推演全部白做;而原子表是人能快速判断对错的最小产物。

阶段 3:组合与剪枝

  • pairs.md 已经给出:带依赖标记的有序对(RAW/WAW/STALE/RACE/LAYER 与优先得分)、三元穿透链、中断点。 三元链默认只列 30 条,被截断时用 --max-chains N 调大。 这是候选清单,不是结论。
  • 在此基础上补三类脚本算不出来的组合:
    • 时间轴:异步写入尚未完成时的下一个动作(RACE 标记的对),TTL 到期前后。
    • 中断:声明了 stages 的原子,在每个阶段被退出/切后台/断网打断。
    • 多端:同一组合在各端分别走一遍,看端实现差异是否改变结果。
  • 按得分排序,从 STALE 和三元链开始推演。候选太多时先做得分 ≥4 的,在 analysis.md 里说明剩余的处理方式。

阶段 4:按缺陷模式推演

对每个候选组合,沿代码走一遍"A 执行后各层状态是什么 → B 读到的是什么 → 用户看到什么", 并对照 defect-patterns.md 的 8 类模式找证据。每条推演都要:

  • 引用 文件:行号,关键处贴代码片段。
  • 先做排除:看似会出问题的路径,是否被兜底逻辑、幂等键、版本号、读时修正挡住了。排除掉的也要写一句, 这比只写问题更能让开发信服。
  • 区分"代码里直接读得到"与"取决于运行期数据"——后者只能标【潜在】,交给实测。

阶段 5:验证、定级、归属

按 verification.md:

  • 标状态:【已确认】【已确认·潜在】【潜在】【已排除】;实测后改为【已实测复现】。
  • 定级看发生概率 × 后果,"静默出错且用户难以察觉"上调;复现需要卡精确时序的下调。
  • 归属按"数据最先在哪里出错"判定,不以"哪端改起来方便"判定;服务端缺陷不让客户端打补丁掩盖。 契约本身缺失(比如字段没有版本号,谁都无法判断新旧)的,归属写"协议"。
  • 每条给出快速指纹:不走完全流程就能判定的信号(同源字段比对、计数、直查存储)。
  • 写 analysis.md,末尾做根因收敛:把具体问题收敛到 3–5 个结构性成因。

⏸ 建议的人工检查点:请用户(或开发)review analysis.md。结论会被拿去指导修复,错一条的代价高于多看一遍。

阶段 6:输出用例

写 cases.md,格式与 case-lite 的 full.md 兼容,可直接用 case-lite 的写回脚本写回测试平台(写回前需用户明确授权并 dry-run)。

  • 场景按原子组合组织,另设竞态、中断、跨端等横切场景。
  • 预期结果写产品应有行为,不写现状;当前实现不符的在测试点末尾 备注: 指向 analysis 章节。 这样缺陷修复后用例不用改,执行时也能区分"用例写错"与"确实是缺陷"。
  • 步骤写清时间要求与端别;需要卡精确时序的白盒边界单独成点。

阶段 7:回流

实测结果、开发反馈、用户纠正回来后:更新 analysis.md 的状态标记和正文(直接写最新结论,不保留推理历史), 同步 cases.md 备注;如果发现了原子表漏掉的动作,补进 atoms.json 重跑脚本——漏掉的原因往往也是一类 值得加进隐式动作清单的动作。

省 token 的做法

  • 先 grep 写入点,只打开命中的方法,不整文件通读。
  • 远程分支文件导出到 /tmp/<repo>/ 后再检索,避免反复 git show。
  • 读写点和原子一旦写进 atoms.json,后续推演引用 ID(W03、A2)而不是重复描述。
  • 候选组合多时,按脚本得分截断,未推演的在 analysis.md 里说明。

与其他 skill 的关系

  • case-lite:从需求文档生成用例。两者可以串联——case-lite 给出功能用例,本 skill 补操作组合与白盒风险用例; cases.md 格式与其 full.md 兼容。
  • case-design-strategy-skill:覆盖度评审策略。在阶段 6 自检时可借用其角度,但产物格式以本 skill 为准。

Download now (ZIP)

Does it work?

Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.

No reviews yet

People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.

  • It worked
  • Partly
  • It didn't
What did you use it for? e.g. Reviewing pull requests in a Rails app

Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.

Your trail

Files you open will collect here, so you can find them again.

Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.

Now do this for your own.

Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.