Unit Test Documentation
Opened this issue ยท 3 comments
WendyYanto commented
Is there any way to unit test update
? If there's a way, is there any documentation ? Thank you
pardom commented
Testing init
, update
, and view
is as simple as calling those functions and asserting on the result. There's nothing to help with effect testing in the library yet, however, it might eventually look something like this:
class EffectAsserter<Msg : Any> {
private val calls: MutableList<Msg> = mutableListOf()
private val dispatch: Dispatch<Msg> = { msg -> calls.add(msg) }
fun run(effect: Effect<Msg>) =
apply { runBlocking { effect(dispatch) } }
fun assertEquals(msgs: Iterable<Msg>) =
apply { assertEquals(msgs, calls) }
fun assertCount(count: Int) =
apply { assertEquals(count, calls.size) }
}
@Test
fun `effect test`() {
val (_, effect) = update(msg, model)
EffectAsserter<Msg>()
.run(effect)
.assertCount(1)
.assertEquals(listOf(Msg.Foo))
}
I've added this issue to the Documentation Project.
jcornaz commented
Personally I create the following simple helpers:
fun <Msg> Effect<Msg>.asFlow(): Flow<Msg> =
channelFlow<Msg> { this@asFlow { sendBlocking(it) } }
suspend fun <Msg> Effect<Msg>.perform(): List<Msg> =
asFlow().toList()
And then in my tests I use it like this:
val (_, effect) = update(msg, model)
// Perform the effect and return the list of dispatched messages
val messages: List<Msg> = runBLocking { effect.perform() }
// assert using my favoring assertion library
messages.shouldBeEmpty()
pardom commented
Follow up: I would recommend using TestCoroutineDispatcher
so you can advance time like this https://github.com/oolong-kt/oolong/blob/main/oolong/src/jvmTest/kotlin/oolong/effect/EffectTest.kt#L48