协作头脑风暴
brainstorming
在实现前澄清需求、探索设计选择,并形成清晰的开发方向。
unit-testing【开发与工程】Writes unit tests for code that already exists — choosing what deserves a test, what the cases are, and how to assert without welding the test to the implementation. Use this whenever the user asks for tests, unit tests, more coverage, or tests for a specific function or module, and also when adding to untested code where a characterization test is n…
独立 GitHub 快照 · 自动分类 · 以原作者文档为准
A test earns its place by failing when something breaks and staying quiet otherwise. A test that never fails is documentation with a runtime cost; a test that fails on every refactor is a tax. Both get deleted eventually, and the second one takes the good tests' credibility with it.
Coverage is not the goal. Coverage measures which lines ran, not whether anything was checked — a suite that executes everything and asserts nothing scores beautifully and catches nothing.
In descending order of value:
Not worth it: generated code, thin pass-throughs, framework behaviour, getters, and anything where the test would restate the implementation line for line.
Done when: you can say why each planned test exists, in terms of a failure it would catch.
Test at the smallest stable interface that exposes the behaviour, not necessarily the smallest unit. A private function extracted for tidiness is an implementation detail; testing it directly freezes a decision you should be free to change.
If a behaviour is only reachable through six layers of setup, that is a design signal. Note it, and test at the level that is reachable rather than mocking your way down.
Done when: the seam is one a caller would actually use.
Go through these deliberately — the value of a test suite is mostly in the cases people forget:
Done when: you have a written case list, with the ones you are deliberately skipping noted.
Name the behaviour, not the function. returns_empty_list_when_no_orders_match tells you
what broke from the failure output alone. test_get_orders_2 tells you to go read it.
One behaviour per test. Multiple assertions are fine when they describe one outcome; multiple scenarios in one test hide everything after the first failure.
Arrange, act, assert — visibly separated. If arrange is longer than the other two combined, the code under test needs too much context, which is itself worth reporting.
Assert against an independent expectation. The expected value must come from somewhere other than the code's own logic. Re-deriving it the same way the implementation does produces a test that passes by construction and can never disagree — the most dangerous kind, because it looks like coverage.
Build test data with factories, not shared fixtures. A fixture mutated by one test bleeds into the next, and the resulting failures are order-dependent and miserable to find. Each test should be readable alone.
Done when: you could rewrite the implementation entirely and the tests would still be correct as specifications.
When the code has no tests and you need to change it, do not start by testing what it should do — pin down what it does:
Doing this in the other order means changing behaviour and structure at once, with no way to tell which broke it.