Test invariants across generated inputs
Property-based testing checks a general rule over many inputs and can shrink failures into smaller counterexamples. Choose rules independent of the implementation, such as sorting preserving size and being idempotent.
With compatible Kotest property and runner dependencies in a JVM learning project:
import io.kotest.core.spec.style.StringSpec
import io.kotest.property.checkAll
import io.kotest.property.arbitrary.*
import kotlin.test.assertEquals
class SortProperties : StringSpec({
"sorting twice equals sorting once" {
checkAll(Arb.list(Arb.int(), 0..100)) { values ->
assertEquals(values.sorted(), values.sorted().sorted())
}
}
})
A property can be true but too weak to catch useful defects; also verify ordering and element multiplicities. Keep deterministic examples for known boundaries and preserve failing seeds when debugging.
Exercise
For a normalization function, test idempotence and that output has no leading or trailing whitespace. Generate empty and whitespace-only strings as well as ordinary text.
Check: explain why comparing a function to the same function with identical input is not a meaningful property test.