Cleanup migrate manga dialog and related code (#2156)
This commit is contained in:
@@ -0,0 +1,145 @@
|
||||
package mihon.domain.migration.usecases
|
||||
|
||||
import eu.kanade.domain.chapter.interactor.SyncChaptersWithSource
|
||||
import eu.kanade.domain.manga.interactor.UpdateManga
|
||||
import eu.kanade.domain.manga.model.hasCustomCover
|
||||
import eu.kanade.domain.manga.model.toSManga
|
||||
import eu.kanade.domain.source.service.SourcePreferences
|
||||
import eu.kanade.tachiyomi.data.cache.CoverCache
|
||||
import eu.kanade.tachiyomi.data.download.DownloadManager
|
||||
import eu.kanade.tachiyomi.data.track.EnhancedTracker
|
||||
import eu.kanade.tachiyomi.data.track.TrackerManager
|
||||
import kotlinx.coroutines.CancellationException
|
||||
import mihon.domain.migration.models.MigrationFlag
|
||||
import tachiyomi.domain.category.interactor.GetCategories
|
||||
import tachiyomi.domain.category.interactor.SetMangaCategories
|
||||
import tachiyomi.domain.chapter.interactor.GetChaptersByMangaId
|
||||
import tachiyomi.domain.chapter.interactor.UpdateChapter
|
||||
import tachiyomi.domain.chapter.model.toChapterUpdate
|
||||
import tachiyomi.domain.manga.model.Manga
|
||||
import tachiyomi.domain.manga.model.MangaUpdate
|
||||
import tachiyomi.domain.source.service.SourceManager
|
||||
import tachiyomi.domain.track.interactor.GetTracks
|
||||
import tachiyomi.domain.track.interactor.InsertTrack
|
||||
import java.time.Instant
|
||||
|
||||
class MigrateMangaUseCase(
|
||||
private val sourcePreferences: SourcePreferences,
|
||||
private val trackerManager: TrackerManager,
|
||||
private val sourceManager: SourceManager,
|
||||
private val downloadManager: DownloadManager,
|
||||
private val updateManga: UpdateManga,
|
||||
private val getChaptersByMangaId: GetChaptersByMangaId,
|
||||
private val syncChaptersWithSource: SyncChaptersWithSource,
|
||||
private val updateChapter: UpdateChapter,
|
||||
private val getCategories: GetCategories,
|
||||
private val setMangaCategories: SetMangaCategories,
|
||||
private val getTracks: GetTracks,
|
||||
private val insertTrack: InsertTrack,
|
||||
private val coverCache: CoverCache,
|
||||
) {
|
||||
private val enhancedServices by lazy { trackerManager.trackers.filterIsInstance<EnhancedTracker>() }
|
||||
|
||||
suspend operator fun invoke(current: Manga, target: Manga, replace: Boolean) {
|
||||
val targetSource = sourceManager.get(target.source) ?: return
|
||||
val currentSource = sourceManager.get(current.source)
|
||||
val flags = sourcePreferences.migrationFlags().get()
|
||||
|
||||
try {
|
||||
val chapters = targetSource.getChapterList(target.toSManga())
|
||||
|
||||
try {
|
||||
syncChaptersWithSource.await(chapters, target, targetSource)
|
||||
} catch (_: Exception) {
|
||||
// Worst case, chapters won't be synced
|
||||
}
|
||||
|
||||
// Update chapters read, bookmark and dateFetch
|
||||
if (MigrationFlag.CHAPTER in flags) {
|
||||
val prevMangaChapters = getChaptersByMangaId.await(current.id)
|
||||
val mangaChapters = getChaptersByMangaId.await(target.id)
|
||||
|
||||
val maxChapterRead = prevMangaChapters
|
||||
.filter { it.read }
|
||||
.maxOfOrNull { it.chapterNumber }
|
||||
|
||||
val updatedMangaChapters = mangaChapters.map { mangaChapter ->
|
||||
var updatedChapter = mangaChapter
|
||||
if (updatedChapter.isRecognizedNumber) {
|
||||
val prevChapter = prevMangaChapters
|
||||
.find { it.isRecognizedNumber && it.chapterNumber == updatedChapter.chapterNumber }
|
||||
|
||||
if (prevChapter != null) {
|
||||
updatedChapter = updatedChapter.copy(
|
||||
dateFetch = prevChapter.dateFetch,
|
||||
bookmark = prevChapter.bookmark,
|
||||
)
|
||||
}
|
||||
|
||||
if (maxChapterRead != null && updatedChapter.chapterNumber <= maxChapterRead) {
|
||||
updatedChapter = updatedChapter.copy(read = true)
|
||||
}
|
||||
}
|
||||
|
||||
updatedChapter
|
||||
}
|
||||
|
||||
val chapterUpdates = updatedMangaChapters.map { it.toChapterUpdate() }
|
||||
updateChapter.awaitAll(chapterUpdates)
|
||||
}
|
||||
|
||||
// Update categories
|
||||
if (MigrationFlag.CHAPTER in flags) {
|
||||
val categoryIds = getCategories.await(current.id).map { it.id }
|
||||
setMangaCategories.await(target.id, categoryIds)
|
||||
}
|
||||
|
||||
// Update track
|
||||
getTracks.await(current.id).mapNotNull { track ->
|
||||
val updatedTrack = track.copy(mangaId = target.id)
|
||||
|
||||
val service = enhancedServices
|
||||
.firstOrNull { it.isTrackFrom(updatedTrack, current, currentSource) }
|
||||
|
||||
if (service != null) {
|
||||
service.migrateTrack(updatedTrack, target, targetSource)
|
||||
} else {
|
||||
updatedTrack
|
||||
}
|
||||
}
|
||||
.takeIf { it.isNotEmpty() }
|
||||
?.let { insertTrack.awaitAll(it) }
|
||||
|
||||
// Delete downloaded
|
||||
if (MigrationFlag.REMOVE_DOWNLOAD in flags && currentSource != null) {
|
||||
downloadManager.deleteManga(current, currentSource)
|
||||
}
|
||||
|
||||
// Update custom cover (recheck if custom cover exists)
|
||||
if (MigrationFlag.CUSTOM_COVER in flags && current.hasCustomCover()) {
|
||||
coverCache.setCustomCoverToCache(target, coverCache.getCustomCoverFile(current.id).inputStream())
|
||||
}
|
||||
|
||||
val currentMangaUpdate = MangaUpdate(
|
||||
id = current.id,
|
||||
favorite = false,
|
||||
dateAdded = 0,
|
||||
)
|
||||
.takeIf { replace }
|
||||
val targetMangaUpdate = MangaUpdate(
|
||||
id = target.id,
|
||||
favorite = true,
|
||||
chapterFlags = current.chapterFlags,
|
||||
viewerFlags = current.viewerFlags,
|
||||
dateAdded = if (replace) current.dateAdded else Instant.now().toEpochMilli(),
|
||||
notes = if (MigrationFlag.NOTES in flags) current.notes else null,
|
||||
)
|
||||
|
||||
updateManga.awaitAll(listOfNotNull(currentMangaUpdate, targetMangaUpdate))
|
||||
} catch (e: Throwable) {
|
||||
if (e is CancellationException) {
|
||||
throw e
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user