diff --git a/app/build.gradle b/app/build.gradle index 6621f9067..e6e7b986f 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -56,6 +56,7 @@ android { kotlinOptions { jvmTarget = JavaVersion.VERSION_1_8.toString() freeCompilerArgs += [ + '-opt-in=kotlin.ExperimentalStdlibApi', '-opt-in=kotlinx.coroutines.ExperimentalCoroutinesApi', '-opt-in=kotlinx.coroutines.FlowPreview', '-opt-in=kotlin.contracts.ExperimentalContracts', diff --git a/app/src/main/java/org/koitharu/kotatsu/core/cache/DeferredLruCache.kt b/app/src/main/java/org/koitharu/kotatsu/core/cache/DeferredLruCache.kt index f92561198..8b9e08aa3 100644 --- a/app/src/main/java/org/koitharu/kotatsu/core/cache/DeferredLruCache.kt +++ b/app/src/main/java/org/koitharu/kotatsu/core/cache/DeferredLruCache.kt @@ -2,15 +2,4 @@ package org.koitharu.kotatsu.core.cache import androidx.collection.LruCache -class DeferredLruCache(maxSize: Int) : LruCache>(maxSize) { - - override fun entryRemoved( - evicted: Boolean, - key: ContentCache.Key, - oldValue: SafeDeferred, - newValue: SafeDeferred?, - ) { - super.entryRemoved(evicted, key, oldValue, newValue) - oldValue.cancel() - } -} +class DeferredLruCache(maxSize: Int) : LruCache>(maxSize) diff --git a/app/src/main/java/org/koitharu/kotatsu/core/parser/RemoteMangaRepository.kt b/app/src/main/java/org/koitharu/kotatsu/core/parser/RemoteMangaRepository.kt index 439d06494..ecd2d170f 100644 --- a/app/src/main/java/org/koitharu/kotatsu/core/parser/RemoteMangaRepository.kt +++ b/app/src/main/java/org/koitharu/kotatsu/core/parser/RemoteMangaRepository.kt @@ -1,8 +1,11 @@ package org.koitharu.kotatsu.core.parser +import kotlinx.coroutines.CoroutineDispatcher import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Dispatchers +import kotlinx.coroutines.MainCoroutineDispatcher import kotlinx.coroutines.async +import kotlinx.coroutines.currentCoroutineContext import org.koitharu.kotatsu.core.cache.ContentCache import org.koitharu.kotatsu.core.cache.SafeDeferred import org.koitharu.kotatsu.core.prefs.SourceSettings @@ -76,9 +79,15 @@ class RemoteMangaRepository( private fun getConfig() = parser.config as SourceSettings - private fun asyncSafe(block: suspend CoroutineScope.() -> T) = SafeDeferred( - processLifecycleScope.async(Dispatchers.Default) { - runCatchingCancellable { block() } - }, - ) + private suspend fun asyncSafe(block: suspend CoroutineScope.() -> T): SafeDeferred { + var dispatcher = currentCoroutineContext()[CoroutineDispatcher.Key] + if (dispatcher == null || dispatcher is MainCoroutineDispatcher) { + dispatcher = Dispatchers.Default + } + return SafeDeferred( + processLifecycleScope.async(dispatcher) { + runCatchingCancellable { block() } + }, + ) + } } diff --git a/app/src/main/java/org/koitharu/kotatsu/details/service/MangaPrefetchService.kt b/app/src/main/java/org/koitharu/kotatsu/details/service/MangaPrefetchService.kt index 06880b7cc..adeeea983 100644 --- a/app/src/main/java/org/koitharu/kotatsu/details/service/MangaPrefetchService.kt +++ b/app/src/main/java/org/koitharu/kotatsu/details/service/MangaPrefetchService.kt @@ -4,7 +4,6 @@ import android.content.Context import android.content.Intent import dagger.hilt.android.AndroidEntryPoint import dagger.hilt.android.EntryPointAccessors -import kotlinx.coroutines.coroutineScope import org.koitharu.kotatsu.base.ui.CoroutineIntentService import org.koitharu.kotatsu.core.cache.ContentCache import org.koitharu.kotatsu.core.model.parcelable.ParcelableManga @@ -47,7 +46,7 @@ class MangaPrefetchService : CoroutineIntentService() { override fun onError(startId: Int, error: Throwable) = Unit - private suspend fun prefetchDetails(manga: Manga) = coroutineScope { + private suspend fun prefetchDetails(manga: Manga) { val source = mangaRepositoryFactory.create(manga.source) runCatchingCancellable { source.getDetails(manga) } } diff --git a/app/src/main/java/org/koitharu/kotatsu/tracker/work/TrackWorker.kt b/app/src/main/java/org/koitharu/kotatsu/tracker/work/TrackWorker.kt index b4575a033..fa488b146 100644 --- a/app/src/main/java/org/koitharu/kotatsu/tracker/work/TrackWorker.kt +++ b/app/src/main/java/org/koitharu/kotatsu/tracker/work/TrackWorker.kt @@ -30,12 +30,11 @@ import coil.ImageLoader import coil.request.ImageRequest import dagger.assisted.Assisted import dagger.assisted.AssistedInject -import kotlinx.coroutines.Deferred import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.NonCancellable import kotlinx.coroutines.async import kotlinx.coroutines.awaitAll -import kotlinx.coroutines.coroutineScope +import kotlinx.coroutines.supervisorScope import kotlinx.coroutines.withContext import org.koitharu.kotatsu.R import org.koitharu.kotatsu.core.logs.FileLogger @@ -94,8 +93,7 @@ class TrackWorker @AssistedInject constructor( return Result.success(workDataOf(0, 0)) } - val updates = checkUpdatesAsync(tracks) - val results = updates.awaitAll() + val results = checkUpdatesAsync(tracks) tracker.gc() var success = 0 @@ -116,9 +114,9 @@ class TrackWorker @AssistedInject constructor( } } - private suspend fun checkUpdatesAsync(tracks: List): List> { + private suspend fun checkUpdatesAsync(tracks: List): List { val dispatcher = Dispatchers.Default.limitedParallelism(MAX_PARALLELISM) - val deferredList = coroutineScope { + return supervisorScope { tracks.map { (track, channelId) -> async(dispatcher) { runCatchingCancellable { @@ -135,9 +133,8 @@ class TrackWorker @AssistedInject constructor( } }.getOrNull() } - } + }.awaitAll() } - return deferredList } private suspend fun showNotification(manga: Manga, channelId: String?, newChapters: List) {