microg: improve installer state detection

This commit is contained in:
Rahul Patel
2026-05-12 20:51:21 +05:30
parent 53aff0e24f
commit ff69759634
3 changed files with 60 additions and 21 deletions

View File

@@ -620,7 +620,7 @@ private fun ScreenContentApp(
is ExtraScreen.MicroG -> MicroGScreen(
packageName = app.packageName,
onNavigateUp = ::onNavigateBack,
onIgnore = { onInstall(ignoreMicroG = it) }
onProceed = { onInstall(ignoreMicroG = true) }
)
is Screen.DevProfile -> DevProfileScreen(

View File

@@ -56,14 +56,14 @@ import com.aurora.store.viewmodel.onboarding.MicroGViewModel
fun MicroGScreen(
packageName: String,
onNavigateUp: () -> Unit,
onIgnore: (Boolean) -> Unit,
onProceed: () -> Unit,
appDetailsViewModel: AppDetailsViewModel = hiltViewModel(key = packageName),
viewModel: MicroGViewModel = hiltViewModel(),
windowAdaptiveInfo: WindowAdaptiveInfo = currentWindowAdaptiveInfoV2()
) {
val app by appDetailsViewModel.app.collectAsStateWithLifecycle()
val topAppBarTitle = when {
windowAdaptiveInfo.isWindowCompact -> app!!.displayName
windowAdaptiveInfo.isWindowCompact -> app?.displayName
else -> stringResource(R.string.onboarding_title_gsf)
}
@@ -73,7 +73,7 @@ fun MicroGScreen(
onNavigateUp = onNavigateUp,
onInstall = { viewModel.downloadMicroG() },
onRetry = { viewModel.retryDownload() },
onIgnore = onIgnore
onProceed = onProceed
)
}
@@ -84,7 +84,7 @@ private fun ScreenContent(
onNavigateUp: () -> Unit = {},
onInstall: () -> Unit = {},
onRetry: () -> Unit = {},
onIgnore: (Boolean) -> Unit = {},
onProceed: () -> Unit = {},
windowAdaptiveInfo: WindowAdaptiveInfo = currentWindowAdaptiveInfoV2()
) {
val context = LocalContext.current
@@ -123,7 +123,7 @@ private fun ScreenContent(
Button(
modifier = Modifier.weight(1F),
onClick = { onIgnore(uiState.isInstalled) },
onClick = onProceed,
enabled = !uiState.isInProgress
) {
Text(

View File

@@ -113,10 +113,22 @@ class MicroGViewModel @Inject constructor(
private val bundle = listOf(microGServiceApk, microGCompanionApk)
init {
AuroraApp.events.installerEvent.onEach {
if (it is InstallerEvent.Installed) refresh()
AuroraApp.events.installerEvent.onEach { event ->
when (event) {
is InstallerEvent.Installed -> refresh()
is InstallerEvent.Uninstalled -> handleUninstall(event.packageName)
else -> {}
}
}.launchIn(AuroraApp.scope)
viewModelScope.launch {
bundle.forEach { apk ->
val download = downloadHelper.getDownload(apk.packageName)
if (download?.status == DownloadStatus.COMPLETED && !isBundleApkInstalled(apk)) {
downloadHelper.removeDownload(apk.packageName)
}
}
combine(
downloadHelper.downloadsList,
networkProvider.status.onStart { emit(NetworkStatus.AVAILABLE) }
@@ -128,6 +140,7 @@ class MicroGViewModel @Inject constructor(
)
}.onEach { uiState = it }.launchIn(viewModelScope)
}
}
fun downloadMicroG() {
viewModelScope.launch(Dispatchers.IO) {
@@ -147,18 +160,44 @@ class MicroGViewModel @Inject constructor(
}
private suspend fun enqueueIfNeeded(apk: ExternalApk) {
if (apk.isInstalled(context)) {
if (isBundleApkInstalled(apk)) {
AuroraApp.events.send(InstallerEvent.Installed(apk.packageName))
} else {
downloadHelper.enqueueStandalone(apk)
}
}
// Validate against the microG-specific signature/version checks rather than mere package
// presence — a stock Play Store or older Companion would otherwise be reported as installed.
private fun isBundleApkInstalled(apk: ExternalApk): Boolean = when (apk.packageName) {
PACKAGE_NAME_GMS -> PackageUtil.hasSupportedMicroGVariant(context)
PACKAGE_NAME_PLAY_STORE -> PackageUtil.hasMicroGCompanion(context)
else -> apk.isInstalled(context)
}
private fun handleUninstall(packageName: String) {
val apk = bundle.find { it.packageName == packageName } ?: return
viewModelScope.launch {
downloadHelper.removeDownload(packageName)
uiState = uiState.copy(
items = uiState.items.map { item ->
if (item.packageName == apk.packageName) {
item.copy(status = InstallStatus.PENDING, progress = 0)
} else {
item
}
}
)
}
}
private fun refresh() {
uiState = uiState.copy(
items = uiState.items.map { item ->
val apk = bundle.find { it.packageName == item.packageName }
if (item.status != InstallStatus.INSTALLED &&
PackageUtil.isInstalled(context, item.packageName)
apk != null &&
isBundleApkInstalled(apk)
) {
item.copy(status = InstallStatus.INSTALLED)
} else {
@@ -170,7 +209,7 @@ class MicroGViewModel @Inject constructor(
private fun buildItem(apk: ExternalApk, download: Download?): ExternalItem {
val state = when {
apk.isInstalled(context) -> InstallStatus.INSTALLED
isBundleApkInstalled(apk) -> InstallStatus.INSTALLED
download == null -> InstallStatus.PENDING
download.status == DownloadStatus.FAILED -> InstallStatus.FAILED
download.status == DownloadStatus.CANCELLED -> InstallStatus.PENDING