Fix crash when probing audio files by updating start/end chapter data type to Long #128, remove unused files and generic database save/load methods

This commit is contained in:
advplyr 2022-04-24 13:28:14 -05:00
parent d5b69be7c1
commit 52fd8ac5e8
11 changed files with 33 additions and 108 deletions

View file

@ -2,11 +2,6 @@ package com.audiobookshelf.app.data
import com.fasterxml.jackson.annotation.JsonIgnore import com.fasterxml.jackson.annotation.JsonIgnore
import com.fasterxml.jackson.annotation.JsonIgnoreProperties import com.fasterxml.jackson.annotation.JsonIgnoreProperties
import com.fasterxml.jackson.annotation.JsonInclude
import com.fasterxml.jackson.annotation.JsonProperty
import com.fasterxml.jackson.core.json.JsonReadFeature
import com.fasterxml.jackson.databind.annotation.JsonDeserialize
import com.fasterxml.jackson.databind.jsonschema.JsonSerializableSchema
@JsonIgnoreProperties(ignoreUnknown = true) @JsonIgnoreProperties(ignoreUnknown = true)
data class AudioProbeStream( data class AudioProbeStream(
@ -27,15 +22,15 @@ data class AudioProbeChapterTags(
@JsonIgnoreProperties(ignoreUnknown = true) @JsonIgnoreProperties(ignoreUnknown = true)
data class AudioProbeChapter( data class AudioProbeChapter(
val id:Int, val id:Int,
val start:Int, val start:Long,
val end:Int, val end:Long,
val tags:AudioProbeChapterTags? val tags:AudioProbeChapterTags?
) { ) {
@JsonIgnore @JsonIgnore
fun getBookChapter():BookChapter { fun getBookChapter():BookChapter {
var startS = start / 1000.0 val startS = start / 1000.0
var endS = end / 1000.0 val endS = end / 1000.0
var title = tags?.title ?: "Chapter $id" val title = tags?.title ?: "Chapter $id"
return BookChapter(id, startS, endS, title) return BookChapter(id, startS, endS, title)
} }
} }

View file

@ -85,7 +85,7 @@ class Podcast(
) : MediaType(metadata, coverPath) { ) : MediaType(metadata, coverPath) {
@JsonIgnore @JsonIgnore
override fun getAudioTracks():List<AudioTrack> { override fun getAudioTracks():List<AudioTrack> {
var tracks = episodes?.map { it.audioTrack } val tracks = episodes?.map { it.audioTrack }
return tracks?.filterNotNull() ?: mutableListOf() return tracks?.filterNotNull() ?: mutableListOf()
} }
@JsonIgnore @JsonIgnore
@ -98,7 +98,7 @@ class Podcast(
// Add new episodes // Add new episodes
audioTracks.forEach { at -> audioTracks.forEach { at ->
if (episodes?.find{ it.audioTrack?.localFileId == at.localFileId } == null) { if (episodes?.find{ it.audioTrack?.localFileId == at.localFileId } == null) {
var newEpisode = PodcastEpisode("local_" + at.localFileId,episodes?.size ?: 0 + 1,null,null,at.title,null,null,null,at,at.duration,0, null) val newEpisode = PodcastEpisode("local_" + at.localFileId,episodes?.size ?: 0 + 1,null,null,at.title,null,null,null,at,at.duration,0, null)
episodes?.add(newEpisode) episodes?.add(newEpisode)
} }
} }
@ -111,7 +111,7 @@ class Podcast(
} }
@JsonIgnore @JsonIgnore
override fun addAudioTrack(audioTrack:AudioTrack) { override fun addAudioTrack(audioTrack:AudioTrack) {
var newEpisode = PodcastEpisode("local_" + audioTrack.localFileId,episodes?.size ?: 0 + 1,null,null,audioTrack.title,null,null,null,audioTrack,audioTrack.duration,0, null) val newEpisode = PodcastEpisode("local_" + audioTrack.localFileId,episodes?.size ?: 0 + 1,null,null,audioTrack.title,null,null,null,audioTrack,audioTrack.duration,0, null)
episodes?.add(newEpisode) episodes?.add(newEpisode)
var index = 1 var index = 1
@ -132,7 +132,7 @@ class Podcast(
} }
@JsonIgnore @JsonIgnore
fun addEpisode(audioTrack:AudioTrack, episode:PodcastEpisode) { fun addEpisode(audioTrack:AudioTrack, episode:PodcastEpisode) {
var newEpisode = PodcastEpisode("local_" + episode.id,episodes?.size ?: 0 + 1,episode.episode,episode.episodeType,episode.title,episode.subtitle,episode.description,null,audioTrack,audioTrack.duration,0, episode.id) val newEpisode = PodcastEpisode("local_" + episode.id,episodes?.size ?: 0 + 1,episode.episode,episode.episodeType,episode.title,episode.subtitle,episode.description,null,audioTrack,audioTrack.duration,0, episode.id)
episodes?.add(newEpisode) episodes?.add(newEpisode)
var index = 1 var index = 1

View file

@ -17,9 +17,9 @@ class DbManager {
} }
fun getLocalLibraryItems(mediaType:String? = null):MutableList<LocalLibraryItem> { fun getLocalLibraryItems(mediaType:String? = null):MutableList<LocalLibraryItem> {
var localLibraryItems:MutableList<LocalLibraryItem> = mutableListOf() val localLibraryItems:MutableList<LocalLibraryItem> = mutableListOf()
Paper.book("localLibraryItems").allKeys.forEach { Paper.book("localLibraryItems").allKeys.forEach {
var localLibraryItem:LocalLibraryItem? = Paper.book("localLibraryItems").read(it) val localLibraryItem:LocalLibraryItem? = Paper.book("localLibraryItems").read(it)
if (localLibraryItem != null && (mediaType.isNullOrEmpty() || mediaType == localLibraryItem.mediaType)) { if (localLibraryItem != null && (mediaType.isNullOrEmpty() || mediaType == localLibraryItem.mediaType)) {
localLibraryItems.add(localLibraryItem) localLibraryItems.add(localLibraryItem)
} }
@ -28,7 +28,7 @@ class DbManager {
} }
fun getLocalLibraryItemsInFolder(folderId:String):List<LocalLibraryItem> { fun getLocalLibraryItemsInFolder(folderId:String):List<LocalLibraryItem> {
var localLibraryItems = getLocalLibraryItems() val localLibraryItems = getLocalLibraryItems()
return localLibraryItems.filter { return localLibraryItems.filter {
it.folderId == folderId it.folderId == folderId
} }
@ -65,7 +65,7 @@ class DbManager {
} }
fun getAllLocalFolders():List<LocalFolder> { fun getAllLocalFolders():List<LocalFolder> {
var localFolders:MutableList<LocalFolder> = mutableListOf() val localFolders:MutableList<LocalFolder> = mutableListOf()
Paper.book("localFolders").allKeys.forEach { localFolderId -> Paper.book("localFolders").allKeys.forEach { localFolderId ->
Paper.book("localFolders").read<LocalFolder>(localFolderId)?.let { Paper.book("localFolders").read<LocalFolder>(localFolderId)?.let {
localFolders.add(it) localFolders.add(it)
@ -75,7 +75,7 @@ class DbManager {
} }
fun removeLocalFolder(folderId:String) { fun removeLocalFolder(folderId:String) {
var localLibraryItems = getLocalLibraryItemsInFolder(folderId) val localLibraryItems = getLocalLibraryItemsInFolder(folderId)
localLibraryItems.forEach { localLibraryItems.forEach {
Paper.book("localLibraryItems").delete(it.id) Paper.book("localLibraryItems").delete(it.id)
} }
@ -91,7 +91,7 @@ class DbManager {
} }
fun getDownloadItems():List<AbsDownloader.DownloadItem> { fun getDownloadItems():List<AbsDownloader.DownloadItem> {
var downloadItems:MutableList<AbsDownloader.DownloadItem> = mutableListOf() val downloadItems:MutableList<AbsDownloader.DownloadItem> = mutableListOf()
Paper.book("downloadItems").allKeys.forEach { downloadItemId -> Paper.book("downloadItems").allKeys.forEach { downloadItemId ->
Paper.book("downloadItems").read<AbsDownloader.DownloadItem>(downloadItemId)?.let { Paper.book("downloadItems").read<AbsDownloader.DownloadItem>(downloadItemId)?.let {
downloadItems.add(it) downloadItems.add(it)
@ -108,7 +108,7 @@ class DbManager {
return Paper.book("localMediaProgress").read(localMediaProgressId) return Paper.book("localMediaProgress").read(localMediaProgressId)
} }
fun getAllLocalMediaProgress():List<LocalMediaProgress> { fun getAllLocalMediaProgress():List<LocalMediaProgress> {
var mediaProgress:MutableList<LocalMediaProgress> = mutableListOf() val mediaProgress:MutableList<LocalMediaProgress> = mutableListOf()
Paper.book("localMediaProgress").allKeys.forEach { localMediaProgressId -> Paper.book("localMediaProgress").allKeys.forEach { localMediaProgressId ->
Paper.book("localMediaProgress").read<LocalMediaProgress>(localMediaProgressId)?.let { Paper.book("localMediaProgress").read<LocalMediaProgress>(localMediaProgressId)?.let {
mediaProgress.add(it) mediaProgress.add(it)
@ -126,14 +126,14 @@ class DbManager {
// Make sure all local file ids still exist // Make sure all local file ids still exist
fun cleanLocalLibraryItems() { fun cleanLocalLibraryItems() {
var localLibraryItems = getLocalLibraryItems() val localLibraryItems = getLocalLibraryItems()
localLibraryItems.forEach { lli -> localLibraryItems.forEach { lli ->
var hasUpates = false var hasUpates = false
// Check local files // Check local files
lli.localFiles = lli.localFiles.filter { localFile -> lli.localFiles = lli.localFiles.filter { localFile ->
var file = File(localFile.absolutePath) val file = File(localFile.absolutePath)
if (!file.exists()) { if (!file.exists()) {
Log.d(tag, "cleanLocalLibraryItems: Local file ${localFile.absolutePath} was removed from library item ${lli.media.metadata.title}") Log.d(tag, "cleanLocalLibraryItems: Local file ${localFile.absolutePath} was removed from library item ${lli.media.metadata.title}")
hasUpates = true hasUpates = true
@ -143,7 +143,7 @@ class DbManager {
// Check audio tracks and episodes // Check audio tracks and episodes
if (lli.isPodcast) { if (lli.isPodcast) {
var podcast = lli.media as Podcast val podcast = lli.media as Podcast
podcast.episodes = podcast.episodes?.filter { ep -> podcast.episodes = podcast.episodes?.filter { ep ->
if (lli.localFiles.find { lf -> lf.id == ep.audioTrack?.localFileId } == null) { if (lli.localFiles.find { lf -> lf.id == ep.audioTrack?.localFileId } == null) {
Log.d(tag, "cleanLocalLibraryItems: Podcast episode ${ep.title} was removed from library item ${lli.media.metadata.title}") Log.d(tag, "cleanLocalLibraryItems: Podcast episode ${ep.title} was removed from library item ${lli.media.metadata.title}")
@ -152,7 +152,7 @@ class DbManager {
ep.audioTrack != null && lli.localFiles.find { lf -> lf.id == ep.audioTrack?.localFileId } != null ep.audioTrack != null && lli.localFiles.find { lf -> lf.id == ep.audioTrack?.localFileId } != null
} as MutableList<PodcastEpisode> } as MutableList<PodcastEpisode>
} else { } else {
var book = lli.media as Book val book = lli.media as Book
book.tracks = book.tracks?.filter { track -> book.tracks = book.tracks?.filter { track ->
if (lli.localFiles.find { lf -> lf.id == track.localFileId } == null) { if (lli.localFiles.find { lf -> lf.id == track.localFileId } == null) {
Log.d(tag, "cleanLocalLibraryItems: Audio track ${track.title} was removed from library item ${lli.media.metadata.title}") Log.d(tag, "cleanLocalLibraryItems: Audio track ${track.title} was removed from library item ${lli.media.metadata.title}")
@ -164,7 +164,7 @@ class DbManager {
// Check cover still there // Check cover still there
lli.coverAbsolutePath?.let { lli.coverAbsolutePath?.let {
var coverFile = File(it) val coverFile = File(it)
if (!coverFile.exists()) { if (!coverFile.exists()) {
Log.d(tag, "cleanLocalLibraryItems: Cover $it was removed from library item ${lli.media.metadata.title}") Log.d(tag, "cleanLocalLibraryItems: Cover $it was removed from library item ${lli.media.metadata.title}")
@ -183,10 +183,10 @@ class DbManager {
// Remove any local media progress where the local media item is not found // Remove any local media progress where the local media item is not found
fun cleanLocalMediaProgress() { fun cleanLocalMediaProgress() {
var localMediaProgress = getAllLocalMediaProgress() val localMediaProgress = getAllLocalMediaProgress()
var localLibraryItems = getLocalLibraryItems() val localLibraryItems = getLocalLibraryItems()
localMediaProgress.forEach { localMediaProgress.forEach {
var matchingLLI = localLibraryItems.find { lli -> lli.id == it.localLibraryItemId } val matchingLLI = localLibraryItems.find { lli -> lli.id == it.localLibraryItemId }
if (matchingLLI == null) { if (matchingLLI == null) {
Log.d(tag, "cleanLocalMediaProgress: No matching local library item for local media progress ${it.id} - removing") Log.d(tag, "cleanLocalMediaProgress: No matching local library item for local media progress ${it.id} - removing")
Paper.book("localMediaProgress").delete(it.id) Paper.book("localMediaProgress").delete(it.id)
@ -195,8 +195,8 @@ class DbManager {
Log.d(tag, "cleanLocalMediaProgress: Podcast media progress has no episode id - removing") Log.d(tag, "cleanLocalMediaProgress: Podcast media progress has no episode id - removing")
Paper.book("localMediaProgress").delete(it.id) Paper.book("localMediaProgress").delete(it.id)
} else { } else {
var podcast = matchingLLI.media as Podcast val podcast = matchingLLI.media as Podcast
var matchingLEp = podcast.episodes?.find { ep -> ep.id == it.localEpisodeId } val matchingLEp = podcast.episodes?.find { ep -> ep.id == it.localEpisodeId }
if (matchingLEp == null) { if (matchingLEp == null) {
Log.d(tag, "cleanLocalMediaProgress: Podcast media progress for episode ${it.localEpisodeId} not found - removing") Log.d(tag, "cleanLocalMediaProgress: Podcast media progress for episode ${it.localEpisodeId} not found - removing")
Paper.book("localMediaProgress").delete(it.id) Paper.book("localMediaProgress").delete(it.id)
@ -212,15 +212,4 @@ class DbManager {
fun getLocalPlaybackSession(playbackSessionId:String):PlaybackSession? { fun getLocalPlaybackSession(playbackSessionId:String):PlaybackSession? {
return Paper.book("localPlaybackSession").read(playbackSessionId) return Paper.book("localPlaybackSession").read(playbackSessionId)
} }
fun saveObject(db:String, key:String, value:JSONObject) {
Log.d(tag, "Saving Object $key ${value.toString()}")
Paper.book(db).write(key, value)
}
fun loadObject(db:String, key:String):JSONObject? {
var json: JSONObject? = Paper.book(db).read(key)
Log.d(tag, "Loaded Object $key $json")
return json
}
} }

View file

@ -288,38 +288,4 @@ class AbsDatabase : Plugin() {
call.resolve() call.resolve()
} }
} }
//
// Generic Webview calls to db
//
@PluginMethod
fun saveFromWebview(call: PluginCall) {
var db = call.getString("db", "").toString()
var key = call.getString("key", "").toString()
var value = call.getObject("value")
GlobalScope.launch(Dispatchers.IO) {
if (db == "" || key == "" || value == null) {
Log.d(tag, "saveFromWebview Invalid key/value")
} else {
var json = value as JSONObject
DeviceManager.dbManager.saveObject(db, key, json)
}
call.resolve()
}
}
@PluginMethod
fun loadFromWebview(call:PluginCall) {
var db = call.getString("db", "").toString()
var key = call.getString("key", "").toString()
if (db == "" || key == "") {
Log.d(tag, "loadFromWebview Invalid Key")
call.resolve()
return
}
var json = DeviceManager.dbManager.loadObject(db, key)
var jsobj = JSObject.fromJSONObject(json)
call.resolve(jsobj)
}
} }

View file

@ -9,13 +9,13 @@ install! 'cocoapods', :disable_input_output_paths => true
def capacitor_pods def capacitor_pods
pod 'Capacitor', :path => '../../node_modules/@capacitor/ios' pod 'Capacitor', :path => '../../node_modules/@capacitor/ios'
pod 'CapacitorCordova', :path => '../../node_modules/@capacitor/ios' pod 'CapacitorCordova', :path => '../../node_modules/@capacitor/ios'
pod 'CapacitorApp', :path => '../../node_modules/@capacitor/app' pod 'CapacitorApp', :path => '..\..\node_modules\@capacitor\app'
pod 'CapacitorDialog', :path => '../../node_modules/@capacitor/dialog' pod 'CapacitorDialog', :path => '..\..\node_modules\@capacitor\dialog'
pod 'CapacitorHaptics', :path => '../../node_modules/@capacitor/haptics' pod 'CapacitorHaptics', :path => '..\..\node_modules\@capacitor\haptics'
pod 'CapacitorNetwork', :path => '../../node_modules/@capacitor/network' pod 'CapacitorNetwork', :path => '..\..\node_modules\@capacitor\network'
pod 'CapacitorStatusBar', :path => '../../node_modules/@capacitor/status-bar' pod 'CapacitorStatusBar', :path => '..\..\node_modules\@capacitor\status-bar'
pod 'CapacitorStorage', :path => '../../node_modules/@capacitor/storage' pod 'CapacitorStorage', :path => '..\..\node_modules\@capacitor\storage'
pod 'RobingenzCapacitorAppUpdate', :path => '../../node_modules/@robingenz/capacitor-app-update' pod 'RobingenzCapacitorAppUpdate', :path => '..\..\node_modules\@robingenz\capacitor-app-update'
end end
target 'App' do target 'App' do

View file

@ -6,28 +6,6 @@ const isWeb = Capacitor.getPlatform() == 'web'
class DbService { class DbService {
constructor() { } constructor() { }
// Please dont use this, it is not implemented in ios (maybe key: primary value: any ?)
save(db, key, value) {
if (isWeb) return
return AbsDatabase.saveFromWebview({ db, key, value }).then(() => {
console.log('Saved data', db, key, JSON.stringify(value))
}).catch((error) => {
console.error('Failed to save data', error)
})
}
// Please dont use this, it is not implemented in ios
load(db, key) {
if (isWeb) return null
return AbsDatabase.loadFromWebview({ db, key }).then((data) => {
console.log('Loaded data', db, key, JSON.stringify(data))
return data
}).catch((error) => {
console.error('Failed to load', error)
return null
})
}
getDeviceData() { getDeviceData() {
return AbsDatabase.getDeviceData().then((data) => { return AbsDatabase.getDeviceData().then((data) => {
console.log('Loaded device data', JSON.stringify(data)) console.log('Loaded device data', JSON.stringify(data))

File diff suppressed because one or more lines are too long

Binary file not shown.

Before

Width:  |  Height:  |  Size: 122 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 151 KiB