This chapter covers
- What property-based tests are and how to write them
- When to write property-based tests and when to write example-based tests
So far, we have been doing what we call "example-based testing". We judiciously divided the input space of the program (in partitions), picked one concrete example out of all the possible ones, and then wrote the test case. What if we do not have to pick one concrete example out of many? What if we could express the "property" we are trying to exercise and let the test framework pick several different concrete examples for us? I can see advantages in this approach: our tests would be less dependent on a concrete example, and the test framework would be able to call the method under test multiple times with different input parameters with virtually zero effort for us.
This is what property-based testing is about. We do not "pick a concrete example"; rather, we define a property (or a set of properties) that the program should hold, and the test framework then tries to find a counterexample that makes the program break such property.
I learned that the best way to teach how to write property-based tests is by means of several examples. And this is what I am going to do in the next sub-sections. I will present five different examples, with varying levels of complexity so that you can see how it works. I want you to focus on my way of thinking; note how much creativity is required to write such tests.