mirror of
https://github.com/Suwayomi/Tachidesk.git
synced 2025-12-21 12:02:35 +01:00
Fix new private parameter in tracking backup (#1463)
* Fix new private parameter in tracking backup * Cleanup uneeded models
This commit is contained in:
@@ -1,29 +0,0 @@
|
|||||||
@file:Suppress("ktlint:standard:property-naming")
|
|
||||||
|
|
||||||
package suwayomi.tachidesk.manga.impl.backup.models
|
|
||||||
|
|
||||||
import eu.kanade.tachiyomi.source.model.SChapter
|
|
||||||
import java.io.Serializable
|
|
||||||
|
|
||||||
interface Chapter :
|
|
||||||
SChapter,
|
|
||||||
Serializable {
|
|
||||||
var id: Long?
|
|
||||||
|
|
||||||
var manga_id: Long?
|
|
||||||
|
|
||||||
var read: Boolean
|
|
||||||
|
|
||||||
var bookmark: Boolean
|
|
||||||
|
|
||||||
var last_page_read: Int
|
|
||||||
|
|
||||||
var date_fetch: Long
|
|
||||||
|
|
||||||
var source_order: Int
|
|
||||||
|
|
||||||
var meta: Map<String, String>
|
|
||||||
|
|
||||||
val isRecognizedNumber: Boolean
|
|
||||||
get() = chapter_number >= 0f
|
|
||||||
}
|
|
||||||
@@ -1,42 +0,0 @@
|
|||||||
@file:Suppress("ktlint:standard:property-naming")
|
|
||||||
|
|
||||||
package suwayomi.tachidesk.manga.impl.backup.models
|
|
||||||
|
|
||||||
class ChapterImpl : Chapter {
|
|
||||||
override var id: Long? = null
|
|
||||||
|
|
||||||
override var manga_id: Long? = null
|
|
||||||
|
|
||||||
override lateinit var url: String
|
|
||||||
|
|
||||||
override lateinit var name: String
|
|
||||||
|
|
||||||
override var scanlator: String? = null
|
|
||||||
|
|
||||||
override var read: Boolean = false
|
|
||||||
|
|
||||||
override var bookmark: Boolean = false
|
|
||||||
|
|
||||||
override var last_page_read: Int = 0
|
|
||||||
|
|
||||||
override var date_fetch: Long = 0
|
|
||||||
|
|
||||||
override var date_upload: Long = 0
|
|
||||||
|
|
||||||
override var chapter_number: Float = 0f
|
|
||||||
|
|
||||||
override var source_order: Int = 0
|
|
||||||
|
|
||||||
override var meta: Map<String, String> = emptyMap()
|
|
||||||
|
|
||||||
override fun equals(other: Any?): Boolean {
|
|
||||||
if (this === other) return true
|
|
||||||
if (other == null || javaClass != other.javaClass) return false
|
|
||||||
|
|
||||||
val chapter = other as Chapter
|
|
||||||
if (url != chapter.url) return false
|
|
||||||
return id == chapter.id
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun hashCode(): Int = url.hashCode() + id.hashCode()
|
|
||||||
}
|
|
||||||
@@ -1,135 +0,0 @@
|
|||||||
@file:Suppress("ktlint:standard:property-naming")
|
|
||||||
|
|
||||||
package suwayomi.tachidesk.manga.impl.backup.models
|
|
||||||
|
|
||||||
import eu.kanade.tachiyomi.source.model.SManga
|
|
||||||
// import eu.kanade.tachiyomi.ui.reader.setting.OrientationType
|
|
||||||
// import eu.kanade.tachiyomi.ui.reader.setting.ReadingModeType
|
|
||||||
|
|
||||||
// substitute for eu.kanade.tachiyomi.ui.reader.setting.OrientationType
|
|
||||||
object OrientationType {
|
|
||||||
const val MASK = 0x00000038
|
|
||||||
}
|
|
||||||
|
|
||||||
// substitute for eu.kanade.tachiyomi.ui.reader.setting.ReadingModeType
|
|
||||||
object ReadingModeType {
|
|
||||||
const val MASK = 0x00000007
|
|
||||||
}
|
|
||||||
|
|
||||||
interface Manga : SManga {
|
|
||||||
var id: Long?
|
|
||||||
|
|
||||||
var source: Long
|
|
||||||
|
|
||||||
var favorite: Boolean
|
|
||||||
|
|
||||||
// last time the chapter list changed in any way
|
|
||||||
var last_update: Long
|
|
||||||
|
|
||||||
// predicted next update time based on latest (by date) 4 chapters' deltas
|
|
||||||
var next_update: Long
|
|
||||||
|
|
||||||
var date_added: Long
|
|
||||||
|
|
||||||
var viewer_flags: Int
|
|
||||||
|
|
||||||
var chapter_flags: Int
|
|
||||||
|
|
||||||
var cover_last_modified: Long
|
|
||||||
|
|
||||||
var meta: Map<String, String>
|
|
||||||
|
|
||||||
fun setChapterOrder(order: Int) {
|
|
||||||
setChapterFlags(order, CHAPTER_SORT_MASK)
|
|
||||||
}
|
|
||||||
|
|
||||||
fun sortDescending(): Boolean = chapter_flags and CHAPTER_SORT_MASK == CHAPTER_SORT_DESC
|
|
||||||
|
|
||||||
fun getGenres(): List<String>? = genre?.split(", ")?.map { it.trim() }
|
|
||||||
|
|
||||||
private fun setChapterFlags(
|
|
||||||
flag: Int,
|
|
||||||
mask: Int,
|
|
||||||
) {
|
|
||||||
chapter_flags = chapter_flags and mask.inv() or (flag and mask)
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun setViewerFlags(
|
|
||||||
flag: Int,
|
|
||||||
mask: Int,
|
|
||||||
) {
|
|
||||||
viewer_flags = viewer_flags and mask.inv() or (flag and mask)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Used to display the chapter's title one way or another
|
|
||||||
var displayMode: Int
|
|
||||||
get() = chapter_flags and CHAPTER_DISPLAY_MASK
|
|
||||||
set(mode) = setChapterFlags(mode, CHAPTER_DISPLAY_MASK)
|
|
||||||
|
|
||||||
var readFilter: Int
|
|
||||||
get() = chapter_flags and CHAPTER_READ_MASK
|
|
||||||
set(filter) = setChapterFlags(filter, CHAPTER_READ_MASK)
|
|
||||||
|
|
||||||
var downloadedFilter: Int
|
|
||||||
get() = chapter_flags and CHAPTER_DOWNLOADED_MASK
|
|
||||||
set(filter) = setChapterFlags(filter, CHAPTER_DOWNLOADED_MASK)
|
|
||||||
|
|
||||||
var bookmarkedFilter: Int
|
|
||||||
get() = chapter_flags and CHAPTER_BOOKMARKED_MASK
|
|
||||||
set(filter) = setChapterFlags(filter, CHAPTER_BOOKMARKED_MASK)
|
|
||||||
|
|
||||||
var sorting: Int
|
|
||||||
get() = chapter_flags and CHAPTER_SORTING_MASK
|
|
||||||
set(sort) = setChapterFlags(sort, CHAPTER_SORTING_MASK)
|
|
||||||
|
|
||||||
var readingModeType: Int
|
|
||||||
get() = viewer_flags and ReadingModeType.MASK
|
|
||||||
set(readingMode) = setViewerFlags(readingMode, ReadingModeType.MASK)
|
|
||||||
|
|
||||||
var orientationType: Int
|
|
||||||
get() = viewer_flags and OrientationType.MASK
|
|
||||||
set(rotationType) = setViewerFlags(rotationType, OrientationType.MASK)
|
|
||||||
|
|
||||||
companion object {
|
|
||||||
// Generic filter that does not filter anything
|
|
||||||
const val SHOW_ALL = 0x00000000
|
|
||||||
|
|
||||||
const val CHAPTER_SORT_DESC = 0x00000000
|
|
||||||
const val CHAPTER_SORT_ASC = 0x00000001
|
|
||||||
const val CHAPTER_SORT_MASK = 0x00000001
|
|
||||||
|
|
||||||
const val CHAPTER_SHOW_UNREAD = 0x00000002
|
|
||||||
const val CHAPTER_SHOW_READ = 0x00000004
|
|
||||||
const val CHAPTER_READ_MASK = 0x00000006
|
|
||||||
|
|
||||||
const val CHAPTER_SHOW_DOWNLOADED = 0x00000008
|
|
||||||
const val CHAPTER_SHOW_NOT_DOWNLOADED = 0x00000010
|
|
||||||
const val CHAPTER_DOWNLOADED_MASK = 0x00000018
|
|
||||||
|
|
||||||
const val CHAPTER_SHOW_BOOKMARKED = 0x00000020
|
|
||||||
const val CHAPTER_SHOW_NOT_BOOKMARKED = 0x00000040
|
|
||||||
const val CHAPTER_BOOKMARKED_MASK = 0x00000060
|
|
||||||
|
|
||||||
const val CHAPTER_SORTING_SOURCE = 0x00000000
|
|
||||||
const val CHAPTER_SORTING_NUMBER = 0x00000100
|
|
||||||
const val CHAPTER_SORTING_UPLOAD_DATE = 0x00000200
|
|
||||||
const val CHAPTER_SORTING_MASK = 0x00000300
|
|
||||||
|
|
||||||
const val CHAPTER_DISPLAY_NAME = 0x00000000
|
|
||||||
const val CHAPTER_DISPLAY_NUMBER = 0x00100000
|
|
||||||
const val CHAPTER_DISPLAY_MASK = 0x00100000
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// fun Manga.toMangaInfo(): MangaInfo {
|
|
||||||
// return MangaInfo(
|
|
||||||
// artist = this.artist ?: "",
|
|
||||||
// author = this.author ?: "",
|
|
||||||
// cover = this.thumbnail_url ?: "",
|
|
||||||
// description = this.description ?: "",
|
|
||||||
// genres = this.getGenres() ?: emptyList(),
|
|
||||||
// key = this.url,
|
|
||||||
// status = this.status,
|
|
||||||
// title = this.title
|
|
||||||
// )
|
|
||||||
// }
|
|
||||||
@@ -1,69 +0,0 @@
|
|||||||
@file:Suppress("ktlint:standard:property-naming")
|
|
||||||
|
|
||||||
package suwayomi.tachidesk.manga.impl.backup.models
|
|
||||||
|
|
||||||
import eu.kanade.tachiyomi.source.model.UpdateStrategy
|
|
||||||
|
|
||||||
open class MangaImpl : Manga {
|
|
||||||
override var id: Long? = null
|
|
||||||
|
|
||||||
override var source: Long = -1
|
|
||||||
|
|
||||||
override lateinit var url: String
|
|
||||||
|
|
||||||
override lateinit var title: String
|
|
||||||
|
|
||||||
override var artist: String? = null
|
|
||||||
|
|
||||||
override var author: String? = null
|
|
||||||
|
|
||||||
override var description: String? = null
|
|
||||||
|
|
||||||
override var genre: String? = null
|
|
||||||
|
|
||||||
override var status: Int = 0
|
|
||||||
|
|
||||||
override var thumbnail_url: String? = null
|
|
||||||
|
|
||||||
override var update_strategy: UpdateStrategy = UpdateStrategy.ALWAYS_UPDATE
|
|
||||||
|
|
||||||
override var favorite: Boolean = false
|
|
||||||
|
|
||||||
override var last_update: Long = 0
|
|
||||||
|
|
||||||
override var next_update: Long = 0
|
|
||||||
|
|
||||||
override var date_added: Long = 0
|
|
||||||
|
|
||||||
override var initialized: Boolean = false
|
|
||||||
|
|
||||||
override var meta: Map<String, String> = emptyMap()
|
|
||||||
|
|
||||||
/** Reader mode value
|
|
||||||
* ref: https://github.com/tachiyomiorg/tachiyomi/blob/ff369010074b058bb734ce24c66508300e6e9ac6/app/src/main/java/eu/kanade/tachiyomi/ui/reader/setting/ReadingModeType.kt#L8
|
|
||||||
* 0 -> Default
|
|
||||||
* 1 -> Left to Right
|
|
||||||
* 2 -> Right to Left
|
|
||||||
* 3 -> Vertical
|
|
||||||
* 4 -> Webtoon
|
|
||||||
* 5 -> Continues Vertical
|
|
||||||
*/
|
|
||||||
override var viewer_flags: Int = 0
|
|
||||||
|
|
||||||
/** Contains some useful info about
|
|
||||||
*/
|
|
||||||
override var chapter_flags: Int = 0
|
|
||||||
|
|
||||||
override var cover_last_modified: Long = 0
|
|
||||||
|
|
||||||
override fun equals(other: Any?): Boolean {
|
|
||||||
if (this === other) return true
|
|
||||||
if (other == null || javaClass != other.javaClass) return false
|
|
||||||
|
|
||||||
val manga = other as Manga
|
|
||||||
if (url != manga.url) return false
|
|
||||||
return id == manga.id
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun hashCode(): Int = url.hashCode() + id.hashCode()
|
|
||||||
}
|
|
||||||
@@ -1,33 +0,0 @@
|
|||||||
@file:Suppress("ktlint:standard:property-naming")
|
|
||||||
|
|
||||||
package suwayomi.tachidesk.manga.impl.backup.models
|
|
||||||
|
|
||||||
import java.io.Serializable
|
|
||||||
|
|
||||||
interface Track : Serializable {
|
|
||||||
var id: Long?
|
|
||||||
|
|
||||||
var manga_id: Long
|
|
||||||
|
|
||||||
var sync_id: Int
|
|
||||||
|
|
||||||
var media_id: Long
|
|
||||||
|
|
||||||
var library_id: Long?
|
|
||||||
|
|
||||||
var title: String
|
|
||||||
|
|
||||||
var last_chapter_read: Int
|
|
||||||
|
|
||||||
var total_chapters: Int
|
|
||||||
|
|
||||||
var score: Float
|
|
||||||
|
|
||||||
var status: Int
|
|
||||||
|
|
||||||
var started_reading_date: Long
|
|
||||||
|
|
||||||
var finished_reading_date: Long
|
|
||||||
|
|
||||||
var tracking_url: String
|
|
||||||
}
|
|
||||||
@@ -1,49 +0,0 @@
|
|||||||
@file:Suppress("ktlint:standard:property-naming")
|
|
||||||
|
|
||||||
package suwayomi.tachidesk.manga.impl.backup.models
|
|
||||||
|
|
||||||
class TrackImpl : Track {
|
|
||||||
override var id: Long? = null
|
|
||||||
|
|
||||||
override var manga_id: Long = 0
|
|
||||||
|
|
||||||
override var sync_id: Int = 0
|
|
||||||
|
|
||||||
override var media_id: Long = 0L
|
|
||||||
|
|
||||||
override var library_id: Long? = null
|
|
||||||
|
|
||||||
override lateinit var title: String
|
|
||||||
|
|
||||||
override var last_chapter_read: Int = 0
|
|
||||||
|
|
||||||
override var total_chapters: Int = 0
|
|
||||||
|
|
||||||
override var score: Float = 0f
|
|
||||||
|
|
||||||
override var status: Int = 0
|
|
||||||
|
|
||||||
override var started_reading_date: Long = 0
|
|
||||||
|
|
||||||
override var finished_reading_date: Long = 0
|
|
||||||
|
|
||||||
override var tracking_url: String = ""
|
|
||||||
|
|
||||||
override fun equals(other: Any?): Boolean {
|
|
||||||
if (this === other) return true
|
|
||||||
if (other == null || javaClass != other.javaClass) return false
|
|
||||||
|
|
||||||
other as Track
|
|
||||||
|
|
||||||
if (manga_id != other.manga_id) return false
|
|
||||||
if (sync_id != other.sync_id) return false
|
|
||||||
return media_id == other.media_id
|
|
||||||
}
|
|
||||||
|
|
||||||
override fun hashCode(): Int {
|
|
||||||
var result = (manga_id xor manga_id.ushr(32)).toInt()
|
|
||||||
result = 31 * result + sync_id
|
|
||||||
result = (31 * result + media_id).toInt()
|
|
||||||
return result
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -290,6 +290,7 @@ object ProtoBackupExport : ProtoBackupBase() {
|
|||||||
startedReadingDate = it.record.startDate,
|
startedReadingDate = it.record.startDate,
|
||||||
finishedReadingDate = it.record.finishDate,
|
finishedReadingDate = it.record.finishDate,
|
||||||
trackingUrl = it.record.remoteUrl,
|
trackingUrl = it.record.remoteUrl,
|
||||||
|
private = it.record.private,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -40,12 +40,11 @@ import suwayomi.tachidesk.manga.impl.Chapter.modifyChaptersMetas
|
|||||||
import suwayomi.tachidesk.manga.impl.Manga.clearThumbnail
|
import suwayomi.tachidesk.manga.impl.Manga.clearThumbnail
|
||||||
import suwayomi.tachidesk.manga.impl.Manga.modifyMangasMetas
|
import suwayomi.tachidesk.manga.impl.Manga.modifyMangasMetas
|
||||||
import suwayomi.tachidesk.manga.impl.Source.modifySourceMetas
|
import suwayomi.tachidesk.manga.impl.Source.modifySourceMetas
|
||||||
import suwayomi.tachidesk.manga.impl.backup.models.Chapter
|
|
||||||
import suwayomi.tachidesk.manga.impl.backup.models.Manga
|
|
||||||
import suwayomi.tachidesk.manga.impl.backup.proto.ProtoBackupValidator.ValidationResult
|
import suwayomi.tachidesk.manga.impl.backup.proto.ProtoBackupValidator.ValidationResult
|
||||||
import suwayomi.tachidesk.manga.impl.backup.proto.ProtoBackupValidator.validate
|
import suwayomi.tachidesk.manga.impl.backup.proto.ProtoBackupValidator.validate
|
||||||
import suwayomi.tachidesk.manga.impl.backup.proto.models.Backup
|
import suwayomi.tachidesk.manga.impl.backup.proto.models.Backup
|
||||||
import suwayomi.tachidesk.manga.impl.backup.proto.models.BackupCategory
|
import suwayomi.tachidesk.manga.impl.backup.proto.models.BackupCategory
|
||||||
|
import suwayomi.tachidesk.manga.impl.backup.proto.models.BackupChapter
|
||||||
import suwayomi.tachidesk.manga.impl.backup.proto.models.BackupHistory
|
import suwayomi.tachidesk.manga.impl.backup.proto.models.BackupHistory
|
||||||
import suwayomi.tachidesk.manga.impl.backup.proto.models.BackupManga
|
import suwayomi.tachidesk.manga.impl.backup.proto.models.BackupManga
|
||||||
import suwayomi.tachidesk.manga.impl.backup.proto.models.BackupServerSettings
|
import suwayomi.tachidesk.manga.impl.backup.proto.models.BackupServerSettings
|
||||||
@@ -62,8 +61,8 @@ import java.io.InputStream
|
|||||||
import java.util.Date
|
import java.util.Date
|
||||||
import java.util.Timer
|
import java.util.Timer
|
||||||
import java.util.TimerTask
|
import java.util.TimerTask
|
||||||
import java.util.concurrent.TimeUnit
|
|
||||||
import kotlin.math.max
|
import kotlin.math.max
|
||||||
|
import kotlin.time.Duration.Companion.milliseconds
|
||||||
import suwayomi.tachidesk.manga.impl.track.Track as Tracker
|
import suwayomi.tachidesk.manga.impl.track.Track as Tracker
|
||||||
|
|
||||||
enum class RestoreMode {
|
enum class RestoreMode {
|
||||||
@@ -144,7 +143,7 @@ object ProtoBackupImport : ProtoBackupBase() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@OptIn(DelicateCoroutinesApi::class)
|
@OptIn(DelicateCoroutinesApi::class)
|
||||||
suspend fun restore(sourceStream: InputStream): String {
|
fun restore(sourceStream: InputStream): String {
|
||||||
val restoreId = System.currentTimeMillis().toString()
|
val restoreId = System.currentTimeMillis().toString()
|
||||||
|
|
||||||
logger.info { "restore($restoreId): queued" }
|
logger.info { "restore($restoreId): queued" }
|
||||||
@@ -279,25 +278,24 @@ object ProtoBackupImport : ProtoBackupBase() {
|
|||||||
backupManga: BackupManga,
|
backupManga: BackupManga,
|
||||||
categoryMapping: Map<Int, Int>,
|
categoryMapping: Map<Int, Int>,
|
||||||
) {
|
) {
|
||||||
val manga = backupManga.getMangaImpl()
|
val chapters = backupManga.chapters
|
||||||
val chapters = backupManga.getChaptersImpl()
|
|
||||||
val categories = backupManga.categories
|
val categories = backupManga.categories
|
||||||
val history = backupManga.history
|
val history = backupManga.history
|
||||||
|
|
||||||
val dbCategoryIds = categories.map { categoryMapping[it]!! }
|
val dbCategoryIds = categories.map { categoryMapping[it]!! }
|
||||||
|
|
||||||
try {
|
try {
|
||||||
restoreMangaData(manga, chapters, dbCategoryIds, history, backupManga.tracking)
|
restoreMangaData(backupManga, chapters, dbCategoryIds, history, backupManga.tracking)
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
val sourceName = sourceMapping[manga.source] ?: manga.source.toString()
|
val sourceName = sourceMapping[backupManga.source] ?: backupManga.source.toString()
|
||||||
errors.add(Date() to "${manga.title} [$sourceName]: ${e.message}")
|
errors.add(Date() to "${backupManga.title} [$sourceName]: ${e.message}")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Suppress("UNUSED_PARAMETER") // TODO: remove
|
@Suppress("UNUSED_PARAMETER") // TODO: remove
|
||||||
private fun restoreMangaData(
|
private fun restoreMangaData(
|
||||||
manga: Manga,
|
manga: BackupManga,
|
||||||
chapters: List<Chapter>,
|
chapters: List<BackupChapter>,
|
||||||
categoryIds: List<Int>,
|
categoryIds: List<Int>,
|
||||||
history: List<BackupHistory>,
|
history: List<BackupHistory>,
|
||||||
tracks: List<BackupTracking>,
|
tracks: List<BackupTracking>,
|
||||||
@@ -324,10 +322,10 @@ object ProtoBackupImport : ProtoBackupBase() {
|
|||||||
it[artist] = manga.artist
|
it[artist] = manga.artist
|
||||||
it[author] = manga.author
|
it[author] = manga.author
|
||||||
it[description] = manga.description
|
it[description] = manga.description
|
||||||
it[genre] = manga.genre
|
it[genre] = manga.genre.joinToString()
|
||||||
it[status] = manga.status
|
it[status] = manga.status
|
||||||
it[thumbnail_url] = manga.thumbnail_url
|
it[thumbnail_url] = manga.thumbnailUrl
|
||||||
it[updateStrategy] = manga.update_strategy.name
|
it[updateStrategy] = manga.updateStrategy.name
|
||||||
|
|
||||||
it[sourceReference] = manga.source
|
it[sourceReference] = manga.source
|
||||||
|
|
||||||
@@ -335,7 +333,7 @@ object ProtoBackupImport : ProtoBackupBase() {
|
|||||||
|
|
||||||
it[inLibrary] = manga.favorite
|
it[inLibrary] = manga.favorite
|
||||||
|
|
||||||
it[inLibraryAt] = TimeUnit.MILLISECONDS.toSeconds(manga.date_added)
|
it[inLibraryAt] = manga.dateAdded.milliseconds.inWholeSeconds
|
||||||
}.value
|
}.value
|
||||||
} else {
|
} else {
|
||||||
val dbMangaId = dbManga[MangaTable.id].value
|
val dbMangaId = dbManga[MangaTable.id].value
|
||||||
@@ -345,16 +343,16 @@ object ProtoBackupImport : ProtoBackupBase() {
|
|||||||
it[artist] = manga.artist ?: dbManga[artist]
|
it[artist] = manga.artist ?: dbManga[artist]
|
||||||
it[author] = manga.author ?: dbManga[author]
|
it[author] = manga.author ?: dbManga[author]
|
||||||
it[description] = manga.description ?: dbManga[description]
|
it[description] = manga.description ?: dbManga[description]
|
||||||
it[genre] = manga.genre ?: dbManga[genre]
|
it[genre] = manga.genre.ifEmpty { null }?.joinToString() ?: dbManga[genre]
|
||||||
it[status] = manga.status
|
it[status] = manga.status
|
||||||
it[thumbnail_url] = manga.thumbnail_url ?: dbManga[thumbnail_url]
|
it[thumbnail_url] = manga.thumbnailUrl ?: dbManga[thumbnail_url]
|
||||||
it[updateStrategy] = manga.update_strategy.name
|
it[updateStrategy] = manga.updateStrategy.name
|
||||||
|
|
||||||
it[initialized] = dbManga[initialized] || manga.description != null
|
it[initialized] = dbManga[initialized] || manga.description != null
|
||||||
|
|
||||||
it[inLibrary] = manga.favorite || dbManga[inLibrary]
|
it[inLibrary] = manga.favorite || dbManga[inLibrary]
|
||||||
|
|
||||||
it[inLibraryAt] = TimeUnit.MILLISECONDS.toSeconds(manga.date_added)
|
it[inLibraryAt] = manga.dateAdded.milliseconds.inWholeSeconds
|
||||||
}
|
}
|
||||||
|
|
||||||
dbMangaId
|
dbMangaId
|
||||||
@@ -384,8 +382,8 @@ object ProtoBackupImport : ProtoBackupBase() {
|
|||||||
private fun getMangaChapterToRestoreInfo(
|
private fun getMangaChapterToRestoreInfo(
|
||||||
mangaId: Int,
|
mangaId: Int,
|
||||||
restoreMode: RestoreMode,
|
restoreMode: RestoreMode,
|
||||||
chapters: List<Chapter>,
|
chapters: List<BackupChapter>,
|
||||||
): Pair<List<Chapter>, List<Pair<Chapter, ResultRow>>> {
|
): Pair<List<BackupChapter>, List<Pair<BackupChapter, ResultRow>>> {
|
||||||
val uniqueChapters = chapters.distinctBy { it.url }
|
val uniqueChapters = chapters.distinctBy { it.url }
|
||||||
|
|
||||||
if (restoreMode == RestoreMode.NEW) {
|
if (restoreMode == RestoreMode.NEW) {
|
||||||
@@ -403,7 +401,7 @@ object ProtoBackupImport : ProtoBackupBase() {
|
|||||||
private fun restoreMangaChapterData(
|
private fun restoreMangaChapterData(
|
||||||
mangaId: Int,
|
mangaId: Int,
|
||||||
restoreMode: RestoreMode,
|
restoreMode: RestoreMode,
|
||||||
chapters: List<Chapter>,
|
chapters: List<BackupChapter>,
|
||||||
) = dbTransaction {
|
) = dbTransaction {
|
||||||
val (chaptersToInsert, chaptersToUpdateToDbChapter) = getMangaChapterToRestoreInfo(mangaId, restoreMode, chapters)
|
val (chaptersToInsert, chaptersToUpdateToDbChapter) = getMangaChapterToRestoreInfo(mangaId, restoreMode, chapters)
|
||||||
|
|
||||||
@@ -412,22 +410,22 @@ object ProtoBackupImport : ProtoBackupBase() {
|
|||||||
.batchInsert(chaptersToInsert) { chapter ->
|
.batchInsert(chaptersToInsert) { chapter ->
|
||||||
this[ChapterTable.url] = chapter.url
|
this[ChapterTable.url] = chapter.url
|
||||||
this[ChapterTable.name] = chapter.name
|
this[ChapterTable.name] = chapter.name
|
||||||
if (chapter.date_upload == 0L) {
|
if (chapter.dateUpload == 0L) {
|
||||||
this[ChapterTable.date_upload] = chapter.date_fetch
|
this[ChapterTable.date_upload] = chapter.dateFetch
|
||||||
} else {
|
} else {
|
||||||
this[ChapterTable.date_upload] = chapter.date_upload
|
this[ChapterTable.date_upload] = chapter.dateUpload
|
||||||
}
|
}
|
||||||
this[ChapterTable.chapter_number] = chapter.chapter_number
|
this[ChapterTable.chapter_number] = chapter.chapterNumber
|
||||||
this[ChapterTable.scanlator] = chapter.scanlator
|
this[ChapterTable.scanlator] = chapter.scanlator
|
||||||
|
|
||||||
this[ChapterTable.sourceOrder] = chaptersToInsert.size - chapter.source_order
|
this[ChapterTable.sourceOrder] = chaptersToInsert.size - chapter.sourceOrder
|
||||||
this[ChapterTable.manga] = mangaId
|
this[ChapterTable.manga] = mangaId
|
||||||
|
|
||||||
this[ChapterTable.isRead] = chapter.read
|
this[ChapterTable.isRead] = chapter.read
|
||||||
this[ChapterTable.lastPageRead] = chapter.last_page_read.coerceAtLeast(0)
|
this[ChapterTable.lastPageRead] = chapter.lastPageRead.coerceAtLeast(0)
|
||||||
this[ChapterTable.isBookmarked] = chapter.bookmark
|
this[ChapterTable.isBookmarked] = chapter.bookmark
|
||||||
|
|
||||||
this[ChapterTable.fetchedAt] = TimeUnit.MILLISECONDS.toSeconds(chapter.date_fetch)
|
this[ChapterTable.fetchedAt] = chapter.dateFetch.milliseconds.inWholeSeconds
|
||||||
}.map { it[ChapterTable.id].value }
|
}.map { it[ChapterTable.id].value }
|
||||||
|
|
||||||
if (chaptersToUpdateToDbChapter.isNotEmpty()) {
|
if (chaptersToUpdateToDbChapter.isNotEmpty()) {
|
||||||
@@ -436,7 +434,7 @@ object ProtoBackupImport : ProtoBackupBase() {
|
|||||||
addBatch(EntityID(dbChapter[ChapterTable.id].value, ChapterTable))
|
addBatch(EntityID(dbChapter[ChapterTable.id].value, ChapterTable))
|
||||||
this[ChapterTable.isRead] = backupChapter.read || dbChapter[ChapterTable.isRead]
|
this[ChapterTable.isRead] = backupChapter.read || dbChapter[ChapterTable.isRead]
|
||||||
this[ChapterTable.lastPageRead] =
|
this[ChapterTable.lastPageRead] =
|
||||||
max(backupChapter.last_page_read, dbChapter[ChapterTable.lastPageRead]).coerceAtLeast(0)
|
max(backupChapter.lastPageRead, dbChapter[ChapterTable.lastPageRead]).coerceAtLeast(0)
|
||||||
this[ChapterTable.isBookmarked] = backupChapter.bookmark || dbChapter[ChapterTable.isBookmarked]
|
this[ChapterTable.isBookmarked] = backupChapter.bookmark || dbChapter[ChapterTable.isBookmarked]
|
||||||
}
|
}
|
||||||
execute(this@dbTransaction)
|
execute(this@dbTransaction)
|
||||||
|
|||||||
@@ -2,7 +2,6 @@ package suwayomi.tachidesk.manga.impl.backup.proto.models
|
|||||||
|
|
||||||
import kotlinx.serialization.Serializable
|
import kotlinx.serialization.Serializable
|
||||||
import kotlinx.serialization.protobuf.ProtoNumber
|
import kotlinx.serialization.protobuf.ProtoNumber
|
||||||
import suwayomi.tachidesk.manga.impl.backup.models.ChapterImpl
|
|
||||||
|
|
||||||
@Serializable
|
@Serializable
|
||||||
data class BackupChapter(
|
data class BackupChapter(
|
||||||
@@ -22,19 +21,4 @@ data class BackupChapter(
|
|||||||
@ProtoNumber(10) var sourceOrder: Int = 0,
|
@ProtoNumber(10) var sourceOrder: Int = 0,
|
||||||
// suwayomi
|
// suwayomi
|
||||||
@ProtoNumber(9000) var meta: Map<String, String> = emptyMap(),
|
@ProtoNumber(9000) var meta: Map<String, String> = emptyMap(),
|
||||||
) {
|
)
|
||||||
fun toChapterImpl(): ChapterImpl =
|
|
||||||
ChapterImpl().apply {
|
|
||||||
url = this@BackupChapter.url
|
|
||||||
name = this@BackupChapter.name
|
|
||||||
chapter_number = this@BackupChapter.chapterNumber
|
|
||||||
scanlator = this@BackupChapter.scanlator
|
|
||||||
read = this@BackupChapter.read
|
|
||||||
bookmark = this@BackupChapter.bookmark
|
|
||||||
last_page_read = this@BackupChapter.lastPageRead
|
|
||||||
date_fetch = this@BackupChapter.dateFetch
|
|
||||||
date_upload = this@BackupChapter.dateUpload
|
|
||||||
source_order = this@BackupChapter.sourceOrder
|
|
||||||
meta = this@BackupChapter.meta
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|||||||
@@ -3,10 +3,6 @@ package suwayomi.tachidesk.manga.impl.backup.proto.models
|
|||||||
import eu.kanade.tachiyomi.source.model.UpdateStrategy
|
import eu.kanade.tachiyomi.source.model.UpdateStrategy
|
||||||
import kotlinx.serialization.Serializable
|
import kotlinx.serialization.Serializable
|
||||||
import kotlinx.serialization.protobuf.ProtoNumber
|
import kotlinx.serialization.protobuf.ProtoNumber
|
||||||
import suwayomi.tachidesk.manga.impl.backup.models.ChapterImpl
|
|
||||||
import suwayomi.tachidesk.manga.impl.backup.models.Manga
|
|
||||||
import suwayomi.tachidesk.manga.impl.backup.models.MangaImpl
|
|
||||||
import suwayomi.tachidesk.manga.impl.backup.models.TrackImpl
|
|
||||||
|
|
||||||
@Serializable
|
@Serializable
|
||||||
data class BackupManga(
|
data class BackupManga(
|
||||||
@@ -40,53 +36,4 @@ data class BackupManga(
|
|||||||
@ProtoNumber(105) var updateStrategy: UpdateStrategy = UpdateStrategy.ALWAYS_UPDATE,
|
@ProtoNumber(105) var updateStrategy: UpdateStrategy = UpdateStrategy.ALWAYS_UPDATE,
|
||||||
// suwayomi
|
// suwayomi
|
||||||
@ProtoNumber(9000) var meta: Map<String, String> = emptyMap(),
|
@ProtoNumber(9000) var meta: Map<String, String> = emptyMap(),
|
||||||
) {
|
)
|
||||||
fun getMangaImpl(): MangaImpl =
|
|
||||||
MangaImpl().apply {
|
|
||||||
url = this@BackupManga.url
|
|
||||||
title = this@BackupManga.title
|
|
||||||
artist = this@BackupManga.artist
|
|
||||||
author = this@BackupManga.author
|
|
||||||
description = this@BackupManga.description
|
|
||||||
genre = this@BackupManga.genre.joinToString()
|
|
||||||
status = this@BackupManga.status
|
|
||||||
thumbnail_url = this@BackupManga.thumbnailUrl
|
|
||||||
favorite = this@BackupManga.favorite
|
|
||||||
source = this@BackupManga.source
|
|
||||||
date_added = this@BackupManga.dateAdded
|
|
||||||
viewer_flags = this@BackupManga.viewer_flags ?: this@BackupManga.viewer
|
|
||||||
chapter_flags = this@BackupManga.chapterFlags
|
|
||||||
update_strategy = this@BackupManga.updateStrategy
|
|
||||||
meta = this@BackupManga.meta
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getChaptersImpl(): List<ChapterImpl> =
|
|
||||||
chapters.map {
|
|
||||||
it.toChapterImpl()
|
|
||||||
}
|
|
||||||
|
|
||||||
fun getTrackingImpl(): List<TrackImpl> =
|
|
||||||
tracking.map {
|
|
||||||
it.getTrackingImpl()
|
|
||||||
}
|
|
||||||
|
|
||||||
companion object {
|
|
||||||
fun copyFrom(manga: Manga): BackupManga =
|
|
||||||
BackupManga(
|
|
||||||
url = manga.url,
|
|
||||||
title = manga.title,
|
|
||||||
artist = manga.artist,
|
|
||||||
author = manga.author,
|
|
||||||
description = manga.description,
|
|
||||||
genre = manga.getGenres() ?: emptyList(),
|
|
||||||
status = manga.status,
|
|
||||||
thumbnailUrl = manga.thumbnail_url,
|
|
||||||
favorite = manga.favorite,
|
|
||||||
source = manga.source,
|
|
||||||
dateAdded = manga.date_added,
|
|
||||||
viewer = manga.readingModeType,
|
|
||||||
viewer_flags = manga.viewer_flags,
|
|
||||||
chapterFlags = manga.chapter_flags,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|||||||
@@ -1,6 +1,5 @@
|
|||||||
package suwayomi.tachidesk.manga.impl.backup.proto.models
|
package suwayomi.tachidesk.manga.impl.backup.proto.models
|
||||||
|
|
||||||
import eu.kanade.tachiyomi.source.Source
|
|
||||||
import kotlinx.serialization.Serializable
|
import kotlinx.serialization.Serializable
|
||||||
import kotlinx.serialization.protobuf.ProtoNumber
|
import kotlinx.serialization.protobuf.ProtoNumber
|
||||||
|
|
||||||
@@ -10,12 +9,4 @@ data class BackupSource(
|
|||||||
@ProtoNumber(2) var sourceId: Long,
|
@ProtoNumber(2) var sourceId: Long,
|
||||||
// suwayomi
|
// suwayomi
|
||||||
@ProtoNumber(9000) var meta: Map<String, String> = emptyMap(),
|
@ProtoNumber(9000) var meta: Map<String, String> = emptyMap(),
|
||||||
) {
|
)
|
||||||
companion object {
|
|
||||||
fun copyFrom(source: Source): BackupSource =
|
|
||||||
BackupSource(
|
|
||||||
name = source.name,
|
|
||||||
sourceId = source.id,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|||||||
@@ -2,8 +2,6 @@ package suwayomi.tachidesk.manga.impl.backup.proto.models
|
|||||||
|
|
||||||
import kotlinx.serialization.Serializable
|
import kotlinx.serialization.Serializable
|
||||||
import kotlinx.serialization.protobuf.ProtoNumber
|
import kotlinx.serialization.protobuf.ProtoNumber
|
||||||
import suwayomi.tachidesk.manga.impl.backup.models.Track
|
|
||||||
import suwayomi.tachidesk.manga.impl.backup.models.TrackImpl
|
|
||||||
|
|
||||||
@Serializable
|
@Serializable
|
||||||
data class BackupTracking(
|
data class BackupTracking(
|
||||||
@@ -28,44 +26,4 @@ data class BackupTracking(
|
|||||||
@ProtoNumber(11) var finishedReadingDate: Long = 0,
|
@ProtoNumber(11) var finishedReadingDate: Long = 0,
|
||||||
@ProtoNumber(12) var private: Boolean = false,
|
@ProtoNumber(12) var private: Boolean = false,
|
||||||
@ProtoNumber(100) var mediaId: Long = 0,
|
@ProtoNumber(100) var mediaId: Long = 0,
|
||||||
) {
|
)
|
||||||
fun getTrackingImpl(): TrackImpl =
|
|
||||||
TrackImpl().apply {
|
|
||||||
sync_id = this@BackupTracking.syncId
|
|
||||||
media_id =
|
|
||||||
if (this@BackupTracking.mediaIdInt != 0) {
|
|
||||||
this@BackupTracking.mediaIdInt.toLong()
|
|
||||||
} else {
|
|
||||||
this@BackupTracking.mediaId
|
|
||||||
}
|
|
||||||
library_id = this@BackupTracking.libraryId
|
|
||||||
title = this@BackupTracking.title
|
|
||||||
// convert from float to int because of 1.x types
|
|
||||||
last_chapter_read = this@BackupTracking.lastChapterRead.toInt()
|
|
||||||
total_chapters = this@BackupTracking.totalChapters
|
|
||||||
score = this@BackupTracking.score
|
|
||||||
status = this@BackupTracking.status
|
|
||||||
started_reading_date = this@BackupTracking.startedReadingDate
|
|
||||||
finished_reading_date = this@BackupTracking.finishedReadingDate
|
|
||||||
tracking_url = this@BackupTracking.trackingUrl
|
|
||||||
}
|
|
||||||
|
|
||||||
companion object {
|
|
||||||
fun copyFrom(track: Track): BackupTracking =
|
|
||||||
BackupTracking(
|
|
||||||
syncId = track.sync_id,
|
|
||||||
mediaId = track.media_id,
|
|
||||||
// forced not null so its compatible with 1.x backup system
|
|
||||||
libraryId = track.library_id!!,
|
|
||||||
title = track.title,
|
|
||||||
// convert to float for 1.x
|
|
||||||
lastChapterRead = track.last_chapter_read.toFloat(),
|
|
||||||
totalChapters = track.total_chapters,
|
|
||||||
score = track.score,
|
|
||||||
status = track.status,
|
|
||||||
startedReadingDate = track.started_reading_date,
|
|
||||||
finishedReadingDate = track.finished_reading_date,
|
|
||||||
trackingUrl = track.tracking_url,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|||||||
Reference in New Issue
Block a user