资讯详情

资讯详情

疑难 Bug 与性能回归诊断方法论:plate 仓库的六阶段调试纪律(Diagnosing Bugs)

疑难 Bug 与性能回归诊断方法论plate 仓库的六阶段调试纪律Diagnosing Bugs【免费下载链接】plateRich-text editor with AI and shadcn/ui项目地址: https://gitcode.com/GitHub_Trending/pl/plate导读本文档对应 plate 仓库中.agents/skills/diagnosing-bugs/SKILL.md技能的核心内容系统讲解面向**疑难 bughard bugs与性能回归performance regressions**的六阶段诊断纪律。它以构建紧致、能变红的反馈循环为第一原则强调在提出任何假设之前必须先有一条能稳定复现用户症状、可自动运行、秒级完成的命令级循环随后依次完成复现最小化、可证伪假设、定向插桩、回归测试与清理复盘。读完本文你将掌握一套可直接运用于本仓库以及任何复杂前端/编辑器工程的调试工作流并了解hitl-loop.template.sh人机协同循环模板与仓库测试设施Playwright、bun test 脚本如何配合该流程落地。来源本文以 .agents/skills/diagnosing-bugs/SKILL.md 为主体并辅以该技能同目录下的 hitl-loop.template.sh、仓库根 package.json 的测试脚本以及packages/playwright测试包等实现证据展开。仓库是只读的文中仅说明查看与使用方法。一、技能定位这是一门纪律不是技巧清单诊断疑难 bug 与性能回归有一套固定的纪律discipline。文档开篇就明确了两个原则分阶段执行跳过阶段必须有明确理由Skip phases only when explicitly justified而非看情况随便跳先建立心智模型再动手探索代码库时如果存在CONTEXT.md先读它以建立相关模块的清晰心智模型同时在你要改动的区域检查是否有 ADR架构决策记录。就当前仓库而言仓库根目录及各包下暂未发现CONTEXT.md或ADR/目录——文档措辞是if it exists即这是可选的前置步骤不应阻塞主流程。取而代之的是本仓库的.agents/skills/下维护了超过 60 个领域技能如reproduce-bug、tdd、testing、resolve-slate-issue等它们与本文的 diagnosing-bugs 技能共同构成了一套技能驱动的开发/排障环境在诊断具体问题时可按需查阅这些相邻技能以补充某阶段的工具细节。二、Phase 1 — 构建反馈循环本技能的核心文档明确强调This is the skill. Everything else is mechanical.——构建反馈循环本身就是这门技能的核心其余阶段都是机械执行。其逻辑是如果你拥有一条针对该 bug 的紧致tight通过/失败信号——一条能对这个 bug 变红的循环——你就能找到根因二分、假设检验、插桩都只是在消费这条信号。反过来如果没有这条信号再怎么盯着代码看也救不了你。因此文档要求在此阶段投入不成比例的努力Spend disproportionate effort here态度要激进、要有创造力、拒绝放弃。2.1 构建循环的十种方式按推荐顺序文档给出了十种构建反馈循环的途径按推荐尝试顺序排列失败测试在能触达 bug 的任意接缝seam上写失败测试——单元、集成或 e2e。Curl / HTTP 脚本对着正在运行的开发服务器发请求。CLI 调用 快照比对用 fixture 输入调用 CLI将 stdout 与已知正确的快照做 diff。无头浏览器脚本Playwright / Puppeteer驱动 UI对 DOM / console / network 做断言。回放捕获的 trace把真实的网络请求 / payload / 事件日志存盘再在隔离环境里沿代码路径回放。一次性 harness搭建系统的最小子集单个服务 mock 依赖用一次函数调用驱动 bug 代码路径。属性 / 模糊测试循环若 bug 表现为输出偶尔错误跑 1000 个随机输入观察失败模式。二分 harness若 bug 出现在两个已知状态commit、数据集、版本之间自动化在状态 X 启动 → 检查 → 重复使其可git bisect run。差分循环对同一输入分别跑旧版本 vs 新版本或两种配置diff 输出。HITL bash 脚本最后手段若必须由人类点击操作用scripts/hitl-loop.template.sh驱动人类让循环依然结构化捕获的输出回传给 Agent。关键结论Build the right feedback loop, and the bug is 90% fixed.——构建出正确的反馈循环bug 就已经解决了 90%。2.2 在 plate 仓库落地反馈循环的现成素材本仓库为上述方式提供了大量可直接使用的现成设施单元 / 集成测试接缝全仓库各包下分布着 360 个*.spec.ts测试文件如packages/ai/src/lib/transforms/aiStreamSnapshot.spec.ts、packages/basic-nodes/src/lib/BaseHeadingPlugin.spec.ts等覆盖从 AI 流式转换到基础节点插件的各类行为。遇到编辑器行为类 bug 时最先考虑在对应包的 spec 文件中新增复现该症状的用例。e2e 设施packages/playwright目录提供了 Playwright 驱动的 e2e 测试包对应文档中第 4 种无头浏览器脚本方式。统一测试脚本仓库根 package.json 中定义了分层测试入口pnpm testbun tooling/scripts/test-fast.mjs快速测试、pnpm test:slow、pnpm test:slowest、pnpm test:coveragebun test --coverage以及pnpm check/pnpm check:push的完整校验链lint typecheck 全量测试。诊断时可先用test-fast快速定位受影响的包再用test:slowest处理性能类回归。性能回归专用文档专门强调性能回归要先测量、后修复见 Phase 4 性能分支而benchmarks/editor下的 benchmark 工程pnpm bench:editor:health、pnpm bench:editor:fuzz等见 package.json提供了带健康检查与模糊测试的性能基准设施可作为性能回归的基线信号。2.3 收紧循环Tighten the loop一旦有了某条循环就要把它当作产品来打磨从三个维度收紧更快吗缓存 setup、跳过无关初始化、缩小测试范围信号更尖锐吗断言具体症状而不是没崩溃更确定吗固定时间、固定 RNG 种子、隔离文件系统、冻结网络文档给出了一个形象的标准一条 30 秒还偶发抖动的循环几乎不比没有循环好一条 2 秒且确定性的循环就是调试的超级力量a debugging superpower。2.4 非确定性 bug目标不是干净复现而是更高的复现率对于 flaky偶发bug目标不是构造一个稳定复现而是提高复现率把触发器循环 100 次并行化加压力收窄时序窗口注入 sleep。判断标准很直接50% 抖动率的 bug 是可调试的1% 则不是——持续把复现率往上提直到它变得可调试。2.5 当确实无法构建循环时停止并明确说出来。文档要求列出你已经尝试过的方式向用户索要(a) 能复现该 bug 的环境访问权(b) 捕获的产物HAR 文件、日志 dump、core dump、带时间戳的录屏或 (c) 允许添加临时生产环境插桩在没有循环之前不得进入假设阶段Do not proceed to hypothesise without a loop。2.6 Phase 1 完成标准一条紧致且能变红的循环Phase 1 完成的定义是循环紧致tight且能变红red-capable——你能说出一条命令脚本路径、测试调用、或一条 curl它满足已至少实际运行过一次粘贴调用与输出能变红——它驱动了真实 bug 代码路径并断言了用户的确切症状因此能针对此 bug 变红、修复后变绿不是运行不报错而是必须能捕获到这个具体 bug确定性——每次运行结论一致flaky bug 则要求固定住的高复现率见 2.4快——秒级而非分钟级Agent 可运行——可无人值守运行只有在scripts/hitl-loop.template.sh介入时才需要人类参与。文档给出了本技能最重要的刹车提示如果你发现自己在这条命令存在之前就开始读代码构建理论——停下。直接跳到假设正是本技能要防止的失败模式。没有能变红的命令就没有 Phase 2。三、Phase 2 — 复现并最小化Reproduce minimise先运行循环看它变红——bug 出现。然后确认三件事循环产生了用户描述的那个失败模式——而不是旁边碰巧发生的另一个失败。错误的 bug 错误的修复失败在多次运行中可复现对非确定性 bug则是复现率高到足以针对调试已捕获确切症状错误消息、错误输出、缓慢的时序供后续阶段验证修复是否真正解决了它。最小化Minimise变红之后把复现收缩到仍然能变红的最小场景一次只削减一类东西输入、调用方、配置、数据、步骤每次削减后重新运行循环只保留对失败承重load-bearing的部分。为什么值得做最小复现会缩小 Phase 3 的假设空间可怀疑的活动部件更少并成为 Phase 5 的干净回归测试。完成标准剩余每个元素都是承重的——移除任意一个都会让循环变绿。未完成复现最小化之前不得进入下一阶段。四、Phase 3 — 提出假设Hypothesise在测试任何假设之前先生成3–5 个排好序的假设。单一假设容易锚定在第一个看似合理的想法上。每个假设必须可证伪说出它做出的预测。文档给出了标准格式如果 是根因那么 改变 Y 将使 bug 消失 / 改变 Z 将使 bug 更严重。如果你说不清预测那假设只是一种感觉——丢弃它或把它磨锋利。把排序后的列表先展示给用户再测试。用户往往拥有能瞬间重新排序的领域知识我们刚部署了 #3 相关的改动或知道哪些假设已被排除。这是一个便宜的检查点却能省大量时间如果用户不在线AFK不要阻塞按你的排序继续。五、Phase 4 — 插桩Instrument每个探针必须对应 Phase 3 的某个具体预测。一次只改变一个变量。工具优先级调试器 / REPL 检查环境支持时一个断点胜过十条日志定向日志打在能区分假设的边界处绝不什么都记下来再 grep。给每条调试日志打唯一前缀标签文档给出的工程实践每条调试日志加唯一前缀例如[DEBUG-a4f2]。收尾清理时一次 grep 全部解决——未打标签的日志存活打标签的日志被清掉。性能分支Perf branch对性能回归日志通常是错的。正确做法先建立基线测量时序 harness、performance.now()、profiler、查询计划再二分bisect。先测量后修复。这与 Phase 1 的差分循环 / 二分 harness方式配合使用在 plate 仓库中可依托benchmarks/editor的基准设施与pnpm test:slowest建立性能基线。六、Phase 5 — 修复 回归测试Fix regression test先写回归测试——但只在存在正确接缝时正确的接缝correct seam是指测试能在调用点发生的真实 bug 模式下运行。如果唯一可用的接缝太浅bug 需要多个调用方协作却只能在单调用方测试里复现单元测试无法还原触发 bug 的链条那么在这里写回归测试只会带来虚假信心。如果没有正确的接缝这本身就是发现记下来说明代码库架构正在阻止这个 bug 被锁死并在下一阶段标记。有正确接缝时的五步走把最小化后的复现转成该接缝上的失败测试看它失败应用修复看它通过重新运行 Phase 1 的反馈循环针对原始未最小化的场景验证。最后一步尤其关键它保证你修的不是最小场景里的影子 bug而是用户报告的真问题。七、Phase 6 — 清理 复盘Cleanup post-mortem宣布完成之前必须满足原始复现不再出现重跑 Phase 1 循环确认回归测试通过或无接缝这一情况已被记录所有[DEBUG-...]插桩已移除grep 该前缀一次性原型已删除或移到明确标记的调试位置最终证实的假设已写入 commit / PR 消息——让下一个调试者学习。然后问什么本可以防止这个 bug如果答案涉及架构性改变没有好的测试接缝、调用方纠缠、隐藏耦合把具体信息移交给/improve-codebase-architecture技能。在修复落地之后再给出建议而不是之前——此刻你拥有的信息比开始时多得多。八、配套工具实操hitl-loop 人机协同循环模板当 bug 必须由人类在真实 UI 中操作才能复现时文档要求用结构化脚本驱动人类而非放任自由操作。仓库提供了现成模板.agents/skills/diagnosing-bugs/scripts/hitl-loop.template.sh。该脚本的使用方式是复制一份、编辑中间的步骤区、然后运行——Agent 运行脚本用户在终端按提示操作捕获输出回传给 Agent# 用法复制本文件、编辑下方步骤、运行 bash hitl-loop.template.sh脚本内置两个辅助函数step instruction # 展示指令等待用户按 Enter capture VAR question # 展示问题把用户回答读入变量 VAR脚本骨架示例原模板中的可编辑区# --- edit below --------------------------------------------------------- step Open the app at http://localhost:3000 and sign in. capture ERRORED Click the Export button. Did it throw an error? (y/n) capture ERROR_MSG Paste the error message (or none): # --- edit above --------------------------------------------------------- printf \n--- Captured ---\n printf ERRORED%s\n $ERRORED printf ERROR_MSG%s\n $ERROR_MSG实现要点step()打印指令并以[Enter when done]等待回车capture()以提示读取回答并写入命名变量结尾统一以KEYVALUE形式输出捕获结果便于 Agent 机械化解析。脚本以set -euo pipefail开头保证出错即停。注意模板本身不可直接修改仓库文件——正确用法是复制到自己的调试位置后编辑。九、六阶段速查表阶段核心任务完成/出口标准Phase 1构建反馈循环一条紧致、能变红、确定性、秒级、Agent 可运行的命令已实际运行过Phase 2复现 最小化循环产出用户描述的确切症状最小场景中每个元素都承重Phase 3提出假设3–5 个排序的、可证伪的假设如果 X 是根因那么改变 Y 会……Phase 4插桩每个探针对应一个预测一次只变一个变量日志带[DEBUG-xxx]前缀性能回归先测后修Phase 5修复 回归测试在正确接缝上先写失败测试 → 修复 → 通过 → 重跑原始循环Phase 6清理 复盘原始复现消失、回归通过、插桩清空、正确假设写入 commit架构建议移交十、结语这套诊断方法论的可贵之处在于它把调试从碰运气的艺术变成了一条可审计的纪律信号先行Phase 1→ 精确复现Phase 2→ 多假设排序Phase 3→ 定向验证Phase 4→ 测试锁定Phase 5→ 清理沉淀Phase 6。其中没有能变红的命令就不许提出假设这条硬约束直接预防了调试中最常见的失败模式——过早理论化。配合 plate 仓库已有的 360 spec 测试、packages/playwrighte2e 设施、分层的pnpm test脚本、benchmarks/editor性能基准以及hitl-loop.template.sh人机协同模板这套流程在本仓库中是完整可落地的。【免费下载链接】plateRich-text editor with AI and shadcn/ui项目地址: https://gitcode.com/GitHub_Trending/pl/plate创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
觉得有用,分享给同行:

为您的企业打造数字门面

稳重轻奢商务风格,端正雅致视觉,长效耐看不易过时。

立即咨询 →