Как игнорировать исключение JobCancellationException? - PullRequest
0 голосов
/ 25 февраля 2019

Недавно я обновил Kotlin Coroutines с экспериментального до 1.1.1 и столкнулся с проблемой, что job.cancel() в новой версии работает по-другому.

Вот код с экспериментальными сопрограммами:

fun <R : Any, T : Deferred<R>> T.runAsync(
        job: Job,
        onSuccess: (result: R) -> Unit,
        onFailed: (errorMsg: String?) -> Unit) {
    launch(UI, parent = job) {
        try {
            val result = this@runAsync.await()
            onSuccess(result)
        } catch (e: Exception) {
            onFailed(e.message)
        }
    }
}

Вот с 1.1.1:

fun <R : Any, T : Deferred<R>> T.runAsync(
        job: Job,
        onSuccess: (result: R) -> Unit,
        onFailed: (errorMsg: String?) -> Unit) {
    GlobalScope.launch(Dispatchers.Main + job) {
        try {
            val result = withContext(Dispatchers.IO) {
                this@runAsync.await()
            }
            onSuccess(result)
        } catch (e: Exception) {
            onFailed(e.message)
        }
    }
}

Например:

Мой фрагмент уничтожен и вызван job.cancel() во время выполнения сопрограммы.

В экспериментальных сопрограммах также нетonSuccess() или onFailed() будет вызван.

В 1.1.1: onFailed() вызван, потому что пойман на JobCancellationException

Я решил добавить catch (e: JobCancellationException), но это невозможно:

/**
 * @suppress **This an internal API and should not be used from general code.**
 */
internal expect class JobCancellationException(

Итак, вопрос: как обращаться / игнорировать JobCancellationException?

1 Ответ

0 голосов
/ 25 февраля 2019

Вместо этого вы пытаетесь перехватить суперкласс CancellationException, который является частью общедоступного API.

Обратите внимание, что если что-то выдает CancellationException, вы, как правило, ожидаете выбросить его, так что объекты верхнего уровняуведомлены об отмене.См. Отмена сотрудничества

...