Let's write a simple and flawed application that can help us, as an example of how to write Functional Tests for concurrent applications. In practice, writing these tests will require more work, but the principles should still apply.
Writing the tests
Creating a flawed UserManager
Using interfaces to define the dependencies of our code will allow us to provide mocks during the tests. Let's start by defining a basic DataSource interface that contains the methods that will be used concurrently:
interface DataSource {
fun getNameAsync(id: Int): Deferred<String>
fun getAgeAsync(id: Int): Deferred<Int>
fun getProfessionAsync(id: Int): Deferred<String>
}
Now, let's define a data class that...