Display App installed in other user in All Apps
Only for admin user. Also clean up unused getInstallationStatus(). Fix: 277299765 Test: Manually with All Apps when multiple users is on Test: Unit test Change-Id: I4de681c101a605e3517dcd8765bf7a95d1b76417
This commit is contained in:
@@ -986,17 +986,6 @@ public final class Utils extends com.android.settingslib.Utils {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the resource id to represent the install status for an app
|
||||
*/
|
||||
@StringRes
|
||||
public static int getInstallationStatus(ApplicationInfo info) {
|
||||
if ((info.flags & ApplicationInfo.FLAG_INSTALLED) == 0) {
|
||||
return R.string.not_installed;
|
||||
}
|
||||
return info.enabled ? R.string.installed : R.string.disabled;
|
||||
}
|
||||
|
||||
private static boolean isVolumeValid(VolumeInfo volume) {
|
||||
return (volume != null) && (volume.getType() == VolumeInfo.TYPE_PRIVATE)
|
||||
&& volume.isMountedReadable();
|
||||
|
@@ -38,6 +38,7 @@ import com.android.settingslib.spa.widget.preference.PreferenceModel
|
||||
import com.android.settingslib.spa.widget.ui.SpinnerOption
|
||||
import com.android.settingslib.spaprivileged.model.app.AppListModel
|
||||
import com.android.settingslib.spaprivileged.model.app.AppRecord
|
||||
import com.android.settingslib.spaprivileged.model.app.installed
|
||||
import com.android.settingslib.spaprivileged.template.app.AppList
|
||||
import com.android.settingslib.spaprivileged.template.app.AppListInput
|
||||
import com.android.settingslib.spaprivileged.template.app.AppListItem
|
||||
@@ -75,6 +76,7 @@ fun AllAppListPage(
|
||||
title = stringResource(R.string.all_apps),
|
||||
listModel = rememberContext(::AllAppListModel),
|
||||
showInstantApps = true,
|
||||
matchAnyUserForAdmin = true,
|
||||
moreOptions = { ResetAppPreferences(resetAppDialogPresenter::open) },
|
||||
appList = appList,
|
||||
)
|
||||
@@ -133,8 +135,13 @@ class AllAppListModel(
|
||||
return remember {
|
||||
derivedStateOf {
|
||||
storageSummary.value +
|
||||
when (isDisabled(record)) {
|
||||
true -> System.lineSeparator() + context.getString(R.string.disabled)
|
||||
when {
|
||||
!record.app.installed -> {
|
||||
System.lineSeparator() + context.getString(R.string.not_installed)
|
||||
}
|
||||
isDisabled(record) -> {
|
||||
System.lineSeparator() + context.getString(R.string.disabled)
|
||||
}
|
||||
else -> ""
|
||||
}
|
||||
}
|
||||
|
@@ -30,8 +30,10 @@ import com.android.settings.notification.app.AppNotificationSettings
|
||||
import com.android.settings.spa.notification.AppNotificationRepository
|
||||
import com.android.settings.spa.notification.IAppNotificationRepository
|
||||
import com.android.settingslib.spa.framework.compose.rememberContext
|
||||
import com.android.settingslib.spa.framework.compose.stateOf
|
||||
import com.android.settingslib.spa.widget.preference.Preference
|
||||
import com.android.settingslib.spa.widget.preference.PreferenceModel
|
||||
import com.android.settingslib.spaprivileged.model.app.installed
|
||||
import kotlinx.coroutines.Dispatchers
|
||||
import kotlinx.coroutines.flow.flow
|
||||
import kotlinx.coroutines.flow.flowOn
|
||||
@@ -53,6 +55,7 @@ fun AppNotificationPreference(
|
||||
override val summary = summaryFlow.collectAsStateWithLifecycle(
|
||||
initialValue = stringResource(R.string.summary_placeholder)
|
||||
)
|
||||
override val enabled = stateOf(app.installed)
|
||||
override val onClick = { navigateToAppNotificationSettings(context, app) }
|
||||
})
|
||||
}
|
||||
|
@@ -141,7 +141,9 @@ class PackageInfoPresenter(
|
||||
private fun getPackageInfo() =
|
||||
packageManagers.getPackageInfoAsUser(
|
||||
packageName = packageName,
|
||||
flags = PackageManager.MATCH_DISABLED_COMPONENTS or PackageManager.GET_PERMISSIONS,
|
||||
flags = PackageManager.MATCH_ANY_USER or
|
||||
PackageManager.MATCH_DISABLED_COMPONENTS or
|
||||
PackageManager.GET_PERMISSIONS,
|
||||
userId = userId,
|
||||
)
|
||||
}
|
||||
|
@@ -28,6 +28,7 @@ import androidx.compose.runtime.livedata.observeAsState
|
||||
import com.android.settings.R
|
||||
import com.android.settingslib.spaprivileged.model.app.AppOpsController
|
||||
import com.android.settingslib.spaprivileged.model.app.AppRecord
|
||||
import com.android.settingslib.spaprivileged.model.app.installed
|
||||
import com.android.settingslib.spaprivileged.model.app.userId
|
||||
import com.android.settingslib.spaprivileged.template.app.TogglePermissionAppListModel
|
||||
import com.android.settingslib.spaprivileged.template.app.TogglePermissionAppListProvider
|
||||
@@ -67,11 +68,12 @@ class PictureInPictureListModel(private val context: Context) :
|
||||
}
|
||||
|
||||
override fun transformItem(app: ApplicationInfo): PictureInPictureRecord {
|
||||
val packageInfo =
|
||||
packageManager.getPackageInfoAsUser(app.packageName, GET_ACTIVITIES_FLAGS, app.userId)
|
||||
return createPictureInPictureRecord(
|
||||
app = app,
|
||||
isSupport = packageInfo.supportsPictureInPicture(),
|
||||
isSupport = app.installed &&
|
||||
packageManager
|
||||
.getPackageInfoAsUser(app.packageName, GET_ACTIVITIES_FLAGS, app.userId)
|
||||
.supportsPictureInPicture(),
|
||||
)
|
||||
}
|
||||
|
||||
|
@@ -160,30 +160,6 @@ public class UtilsTest {
|
||||
Utils.maybeInitializeVolume(storageManager, new Bundle());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getInstallationStatus_notInstalled_shouldReturnUninstalled() {
|
||||
assertThat(Utils.getInstallationStatus(new ApplicationInfo()))
|
||||
.isEqualTo(R.string.not_installed);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getInstallationStatus_enabled_shouldReturnInstalled() {
|
||||
final ApplicationInfo info = new ApplicationInfo();
|
||||
info.flags = ApplicationInfo.FLAG_INSTALLED;
|
||||
info.enabled = true;
|
||||
|
||||
assertThat(Utils.getInstallationStatus(info)).isEqualTo(R.string.installed);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getInstallationStatus_disabled_shouldReturnDisabled() {
|
||||
final ApplicationInfo info = new ApplicationInfo();
|
||||
info.flags = ApplicationInfo.FLAG_INSTALLED;
|
||||
info.enabled = false;
|
||||
|
||||
assertThat(Utils.getInstallationStatus(info)).isEqualTo(R.string.disabled);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void isProfileOrDeviceOwner_deviceOwnerApp_returnTrue() {
|
||||
when(mDevicePolicyManager.isDeviceOwnerAppOnAnyUser(PACKAGE_NAME)).thenReturn(true);
|
||||
|
@@ -147,6 +147,7 @@ class AllAppListTest {
|
||||
val listModel = AllAppListModel(context) { stateOf(SUMMARY) }
|
||||
val disabledApp = ApplicationInfo().apply {
|
||||
packageName = PACKAGE_NAME
|
||||
flags = ApplicationInfo.FLAG_INSTALLED
|
||||
enabled = false
|
||||
}
|
||||
|
||||
@@ -159,6 +160,23 @@ class AllAppListTest {
|
||||
assertThat(summaryState.value).isEqualTo("$SUMMARY${System.lineSeparator()}Disabled")
|
||||
}
|
||||
|
||||
@Test
|
||||
fun allAppListModel_getSummaryWhenNotInstalled() {
|
||||
val listModel = AllAppListModel(context) { stateOf(SUMMARY) }
|
||||
val notInstalledApp = ApplicationInfo().apply {
|
||||
packageName = PACKAGE_NAME
|
||||
}
|
||||
|
||||
lateinit var summaryState: State<String>
|
||||
composeTestRule.setContent {
|
||||
summaryState =
|
||||
listModel.getSummary(option = 0, record = AppRecordWithSize(app = notInstalledApp))
|
||||
}
|
||||
|
||||
assertThat(summaryState.value)
|
||||
.isEqualTo("$SUMMARY${System.lineSeparator()}Not installed for this user")
|
||||
}
|
||||
|
||||
private fun getAppListInput(): AppListInput<AppRecordWithSize> {
|
||||
lateinit var input: AppListInput<AppRecordWithSize>
|
||||
composeTestRule.setContent {
|
||||
@@ -192,6 +210,7 @@ class AllAppListTest {
|
||||
const val SUMMARY = "Summary"
|
||||
val APP = ApplicationInfo().apply {
|
||||
packageName = PACKAGE_NAME
|
||||
flags = ApplicationInfo.FLAG_INSTALLED
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -21,6 +21,7 @@ import android.content.pm.ApplicationInfo
|
||||
import androidx.compose.runtime.CompositionLocalProvider
|
||||
import androidx.compose.ui.platform.LocalContext
|
||||
import androidx.compose.ui.test.assertIsDisplayed
|
||||
import androidx.compose.ui.test.assertIsNotEnabled
|
||||
import androidx.compose.ui.test.junit4.createComposeRule
|
||||
import androidx.compose.ui.test.onNodeWithText
|
||||
import androidx.compose.ui.test.onRoot
|
||||
@@ -72,7 +73,7 @@ class AppNotificationPreferenceTest {
|
||||
|
||||
@Test
|
||||
fun title_displayed() {
|
||||
setContent()
|
||||
setContent(APP)
|
||||
|
||||
composeTestRule.onNodeWithText(context.getString(R.string.notifications_label))
|
||||
.assertIsDisplayed()
|
||||
@@ -80,14 +81,25 @@ class AppNotificationPreferenceTest {
|
||||
|
||||
@Test
|
||||
fun summary_displayed() {
|
||||
setContent()
|
||||
setContent(APP)
|
||||
|
||||
composeTestRule.onNodeWithText(SUMMARY).assertIsDisplayed()
|
||||
}
|
||||
|
||||
@Test
|
||||
fun whenNotInstalled_disable() {
|
||||
setContent(ApplicationInfo().apply {
|
||||
packageName = PACKAGE_NAME
|
||||
uid = UID
|
||||
})
|
||||
|
||||
composeTestRule.onNodeWithText(context.getString(R.string.notifications_label))
|
||||
.assertIsNotEnabled()
|
||||
}
|
||||
|
||||
@Test
|
||||
fun onClick_startActivity() {
|
||||
setContent()
|
||||
setContent(APP)
|
||||
|
||||
composeTestRule.onRoot().performClick()
|
||||
composeTestRule.delay()
|
||||
@@ -102,10 +114,10 @@ class AppNotificationPreferenceTest {
|
||||
}
|
||||
}
|
||||
|
||||
private fun setContent() {
|
||||
private fun setContent(app: ApplicationInfo) {
|
||||
composeTestRule.setContent {
|
||||
CompositionLocalProvider(LocalContext provides context) {
|
||||
AppNotificationPreference(app = APP, repository = repository)
|
||||
AppNotificationPreference(app = app, repository = repository)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -116,6 +128,7 @@ class AppNotificationPreferenceTest {
|
||||
val APP = ApplicationInfo().apply {
|
||||
packageName = PACKAGE_NAME
|
||||
uid = UID
|
||||
flags = ApplicationInfo.FLAG_INSTALLED
|
||||
}
|
||||
const val SUMMARY = "Summary"
|
||||
}
|
||||
|
@@ -167,6 +167,7 @@ class PictureInPictureTest {
|
||||
const val PICTURE_IN_PICTURE_PACKAGE_NAME = "picture.in.picture.package.name"
|
||||
val PICTURE_IN_PICTURE_APP = ApplicationInfo().apply {
|
||||
packageName = PICTURE_IN_PICTURE_PACKAGE_NAME
|
||||
flags = ApplicationInfo.FLAG_INSTALLED
|
||||
}
|
||||
val PICTURE_IN_PICTURE_PACKAGE_INFO = PackageInfo().apply {
|
||||
packageName = PICTURE_IN_PICTURE_PACKAGE_NAME
|
||||
|
Reference in New Issue
Block a user