Update merge chapters in parallel, protect against one failing and stopping the whole thing

This commit is contained in:
Jobobby04 2021-05-09 18:41:19 -04:00
parent fc354f5792
commit 7e1389ef05

View File

@ -22,6 +22,10 @@ import exh.log.xLogW
import exh.merged.sql.models.MergedMangaReference import exh.merged.sql.models.MergedMangaReference
import exh.source.MERGED_SOURCE_ID import exh.source.MERGED_SOURCE_ID
import exh.util.executeOnIO import exh.util.executeOnIO
import kotlinx.coroutines.CancellationException
import kotlinx.coroutines.async
import kotlinx.coroutines.awaitAll
import kotlinx.coroutines.supervisorScope
import okhttp3.Response import okhttp3.Response
import rx.Observable import rx.Observable
import tachiyomi.source.model.ChapterInfo import tachiyomi.source.model.ChapterInfo
@ -142,33 +146,44 @@ class MergedSource : HttpSource() {
if (mangaReferences.isEmpty()) throw IllegalArgumentException("Manga references are empty, chapters unavailable, merge is likely corrupted") if (mangaReferences.isEmpty()) throw IllegalArgumentException("Manga references are empty, chapters unavailable, merge is likely corrupted")
val ifDownloadNewChapters = downloadChapters && manga.shouldDownloadNewChapters(db, preferences) val ifDownloadNewChapters = downloadChapters && manga.shouldDownloadNewChapters(db, preferences)
return mangaReferences.filter { it.mangaSourceId != MERGED_SOURCE_ID }.map { var exception: Exception? = null
it.load(db, sourceManager) return supervisorScope {
}.mapNotNull { loadedManga -> mangaReferences
withIOContext { .map {
if (loadedManga.manga != null && loadedManga.reference.getChapterUpdates) { async {
loadedManga.source.getChapterList(loadedManga.manga.toMangaInfo()) try {
.map { it.toSChapter() } if (it.mangaSourceId == MERGED_SOURCE_ID) return@async null
.let { syncChaptersWithSource(db, it, loadedManga.manga, loadedManga.source) } val (source, loadedManga, reference) =
.also { it.load(db, sourceManager)
if (ifDownloadNewChapters && loadedManga.reference.downloadChapters) { if (loadedManga != null && reference.getChapterUpdates) {
downloadManager.downloadChapters(loadedManga.manga, it.first) val chapterList = source.getChapterList(loadedManga.toMangaInfo())
.map { it.toSChapter() }
val results =
syncChaptersWithSource(db, chapterList, loadedManga, source)
if (ifDownloadNewChapters && reference.downloadChapters) {
downloadManager.downloadChapters(
loadedManga,
results.first
)
}
results
} else {
null
} }
} catch (e: Exception) {
if (e is CancellationException) throw e
exception = e
null
} }
} else { }
null }
.awaitAll()
.let { pairs ->
if (exception != null) {
throw exception!!
}
pairs.flatMap { it?.first.orEmpty() } to pairs.flatMap { it?.second.orEmpty() }
} }
}
}.let { pairs ->
val firsts = mutableListOf<Chapter>()
val seconds = mutableListOf<Chapter>()
pairs.forEach {
firsts.addAll(it.first)
seconds.addAll(it.second)
}
firsts to seconds
} }
} }