Not just complete sentences, test names should describe in plain English, with no reference to code or variable names, exactly what's being tested and exactly the expected outcome: "when [something happens], [the result is x]"
Shallow/meh, article. Demonstrates complete lack of familiarity with many popular testing frameworks/approaches, and proposes a subpar solutions for problems that have already been solved in superior ways.
Your test description/documentation should be sentences, but there is absolutely zero reason to try to encode that into the name of your test function. Not to mention this article then suggests using another tool to decode this function name into a proper sentence for reporting... ok now you completely lost the ability to ctrl+f and jump to the function... terrible advice all around.
Why not just use a testing framework that actually supports free-form sentence descriptions/documentation for your tests?
If my unit testing framework supports free-form sentence descriptions, I'll use it. But I won't use that feature as a wedge issue. It doesn't bother me all that much to have test functions with names like `test_transaction_fails_if_insufficient_funds_are_available()`. Other features of the test framework might have a much bigger impact on my developer experience.
Pretty much every major language/framework now supports free-form test names/descriptions, including JUnit, which is referenced in the article ^ (again, highlighting the author's ignorance). Just because something doesn't bother you personally doesn't mean it's a good thing to follow, especially when its clearly inferior to other options.
> It doesn't bother me all that much to have test functions with names like `test_transaction_fails_if_insufficient_funds_are_available()
I mean, that's one example where you have one outcome based on one parameter/state. Expand this to a 2-field outcome based on 3 state conditions/parameters and now you have a 100-character long function name.
You seem to be focusing on the most obtuse possible way of structuring descriptive test names for rhetorical purposes. I don't know if that's intentional or not, but either way it's not terribly convincing? If you name tests according to business domain concepts rather than tying it to individual parameters through some formulaic rubric, it's often possible to come up with test names that are both more concise and easier to understand than the specific way of naming tests that you've been consistently steering the conversation back toward throughout this thread.
> You seem to be focusing on the most obtuse possible way of structuring descriptive test names for rhetorical purposes.
No, I'm focusing on the most realistic and common ways this kind of pattern actually exists (based on my experience).
> If you name tests according to business domain concepts rather than tying it to individual parameters through some formulaic rubric,
While you say I'm focusing on 'the most obtuse possible way...', this kind of comment makes it seem like you haven't focused on any actual way at all. You're speaking in very ambiguous and vague terms, which actually can't be applied and enforced in practice. If you're actually trying to write a suite of unit tests around, say a function, with 3 parameters and multiple possible outcome states - you can't name your function the same for the different combinations of inputs/outputs, and you can't just handwave a 'business domain concepts' name into existence to cover each case - that just turns into an exercise of finding synonyms, abbreviations, and vague generalizations - it doesn't solve the fact that you still need all of the same test cases and they all still need to have unique function names.
You haven't actually thought through what you're proposing here.
When a unit test fails in code I'm working on I don't read the name of the test, I jump to the line in the file for the test and read the code so I never really understood what people find advantageous for this naming convention.
I've worked at companies that required this style naming for tests and it was an unholy mess, and it only works if the unit test is small enough that the name is still a reasonable length which at that point the code should be clear enough to understand what is being tested anyway.
Names, descriptions for tests are useful for many purposes, I'll leave it at that.
The point I'm making (and I think you are agreeing with me) is that trying to stuff a test description into a test function name is cumbersome and pointless. There are far better ways of adding descriptions/documentation for unit tests and pretty much every major language/testing framework supports these, nowadays.
“If you get fired as a result of applying the advice in this book, then that’s probably for the best, all things considered. But if it happens, I’ll make it my personal mission to get you a job with a better company: one where people are rewarded, not punished, for producing software that actually works.”
I came up with this idea because I was trying to encourage people to think about how they name their tests. One useful technique is to make the test name a complete (but brief) sentence describing the required behaviour.
This is helpful when the test fails, because you see the name printed out as part of the failure message. But it's also a good thinking tool as you're writing the test, because you have to start by deciding exactly what the behaviour under test should be.
As some guy named Sam Altman said, "If it takes more than a sentence to explain what you're doing, that's almost always a sign that it's too complicated." This is a good guide for programmers too, because the amount of behaviour that can be concisely described in a sentence is also about the right amount for a software component or function.
Hence a program that parses your (Go) test names, eliminating camel case and underscores and so forth, and prints them out as readable English sentences. For example, if the test name is 'TestFooReturnsErrorForInvalidInput', the program will print:
Foo returns error for invalid input
(preceded by a tick or a cross to show the current test status)
To try it out, run:
go install github.com/bitfield/gotestdox/cmd/gotestdox@latest
Then run 'gotestdox' in some Go project or package (the default target is the current package, but it can also take any arguments that 'go test' takes, such as a package list like './...').
The original implementation of this simple but useful idea was 'agiledox', written by Chris Stevenson for JUnit. It has been ported to various other languages and test frameworks, but not (as far as I know) to Go, until now.