mcpField
T
tdd-red-green-refactor

tdd-red-green-refactor

github.com/yonatankarp测试与质量139 次安装23 周前更新
代码仓库

关于 tdd-red-green-refactor

介绍红—绿—重构循环的 TDD 技能,面向以测试驱动新功能、修复缺陷或设计 API 的开发者。重点是先写失败测试、用最少代码通过,再在测试保持通过时重构。

主要功能

  1. 01讲解红—绿—重构循环
  2. 02要求先确认测试因预期原因失败
  3. 03强调最小实现以通过测试
  4. 04指导仅在测试通过时重构
  5. 05列出适用与不适用的场景

适用场景

  1. 01通过测试驱动新功能开发
  2. 02先写回归测试再修复缺陷
  3. 03从调用方角度设计 API

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/yonatankarp/software-design-skills --skill tdd-red-green-refactor

安装后在 Claude Code 中输入/tdd-red-green-refactor确认已加载。

详细介绍

一句话总结

TDD 循环:编写一个失败的测试(红),编写通过测试所需的最少代码(绿),在保持测试通过的同时重构。每次只重复一个微小步骤。关键在于遵循顺序和做到最少——这两点都很容易被跳过。

何时使用此技能

  • 在可以将预期结果描述为测试的代码中构建新行为。
  • 修复 Bug——先编写回归测试(参见 tdd-regression-test),再修复。
  • 从调用方的角度设计 API——第一个测试会迫使你考虑调用代码需要什么。
  • 在测试套件完善、采用 TDD 不会增加多少阻力的代码库中工作。

何时不使用此技能

  • 纯探索或试验性开发:你还不确定要构建的内容是什么样子。先进行试验性开发,然后通过测试驱动重写。
  • 一次性脚本、一次性工具,或不会维护的快速原型。
  • UI 微调:对于“编写测试、修改一个像素、确认测试通过”这样的循环,付出的代价大于收益。
  • 没有现成测试基础设施的代码库:为一个功能搭建测试框架,投入与收益不成比例。添加测试;如果做不到,就不要假装自己在做 TDD。

核心内容

红——编写失败的测试。 为尚不存在(或即将扩展)的行为编写一个小测试。运行它。确认它因正确的原因失败——在预期位置出现编译错误或断言失败,而不是在三层调用之外随机抛出 NullPointerException。

绿——以最低限度通过测试。 只编写足以让测试变绿的生产代码。最低限度至关重要——此时可以不惜一切手段快速实现(return "hardcoded" 也没问题)。最低限度的实现是确认测试连接正确的最廉价信号。

重构——保持测试通过的同时清理代码。 有了通过的测试网作为保障,调整代码结构。提取方法、重命名变量、消除重复。每次小改动后都运行测试。如果测试变红,说明重构有误;撤销后尝试更小的改动。

顺序为何重要。

  • 先红会迫使你编写一个会失败的测试。如果先写生产代码,之后编写的测试可能并非必需。
  • 最低限度变绿是这个循环的纪律所在。没有它,你就会过度设计;循环也就不再紧凑。
  • 有测试网兜底时重构,设计才能得到改进。没有测试,你会害怕改动代码。有了测试,你就可以放心尝试。

循环时长。 一个完整循环应该以分钟计,而不是以小时计。如果一个循环超过约 30 分钟,说明测试太大了——可以使用 tdd-child-test。

TDD 不等于“编写测试”。 事后编写测试是在做测试。先写测试是在做设计。顺序会改变代码的形成方式;两者都会产出测试,但只有一种能驱动设计。

决策启发

  • 每个循环步骤都要运行测试。不要批量运行测试——快速反馈才是重点。
  • 新功能的第一个测试应该小巧且运行迅速。第一个测试太大或太慢,都会破坏循环。
  • 只在测试通过时重构。在测试失败时重构,就是“在代码出问题时改代码”——这已经不是 TDD。
  • 如果你发现自己在测试之前就编写生产代码,那么测试就会偏向于你已经写好的内容。停下来,回到起点。

反模式

  • 代码写完后才编写测试。 没有真正做过 TDD 的人常把这称作“TDD”。这无法驱动设计。
  • 覆盖范围过大的测试。 运行缓慢、难以通过,失败时提供的信息也很少。
  • 在测试失败时重构。 “我正在改进设计,完成后测试也会通过。”这混淆了两种活动;两者都会出问题。
  • 跳过最低限度变绿这一步。 从红直接跳到“真正的”实现。这往往会引入测试并未要求的复杂性。
  • 把 TDD 当作教条。 坚持在不适合 TDD 的代码上使用 TDD(一次性脚本、探索性试验)。遵循纪律确实有成本;只在能带来帮助的地方付出这些成本。

另请参阅

  • tdd-identify — 如果卡在循环中,可用它找到合适的技巧。
  • tdd-fake-it、tdd-obvious-implementation、tdd-triangulate — 完成“绿色”步骤的三种方法。
  • tdd-child-test、tdd-one-step-test — 如果红色测试规模过大,或不知道该选哪个。
  • tdd-anti-patterns — 表明 TDD 出现问题的代码异味。
  • Superpowers 的 superpowers:test-driven-development — 工作流级别的触发器。

参考资料

  • Kent Beck,《Test-Driven Development By Example》(Addison-Wesley,2002 年)——权威参考资料。第一部分(Money 示例)逐步演示了数十个红—绿—重构循环。
  • Beck 的 “TDD by Example” 演讲(经常发表)——对同一内容的精简讲解。

评论

支持 Markdown