Remove redundancy in ExtensionManager

(cherry picked from commit 93925a72866892358b7f46645e1f189b2cf3bc1d)

# Conflicts:
#	app/src/main/java/eu/kanade/tachiyomi/extension/ExtensionManager.kt
#	app/src/main/java/eu/kanade/tachiyomi/source/SourceManager.kt
#	app/src/main/java/eu/kanade/tachiyomi/ui/browse/source/globalsearch/GlobalSearchPresenter.kt
This commit is contained in:
arkon 2022-10-21 14:42:21 -04:00 committed by Jobobby04
parent 893443222d
commit 9fafe15081
8 changed files with 49 additions and 94 deletions

View File

@ -13,7 +13,7 @@ class GetExtensionLanguages(
fun subscribe(): Flow<List<String>> {
return combine(
preferences.enabledLanguages().changes(),
extensionManager.getAvailableExtensionsFlow(),
extensionManager.availableExtensionsFlow,
) { enabledLanguage, availableExtensions ->
availableExtensions
.flatMap { ext ->

View File

@ -17,9 +17,9 @@ class GetExtensionsByType(
return combine(
preferences.enabledLanguages().changes(),
extensionManager.getInstalledExtensionsFlow(),
extensionManager.getUntrustedExtensionsFlow(),
extensionManager.getAvailableExtensionsFlow(),
extensionManager.installedExtensionsFlow,
extensionManager.untrustedExtensionsFlow,
extensionManager.availableExtensionsFlow,
) { _activeLanguages, _installed, _untrusted, _available ->
val (updates, installed) = _installed
.filter { (showNsfwSources || it.isNsfw.not()) }

View File

@ -3,7 +3,6 @@ package eu.kanade.tachiyomi.extension
import android.content.Context
import android.graphics.drawable.Drawable
import androidx.core.content.ContextCompat
import com.jakewharton.rxrelay.BehaviorRelay
import eu.kanade.domain.source.model.SourceData
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.tachiyomi.R
@ -15,7 +14,6 @@ import eu.kanade.tachiyomi.extension.model.LoadResult
import eu.kanade.tachiyomi.extension.util.ExtensionInstallReceiver
import eu.kanade.tachiyomi.extension.util.ExtensionInstaller
import eu.kanade.tachiyomi.extension.util.ExtensionLoader
import eu.kanade.tachiyomi.source.Source
import eu.kanade.tachiyomi.util.lang.launchNow
import eu.kanade.tachiyomi.util.lang.withUIContext
import eu.kanade.tachiyomi.util.preference.plusAssign
@ -26,10 +24,14 @@ import exh.source.BlacklistedSources
import exh.source.EH_SOURCE_ID
import exh.source.EXH_SOURCE_ID
import exh.source.MERGED_SOURCE_ID
import kotlinx.coroutines.DelicateCoroutinesApi
import kotlinx.coroutines.GlobalScope
import kotlinx.coroutines.async
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.flow.SharingStarted
import kotlinx.coroutines.flow.asStateFlow
import kotlinx.coroutines.flow.map
import kotlinx.coroutines.flow.stateIn
import logcat.LogPriority
import rx.Observable
import uy.kohesive.injekt.Injekt
@ -61,37 +63,15 @@ class ExtensionManager(
*/
private val installer by lazy { ExtensionInstaller(context) }
/**
* Relay used to notify the installed extensions.
*/
private val installedExtensionsRelay = BehaviorRelay.create<List<Extension.Installed>>()
private val iconMap = mutableMapOf<String, Drawable>()
/**
* List of the currently installed extensions.
*/
var installedExtensions = emptyList<Extension.Installed>()
private set(value) {
field = value
installedExtensionsFlow.value = field
installedExtensionsRelay.call(value)
}
private val installedExtensionsFlow = MutableStateFlow(installedExtensions)
private val _installedExtensionsFlow = MutableStateFlow(emptyList<Extension.Installed>())
val installedExtensionsFlow = _installedExtensionsFlow.asStateFlow()
private var subLanguagesEnabledOnFirstRun = preferences.enabledLanguages().isSet()
fun getInstalledExtensionsFlow(): StateFlow<List<Extension.Installed>> {
return installedExtensionsFlow.asStateFlow()
}
fun getAppIconForSource(source: Source): Drawable? {
return getAppIconForSource(source.id)
}
fun getAppIconForSource(sourceId: Long): Drawable? {
val pkgName = installedExtensions.find { ext -> ext.sources.any { it.id == sourceId } }?.pkgName
val pkgName = _installedExtensionsFlow.value.find { ext -> ext.sources.any { it.id == sourceId } }?.pkgName
if (pkgName != null) {
return iconMap[pkgName] ?: iconMap.getOrPut(pkgName) { context.packageManager.getApplicationIcon(pkgName) }
}
@ -106,22 +86,14 @@ class ExtensionManager(
// SY <--
}
/**
* List of the currently available extensions.
*/
var availableExtensions = emptyList<Extension.Available>()
private set(value) {
field = value
availableExtensionsFlow.value = field
updatedInstalledExtensionsStatuses(value)
setupAvailableExtensionsSourcesDataMap(value)
}
private val _availableExtensionsFlow = MutableStateFlow(emptyList<Extension.Available>())
private val availableExtensionsFlow = MutableStateFlow(availableExtensions)
fun getAvailableExtensionsFlow(): StateFlow<List<Extension.Available>> {
return availableExtensionsFlow.asStateFlow()
}
// SY -->
@OptIn(DelicateCoroutinesApi::class)
val availableExtensionsFlow = _availableExtensionsFlow
.map { it.filterNotBlacklisted() }
.stateIn(GlobalScope, SharingStarted.Eagerly, emptyList())
// SY <--
private var availableExtensionsSourcesData: Map<Long, SourceData> = mapOf()
@ -134,24 +106,8 @@ class ExtensionManager(
fun getSourceData(id: Long) = availableExtensionsSourcesData[id]
// SY -->
var unalteredAvailableExtensions = emptyList<Extension.Available>()
// SY <--
/**
* List of the currently untrusted extensions.
*/
var untrustedExtensions = emptyList<Extension.Untrusted>()
private set(value) {
field = value
untrustedExtensionsFlow.value = field
}
private val untrustedExtensionsFlow = MutableStateFlow(untrustedExtensions)
fun getUntrustedExtensionsFlow(): StateFlow<List<Extension.Untrusted>> {
return untrustedExtensionsFlow.asStateFlow()
}
private val _untrustedExtensionsFlow = MutableStateFlow(emptyList<Extension.Untrusted>())
val untrustedExtensionsFlow = _untrustedExtensionsFlow.asStateFlow()
init {
initExtensions()
@ -164,11 +120,11 @@ class ExtensionManager(
private fun initExtensions() {
val extensions = ExtensionLoader.loadExtensions(context)
installedExtensions = extensions
_installedExtensionsFlow.value = extensions
.filterIsInstance<LoadResult.Success>()
.map { it.extension }
untrustedExtensions = extensions
_untrustedExtensionsFlow.value = extensions
.filterIsInstance<LoadResult.Untrusted>()
.map { it.extension }
// SY -->
@ -206,10 +162,9 @@ class ExtensionManager(
enableAdditionalSubLanguages(extensions)
// SY -->
unalteredAvailableExtensions = extensions
availableExtensions = extensions.filterNotBlacklisted()
// SY <--
_availableExtensionsFlow.value = extensions
updatedInstalledExtensionsStatuses(extensions)
setupAvailableExtensionsSourcesDataMap(extensions)
}
/**
@ -253,13 +208,13 @@ class ExtensionManager(
return
}
val mutInstalledExtensions = installedExtensions.toMutableList()
val mutInstalledExtensions = _installedExtensionsFlow.value.toMutableList()
var changed = false
for ((index, installedExt) in mutInstalledExtensions.withIndex()) {
val pkgName = installedExt.pkgName
// SY -->
val availableExt = unalteredAvailableExtensions.find { it.pkgName == pkgName }
val availableExt = _availableExtensionsFlow.value.find { it.pkgName == pkgName }
// SY <--
if (!installedExt.isUnofficial && availableExt == null && !installedExt.isObsolete) {
@ -286,7 +241,7 @@ class ExtensionManager(
}
}
if (changed) {
installedExtensions = mutInstalledExtensions
_installedExtensionsFlow.value = mutInstalledExtensions
}
updatePendingUpdatesCount()
}
@ -310,7 +265,7 @@ class ExtensionManager(
* @param extension The extension to be updated.
*/
fun updateExtension(extension: Extension.Installed): Observable<InstallStep> {
val availableExt = availableExtensions.find { it.pkgName == extension.pkgName }
val availableExt = _availableExtensionsFlow.value.find { it.pkgName == extension.pkgName }
?: return Observable.empty()
return installExtension(availableExt)
}
@ -348,14 +303,14 @@ class ExtensionManager(
* @param signature The signature to whitelist.
*/
fun trustSignature(signature: String) {
val untrustedSignatures = untrustedExtensions.map { it.signatureHash }.toSet()
val untrustedSignatures = _untrustedExtensionsFlow.value.map { it.signatureHash }.toSet()
if (signature !in untrustedSignatures) return
ExtensionLoader.trustedSignatures += signature
preferences.trustedSignatures() += signature
val nowTrustedExtensions = untrustedExtensions.filter { it.signatureHash == signature }
untrustedExtensions -= nowTrustedExtensions
val nowTrustedExtensions = _untrustedExtensionsFlow.value.filter { it.signatureHash == signature }
_untrustedExtensionsFlow.value -= nowTrustedExtensions
val ctx = context
launchNow {
@ -385,7 +340,7 @@ class ExtensionManager(
}
// SY <--
installedExtensions += extension
_installedExtensionsFlow.value += extension
}
/**
@ -402,13 +357,13 @@ class ExtensionManager(
}
// SY <--
val mutInstalledExtensions = installedExtensions.toMutableList()
val mutInstalledExtensions = _installedExtensionsFlow.value.toMutableList()
val oldExtension = mutInstalledExtensions.find { it.pkgName == extension.pkgName }
if (oldExtension != null) {
mutInstalledExtensions -= oldExtension
}
mutInstalledExtensions += extension
installedExtensions = mutInstalledExtensions
_installedExtensionsFlow.value = mutInstalledExtensions
}
/**
@ -418,13 +373,13 @@ class ExtensionManager(
* @param pkgName The package name of the uninstalled application.
*/
private fun unregisterExtension(pkgName: String) {
val installedExtension = installedExtensions.find { it.pkgName == pkgName }
val installedExtension = _installedExtensionsFlow.value.find { it.pkgName == pkgName }
if (installedExtension != null) {
installedExtensions -= installedExtension
_installedExtensionsFlow.value -= installedExtension
}
val untrustedExtension = untrustedExtensions.find { it.pkgName == pkgName }
val untrustedExtension = _untrustedExtensionsFlow.value.find { it.pkgName == pkgName }
if (untrustedExtension != null) {
untrustedExtensions -= untrustedExtension
_untrustedExtensionsFlow.value -= untrustedExtension
}
}
@ -444,7 +399,7 @@ class ExtensionManager(
}
override fun onExtensionUntrusted(extension: Extension.Untrusted) {
untrustedExtensions += extension
_untrustedExtensionsFlow.value += extension
}
override fun onPackageUninstalled(pkgName: String) {
@ -457,14 +412,14 @@ class ExtensionManager(
* Extension method to set the update field of an installed extension.
*/
private fun Extension.Installed.withUpdateCheck(): Extension.Installed {
val availableExt = availableExtensions.find { it.pkgName == pkgName }
if ((isUnofficial.not() || availableExt?.isRepoSource == true) && availableExt != null && availableExt.versionCode > versionCode) {
val availableExt = _availableExtensionsFlow.value.find { it.pkgName == pkgName }
if ((!isUnofficial || availableExt?.isRepoSource == true) && availableExt != null && availableExt.versionCode > versionCode) {
return copy(hasUpdate = true)
}
return this
}
private fun updatePendingUpdatesCount() {
preferences.extensionUpdatesCount().set(installedExtensions.count { it.hasUpdate })
preferences.extensionUpdatesCount().set(_installedExtensionsFlow.value.count { it.hasUpdate })
}
}

View File

@ -96,7 +96,7 @@ internal class ExtensionGithubApi {
}
val extensions = if (fromAvailableExtensionList) {
extensionManager.availableExtensions
extensionManager.availableExtensionsFlow.value
} else {
findExtensions().also { lastExtCheck.set(Date().time) }
}

View File

@ -7,7 +7,7 @@ import eu.kanade.tachiyomi.extension.ExtensionManager
import uy.kohesive.injekt.Injekt
import uy.kohesive.injekt.api.get
fun Source.icon(): Drawable? = Injekt.get<ExtensionManager>().getAppIconForSource(this)
fun Source.icon(): Drawable? = Injekt.get<ExtensionManager>().getAppIconForSource(this.id)
fun Source.getPreferenceKey(): String = "source_$id"

View File

@ -73,7 +73,7 @@ class SourceManager(
init {
scope.launch {
extensionManager.getInstalledExtensionsFlow()
extensionManager.installedExtensionsFlow
// SY -->
.combine(preferences.enableExhentai().changes()) { extensions, enableExhentai ->
extensions to enableExhentai

View File

@ -36,7 +36,7 @@ class ExtensionDetailsPresenter(
super.onCreate(savedState)
presenterScope.launchIO {
extensionManager.getInstalledExtensionsFlow()
extensionManager.installedExtensionsFlow
.map { it.firstOrNull { pkg -> pkg.pkgName == pkgName } }
.collectLatest { extension ->
// If extension is null it's most likely uninstalled

View File

@ -117,7 +117,7 @@ open class GlobalSearchPresenter(
if (!filter.isNullOrEmpty()) {
// SY -->
val filteredSourceIds = extensionManager.installedExtensions
val filteredSourceIds = extensionManager.installedExtensionsFlow.value
.filter { it.pkgName == filter }
.flatMap { it.sources }
.map { it.id }