mirror of
				https://github.com/mihonapp/mihon.git
				synced 2025-11-04 08:08:55 +01:00 
			
		
		
		
	Use SQLDelight for all Chapter related queries (#7440)
This commit is contained in:
		@@ -99,4 +99,8 @@ class ChapterRepositoryImpl(
 | 
			
		||||
    override suspend fun getChapterByMangaIdAsFlow(mangaId: Long): Flow<List<Chapter>> {
 | 
			
		||||
        return handler.subscribeToList { chaptersQueries.getChaptersByMangaId(mangaId, chapterMapper) }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    override suspend fun getChapterByUrlAndMangaId(url: String, mangaId: Long): Chapter? {
 | 
			
		||||
        return handler.awaitOneOrNull { chaptersQueries.getChapterByUrlAndMangaId(url, mangaId, chapterMapper) }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -17,4 +17,13 @@ class GetChapter(
 | 
			
		||||
            null
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    suspend fun await(url: String, mangaId: Long): Chapter? {
 | 
			
		||||
        return try {
 | 
			
		||||
            chapterRepository.getChapterByUrlAndMangaId(url, mangaId)
 | 
			
		||||
        } catch (e: Exception) {
 | 
			
		||||
            logcat(LogPriority.ERROR, e)
 | 
			
		||||
            null
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -19,4 +19,6 @@ interface ChapterRepository {
 | 
			
		||||
    suspend fun getChapterById(id: Long): Chapter?
 | 
			
		||||
 | 
			
		||||
    suspend fun getChapterByMangaIdAsFlow(mangaId: Long): Flow<List<Chapter>>
 | 
			
		||||
 | 
			
		||||
    suspend fun getChapterByUrlAndMangaId(url: String, mangaId: Long): Chapter?
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -8,7 +8,6 @@ import eu.kanade.tachiyomi.data.database.mappers.MangaTypeMapping
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.models.Chapter
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.models.Manga
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.models.MangaCategory
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.queries.ChapterQueries
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.queries.MangaCategoryQueries
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.queries.MangaQueries
 | 
			
		||||
 | 
			
		||||
@@ -18,7 +17,7 @@ import eu.kanade.tachiyomi.data.database.queries.MangaQueries
 | 
			
		||||
class DatabaseHelper(
 | 
			
		||||
    openHelper: SupportSQLiteOpenHelper,
 | 
			
		||||
) :
 | 
			
		||||
    MangaQueries, ChapterQueries, MangaCategoryQueries {
 | 
			
		||||
    MangaQueries, MangaCategoryQueries {
 | 
			
		||||
 | 
			
		||||
    override val db = DefaultStorIOSQLite.builder()
 | 
			
		||||
        .sqliteOpenHelper(openHelper)
 | 
			
		||||
 
 | 
			
		||||
@@ -1,37 +0,0 @@
 | 
			
		||||
package eu.kanade.tachiyomi.data.database.queries
 | 
			
		||||
 | 
			
		||||
import com.pushtorefresh.storio.sqlite.queries.Query
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.DbProvider
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.models.Chapter
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.resolvers.ChapterProgressPutResolver
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.tables.ChapterTable
 | 
			
		||||
 | 
			
		||||
interface ChapterQueries : DbProvider {
 | 
			
		||||
 | 
			
		||||
    fun getChapter(id: Long) = db.get()
 | 
			
		||||
        .`object`(Chapter::class.java)
 | 
			
		||||
        .withQuery(
 | 
			
		||||
            Query.builder()
 | 
			
		||||
                .table(ChapterTable.TABLE)
 | 
			
		||||
                .where("${ChapterTable.COL_ID} = ?")
 | 
			
		||||
                .whereArgs(id)
 | 
			
		||||
                .build(),
 | 
			
		||||
        )
 | 
			
		||||
        .prepare()
 | 
			
		||||
 | 
			
		||||
    fun getChapter(url: String, mangaId: Long) = db.get()
 | 
			
		||||
        .`object`(Chapter::class.java)
 | 
			
		||||
        .withQuery(
 | 
			
		||||
            Query.builder()
 | 
			
		||||
                .table(ChapterTable.TABLE)
 | 
			
		||||
                .where("${ChapterTable.COL_URL} = ? AND ${ChapterTable.COL_MANGA_ID} = ?")
 | 
			
		||||
                .whereArgs(url, mangaId)
 | 
			
		||||
                .build(),
 | 
			
		||||
        )
 | 
			
		||||
        .prepare()
 | 
			
		||||
 | 
			
		||||
    fun updateChapterProgress(chapter: Chapter) = db.put()
 | 
			
		||||
        .`object`(chapter)
 | 
			
		||||
        .withPutResolver(ChapterProgressPutResolver())
 | 
			
		||||
        .prepare()
 | 
			
		||||
}
 | 
			
		||||
@@ -2,11 +2,15 @@ package eu.kanade.tachiyomi.data.download
 | 
			
		||||
 | 
			
		||||
import android.content.Context
 | 
			
		||||
import androidx.core.content.edit
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.DatabaseHelper
 | 
			
		||||
import eu.kanade.domain.chapter.interactor.GetChapter
 | 
			
		||||
import eu.kanade.domain.chapter.model.toDbChapter
 | 
			
		||||
import eu.kanade.domain.manga.interactor.GetMangaById
 | 
			
		||||
import eu.kanade.domain.manga.model.toDbManga
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.models.Manga
 | 
			
		||||
import eu.kanade.tachiyomi.data.download.model.Download
 | 
			
		||||
import eu.kanade.tachiyomi.source.SourceManager
 | 
			
		||||
import eu.kanade.tachiyomi.source.online.HttpSource
 | 
			
		||||
import kotlinx.coroutines.runBlocking
 | 
			
		||||
import kotlinx.serialization.Serializable
 | 
			
		||||
import kotlinx.serialization.decodeFromString
 | 
			
		||||
import kotlinx.serialization.encodeToString
 | 
			
		||||
@@ -29,7 +33,9 @@ class DownloadStore(
 | 
			
		||||
    private val preferences = context.getSharedPreferences("active_downloads", Context.MODE_PRIVATE)
 | 
			
		||||
 | 
			
		||||
    private val json: Json by injectLazy()
 | 
			
		||||
    private val db: DatabaseHelper by injectLazy()
 | 
			
		||||
 | 
			
		||||
    private val getMangaById: GetMangaById by injectLazy()
 | 
			
		||||
    private val getChapter: GetChapter by injectLazy()
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Counter used to keep the queue order.
 | 
			
		||||
@@ -90,10 +96,10 @@ class DownloadStore(
 | 
			
		||||
            val cachedManga = mutableMapOf<Long, Manga?>()
 | 
			
		||||
            for ((mangaId, chapterId) in objs) {
 | 
			
		||||
                val manga = cachedManga.getOrPut(mangaId) {
 | 
			
		||||
                    db.getManga(mangaId).executeAsBlocking()
 | 
			
		||||
                    runBlocking { getMangaById.await(mangaId)?.toDbManga() }
 | 
			
		||||
                } ?: continue
 | 
			
		||||
                val source = sourceManager.get(manga.source) as? HttpSource ?: continue
 | 
			
		||||
                val chapter = db.getChapter(chapterId).executeAsBlocking() ?: continue
 | 
			
		||||
                val chapter = runBlocking { getChapter.await(chapterId) }?.toDbChapter() ?: continue
 | 
			
		||||
                downloads.add(Download(source, manga, chapter))
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 
 | 
			
		||||
@@ -7,9 +7,14 @@ import android.content.Intent
 | 
			
		||||
import android.net.Uri
 | 
			
		||||
import android.os.Build
 | 
			
		||||
import androidx.core.content.ContextCompat
 | 
			
		||||
import eu.kanade.domain.chapter.interactor.GetChapter
 | 
			
		||||
import eu.kanade.domain.chapter.interactor.UpdateChapter
 | 
			
		||||
import eu.kanade.domain.chapter.model.toChapterUpdate
 | 
			
		||||
import eu.kanade.domain.chapter.model.toDbChapter
 | 
			
		||||
import eu.kanade.domain.manga.interactor.GetMangaById
 | 
			
		||||
import eu.kanade.domain.manga.model.toDbManga
 | 
			
		||||
import eu.kanade.tachiyomi.R
 | 
			
		||||
import eu.kanade.tachiyomi.data.backup.BackupRestoreService
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.DatabaseHelper
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.models.Chapter
 | 
			
		||||
import eu.kanade.tachiyomi.data.database.models.Manga
 | 
			
		||||
import eu.kanade.tachiyomi.data.download.DownloadManager
 | 
			
		||||
@@ -27,6 +32,7 @@ import eu.kanade.tachiyomi.util.storage.getUriCompat
 | 
			
		||||
import eu.kanade.tachiyomi.util.system.notificationManager
 | 
			
		||||
import eu.kanade.tachiyomi.util.system.toShareIntent
 | 
			
		||||
import eu.kanade.tachiyomi.util.system.toast
 | 
			
		||||
import kotlinx.coroutines.runBlocking
 | 
			
		||||
import uy.kohesive.injekt.Injekt
 | 
			
		||||
import uy.kohesive.injekt.api.get
 | 
			
		||||
import uy.kohesive.injekt.injectLazy
 | 
			
		||||
@@ -40,6 +46,9 @@ import eu.kanade.tachiyomi.BuildConfig.APPLICATION_ID as ID
 | 
			
		||||
 */
 | 
			
		||||
class NotificationReceiver : BroadcastReceiver() {
 | 
			
		||||
 | 
			
		||||
    private val getMangaById: GetMangaById by injectLazy()
 | 
			
		||||
    private val getChapter: GetChapter by injectLazy()
 | 
			
		||||
    private val updateChapter: UpdateChapter by injectLazy()
 | 
			
		||||
    private val downloadManager: DownloadManager by injectLazy()
 | 
			
		||||
 | 
			
		||||
    override fun onReceive(context: Context, intent: Intent) {
 | 
			
		||||
@@ -169,9 +178,8 @@ class NotificationReceiver : BroadcastReceiver() {
 | 
			
		||||
     * @param chapterId id of chapter
 | 
			
		||||
     */
 | 
			
		||||
    private fun openChapter(context: Context, mangaId: Long, chapterId: Long) {
 | 
			
		||||
        val db = Injekt.get<DatabaseHelper>()
 | 
			
		||||
        val manga = db.getManga(mangaId).executeAsBlocking()
 | 
			
		||||
        val chapter = db.getChapter(chapterId).executeAsBlocking()
 | 
			
		||||
        val manga = runBlocking { getMangaById.await(mangaId) }
 | 
			
		||||
        val chapter = runBlocking { getChapter.await(chapterId) }
 | 
			
		||||
        if (manga != null && chapter != null) {
 | 
			
		||||
            val intent = ReaderActivity.newIntent(context, manga.id, chapter.id).apply {
 | 
			
		||||
                flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_ACTIVITY_CLEAR_TOP
 | 
			
		||||
@@ -232,25 +240,25 @@ class NotificationReceiver : BroadcastReceiver() {
 | 
			
		||||
     * @param mangaId id of manga
 | 
			
		||||
     */
 | 
			
		||||
    private fun markAsRead(chapterUrls: Array<String>, mangaId: Long) {
 | 
			
		||||
        val db: DatabaseHelper = Injekt.get()
 | 
			
		||||
        val preferences: PreferencesHelper = Injekt.get()
 | 
			
		||||
        val sourceManager: SourceManager = Injekt.get()
 | 
			
		||||
 | 
			
		||||
        launchIO {
 | 
			
		||||
            chapterUrls.mapNotNull { db.getChapter(it, mangaId).executeAsBlocking() }
 | 
			
		||||
                .forEach {
 | 
			
		||||
                    it.read = true
 | 
			
		||||
                    db.updateChapterProgress(it).executeAsBlocking()
 | 
			
		||||
            val toUpdate = chapterUrls.mapNotNull { getChapter.await(it, mangaId) }
 | 
			
		||||
                .map {
 | 
			
		||||
                    val chapter = it.copy(read = true)
 | 
			
		||||
                    if (preferences.removeAfterMarkedAsRead()) {
 | 
			
		||||
                        val manga = db.getManga(mangaId).executeAsBlocking()
 | 
			
		||||
                        val manga = getMangaById.await(mangaId)
 | 
			
		||||
                        if (manga != null) {
 | 
			
		||||
                            val source = sourceManager.get(manga.source)
 | 
			
		||||
                            if (source != null) {
 | 
			
		||||
                                downloadManager.deleteChapters(listOf(it), manga, source)
 | 
			
		||||
                                downloadManager.deleteChapters(listOf(it.toDbChapter()), manga.toDbManga(), source)
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                    chapter.toChapterUpdate()
 | 
			
		||||
                }
 | 
			
		||||
            updateChapter.awaitAll(toUpdate)
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@@ -261,12 +269,10 @@ class NotificationReceiver : BroadcastReceiver() {
 | 
			
		||||
     * @param mangaId id of manga
 | 
			
		||||
     */
 | 
			
		||||
    private fun downloadChapters(chapterUrls: Array<String>, mangaId: Long) {
 | 
			
		||||
        val db: DatabaseHelper = Injekt.get()
 | 
			
		||||
 | 
			
		||||
        launchIO {
 | 
			
		||||
            val chapters = chapterUrls.mapNotNull { db.getChapter(it, mangaId).executeAsBlocking() }
 | 
			
		||||
            val manga = db.getManga(mangaId).executeAsBlocking()
 | 
			
		||||
            if (chapters.isNotEmpty() && manga != null) {
 | 
			
		||||
            val manga = getMangaById.await(mangaId)?.toDbManga()
 | 
			
		||||
            val chapters = chapterUrls.mapNotNull { getChapter.await(it, mangaId)?.toDbChapter() }
 | 
			
		||||
            if (manga != null && chapters.isNotEmpty()) {
 | 
			
		||||
                downloadManager.downloadChapters(manga, chapters)
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 
 | 
			
		||||
@@ -540,13 +540,16 @@ class ReaderPresenter(
 | 
			
		||||
     * Bookmarks the currently active chapter.
 | 
			
		||||
     */
 | 
			
		||||
    fun bookmarkCurrentChapter(bookmarked: Boolean) {
 | 
			
		||||
        if (getCurrentChapter()?.chapter == null) {
 | 
			
		||||
            return
 | 
			
		||||
        val chapter = getCurrentChapter()?.chapter ?: return
 | 
			
		||||
        chapter.bookmark = bookmarked // Otherwise the bookmark icon doesn't update
 | 
			
		||||
        launchIO {
 | 
			
		||||
            updateChapter.await(
 | 
			
		||||
                ChapterUpdate(
 | 
			
		||||
                    id = chapter.id!!.toLong(),
 | 
			
		||||
                    bookmark = bookmarked,
 | 
			
		||||
                ),
 | 
			
		||||
            )
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        val chapter = getCurrentChapter()?.chapter!!
 | 
			
		||||
        chapter.bookmark = bookmarked
 | 
			
		||||
        db.updateChapterProgress(chapter).executeAsBlocking()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user