diff --git a/app/src/main/java/eu/kanade/tachiyomi/extension/util/ExtensionInstaller.kt b/app/src/main/java/eu/kanade/tachiyomi/extension/util/ExtensionInstaller.kt index 37dbcfc1f..93638ee61 100644 --- a/app/src/main/java/eu/kanade/tachiyomi/extension/util/ExtensionInstaller.kt +++ b/app/src/main/java/eu/kanade/tachiyomi/extension/util/ExtensionInstaller.kt @@ -1,8 +1,12 @@ package eu.kanade.tachiyomi.extension.util import android.app.DownloadManager -import android.content.* +import android.content.BroadcastReceiver +import android.content.Context +import android.content.Intent +import android.content.IntentFilter import android.net.Uri +import android.os.Build import com.jakewharton.rxrelay.PublishRelay import eu.kanade.tachiyomi.extension.model.Extension import eu.kanade.tachiyomi.extension.model.InstallStep @@ -74,7 +78,7 @@ internal class ExtensionInstaller(private val context: Context) { // Force an error if the download takes more than 3 minutes .mergeWith(Observable.timer(3, TimeUnit.MINUTES).map { InstallStep.Error }) // Force an error if the install process takes more than 10 seconds - .flatMap { timeoutWhenInstalling(it) } + .flatMap { Observable.just(it).mergeWith(timeoutWhenInstalling(it)) } // Stop when the application is installed or errors .takeUntil { it.isCompleted() } // Always notify on main thread @@ -121,13 +125,10 @@ internal class ExtensionInstaller(private val context: Context) { * @param currentStep The current step of the installation process. */ private fun timeoutWhenInstalling(currentStep: InstallStep): Observable { - return if (currentStep == InstallStep.Installing) { - Observable.timer(10, TimeUnit.SECONDS) - .map { InstallStep.Error } - .startWith(currentStep) - } else { - Observable.just(currentStep) - } + return Observable.just(currentStep) + .filter { it == InstallStep.Installing } + .delay(10, TimeUnit.SECONDS) + .map { InstallStep.Error } } /** @@ -233,13 +234,9 @@ internal class ExtensionInstaller(private val context: Context) { return } - // Due to a bug in older Android versions (L and M at least), the installer can't open - // files that do not contain the apk extension, even if you specify the correct MIME. - // We workaround it by querying the actual file path and using the file provider when - // it fails. - try { - installApk(uri) - } catch (_: ActivityNotFoundException) { + // Due to a bug in Android versions prior to N, the installer can't open files that do + // not contain the extension in the path, even if you specify the correct MIME. + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.N) { val query = DownloadManager.Query().setFilterById(id) downloadManager.query(query).use { cursor -> if (cursor.moveToFirst()) { @@ -249,6 +246,8 @@ internal class ExtensionInstaller(private val context: Context) { installApk(uriCompat) } } + } else { + installApk(uri) } } } diff --git a/app/src/main/java/eu/kanade/tachiyomi/ui/extension/ExtensionPresenter.kt b/app/src/main/java/eu/kanade/tachiyomi/ui/extension/ExtensionPresenter.kt index 36ea36700..54edce30f 100644 --- a/app/src/main/java/eu/kanade/tachiyomi/ui/extension/ExtensionPresenter.kt +++ b/app/src/main/java/eu/kanade/tachiyomi/ui/extension/ExtensionPresenter.kt @@ -52,13 +52,13 @@ open class ExtensionPresenter( val items = mutableListOf() - val installedSorted = installed.sortedWith(compareBy({ !it.hasUpdate }, { it.name })) - val untrustedSorted = untrusted.sortedBy { it.name } + val installedSorted = installed.sortedWith(compareBy({ !it.hasUpdate }, { it.pkgName })) + val untrustedSorted = untrusted.sortedBy { it.pkgName } val availableSorted = available // Filter out already installed extensions .filter { avail -> installed.none { it.pkgName == avail.pkgName } && untrusted.none { it.pkgName == avail.pkgName } } - .sortedBy { it.name } + .sortedBy { it.pkgName } if (installedSorted.isNotEmpty() || untrustedSorted.isNotEmpty()) { val header = ExtensionGroupItem(true, installedSorted.size + untrustedSorted.size)