Практичне використання Kotlin Coroutines: Перевірка диспетчера в юніт-тестуванні

Практичне використання Kotlin Coroutines: Перевірка диспетчера в юніт-тестуванні

8 Березня 2024 в 00:04 22

Кotlin Coroutines стали популярним інструментом для роботи з асинхронним кодом в мові програмування Kotlin. Вони дозволяють зручно та ефективно працювати з паралельним виконанням, уникнути блокування потоків і забезпечити зручний синтаксис. Однак, при розробці програм з використанням корутин виникають ситуації, коли потрібно перевірити, які саме диспетчери використовуються у ваших асинхронних операціях, зокрема, під час юніт-тестування. У цій статті ми розглянемо, як правильно перевіряти диспетчери корутин під час юніт-тестування на прикладі Kotlin-класу, який приймає диспетчер як параметр.

Спочатку давайте зрозуміємо, що таке диспетчер корутин. Диспетчер – це механізм, який визначає, на якому потоці або потоках виконується корутинна робота. Kotlin надає кілька вбудованих диспетчерів, таких як Dispatchers.Main, Dispatchers.IO, Dispatchers.Default та інші. Ви також можете створювати власні диспетчери за допомогою класу CoroutineDispatcher.

У багатьох випадках ви використовуватимете деякий диспетчер у вашому коді, і у нього буде важливе значення під час тестування. Наприклад, ви можете мати клас, який приймає диспетчер як параметр у конструкторі та використовує його для виконання асинхронних операцій:

Тепер, якщо ви хочете написати юніт-тест для цього класу, де ви хочете перевірити, що fetchData() викликається з відповідним диспетчером, вам потрібно буде знати, який саме диспетчер використовується у вашому тесті.

Давайте розглянемо практичний приклад. Уявімо, що у нас є клас Test, який приймає диспетчер як параметр та використовує його для виконання асинхронних операцій:

Для того щоб протестувати цей клас, ми можемо передати власний диспетчер під час створення екземпляру класу Test у нашому тесті:

Тепер ми хочемо переконатися, що метод doSomething() викликається з відповідним диспетчером. Для цього ми можемо використати функцію coAnswers з бібліотеки MockK, яка дозволяє нам визначити поведінку мока в асинхронному контексті. У нашому тесті ми перевіряємо, що контекст відповідності диспетчера дорівнює тому, який ми передали під час створення класу:

У цьому тесті ми використовуємо функцію every з MockK для визначення поведінки мока, який відповідає на виклик doSomething()