diff --git a/app/build.gradle b/app/build.gradle index b5a3876f1..0fb5009b1 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -82,7 +82,7 @@ afterEvaluate { } dependencies { //noinspection GradleDependency - implementation('com.github.KotatsuApp:kotatsu-parsers:44c2c074a8') { + implementation('com.github.KotatsuApp:kotatsu-parsers:786cd12dba') { exclude group: 'org.json', module: 'json' } diff --git a/app/src/main/kotlin/org/koitharu/kotatsu/core/db/dao/MangaDao.kt b/app/src/main/kotlin/org/koitharu/kotatsu/core/db/dao/MangaDao.kt index 404fa10c3..7ee5567b0 100644 --- a/app/src/main/kotlin/org/koitharu/kotatsu/core/db/dao/MangaDao.kt +++ b/app/src/main/kotlin/org/koitharu/kotatsu/core/db/dao/MangaDao.kt @@ -1,6 +1,7 @@ package org.koitharu.kotatsu.core.db.dao import androidx.room.Dao +import androidx.room.Delete import androidx.room.Insert import androidx.room.OnConflictStrategy import androidx.room.Query @@ -23,6 +24,10 @@ abstract class MangaDao { @Query("SELECT * FROM manga WHERE public_url = :publicUrl") abstract suspend fun findByPublicUrl(publicUrl: String): MangaWithTags? + @Transaction + @Query("SELECT * FROM manga WHERE source = :source") + abstract suspend fun findAllBySource(source: String): List + @Transaction @Query("SELECT * FROM manga WHERE (title LIKE :query OR alt_title LIKE :query) AND manga_id IN (SELECT manga_id FROM favourites UNION SELECT manga_id FROM history) LIMIT :limit") abstract suspend fun searchByTitle(query: String, limit: Int): List @@ -43,6 +48,10 @@ abstract class MangaDao { @Query("DELETE FROM manga_tags WHERE manga_id = :mangaId") abstract suspend fun clearTagRelation(mangaId: Long) + @Transaction + @Delete + abstract suspend fun delete(subjects: Collection) + @Transaction open suspend fun upsert(manga: MangaEntity, tags: Iterable? = null) { upsert(manga) diff --git a/app/src/main/kotlin/org/koitharu/kotatsu/core/parser/MangaDataRepository.kt b/app/src/main/kotlin/org/koitharu/kotatsu/core/parser/MangaDataRepository.kt index 4e2f9575b..ba2b08223 100644 --- a/app/src/main/kotlin/org/koitharu/kotatsu/core/parser/MangaDataRepository.kt +++ b/app/src/main/kotlin/org/koitharu/kotatsu/core/parser/MangaDataRepository.kt @@ -1,5 +1,6 @@ package org.koitharu.kotatsu.core.parser +import androidx.core.net.toUri import androidx.room.withTransaction import dagger.Reusable import kotlinx.coroutines.flow.Flow @@ -13,6 +14,7 @@ import org.koitharu.kotatsu.core.db.entity.toManga import org.koitharu.kotatsu.core.db.entity.toMangaTags import org.koitharu.kotatsu.core.model.isLocal import org.koitharu.kotatsu.core.prefs.ReaderMode +import org.koitharu.kotatsu.core.util.ext.toFileOrNull import org.koitharu.kotatsu.parsers.model.Manga import org.koitharu.kotatsu.parsers.model.MangaSource import org.koitharu.kotatsu.parsers.model.MangaTag @@ -97,6 +99,15 @@ class MangaDataRepository @Inject constructor( return db.getTagsDao().findTags(source.name).toMangaTags() } + suspend fun cleanupLocalManga() { + val dao = db.getMangaDao() + val broken = dao.findAllBySource(MangaSource.LOCAL.name) + .filter { x -> x.manga.url.toUri().toFileOrNull()?.exists() == false } + if (broken.isNotEmpty()) { + dao.delete(broken.map { it.manga }) + } + } + private fun MangaPrefsEntity.getColorFilterOrNull(): ReaderColorFilter? { return if (cfBrightness != 0f || cfContrast != 0f || cfInvert || cfGrayscale) { ReaderColorFilter(cfBrightness, cfContrast, cfInvert, cfGrayscale) diff --git a/app/src/main/kotlin/org/koitharu/kotatsu/local/ui/LocalStorageCleanupWorker.kt b/app/src/main/kotlin/org/koitharu/kotatsu/local/ui/LocalStorageCleanupWorker.kt index c505d4708..5791a3391 100644 --- a/app/src/main/kotlin/org/koitharu/kotatsu/local/ui/LocalStorageCleanupWorker.kt +++ b/app/src/main/kotlin/org/koitharu/kotatsu/local/ui/LocalStorageCleanupWorker.kt @@ -12,6 +12,7 @@ import androidx.work.WorkerParameters import androidx.work.await import dagger.assisted.Assisted import dagger.assisted.AssistedInject +import org.koitharu.kotatsu.core.parser.MangaDataRepository import org.koitharu.kotatsu.local.data.LocalMangaRepository import java.util.concurrent.TimeUnit @@ -20,10 +21,12 @@ class LocalStorageCleanupWorker @AssistedInject constructor( @Assisted appContext: Context, @Assisted params: WorkerParameters, private val localMangaRepository: LocalMangaRepository, + private val dataRepository: MangaDataRepository, ) : CoroutineWorker(appContext, params) { override suspend fun doWork(): Result { return if (localMangaRepository.cleanup()) { + dataRepository.cleanupLocalManga() Result.success() } else { Result.retry()