Reduce the friction of executing a test
To practice test-driven development (TDD), I recommend developers reduce the friction involved in running an individual test.
Since TDD uses test failures as guidance for implementation, it is most helpful when we have a tight feedback loop. But if running a test takes a long time, we don’t run it as frequently, and we miss out on the test’s feedback.
Usually, developers focus on reducing the time it takes for the test to execute (for example, by reducing the number of database calls the test makes). And that’s important. But to have tight feedback loops, it’s equally important that we be able to execute the test quickly.
The time between us thinking about running the test and us actually running the test is integral to the cost of running the test. And the higher the cost of anything, the less we do it.
In vim, it’s possible to run tests almost at the speed of thought. When my
cursor is anywhere within the test body, I can press
SPACE + s, and
the test runs automatically in a separate tmux pane (opening one if it isn’t
My brain is so trained that I hardly think about it, and the test is already running.
Moreover, once I’ve run the test, I can rerun that same test from anywhere in my
project by typing
SPACE + l. That gives me the ability to focus on the
implementation while continuously running the test.
All of that magic happens through vim-test.
Compare that to the alternative flow I typically see people use:
- Open test file
- Memorize the name of the file
- Look at the line number you want to run
- Open up your terminal
test command test/path/to/file
- Go back to the test file because you forgot the line number
- Append the line number to your test command
mix test test/my_app/users_test.exs:23
- Once you see the result, go back to the text editor to make a change
That’s 5-8 steps (depending on how good your memory is) instead of 1!
The difference might seem insignificant if you only do it once. But the friction involved in running a single test means we will run tests less often. And consequently, the gap between running a test and implementing code will become larger and larger – robbing us of beneficial test feedback for our implementation.
So, reduce the friction present in running a single test, and you’ll see how much more value you get out of testing first.
What if I don’t use vim?
You could switch to vim 😄. If that doesn’t appeal to you, other text editors likely have libraries or plugins that allow you to do the same.
A quick search (and tweet) gave me the following:
- VSCode: vscode-test, vscode-elixir-test (elixir specific)
- Atom: atom-test-runner
- Sublime: Test Runner