ソースを参照

优化下载逻辑

HapeLee 6 ヶ月 前
親
コミット
6a0954377a

+ 47 - 17
app/src/main/java/io/legado/app/model/CacheBook.kt

@@ -1,6 +1,8 @@
 package io.legado.app.model
 
 import android.content.Context
+import android.content.Intent
+import androidx.core.content.ContextCompat
 import io.legado.app.constant.IntentAction
 import io.legado.app.data.appDb
 import io.legado.app.data.entities.Book
@@ -12,8 +14,8 @@ import io.legado.app.model.cache.CacheDownloadStateStore
 import io.legado.app.model.cache.ChapterSelection
 import io.legado.app.service.CacheBookService
 import io.legado.app.ui.config.otherConfig.OtherConfig
+import io.legado.app.utils.LogUtils
 import io.legado.app.utils.onEachParallel
-import io.legado.app.utils.startService
 import kotlinx.coroutines.CompletableDeferred
 import kotlinx.coroutines.TimeoutCancellationException
 import kotlinx.coroutines.coroutineScope
@@ -233,7 +235,7 @@ object CacheBook {
         if (isLocal) return
         if (!request.hasValidSelection()) return
         isPaused = false
-        context.startService<CacheBookService> {
+        startCacheBookService(context) {
             action = IntentAction.start
             putRequestExtras(request)
         }
@@ -247,7 +249,7 @@ object CacheBook {
             }
             .forEach { request ->
                 isPaused = false
-                context.startService<CacheBookService> {
+                startCacheBookService(context) {
                     action = IntentAction.start
                     putRequestExtras(request)
                 }
@@ -272,15 +274,29 @@ object CacheBook {
         }
     }
 
+    private fun startCacheBookService(context: Context, configIntent: Intent.() -> Unit = {}): Boolean {
+        val intent = Intent(context, CacheBookService::class.java).apply(configIntent)
+        return try {
+            ContextCompat.startForegroundService(context, intent)
+            true
+        } catch (e: Exception) {
+            LogUtils.e("CacheBook", "启动下载服务失败: ${e.localizedMessage}")
+            false
+        }
+    }
+
     fun remove(context: Context, bookUrl: String) {
         if (!CacheBookService.isRun) {
             removeBookFromService(bookUrl)
             return
         }
-        context.startService<CacheBookService> {
+        val started = startCacheBookService(context) {
             action = IntentAction.remove
             putExtra("bookUrl", bookUrl)
         }
+        if (!started) {
+            removeBookFromService(bookUrl)
+        }
     }
 
     suspend fun removeAwait(context: Context, bookUrl: String): Boolean {
@@ -290,15 +306,14 @@ object CacheBook {
         val requestId = pendingRequestId.incrementAndGet()
         val removeRequest = CompletableDeferred<Boolean>()
         pendingRemoveRequests[requestId] = removeRequest
-        runCatching {
-            context.startService<CacheBookService> {
-                action = IntentAction.remove
-                putExtra("bookUrl", bookUrl)
-                putExtra("removeRequestId", requestId)
-            }
-        }.onFailure {
+        val started = startCacheBookService(context) {
+            action = IntentAction.remove
+            putExtra("bookUrl", bookUrl)
+            putExtra("removeRequestId", requestId)
+        }
+        if (!started) {
             pendingRemoveRequests.remove(requestId)
-            removeRequest.completeExceptionally(it)
+            return removeBookFromService(bookUrl)
         }
         return try {
             withTimeout(30_000L) {
@@ -340,17 +355,23 @@ object CacheBook {
 
     fun stop(context: Context) {
         if (CacheBookService.isRun) {
-            context.startService<CacheBookService> {
+            val started = startCacheBookService(context) {
                 action = IntentAction.stop
             }
+            if (!started) {
+                close(clearFailureState = false)
+            }
         }
     }
 
     fun pause(context: Context) {
         if (CacheBookService.isRun) {
-            context.startService<CacheBookService> {
+            val started = startCacheBookService(context) {
                 action = IntentAction.pause
             }
+            if (!started) {
+                pauseAllFromService()
+            }
         } else {
             pauseAllFromService()
         }
@@ -359,9 +380,12 @@ object CacheBook {
     fun resume(context: Context): Boolean {
         if (!hasQueuedDownloads) return false
         isPaused = false
-        context.startService<CacheBookService> {
+        val started = startCacheBookService(context) {
             action = IntentAction.resume
         }
+        if (!started) {
+            resumeFromService()
+        }
         return true
     }
 
@@ -399,9 +423,12 @@ object CacheBook {
             isPaused = false
             updateSummary()
             _queueChangedFlow.tryEmit(bookUrl)
-            context.startService<CacheBookService> {
+            val started = startCacheBookService(context) {
                 action = IntentAction.resume
             }
+            if (!started) {
+                resumeFromService()
+            }
         }
         return resumed
     }
@@ -421,9 +448,12 @@ object CacheBook {
             isPaused = false
             updateSummary()
             _queueChangedFlow.tryEmit(bookUrl)
-            context.startService<CacheBookService> {
+            val started = startCacheBookService(context) {
                 action = IntentAction.resume
             }
+            if (!started) {
+                resumeFromService()
+            }
         }
         return resumed
     }

+ 2 - 2
app/src/main/java/io/legado/app/utils/ContextExtensions.kt

@@ -170,9 +170,9 @@ inline fun <reified T : BroadcastReceiver> Context.broadcastPendingIntent(
 
 fun Context.startForegroundServiceCompat(intent: Intent) {
     try {
-        startService(intent)
-    } catch (e: IllegalStateException) {
         ContextCompat.startForegroundService(this, intent)
+    } catch (e: Exception) {
+        startService(intent)
     }
 }