testing-coroutines-with-runtest

Test JVM coroutines deterministically with kotlinx-coroutines-test virtual time.

303|10|Updated May 15, 2026
One-click install
npx skills add https://github.com/skydoves/android-testing-skills --skill testing-coroutines-with-runtest
Or copy as Structured Prompt for Agent▼
Please help me install this Agent Skill.
Skill: testing-coroutines-with-runtest
Source: https://github.com/skydoves/android-testing-skills/tree/main/jvm-tests/coroutines/testing-coroutines-with-runtest
Command: npx skills add https://github.com/skydoves/android-testing-skills --skill testing-coroutines-with-runtest

SYSTEM DOCUMENTATION & REQUIREMENTS

💡 This Skill includes references (resource) components.

What problem does it solve?

This Skill helps you reliably test suspend functions and coroutine-driven classes on the JVM without real-time delays, flakiness, or tests hanging due to incorrect coroutine test setup.

Core Features & Use Cases

  • Correct entry point with virtual time: Uses runTest with TestScope and virtual clock control via TestCoroutineScheduler.
  • Dispatcher correctness for stateful code: Explains StandardTestDispatcher vs UnconfinedTestDispatcher, and how Dispatchers.setMain prevents missing-main-dispatcher crashes in viewModelScope tests.
  • Flow-collector safety: Covers the common hang scenario when collecting hot flows directly in TestScope, steering you to backgroundScope or the sibling Turbine skill.
  • KMP correctness note: Describes the TestResult contract and why single-expression @Test fun foo() = runTest { ... } matters for Kotlin/JS and wasm targets.

Real-world example: testing a ViewModel that emits Loading -> Success from a coroutine where you need to advance virtual time (advanceUntilIdle or advanceTimeBy) to deterministically assert intermediate states.

Quick Start

Use the testing-coroutines-with-runtest skill when you need to write a JVM runTest for a viewModelScope-backed suspend flow that currently hangs or is timing out in CI.

Frequently Asked Questions about testing-coroutines-with-runtest

High-intent search queries and answers about installing and using this skill.

FAQPage Schema
Why does my Kotlin coroutine test hang when collecting a hot Flow in runTest?▼

Kotlin coroutine tests hang because collecting hot flows directly in TestScope never completes. Use backgroundScope or a library like Turbine to safely collect emissions without blocking virtual time.

How do I test a ViewModel that emits Loading and Success states using runTest?▼

Test ViewModel state emissions by replacing real time with virtual time using TestCoroutineScheduler. Call advanceUntilIdle or advanceTimeBy inside runTest to deterministically assert intermediate Loading and Success states.

Do I need to set Dispatchers.setMain for viewModelScope JVM unit testing?▼

Yes, you need Dispatchers.setMain configured via a MainDispatcherRule for viewModelScope JVM unit testing. Without it, tests crash with a missing main dispatcher error because viewModelScope defaults to Dispatchers.Main.

What is the difference between StandardTestDispatcher and UnconfinedTestDispatcher in kotlinx-coroutines-test?▼

StandardTestDispatcher queues coroutines without executing them until advanced, whereas UnconfinedTestDispatcher executes eagerly like real code. Choose StandardTestDispatcher for precise virtual time control and UnconfinedTestDispatcher for simpler sequential execution.

Can I use single-expression runTest functions for Kotlin Multiplatform JVM and wasm tests?▼

Yes, use single-expression @Test fun foo() = runTest { ... } for Kotlin Multiplatform tests. This format fulfills the TestResult contract required by Kotlin/JS and wasm targets to properly return asynchronous test results.