Show all apps that requested cross profile permission
show all apps that requested the permission, show the admin restricted dialog if the app is not whitelisted by the admin, and show a link to install the app if the app is missing in one of the profiles. Bug: 149742043 Test: make RunSettingsRoboTests ROBOTEST_FILTER=InteractAcrossProfilesPreferenceControllerTest Test: make RunSettingsRoboTests ROBOTEST_FILTER=InteractAcrossProfilesControllerTest Test: make RunSettingsRoboTests ROBOTEST_FILTER=InteractAcrossProfilesSettingsTest Test: make RunSettingsRoboTests ROBOTEST_FILTER=InteractAcrossProfilesDetailsTest Change-Id: I2bc86b9966a2e14a12ee8f4b7f1b75f866ed98e3
This commit is contained in:
@@ -22,14 +22,18 @@ import static org.robolectric.Shadows.shadowOf;
|
||||
|
||||
import android.app.AppOpsManager;
|
||||
import android.content.Context;
|
||||
import android.content.pm.CrossProfileApps;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.content.pm.PermissionInfo;
|
||||
import android.os.Process;
|
||||
import android.content.pm.UserInfo;
|
||||
import android.os.UserManager;
|
||||
|
||||
import androidx.test.core.app.ApplicationProvider;
|
||||
|
||||
import com.android.settings.R;
|
||||
|
||||
import com.google.common.collect.ImmutableList;
|
||||
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
import org.robolectric.RobolectricTestRunner;
|
||||
@@ -37,6 +41,9 @@ import org.robolectric.RobolectricTestRunner;
|
||||
@RunWith(RobolectricTestRunner.class)
|
||||
public class InteractAcrossProfilesDetailsTest {
|
||||
|
||||
private static final int PERSONAL_PROFILE_ID = 0;
|
||||
private static final int WORK_PROFILE_ID = 10;
|
||||
private static final int PACKAGE_UID = 0;
|
||||
private static final String CROSS_PROFILE_PACKAGE_NAME = "crossProfilePackage";
|
||||
public static final String INTERACT_ACROSS_PROFILES_PERMISSION =
|
||||
"android.permission.INTERACT_ACROSS_PROFILES";
|
||||
@@ -44,29 +51,53 @@ public class InteractAcrossProfilesDetailsTest {
|
||||
private final Context mContext = ApplicationProvider.getApplicationContext();
|
||||
private final AppOpsManager mAppOpsManager = mContext.getSystemService(AppOpsManager.class);
|
||||
private final PackageManager mPackageManager = mContext.getPackageManager();
|
||||
private final InteractAcrossProfilesDetails mFragment = new InteractAcrossProfilesDetails();
|
||||
private final UserManager mUserManager = mContext.getSystemService(UserManager.class);
|
||||
private final CrossProfileApps mCrossProfileApps = mContext.getSystemService(
|
||||
CrossProfileApps.class);
|
||||
|
||||
@Test
|
||||
public void getPreferenceSummary_appOpAllowed_returnsAllowed() {
|
||||
shadowOf(mUserManager).addUser(
|
||||
PERSONAL_PROFILE_ID, "personal-profile"/* name */, 0/* flags */);
|
||||
shadowOf(mUserManager).addProfile(
|
||||
PERSONAL_PROFILE_ID, WORK_PROFILE_ID,
|
||||
"work-profile"/* profileName */, UserInfo.FLAG_MANAGED_PROFILE);
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
PERSONAL_PROFILE_ID, ImmutableList.of(CROSS_PROFILE_PACKAGE_NAME));
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
WORK_PROFILE_ID, ImmutableList.of(CROSS_PROFILE_PACKAGE_NAME));
|
||||
shadowOf(mCrossProfileApps).addCrossProfilePackage(
|
||||
CROSS_PROFILE_PACKAGE_NAME);
|
||||
String appOp = AppOpsManager.permissionToOp(INTERACT_ACROSS_PROFILES_PERMISSION);
|
||||
shadowOf(mAppOpsManager).setMode(
|
||||
appOp, Process.myUid(), CROSS_PROFILE_PACKAGE_NAME, AppOpsManager.MODE_ALLOWED);
|
||||
appOp, PACKAGE_UID, CROSS_PROFILE_PACKAGE_NAME, AppOpsManager.MODE_ALLOWED);
|
||||
shadowOf(mPackageManager).addPermissionInfo(createCrossProfilesPermissionInfo());
|
||||
|
||||
assertThat(mFragment.getPreferenceSummary(
|
||||
mContext, CROSS_PROFILE_PACKAGE_NAME, Process.myUid()))
|
||||
assertThat(InteractAcrossProfilesDetails.getPreferenceSummary(
|
||||
mContext, CROSS_PROFILE_PACKAGE_NAME))
|
||||
.isEqualTo(mContext.getString(R.string.app_permission_summary_allowed));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getPreferenceSummary_appOpNotAllowed_returnsNotAllowed() {
|
||||
shadowOf(mUserManager).addUser(
|
||||
PERSONAL_PROFILE_ID, "personal-profile"/* name */, 0/* flags */);
|
||||
shadowOf(mUserManager).addProfile(
|
||||
PERSONAL_PROFILE_ID, WORK_PROFILE_ID,
|
||||
"work-profile"/* profileName */, UserInfo.FLAG_MANAGED_PROFILE);
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
PERSONAL_PROFILE_ID, ImmutableList.of(CROSS_PROFILE_PACKAGE_NAME));
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
WORK_PROFILE_ID, ImmutableList.of(CROSS_PROFILE_PACKAGE_NAME));
|
||||
shadowOf(mCrossProfileApps).addCrossProfilePackage(
|
||||
CROSS_PROFILE_PACKAGE_NAME);
|
||||
String appOp = AppOpsManager.permissionToOp(INTERACT_ACROSS_PROFILES_PERMISSION);
|
||||
shadowOf(mAppOpsManager).setMode(
|
||||
appOp, Process.myUid(), CROSS_PROFILE_PACKAGE_NAME, AppOpsManager.MODE_IGNORED);
|
||||
appOp, PACKAGE_UID, CROSS_PROFILE_PACKAGE_NAME, AppOpsManager.MODE_IGNORED);
|
||||
shadowOf(mPackageManager).addPermissionInfo(createCrossProfilesPermissionInfo());
|
||||
|
||||
assertThat(mFragment.getPreferenceSummary(
|
||||
mContext, CROSS_PROFILE_PACKAGE_NAME, Process.myUid()))
|
||||
assertThat(InteractAcrossProfilesDetails.getPreferenceSummary(
|
||||
mContext, CROSS_PROFILE_PACKAGE_NAME))
|
||||
.isEqualTo(mContext.getString(R.string.app_permission_summary_not_allowed));
|
||||
}
|
||||
|
||||
|
@@ -21,12 +21,15 @@ import static com.google.common.truth.Truth.assertThat;
|
||||
import static org.robolectric.Shadows.shadowOf;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.pm.CrossProfileApps;
|
||||
import android.content.pm.PackageInfo;
|
||||
import android.content.pm.PackageManager;
|
||||
|
||||
import androidx.test.core.app.ApplicationProvider;
|
||||
|
||||
import com.android.settings.core.BasePreferenceController;
|
||||
|
||||
import com.google.common.collect.ImmutableList;
|
||||
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
import org.robolectric.RobolectricTestRunner;
|
||||
@@ -36,25 +39,34 @@ public class InteractAcrossProfilesPreferenceControllerTest {
|
||||
|
||||
private static final String CROSS_PROFILE_PACKAGE_NAME = "crossProfilePackage";
|
||||
private static final String NOT_CROSS_PROFILE_PACKAGE_NAME = "notCrossProfilePackage";
|
||||
public static final String INTERACT_ACROSS_PROFILES_PERMISSION =
|
||||
"android.permission.INTERACT_ACROSS_PROFILES";
|
||||
private static final int PROFILE_ID = 0;
|
||||
|
||||
private final Context mContext = ApplicationProvider.getApplicationContext();
|
||||
private final CrossProfileApps mCrossProfileApps =
|
||||
mContext.getSystemService(CrossProfileApps.class);
|
||||
private final PackageManager mPackageManager = mContext.getPackageManager();
|
||||
private final InteractAcrossProfilesDetailsPreferenceController mController =
|
||||
new InteractAcrossProfilesDetailsPreferenceController(mContext, "test_key");
|
||||
|
||||
@Test
|
||||
public void getAvailabilityStatus_crossProfilePackage_returnsAvailable() {
|
||||
public void getAvailabilityStatus_requestedCrossProfilePermission_returnsAvailable() {
|
||||
mController.setPackageName(CROSS_PROFILE_PACKAGE_NAME);
|
||||
shadowOf(mCrossProfileApps).addCrossProfilePackage(CROSS_PROFILE_PACKAGE_NAME);
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
PROFILE_ID, ImmutableList.of(CROSS_PROFILE_PACKAGE_NAME));
|
||||
PackageInfo packageInfo = shadowOf(mPackageManager).getInternalMutablePackageInfo(
|
||||
CROSS_PROFILE_PACKAGE_NAME);
|
||||
packageInfo.requestedPermissions = new String[]{
|
||||
INTERACT_ACROSS_PROFILES_PERMISSION};
|
||||
|
||||
assertThat(mController.getAvailabilityStatus())
|
||||
.isEqualTo(BasePreferenceController.AVAILABLE);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getAvailabilityStatus_notCrossProfilePackage_returnsDisabled() {
|
||||
public void getAvailabilityStatus_notRequestedCrossProfilePermission_returnsDisabled() {
|
||||
mController.setPackageName(NOT_CROSS_PROFILE_PACKAGE_NAME);
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
PROFILE_ID, ImmutableList.of(NOT_CROSS_PROFILE_PACKAGE_NAME));
|
||||
|
||||
assertThat(mController.getAvailabilityStatus())
|
||||
.isEqualTo(BasePreferenceController.DISABLED_FOR_USER);
|
||||
|
@@ -18,14 +18,17 @@ package com.android.settings.applications.specialaccess.interactacrossprofiles;
|
||||
|
||||
import static com.google.common.truth.Truth.assertThat;
|
||||
|
||||
import static org.junit.Assert.assertTrue;
|
||||
import static org.robolectric.Shadows.shadowOf;
|
||||
|
||||
import android.app.AppOpsManager;
|
||||
import android.content.Context;
|
||||
import android.content.pm.ApplicationInfo;
|
||||
import android.content.pm.CrossProfileApps;
|
||||
import android.content.pm.PackageInfo;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.content.pm.PermissionInfo;
|
||||
import android.content.pm.UserInfo;
|
||||
import android.os.UserHandle;
|
||||
import android.os.UserManager;
|
||||
import android.util.Pair;
|
||||
@@ -68,49 +71,56 @@ public class InteractAcrossProfilesSettingsTest {
|
||||
private final CrossProfileApps mCrossProfileApps =
|
||||
mContext.getSystemService(CrossProfileApps.class);
|
||||
private final AppOpsManager mAppOpsManager = mContext.getSystemService(AppOpsManager.class);
|
||||
private final InteractAcrossProfilesSettings mFragment = new InteractAcrossProfilesSettings();
|
||||
|
||||
@Test
|
||||
public void collectConfigurableApps_fromPersonal_returnsPersonalPackages() {
|
||||
public void collectConfigurableApps_fromPersonal_returnsCombinedPackages() {
|
||||
shadowOf(mUserManager).addUser(
|
||||
PERSONAL_PROFILE_ID, "personal-profile"/* name */, 0/* flags */);
|
||||
shadowOf(mUserManager).addProfile(
|
||||
PERSONAL_PROFILE_ID, WORK_PROFILE_ID,
|
||||
"work-profile"/* profileName */, 0/* profileFlags */);
|
||||
"work-profile"/* profileName */, UserInfo.FLAG_MANAGED_PROFILE);
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
PERSONAL_PROFILE_ID, PERSONAL_PROFILE_INSTALLED_PACKAGES);
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
WORK_PROFILE_ID, WORK_PROFILE_INSTALLED_PACKAGES);
|
||||
shadowOf(mCrossProfileApps).addCrossProfilePackage(PERSONAL_CROSS_PROFILE_PACKAGE);
|
||||
shadowOf(mCrossProfileApps).addCrossProfilePackage(WORK_CROSS_PROFILE_PACKAGE);
|
||||
installCrossProfilePackage(PERSONAL_PROFILE_ID, PERSONAL_CROSS_PROFILE_PACKAGE);
|
||||
installCrossProfilePackage(WORK_PROFILE_ID, WORK_CROSS_PROFILE_PACKAGE);
|
||||
|
||||
List<Pair<ApplicationInfo, UserHandle>> apps = mFragment.collectConfigurableApps(
|
||||
mPackageManager, mUserManager, mCrossProfileApps);
|
||||
List<Pair<ApplicationInfo, UserHandle>> apps =
|
||||
InteractAcrossProfilesSettings.collectConfigurableApps(
|
||||
mPackageManager, mUserManager, mCrossProfileApps);
|
||||
|
||||
assertThat(apps.size()).isEqualTo(1);
|
||||
assertThat(apps.get(0).first.packageName).isEqualTo(PERSONAL_CROSS_PROFILE_PACKAGE);
|
||||
assertThat(apps.size()).isEqualTo(2);
|
||||
assertTrue(apps.stream().anyMatch(
|
||||
app -> app.first.packageName.equals(PERSONAL_CROSS_PROFILE_PACKAGE)));
|
||||
assertTrue(apps.stream().anyMatch(
|
||||
app -> app.first.packageName.equals(WORK_CROSS_PROFILE_PACKAGE)));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void collectConfigurableApps_fromWork_returnsPersonalPackages() {
|
||||
public void collectConfigurableApps_fromWork_returnsCombinedPackages() {
|
||||
shadowOf(mUserManager).addUser(
|
||||
PERSONAL_PROFILE_ID, "personal-profile"/* name */, 0/* flags */);
|
||||
shadowOf(mUserManager).addProfile(
|
||||
PERSONAL_PROFILE_ID, WORK_PROFILE_ID,
|
||||
"work-profile"/* profileName */, 0/* profileFlags */);
|
||||
"work-profile"/* profileName */, UserInfo.FLAG_MANAGED_PROFILE);
|
||||
ShadowProcess.setUid(WORK_UID);
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
PERSONAL_PROFILE_ID, PERSONAL_PROFILE_INSTALLED_PACKAGES);
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
WORK_PROFILE_ID, WORK_PROFILE_INSTALLED_PACKAGES);
|
||||
shadowOf(mCrossProfileApps).addCrossProfilePackage(PERSONAL_CROSS_PROFILE_PACKAGE);
|
||||
shadowOf(mCrossProfileApps).addCrossProfilePackage(WORK_CROSS_PROFILE_PACKAGE);
|
||||
installCrossProfilePackage(PERSONAL_PROFILE_ID, PERSONAL_CROSS_PROFILE_PACKAGE);
|
||||
installCrossProfilePackage(WORK_PROFILE_ID, WORK_CROSS_PROFILE_PACKAGE);
|
||||
|
||||
List<Pair<ApplicationInfo, UserHandle>> apps = mFragment.collectConfigurableApps(
|
||||
mPackageManager, mUserManager, mCrossProfileApps);
|
||||
List<Pair<ApplicationInfo, UserHandle>> apps =
|
||||
InteractAcrossProfilesSettings.collectConfigurableApps(
|
||||
mPackageManager, mUserManager, mCrossProfileApps);
|
||||
|
||||
assertThat(apps.size()).isEqualTo(1);
|
||||
assertThat(apps.get(0).first.packageName).isEqualTo(PERSONAL_CROSS_PROFILE_PACKAGE);
|
||||
assertThat(apps.size()).isEqualTo(2);
|
||||
assertTrue(apps.stream().anyMatch(
|
||||
app -> app.first.packageName.equals(PERSONAL_CROSS_PROFILE_PACKAGE)));
|
||||
assertTrue(apps.stream().anyMatch(
|
||||
app -> app.first.packageName.equals(WORK_CROSS_PROFILE_PACKAGE)));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -119,10 +129,11 @@ public class InteractAcrossProfilesSettingsTest {
|
||||
PERSONAL_PROFILE_ID, "personal-profile"/* name */, 0/* flags */);
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
PERSONAL_PROFILE_ID, PERSONAL_PROFILE_INSTALLED_PACKAGES);
|
||||
shadowOf(mCrossProfileApps).addCrossProfilePackage(PERSONAL_CROSS_PROFILE_PACKAGE);
|
||||
installCrossProfilePackage(PERSONAL_PROFILE_ID, PERSONAL_CROSS_PROFILE_PACKAGE);
|
||||
|
||||
List<Pair<ApplicationInfo, UserHandle>> apps = mFragment.collectConfigurableApps(
|
||||
mPackageManager, mUserManager, mCrossProfileApps);
|
||||
List<Pair<ApplicationInfo, UserHandle>> apps =
|
||||
InteractAcrossProfilesSettings.collectConfigurableApps(
|
||||
mPackageManager, mUserManager, mCrossProfileApps);
|
||||
|
||||
assertThat(apps).isEmpty();
|
||||
}
|
||||
@@ -133,11 +144,14 @@ public class InteractAcrossProfilesSettingsTest {
|
||||
PERSONAL_PROFILE_ID, "personal-profile"/* name */, 0/* flags */);
|
||||
shadowOf(mUserManager).addProfile(
|
||||
PERSONAL_PROFILE_ID, WORK_PROFILE_ID,
|
||||
"work-profile"/* profileName */, 0/* profileFlags */);
|
||||
"work-profile"/* profileName */, UserInfo.FLAG_MANAGED_PROFILE);
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
PERSONAL_PROFILE_ID, PERSONAL_PROFILE_INSTALLED_PACKAGES);
|
||||
shadowOf(mPackageManager).setInstalledPackagesForUserId(
|
||||
WORK_PROFILE_ID, WORK_PROFILE_INSTALLED_PACKAGES);
|
||||
installCrossProfilePackage(PERSONAL_PROFILE_ID, PERSONAL_CROSS_PROFILE_PACKAGE);
|
||||
installCrossProfilePackage(WORK_PROFILE_ID, WORK_CROSS_PROFILE_PACKAGE);
|
||||
shadowOf(mCrossProfileApps).addCrossProfilePackage(PERSONAL_CROSS_PROFILE_PACKAGE);
|
||||
shadowOf(mCrossProfileApps).addCrossProfilePackage(PERSONAL_NON_CROSS_PROFILE_PACKAGE);
|
||||
String appOp = AppOpsManager.permissionToOp(INTERACT_ACROSS_PROFILES_PERMISSION);
|
||||
shadowOf(mAppOpsManager).setMode(
|
||||
appOp, PACKAGE_UID, PERSONAL_CROSS_PROFILE_PACKAGE, AppOpsManager.MODE_ALLOWED);
|
||||
@@ -145,12 +159,19 @@ public class InteractAcrossProfilesSettingsTest {
|
||||
appOp, PACKAGE_UID, PERSONAL_NON_CROSS_PROFILE_PACKAGE, AppOpsManager.MODE_IGNORED);
|
||||
shadowOf(mPackageManager).addPermissionInfo(createCrossProfilesPermissionInfo());
|
||||
|
||||
int numOfApps = mFragment.getNumberOfEnabledApps(
|
||||
int numOfApps = InteractAcrossProfilesSettings.getNumberOfEnabledApps(
|
||||
mContext, mPackageManager, mUserManager, mCrossProfileApps);
|
||||
|
||||
assertThat(numOfApps).isEqualTo(1);
|
||||
}
|
||||
|
||||
private void installCrossProfilePackage(int profileId, String packageName) {
|
||||
PackageInfo personalPackageInfo = shadowOf(mPackageManager).getInternalMutablePackageInfo(
|
||||
packageName);
|
||||
personalPackageInfo.requestedPermissions = new String[]{
|
||||
INTERACT_ACROSS_PROFILES_PERMISSION};
|
||||
}
|
||||
|
||||
private PermissionInfo createCrossProfilesPermissionInfo() {
|
||||
PermissionInfo permissionInfo = new PermissionInfo();
|
||||
permissionInfo.name = INTERACT_ACROSS_PROFILES_PERMISSION;
|
||||
|
Reference in New Issue
Block a user