Listen to this post
We should consider testing, which is an activity, versus testability, which is a quality of design.
If we start with the word “test” itself we note that it is both a noun and a verb. I can say, “I have a test for that behavior,” or I can “test a behavior.” As a noun, it is an artifact that can express the nature of a desired behavior (if the test is written first) and it can capture that knowledge for the future. As a verb it can drive that behavior into the code, and then be used to subsequently verify its correctness later.
“Testability”, on the other hand, is a quality of the system being tested. What kinds of tests can you write about it? What kinds of test do you have to write about it? What will tests tell you when they fail? How much effort is required to create these tests?
The fact is, bad design is hard to test. We see this with a lot of legacy code: it has no tests, or the tests are very slow and cumbersome. When we try to test something and find the effort to be extremely difficult, this can be called “pain”, and pain is a diagnostic tool. That’s why pain exists.
This pain can be revealed whether you actually write the tests or not. It is certain to be revealed if you do. The earlier, of course, the better.