@@ -219,6 +219,8 @@ object LocalBook {
|
|||||||
fileName: String,
|
fileName: String,
|
||||||
source: BaseSource? = null,
|
source: BaseSource? = null,
|
||||||
): Uri {
|
): Uri {
|
||||||
|
AppConfig.defaultBookTreeUri
|
||||||
|
?: throw NoStackTraceException("没有设置书籍保存位置!")
|
||||||
val bytes = when {
|
val bytes = when {
|
||||||
str.isAbsUrl() -> AnalyzeUrl(str, source = source).getByteArray()
|
str.isAbsUrl() -> AnalyzeUrl(str, source = source).getByteArray()
|
||||||
str.isDataUrl() -> Base64.decode(str.substringAfter("base64,"), Base64.DEFAULT)
|
str.isDataUrl() -> Base64.decode(str.substringAfter("base64,"), Base64.DEFAULT)
|
||||||
@@ -241,7 +243,7 @@ object LocalBook {
|
|||||||
return type ?: fileType
|
return type ?: fileType
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun saveBookFile(
|
fun saveBookFile(
|
||||||
bytes: ByteArray,
|
bytes: ByteArray,
|
||||||
fileName: String
|
fileName: String
|
||||||
): Uri {
|
): Uri {
|
||||||
@@ -269,6 +271,26 @@ object LocalBook {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun isOnBookShelf(
|
||||||
|
fileName: String
|
||||||
|
): Boolean {
|
||||||
|
val defaultBookTreeUri = AppConfig.defaultBookTreeUri
|
||||||
|
if (defaultBookTreeUri.isNullOrBlank()) throw NoStackTraceException("没有设置书籍保存位置!")
|
||||||
|
val treeUri = Uri.parse(defaultBookTreeUri)
|
||||||
|
var bookUrl: String = ""
|
||||||
|
if (treeUri.isContentScheme()) {
|
||||||
|
val treeDoc = DocumentFile.fromTreeUri(appCtx, treeUri)
|
||||||
|
var doc = treeDoc!!.findFile(fileName) ?: return false
|
||||||
|
bookUrl = doc.uri.toString()
|
||||||
|
} else {
|
||||||
|
val treeFile = File(treeUri.path!!)
|
||||||
|
val file = treeFile.getFile(fileName)
|
||||||
|
if (!file.exists()) return false
|
||||||
|
bookUrl = file.absolutePath
|
||||||
|
}
|
||||||
|
return appDb.bookDao.getBook(bookUrl) != null
|
||||||
|
}
|
||||||
|
|
||||||
//文件类书源 合并在线书籍信息 在线 > 本地
|
//文件类书源 合并在线书籍信息 在线 > 本地
|
||||||
fun mergeBook(localBook: Book, onLineBook: Book?): Book {
|
fun mergeBook(localBook: Book, onLineBook: Book?): Book {
|
||||||
onLineBook ?: return localBook
|
onLineBook ?: return localBook
|
||||||
|
|||||||
@@ -5,5 +5,6 @@ data class RemoteBook(
|
|||||||
val urlName: String,
|
val urlName: String,
|
||||||
val size: Long,
|
val size: Long,
|
||||||
val contentType: String,
|
val contentType: String,
|
||||||
val lastModify: Long
|
val lastModify: Long,
|
||||||
|
val isOnBookShelf: Boolean
|
||||||
)
|
)
|
||||||
@@ -2,11 +2,8 @@ package io.legado.app.ui.book.remote
|
|||||||
|
|
||||||
import android.net.Uri
|
import android.net.Uri
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
abstract class RemoteBookManager {
|
abstract class RemoteBookManager {
|
||||||
protected val remoteBookFolder : String = "books"
|
protected val remoteBookFolder : String = "books"
|
||||||
protected val contentTypeList: ArrayList<String> = arrayListOf("epub","txt")
|
|
||||||
abstract suspend fun initRemoteContext()
|
abstract suspend fun initRemoteContext()
|
||||||
abstract suspend fun getRemoteBookList(): MutableList<RemoteBook>
|
abstract suspend fun getRemoteBookList(): MutableList<RemoteBook>
|
||||||
abstract suspend fun upload(localBookUri: Uri): Boolean
|
abstract suspend fun upload(localBookUri: Uri): Boolean
|
||||||
@@ -15,5 +12,5 @@ abstract class RemoteBookManager {
|
|||||||
/**
|
/**
|
||||||
* @return String:下载到本地的路径
|
* @return String:下载到本地的路径
|
||||||
*/
|
*/
|
||||||
abstract suspend fun getRemoteBook(remoteBook: RemoteBook): String?
|
abstract suspend fun getRemoteBook(remoteBook: RemoteBook): Uri?
|
||||||
}
|
}
|
||||||
@@ -73,7 +73,7 @@ class RemoteBookViewModel(application: Application): BaseViewModel(application){
|
|||||||
execute {
|
execute {
|
||||||
val downloadBookPath = RemoteBookWebDav.getRemoteBook(remoteBook)
|
val downloadBookPath = RemoteBookWebDav.getRemoteBook(remoteBook)
|
||||||
downloadBookPath?.let {
|
downloadBookPath?.let {
|
||||||
LocalBook.importFile(Uri.parse(it))
|
LocalBook.importFile(it)
|
||||||
}
|
}
|
||||||
}.onFinally {
|
}.onFinally {
|
||||||
finally.invoke()
|
finally.invoke()
|
||||||
|
|||||||
@@ -3,11 +3,13 @@ package io.legado.app.ui.book.remote.manager
|
|||||||
|
|
||||||
import android.net.Uri
|
import android.net.Uri
|
||||||
import io.legado.app.constant.PreferKey
|
import io.legado.app.constant.PreferKey
|
||||||
|
import io.legado.app.constant.AppPattern.bookFileRegex
|
||||||
import io.legado.app.exception.NoStackTraceException
|
import io.legado.app.exception.NoStackTraceException
|
||||||
import io.legado.app.help.AppWebDav
|
import io.legado.app.help.AppWebDav
|
||||||
import io.legado.app.help.config.AppConfig
|
import io.legado.app.help.config.AppConfig
|
||||||
import io.legado.app.lib.webdav.WebDav
|
import io.legado.app.lib.webdav.WebDav
|
||||||
import io.legado.app.lib.webdav.WebDavFile
|
import io.legado.app.lib.webdav.WebDavFile
|
||||||
|
import io.legado.app.model.localBook.LocalBook
|
||||||
import io.legado.app.ui.book.remote.RemoteBook
|
import io.legado.app.ui.book.remote.RemoteBook
|
||||||
import io.legado.app.ui.book.remote.RemoteBookManager
|
import io.legado.app.ui.book.remote.RemoteBookManager
|
||||||
import io.legado.app.utils.*
|
import io.legado.app.utils.*
|
||||||
@@ -17,7 +19,6 @@ import java.io.File
|
|||||||
|
|
||||||
object RemoteBookWebDav : RemoteBookManager() {
|
object RemoteBookWebDav : RemoteBookManager() {
|
||||||
private val remoteBookUrl get() = "${rootWebDavUrl}${remoteBookFolder}"
|
private val remoteBookUrl get() = "${rootWebDavUrl}${remoteBookFolder}"
|
||||||
private val localSaveFolder get() = "${appCtx.externalFiles.absolutePath}${File.separator}${remoteBookFolder}"
|
|
||||||
|
|
||||||
init {
|
init {
|
||||||
runBlocking {
|
runBlocking {
|
||||||
@@ -68,31 +69,35 @@ object RemoteBookWebDav : RemoteBookManager() {
|
|||||||
val fileExtension = webDavFileName.substringAfterLast(".")
|
val fileExtension = webDavFileName.substringAfterLast(".")
|
||||||
|
|
||||||
//扩展名符合阅读的格式则认为是书籍
|
//扩展名符合阅读的格式则认为是书籍
|
||||||
if (contentTypeList.contains(fileExtension)) {
|
if (bookFileRegex.matches(webDavFileName)) {
|
||||||
remoteBooks.add(RemoteBook(webDavFileName,webDavUrlName,webDavFile.size,fileExtension,webDavFile.lastModify))
|
val isOnBookShelf = LocalBook.isOnBookShelf(webDavFileName)
|
||||||
|
remoteBooks.add(
|
||||||
|
RemoteBook(
|
||||||
|
webDavFileName, webDavUrlName, webDavFile.size,
|
||||||
|
fileExtension, webDavFile.lastModify, isOnBookShelf
|
||||||
|
)
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} ?: throw NoStackTraceException("webDav没有配置")
|
} ?: throw NoStackTraceException("webDav没有配置")
|
||||||
return remoteBooks
|
return remoteBooks
|
||||||
}
|
}
|
||||||
|
|
||||||
override suspend fun getRemoteBook(remoteBook: RemoteBook): String? {
|
override suspend fun getRemoteBook(remoteBook: RemoteBook): Uri? {
|
||||||
val saveFilePath= "${localSaveFolder}${File.separator}${remoteBook.filename}"
|
return kotlin.runCatching {
|
||||||
kotlin.runCatching {
|
|
||||||
AppWebDav.authorization?.let {
|
AppWebDav.authorization?.let {
|
||||||
FileUtils.createFolderIfNotExist(localSaveFolder).run {
|
val webdav = WebDav(
|
||||||
val webdav = WebDav(
|
remoteBook.urlName,
|
||||||
remoteBook.urlName,
|
it
|
||||||
it
|
)
|
||||||
)
|
webdav.download().let { bytes ->
|
||||||
webdav.downloadTo(saveFilePath, true)
|
LocalBook.saveBookFile(bytes, remoteBook.filename)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.onFailure {
|
}.onFailure {
|
||||||
it.printStackTrace()
|
it.printStackTrace()
|
||||||
return null
|
null
|
||||||
}
|
}.getOrNull()
|
||||||
return saveFilePath
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
Reference in New Issue
Block a user