summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author Elliot Sisteron <elliotsisteron@google.com> 2023-10-06 13:01:22 +0000
committer Elliot Sisteron <elliotsisteron@google.com> 2023-10-11 09:53:40 +0000
commit1a104954590080caac06ded0e63e452e9bd8bf06 (patch)
tree4715c21ce5ef0c4270f1bb372087143f997b44ed
parent4b0638624690a39de2c35ac5e00f17136973aad8 (diff)
Fix Intent resolution ordering.
The intended order was to have the implicit intent checked first. However, we changed it to check the explicit intent first in ag/21033470 as resolveActivity always returned a value regardless of whether the non-exported internal activity actually resolved. By checking manually if the activity is exported, we can use the original (intended) order, which fixes an issue with the overriding of the OTA source intent by setting a higher priority. Test: atest SafetyCenterFunctionalTestCases Bug: 296053629 Bug: 282920658 Relnote: Fix intent resolution ordering for Safety Center, which allows overridng OTA source intent by setting higher priority. Change-Id: I332200401340deb48f9ebd23d841f4e01c9d9e0d
-rw-r--r--service/java/com/android/safetycenter/PendingIntentFactory.java36
-rw-r--r--tests/functional/safetycenter/multiusers/src/android/safetycenter/functional/multiusers/SafetyCenterMultiUsersTest.kt105
-rw-r--r--tests/functional/safetycenter/safetycenteractivity/src/android/safetycenter/functional/ui/SafetyCenterActivityTest.kt2
-rw-r--r--tests/functional/safetycenter/singleuser/src/android/safetycenter/functional/SafetyCenterManagerTest.kt129
-rw-r--r--tests/functional/safetycenter/singleuser/src/android/safetycenter/functional/SafetyCenterNotificationTest.kt14
-rw-r--r--tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetyCenterTestConfigs.kt61
-rw-r--r--tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetyCenterTestData.kt23
-rw-r--r--tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetySourceTestData.kt125
8 files changed, 329 insertions, 166 deletions
diff --git a/service/java/com/android/safetycenter/PendingIntentFactory.java b/service/java/com/android/safetycenter/PendingIntentFactory.java
index b52365c38..a857a07cb 100644
--- a/service/java/com/android/safetycenter/PendingIntentFactory.java
+++ b/service/java/com/android/safetycenter/PendingIntentFactory.java
@@ -22,6 +22,7 @@ import android.annotation.UserIdInt;
import android.app.PendingIntent;
import android.content.Context;
import android.content.Intent;
+import android.content.pm.ActivityInfo;
import android.content.pm.PackageManager;
import android.content.pm.PackageManager.ResolveInfoFlags;
import android.content.pm.ResolveInfo;
@@ -60,9 +61,9 @@ public final class PendingIntentFactory {
* Creates or retrieves a {@link PendingIntent} that will start a new {@code Activity} matching
* the given {@code intentAction}.
*
- * <p>If the given {@code intentAction} resolves for the given {@code packageName}, the {@link
- * PendingIntent} will explicitly target the {@code packageName}. If the {@code intentAction}
- * resolves elsewhere, the {@link PendingIntent} will be implicit.
+ * <p>If the given {@code intentAction} resolves, the {@link PendingIntent} will use an implicit
+ * {@link Intent}. Otherwise, the {@link PendingIntent} will explicitly target the {@code
+ * packageName} if it resolves.
*
* <p>The {@code PendingIntent} is associated with a specific source given by {@code sourceId}.
*
@@ -113,26 +114,25 @@ public final class PendingIntentFactory {
intent.setIdentifier("with_settings_homepage_extra");
}
+ if (intentResolvesToActivity(packageContext, intent)) {
+ return intent;
+ }
+
// If the intent resolves for the package provided, then we make the assumption that it is
// the desired app and make the intent explicit. This is to workaround implicit internal
// intents that may not be exported which will stop working on Android U+.
- // This assumes that the source or the caller has the highest priority to resolve the intent
- // action.
Intent explicitIntent = new Intent(intent).setPackage(packageContext.getPackageName());
- if (intentResolves(packageContext, explicitIntent)) {
+ if (intentResolvesToActivity(packageContext, explicitIntent)) {
return explicitIntent;
}
- if (intentResolves(packageContext, intent)) {
- return intent;
- }
-
// resolveActivity does not return any activity when the work profile is in quiet mode, even
// though it opens the quiet mode dialog and/or the original intent would otherwise resolve
// when quiet mode is turned off. So, we assume that the explicit intent will always resolve
// to this dialog. This heuristic is preferable on U+ as it has a higher chance of resolving
// once the work profile is enabled considering the implicit internal intent restriction.
if (isQuietModeEnabled) {
+ // TODO(b/266538628): Find a way to fix this, this heuristic isn't ideal.
return explicitIntent;
}
@@ -147,8 +147,20 @@ public final class PendingIntentFactory {
.contains(sourceId);
}
- private static boolean intentResolves(Context packageContext, Intent intent) {
- return resolveActivity(packageContext, intent) != null;
+ private static boolean intentResolvesToActivity(Context packageContext, Intent intent) {
+ ResolveInfo resolveInfo = resolveActivity(packageContext, intent);
+ if (resolveInfo == null) {
+ return false;
+ }
+ ActivityInfo activityInfo = resolveInfo.activityInfo;
+ if (activityInfo == null) {
+ return false;
+ }
+ boolean intentIsImplicit = intent.getPackage() == null && intent.getComponent() == null;
+ if (intentIsImplicit) {
+ return activityInfo.exported;
+ }
+ return true;
}
@Nullable
diff --git a/tests/functional/safetycenter/multiusers/src/android/safetycenter/functional/multiusers/SafetyCenterMultiUsersTest.kt b/tests/functional/safetycenter/multiusers/src/android/safetycenter/functional/multiusers/SafetyCenterMultiUsersTest.kt
index 9534b597a..acbc5cfc0 100644
--- a/tests/functional/safetycenter/multiusers/src/android/safetycenter/functional/multiusers/SafetyCenterMultiUsersTest.kt
+++ b/tests/functional/safetycenter/multiusers/src/android/safetycenter/functional/multiusers/SafetyCenterMultiUsersTest.kt
@@ -20,7 +20,6 @@ import android.Manifest.permission.INTERACT_ACROSS_USERS
import android.Manifest.permission.INTERACT_ACROSS_USERS_FULL
import android.app.PendingIntent
import android.content.Context
-import android.content.Intent
import android.os.UserHandle
import android.safetycenter.SafetyCenterData
import android.safetycenter.SafetyCenterEntry
@@ -60,7 +59,6 @@ import com.android.safetycenter.testing.SafetyCenterApisWithShellPermissions.get
import com.android.safetycenter.testing.SafetyCenterApisWithShellPermissions.setSafetySourceDataWithPermission
import com.android.safetycenter.testing.SafetyCenterFlags
import com.android.safetycenter.testing.SafetyCenterTestConfigs
-import com.android.safetycenter.testing.SafetyCenterTestConfigs.Companion.ACTION_TEST_ACTIVITY
import com.android.safetycenter.testing.SafetyCenterTestConfigs.Companion.DYNAMIC_BAREBONE_ID
import com.android.safetycenter.testing.SafetyCenterTestConfigs.Companion.DYNAMIC_DISABLED_ID
import com.android.safetycenter.testing.SafetyCenterTestConfigs.Companion.DYNAMIC_GROUP_ID
@@ -244,69 +242,67 @@ class SafetyCenterMultiUsersTest {
private val staticAllOptional =
safetyCenterTestData.safetyCenterEntryDefaultStaticBuilder(STATIC_ALL_OPTIONAL_ID).build()
- private fun staticAllOptionalForWorkBuilder(inQuietMode: Boolean = false) =
- safetyCenterTestData
- .safetyCenterEntryDefaultStaticBuilder(
- STATIC_ALL_OPTIONAL_ID,
- userId = deviceState.workProfile().id(),
- title = "Paste"
- )
- .setPendingIntent(
- createTestActivityRedirectPendingIntentForUser(
- deviceState.workProfile().userHandle(),
- inQuietMode
+ private val staticAllOptionalForWorkBuilder
+ get() =
+ safetyCenterTestData
+ .safetyCenterEntryDefaultStaticBuilder(
+ STATIC_ALL_OPTIONAL_ID,
+ userId = deviceState.workProfile().id(),
+ title = "Paste"
+ )
+ .setPendingIntent(
+ createTestActivityRedirectPendingIntentForUser(
+ deviceState.workProfile().userHandle(),
+ explicit = false
+ )
)
- )
private val staticAllOptionalForWork
- get() = staticAllOptionalForWorkBuilder().build()
+ get() = staticAllOptionalForWorkBuilder.build()
private val staticAllOptionalForWorkPaused
get() =
- staticAllOptionalForWorkBuilder(inQuietMode = true)
+ staticAllOptionalForWorkBuilder
.setSummary(safetyCenterResourcesApk.getStringByName("work_profile_paused"))
.setEnabled(false)
.build()
- private val staticEntry: SafetyCenterStaticEntry
- get() =
- SafetyCenterStaticEntry.Builder("OK")
- .setSummary("OK")
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
- .build()
+ private fun createStaticEntry(explicit: Boolean = true): SafetyCenterStaticEntry =
+ SafetyCenterStaticEntry.Builder("OK")
+ .setSummary("OK")
+ .setPendingIntent(
+ safetySourceTestData.createTestActivityRedirectPendingIntent(explicit)
+ )
+ .build()
private val staticEntryUpdated: SafetyCenterStaticEntry
get() =
SafetyCenterStaticEntry.Builder("Unspecified title")
.setSummary("Unspecified summary")
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
+ .setPendingIntent(safetySourceTestData.createTestActivityRedirectPendingIntent())
.build()
- private fun staticEntryForWorkBuilder(
- title: CharSequence = "Paste",
- inQuietMode: Boolean = false
- ) =
+ private fun staticEntryForWorkBuilder(title: CharSequence = "Paste", explicit: Boolean = true) =
SafetyCenterStaticEntry.Builder(title)
.setSummary("OK")
.setPendingIntent(
createTestActivityRedirectPendingIntentForUser(
deviceState.workProfile().userHandle(),
- inQuietMode
+ explicit
)
)
- private val staticEntryForWork: SafetyCenterStaticEntry
- get() = staticEntryForWorkBuilder().build()
+ private fun createStaticEntryForWork(explicit: Boolean = true): SafetyCenterStaticEntry =
+ staticEntryForWorkBuilder(explicit = explicit).build()
- private val staticEntryForWorkPaused: SafetyCenterStaticEntry
- get() =
- staticEntryForWorkBuilder(inQuietMode = true)
- .setSummary(safetyCenterResourcesApk.getStringByName("work_profile_paused"))
- .build()
+ private fun createStaticEntryForWorkPaused(): SafetyCenterStaticEntry =
+ staticEntryForWorkBuilder(explicit = false)
+ .setSummary(safetyCenterResourcesApk.getStringByName("work_profile_paused"))
+ .build()
- private val staticEntryForWorkPausedUpdated
+ private val staticEntryForWorkPausedUpdated: SafetyCenterStaticEntry
get() =
- staticEntryForWorkBuilder(title = "Unspecified title for Work", inQuietMode = true)
+ staticEntryForWorkBuilder(title = "Unspecified title for Work")
.setSummary(safetyCenterResourcesApk.getStringByName("work_profile_paused"))
.build()
@@ -314,7 +310,7 @@ class SafetyCenterMultiUsersTest {
get() =
SafetyCenterStaticEntry.Builder("Unspecified title for Work")
.setSummary("Unspecified summary")
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
+ .setPendingIntent(safetySourceTestData.createTestActivityRedirectPendingIntent())
.build()
private val safetyCenterDataForAdditionalUser
@@ -543,7 +539,12 @@ class SafetyCenterMultiUsersTest {
.build()
)
),
- listOf(SafetyCenterStaticEntryGroup("OK", listOf(staticEntry, staticEntry)))
+ listOf(
+ SafetyCenterStaticEntryGroup(
+ "OK",
+ listOf(createStaticEntry(), createStaticEntry(explicit = false))
+ )
+ )
)
assertThat(apiSafetyCenterData.withoutExtras()).isEqualTo(safetyCenterDataFromComplexConfig)
}
@@ -589,7 +590,12 @@ class SafetyCenterMultiUsersTest {
listOf(
SafetyCenterStaticEntryGroup(
"OK",
- listOf(staticEntry, staticEntryForWork, staticEntry, staticEntryForWork)
+ listOf(
+ createStaticEntry(),
+ createStaticEntryForWork(),
+ createStaticEntry(explicit = false),
+ createStaticEntryForWork(explicit = false)
+ )
)
)
)
@@ -639,9 +645,9 @@ class SafetyCenterMultiUsersTest {
"OK",
listOf(
staticEntryUpdated,
- staticEntryForWork,
- staticEntry,
- staticEntryForWork
+ createStaticEntryForWork(),
+ createStaticEntry(explicit = false),
+ createStaticEntryForWork(explicit = false)
)
)
)
@@ -749,8 +755,8 @@ class SafetyCenterMultiUsersTest {
listOf(
staticEntryUpdated,
staticEntryForWorkUpdated,
- staticEntry,
- staticEntryForWork
+ createStaticEntry(explicit = false),
+ createStaticEntryForWork(explicit = false)
)
)
)
@@ -809,8 +815,8 @@ class SafetyCenterMultiUsersTest {
listOf(
staticEntryUpdated,
staticEntryForWorkPausedUpdated,
- staticEntry,
- staticEntryForWorkPaused
+ createStaticEntry(explicit = false),
+ createStaticEntryForWorkPaused()
)
)
)
@@ -1228,13 +1234,12 @@ class SafetyCenterMultiUsersTest {
private fun createTestActivityRedirectPendingIntentForUser(
user: UserHandle,
- inQuietMode: Boolean = false
+ explicit: Boolean = true
): PendingIntent {
return callWithShellPermissionIdentity(INTERACT_ACROSS_USERS) {
SafetySourceTestData.createRedirectPendingIntent(
getContextForUser(user),
- Intent(ACTION_TEST_ACTIVITY),
- inQuietMode
+ SafetySourceTestData.createTestActivityIntent(getContextForUser(user), explicit)
)
}
}
diff --git a/tests/functional/safetycenter/safetycenteractivity/src/android/safetycenter/functional/ui/SafetyCenterActivityTest.kt b/tests/functional/safetycenter/safetycenteractivity/src/android/safetycenter/functional/ui/SafetyCenterActivityTest.kt
index 73c33f904..73f435615 100644
--- a/tests/functional/safetycenter/safetycenteractivity/src/android/safetycenter/functional/ui/SafetyCenterActivityTest.kt
+++ b/tests/functional/safetycenter/safetycenteractivity/src/android/safetycenter/functional/ui/SafetyCenterActivityTest.kt
@@ -1452,7 +1452,7 @@ class SafetyCenterActivityTest {
@Test
fun startStaticEntryActivity_withConfigToBeSettingsActivity_trueExtraInBundle() {
- safetyCenterTestHelper.setConfig(safetyCenterTestConfigs.singleStaticSettingsSource)
+ safetyCenterTestHelper.setConfig(safetyCenterTestConfigs.singleStaticSettingsSourceConfig)
context.launchSafetyCenterActivity {
waitDisplayed(By.text("OK")) { it.click() }
diff --git a/tests/functional/safetycenter/singleuser/src/android/safetycenter/functional/SafetyCenterManagerTest.kt b/tests/functional/safetycenter/singleuser/src/android/safetycenter/functional/SafetyCenterManagerTest.kt
index e2a7802b3..19922e4f7 100644
--- a/tests/functional/safetycenter/singleuser/src/android/safetycenter/functional/SafetyCenterManagerTest.kt
+++ b/tests/functional/safetycenter/singleuser/src/android/safetycenter/functional/SafetyCenterManagerTest.kt
@@ -16,7 +16,6 @@
package android.safetycenter.functional
-import android.app.PendingIntent
import android.content.Context
import android.content.Intent
import android.os.Build.VERSION_CODES.TIRAMISU
@@ -81,6 +80,7 @@ import com.android.safetycenter.testing.SafetyCenterApisWithShellPermissions.ref
import com.android.safetycenter.testing.SafetyCenterApisWithShellPermissions.reportSafetySourceErrorWithPermission
import com.android.safetycenter.testing.SafetyCenterFlags
import com.android.safetycenter.testing.SafetyCenterTestConfigs
+import com.android.safetycenter.testing.SafetyCenterTestConfigs.Companion.ACTION_TEST_ACTIVITY
import com.android.safetycenter.testing.SafetyCenterTestConfigs.Companion.ACTION_TEST_ACTIVITY_EXPORTED
import com.android.safetycenter.testing.SafetyCenterTestConfigs.Companion.ANDROID_LOCK_SCREEN_SOURCES_GROUP_ID
import com.android.safetycenter.testing.SafetyCenterTestConfigs.Companion.DYNAMIC_ALL_OPTIONAL_ID
@@ -332,7 +332,9 @@ class SafetyCenterManagerTest {
.setSeverityLevel(ENTRY_SEVERITY_LEVEL_UNSPECIFIED)
.setSummary("OK")
.setPendingIntent(
- safetySourceTestData.testActivityRedirectPendingIntent
+ safetySourceTestData.createTestActivityRedirectPendingIntent(
+ explicit = false
+ )
)
.setSeverityUnspecifiedIconType(
SEVERITY_UNSPECIFIED_ICON_TYPE_NO_ICON
@@ -352,11 +354,19 @@ class SafetyCenterManagerTest {
"OK",
listOf(
SafetyCenterStaticEntry.Builder("OK")
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
+ .setPendingIntent(
+ safetySourceTestData.createTestActivityRedirectPendingIntent(
+ explicit = false
+ )
+ )
.build(),
SafetyCenterStaticEntry.Builder("OK")
.setSummary("OK")
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
+ .setPendingIntent(
+ safetySourceTestData.createTestActivityRedirectPendingIntent(
+ explicit = false
+ )
+ )
.build()
)
)
@@ -368,11 +378,17 @@ class SafetyCenterManagerTest {
listOf(
SafetyCenterStaticEntry.Builder("OK")
.setSummary("OK")
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
+ .setPendingIntent(
+ safetySourceTestData.createTestActivityRedirectPendingIntent()
+ )
.build(),
SafetyCenterStaticEntry.Builder("OK")
.setSummary("OK")
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
+ .setPendingIntent(
+ safetySourceTestData.createTestActivityRedirectPendingIntent(
+ explicit = false
+ )
+ )
.build()
)
)
@@ -385,11 +401,17 @@ class SafetyCenterManagerTest {
listOf(
SafetyCenterStaticEntry.Builder("Unspecified title")
.setSummary("Unspecified summary")
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
+ .setPendingIntent(
+ safetySourceTestData.createTestActivityRedirectPendingIntent()
+ )
.build(),
SafetyCenterStaticEntry.Builder("OK")
.setSummary("OK")
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
+ .setPendingIntent(
+ safetySourceTestData.createTestActivityRedirectPendingIntent(
+ explicit = false
+ )
+ )
.build()
)
)
@@ -457,7 +479,7 @@ class SafetyCenterManagerTest {
.safetyCenterEntryOkBuilder(SINGLE_SOURCE_ID)
.setIconAction(
ICON_ACTION_TYPE_INFO,
- safetySourceTestData.testActivityRedirectPendingIntent
+ safetySourceTestData.createTestActivityRedirectPendingIntent()
)
.build()
)
@@ -974,28 +996,105 @@ class SafetyCenterManagerTest {
}
@Test
+ fun getSafetyCenterData_withoutDataExplicitIntentConfig_defaultEntryHasExplicitIntent() {
+ safetyCenterTestHelper.setConfig(safetyCenterTestConfigs.singleSourceConfig)
+
+ val apiSafetyCenterData = safetyCenterManager.getSafetyCenterDataWithPermission()
+
+ val expectedExplicitPendingIntent =
+ SafetySourceTestData.createRedirectPendingIntent(
+ context,
+ Intent(ACTION_TEST_ACTIVITY).setPackage(context.packageName)
+ )
+ val defaultEntryPendingIntent =
+ apiSafetyCenterData.entriesOrGroups.firstOrNull()?.entry?.pendingIntent
+ val defaultEntryIntentFilterEqualsToExplicitIntent =
+ callWithShellPermissionIdentity("android.permission.GET_INTENT_SENDER_INTENT") {
+ expectedExplicitPendingIntent.intentFilterEquals(defaultEntryPendingIntent)
+ }
+ assertThat(defaultEntryIntentFilterEqualsToExplicitIntent).isTrue()
+ }
+
+ @Test
fun getSafetyCenterData_withoutDataImplicitIntentConfig_defaultEntryHasImplicitIntent() {
safetyCenterTestHelper.setConfig(safetyCenterTestConfigs.implicitIntentSingleSourceConfig)
val apiSafetyCenterData = safetyCenterManager.getSafetyCenterDataWithPermission()
- val implicitPendingIntentCreatedByCts =
- PendingIntent.getActivity(
+ val expectedImplicitPendingIntent =
+ SafetySourceTestData.createRedirectPendingIntent(
context,
- 0 /* requestCode */,
- Intent(ACTION_TEST_ACTIVITY_EXPORTED),
- PendingIntent.FLAG_IMMUTABLE
+ Intent(ACTION_TEST_ACTIVITY_EXPORTED)
)
val defaultEntryPendingIntent =
apiSafetyCenterData.entriesOrGroups.firstOrNull()?.entry?.pendingIntent
val defaultEntryIntentFilterEqualsToImplicitIntent =
callWithShellPermissionIdentity("android.permission.GET_INTENT_SENDER_INTENT") {
- implicitPendingIntentCreatedByCts.intentFilterEquals(defaultEntryPendingIntent)
+ expectedImplicitPendingIntent.intentFilterEquals(defaultEntryPendingIntent)
}
assertThat(defaultEntryIntentFilterEqualsToImplicitIntent).isTrue()
}
@Test
+ fun getSafetyCenterData_withStaticImplicitResolving_implicitStaticEntry() {
+ safetyCenterTestHelper.setConfig(safetyCenterTestConfigs.staticSourcesConfig)
+
+ val apiSafetyCenterData = safetyCenterManager.getSafetyCenterDataWithPermission()
+
+ val expectedImplicitPendingIntent =
+ SafetySourceTestData.createRedirectPendingIntent(
+ context,
+ Intent(ACTION_TEST_ACTIVITY_EXPORTED)
+ )
+ val staticEntryPendingIntent =
+ apiSafetyCenterData.staticEntryGroups
+ .firstOrNull()
+ ?.staticEntries
+ ?.firstOrNull()
+ ?.pendingIntent
+ val staticEntryIntentFilterEqualsToImplicitIntent =
+ callWithShellPermissionIdentity("android.permission.GET_INTENT_SENDER_INTENT") {
+ expectedImplicitPendingIntent.intentFilterEquals(staticEntryPendingIntent)
+ }
+ assertThat(staticEntryIntentFilterEqualsToImplicitIntent).isTrue()
+ }
+
+ @Test
+ fun getSafetyCenterData_withStaticImplicitNotExported_explicitStaticEntryUsingCallerPackage() {
+ safetyCenterTestHelper.setConfig(
+ safetyCenterTestConfigs.singleStaticImplicitIntentNotExportedConfig
+ )
+
+ val apiSafetyCenterData = safetyCenterManager.getSafetyCenterDataWithPermission()
+
+ val expectedExplicitPendingIntent =
+ SafetySourceTestData.createRedirectPendingIntent(
+ context,
+ Intent(ACTION_TEST_ACTIVITY).setPackage(context.packageName)
+ )
+ val staticEntryPendingIntent =
+ apiSafetyCenterData.staticEntryGroups
+ .firstOrNull()
+ ?.staticEntries
+ ?.firstOrNull()
+ ?.pendingIntent
+ val staticEntryIntentFilterEqualsToExplicitIntent =
+ callWithShellPermissionIdentity("android.permission.GET_INTENT_SENDER_INTENT") {
+ expectedExplicitPendingIntent.intentFilterEquals(staticEntryPendingIntent)
+ }
+ assertThat(staticEntryIntentFilterEqualsToExplicitIntent).isTrue()
+ }
+
+ @Test
+ fun getSafetyCenterData_withStaticNotResolving_noStaticEntry() {
+ safetyCenterTestHelper.setConfig(safetyCenterTestConfigs.singleStaticInvalidIntentConfig)
+
+ val apiSafetyCenterData = safetyCenterManager.getSafetyCenterDataWithPermission()
+
+ assertThat(apiSafetyCenterData.staticEntryGroups).isEmpty()
+ }
+
+ @Test
fun getSafetyCenterData_withComplexConfigWithoutDataProvided_returnsDataFromConfig() {
safetyCenterTestHelper.setConfig(safetyCenterTestConfigs.complexConfig)
diff --git a/tests/functional/safetycenter/singleuser/src/android/safetycenter/functional/SafetyCenterNotificationTest.kt b/tests/functional/safetycenter/singleuser/src/android/safetycenter/functional/SafetyCenterNotificationTest.kt
index 20802dd2f..9c9e9b009 100644
--- a/tests/functional/safetycenter/singleuser/src/android/safetycenter/functional/SafetyCenterNotificationTest.kt
+++ b/tests/functional/safetycenter/singleuser/src/android/safetycenter/functional/SafetyCenterNotificationTest.kt
@@ -296,8 +296,8 @@ class SafetyCenterNotificationTest {
@Test
fun setSafetySourceData_issueWithTwoActions_notificationWithTwoActions() {
- val intent1 = safetySourceTestData.testActivityRedirectPendingIntent(identifier = "1")
- val intent2 = safetySourceTestData.testActivityRedirectPendingIntent(identifier = "2")
+ val intent1 = safetySourceTestData.createTestActivityRedirectPendingIntent(identifier = "1")
+ val intent2 = safetySourceTestData.createTestActivityRedirectPendingIntent(identifier = "2")
val data =
safetySourceTestData
@@ -361,8 +361,8 @@ class SafetyCenterNotificationTest {
@Test
@SdkSuppress(minSdkVersion = UPSIDE_DOWN_CAKE)
fun setSafetySourceData_withCustomNotification_usesCustomValues() {
- val intent1 = safetySourceTestData.testActivityRedirectPendingIntent(identifier = "1")
- val intent2 = safetySourceTestData.testActivityRedirectPendingIntent(identifier = "2")
+ val intent1 = safetySourceTestData.createTestActivityRedirectPendingIntent(identifier = "1")
+ val intent2 = safetySourceTestData.createTestActivityRedirectPendingIntent(identifier = "2")
val notification =
SafetySourceIssue.Notification.Builder("Custom title", "Custom text")
@@ -384,7 +384,7 @@ class SafetyCenterNotificationTest {
SafetySourceIssue.Action.Builder(
"default_action",
"Default action",
- safetySourceTestData.testActivityRedirectPendingIntent
+ safetySourceTestData.createTestActivityRedirectPendingIntent()
)
.build()
)
@@ -422,7 +422,7 @@ class SafetyCenterNotificationTest {
SafetySourceIssue.Action.Builder(
"default_action",
"Default action",
- safetySourceTestData.testActivityRedirectPendingIntent
+ safetySourceTestData.createTestActivityRedirectPendingIntent()
)
.build()
)
@@ -475,7 +475,7 @@ class SafetyCenterNotificationTest {
SafetySourceIssue.Action.Builder(
"new_action",
"New action",
- safetySourceTestData.testActivityRedirectPendingIntent(
+ safetySourceTestData.createTestActivityRedirectPendingIntent(
identifier = "new_action"
)
)
diff --git a/tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetyCenterTestConfigs.kt b/tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetyCenterTestConfigs.kt
index de4cf7094..fea9b45cc 100644
--- a/tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetyCenterTestConfigs.kt
+++ b/tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetyCenterTestConfigs.kt
@@ -64,7 +64,9 @@ class SafetyCenterTestConfigs(private val context: Context) {
*/
val singleSourceInvalidIntentConfig =
singleSourceConfig(
- dynamicSafetySourceBuilder(SINGLE_SOURCE_ID).setIntentAction("stub").build()
+ dynamicSafetySourceBuilder(SINGLE_SOURCE_ID)
+ .setIntentAction(INTENT_ACTION_NOT_RESOLVING)
+ .build()
)
/**
@@ -348,7 +350,9 @@ class SafetyCenterTestConfigs(private val context: Context) {
.addSafetySourcesGroup(
safetySourcesGroupBuilder(MULTIPLE_SOURCES_GROUP_ID_1)
.addSafetySource(
- dynamicSafetySourceBuilder(SOURCE_ID_1).setIntentAction("stub").build()
+ dynamicSafetySourceBuilder(SOURCE_ID_1)
+ .setIntentAction(INTENT_ACTION_NOT_RESOLVING)
+ .build()
)
.addSafetySource(dynamicSafetySource(SOURCE_ID_2))
.build()
@@ -373,9 +377,7 @@ class SafetyCenterTestConfigs(private val context: Context) {
* Source group provided by [staticSourcesConfig] containing a single source [staticSource1].
*/
val staticSourceGroup1 =
- SafetySourcesGroup.Builder()
- .setId("test_static_sources_group_id_1")
- .setTitleResId(android.R.string.paste)
+ staticSafetySourcesGroupBuilder("test_static_sources_group_id_1")
.addSafetySource(staticSource1)
.build()
@@ -383,8 +385,7 @@ class SafetyCenterTestConfigs(private val context: Context) {
* Source group provided by [staticSourcesConfig] containing a single source [staticSource2].
*/
val staticSourceGroup2 =
- SafetySourcesGroup.Builder()
- .setId("test_static_sources_group_id_2")
+ staticSafetySourcesGroupBuilder("test_static_sources_group_id_2")
.setTitleResId(android.R.string.copy)
.addSafetySource(staticSource2)
.build()
@@ -402,7 +403,44 @@ class SafetyCenterTestConfigs(private val context: Context) {
* The particular source ID is configured in the same way as sources hosted by the Settings app,
* to launch as if it is part of the Settings app UI.
*/
- val singleStaticSettingsSource = singleSourceConfig(staticSafetySource("TestSource"))
+ val singleStaticSettingsSourceConfig =
+ SafetyCenterConfig.Builder()
+ .addSafetySourcesGroup(
+ staticSafetySourcesGroupBuilder("single_static_source_group")
+ .addSafetySource(staticSafetySource("TestSource"))
+ .build()
+ )
+ .build()
+
+ /** A [SafetyCenterConfig] with a single static source and an intent that doesn't resolve */
+ val singleStaticInvalidIntentConfig =
+ SafetyCenterConfig.Builder()
+ .addSafetySourcesGroup(
+ staticSafetySourcesGroupBuilder("single_static_source_group")
+ .addSafetySource(
+ staticSafetySourceBuilder(SINGLE_SOURCE_ID)
+ .setIntentAction(INTENT_ACTION_NOT_RESOLVING)
+ .build()
+ )
+ .build()
+ )
+ .build()
+
+ /**
+ * A [SafetyCenterConfig] with a single static source and an implicit intent that isn't exported
+ */
+ val singleStaticImplicitIntentNotExportedConfig =
+ SafetyCenterConfig.Builder()
+ .addSafetySourcesGroup(
+ staticSafetySourcesGroupBuilder("single_static_source_group")
+ .addSafetySource(
+ staticSafetySourceBuilder(SINGLE_SOURCE_ID)
+ .setIntentAction(ACTION_TEST_ACTIVITY)
+ .build()
+ )
+ .build()
+ )
+ .build()
/** [SafetyCenterConfig] used in tests for Your Work Policy Info source. */
val workPolicyInfoConfig =
@@ -750,7 +788,7 @@ class SafetyCenterTestConfigs(private val context: Context) {
.setId(id)
.setTitleResId(android.R.string.ok)
.setSummaryResId(android.R.string.ok)
- .setIntentAction(ACTION_TEST_ACTIVITY)
+ .setIntentAction(ACTION_TEST_ACTIVITY_EXPORTED)
.setProfile(SafetySource.PROFILE_PRIMARY)
private fun staticAllProfileSafetySourceBuilder(id: String) =
@@ -780,6 +818,9 @@ class SafetyCenterTestConfigs(private val context: Context) {
.setTitleResId(android.R.string.ok)
.setSummaryResId(android.R.string.ok)
+ private fun staticSafetySourcesGroupBuilder(id: String) =
+ SafetySourcesGroup.Builder().setId(id).setTitleResId(android.R.string.paste)
+
fun singleSourceConfig(safetySource: SafetySource) =
SafetyCenterConfig.Builder()
.addSafetySourcesGroup(
@@ -1033,5 +1074,7 @@ class SafetyCenterTestConfigs(private val context: Context) {
* [privacySubpageWithoutDataSourcesConfig], to replicate the privacy sources group.
*/
const val ANDROID_PRIVACY_SOURCES_GROUP_ID = "AndroidPrivacySources"
+
+ private const val INTENT_ACTION_NOT_RESOLVING = "there.is.no.way.this.resolves"
}
}
diff --git a/tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetyCenterTestData.kt b/tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetyCenterTestData.kt
index 31e9855ae..289bc32a8 100644
--- a/tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetyCenterTestData.kt
+++ b/tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetyCenterTestData.kt
@@ -164,7 +164,8 @@ class SafetyCenterTestData(context: Context) {
sourceId: String,
userId: Int = UserHandle.myUserId(),
title: CharSequence = "OK",
- pendingIntent: PendingIntent? = safetySourceTestData.testActivityRedirectPendingIntent
+ pendingIntent: PendingIntent? =
+ safetySourceTestData.createTestActivityRedirectPendingIntent()
) =
SafetyCenterEntry.Builder(entryId(sourceId, userId), title)
.setSeverityLevel(ENTRY_SEVERITY_LEVEL_UNKNOWN)
@@ -181,7 +182,8 @@ class SafetyCenterTestData(context: Context) {
sourceId: String,
userId: Int = UserHandle.myUserId(),
title: CharSequence = "OK",
- pendingIntent: PendingIntent? = safetySourceTestData.testActivityRedirectPendingIntent
+ pendingIntent: PendingIntent? =
+ safetySourceTestData.createTestActivityRedirectPendingIntent()
) = safetyCenterEntryDefaultBuilder(sourceId, userId, title, pendingIntent).build()
/**
@@ -197,7 +199,9 @@ class SafetyCenterTestData(context: Context) {
SafetyCenterEntry.Builder(entryId(sourceId, userId), title)
.setSeverityLevel(ENTRY_SEVERITY_LEVEL_UNSPECIFIED)
.setSummary("OK")
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
+ .setPendingIntent(
+ safetySourceTestData.createTestActivityRedirectPendingIntent(explicit = false)
+ )
.setSeverityUnspecifiedIconType(SEVERITY_UNSPECIFIED_ICON_TYPE_NO_ICON)
/**
@@ -214,7 +218,8 @@ class SafetyCenterTestData(context: Context) {
*/
fun safetyCenterEntryUnspecified(
sourceId: String,
- pendingIntent: PendingIntent? = safetySourceTestData.testActivityRedirectPendingIntent
+ pendingIntent: PendingIntent? =
+ safetySourceTestData.createTestActivityRedirectPendingIntent()
) =
SafetyCenterEntry.Builder(entryId(sourceId), "Unspecified title")
.setSeverityLevel(ENTRY_SEVERITY_LEVEL_UNSPECIFIED)
@@ -237,7 +242,7 @@ class SafetyCenterTestData(context: Context) {
SafetyCenterEntry.Builder(entryId(sourceId, userId), title)
.setSeverityLevel(ENTRY_SEVERITY_LEVEL_OK)
.setSummary("Ok summary")
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
+ .setPendingIntent(safetySourceTestData.createTestActivityRedirectPendingIntent())
.setSeverityUnspecifiedIconType(SEVERITY_UNSPECIFIED_ICON_TYPE_NO_RECOMMENDATION)
/**
@@ -262,7 +267,7 @@ class SafetyCenterTestData(context: Context) {
SafetyCenterEntry.Builder(entryId(sourceId), "Recommendation title")
.setSeverityLevel(ENTRY_SEVERITY_LEVEL_RECOMMENDATION)
.setSummary(summary)
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
+ .setPendingIntent(safetySourceTestData.createTestActivityRedirectPendingIntent())
.setSeverityUnspecifiedIconType(SEVERITY_UNSPECIFIED_ICON_TYPE_NO_RECOMMENDATION)
.build()
@@ -274,7 +279,7 @@ class SafetyCenterTestData(context: Context) {
SafetyCenterEntry.Builder(entryId(sourceId), "Critical title")
.setSeverityLevel(ENTRY_SEVERITY_LEVEL_CRITICAL_WARNING)
.setSummary("Critical summary")
- .setPendingIntent(safetySourceTestData.testActivityRedirectPendingIntent)
+ .setPendingIntent(safetySourceTestData.createTestActivityRedirectPendingIntent())
.setSeverityUnspecifiedIconType(SEVERITY_UNSPECIFIED_ICON_TYPE_NO_RECOMMENDATION)
.build()
@@ -305,7 +310,7 @@ class SafetyCenterTestData(context: Context) {
userId
),
"Review",
- safetySourceTestData.testActivityRedirectPendingIntent
+ safetySourceTestData.createTestActivityRedirectPendingIntent()
)
.build()
)
@@ -345,7 +350,7 @@ class SafetyCenterTestData(context: Context) {
userId
),
"See issue",
- safetySourceTestData.testActivityRedirectPendingIntent
+ safetySourceTestData.createTestActivityRedirectPendingIntent()
)
.apply {
if (confirmationDialog && SdkLevel.isAtLeastU()) {
diff --git a/tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetySourceTestData.kt b/tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetySourceTestData.kt
index 0dda827ee..0b2a6c840 100644
--- a/tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetySourceTestData.kt
+++ b/tests/utils/safetycenter/java/com/android/safetycenter/testing/SafetySourceTestData.kt
@@ -20,7 +20,6 @@ import android.app.PendingIntent
import android.content.Context
import android.content.Intent
import android.content.Intent.FLAG_RECEIVER_FOREGROUND
-import android.content.pm.PackageManager.ResolveInfoFlags
import android.os.Build.VERSION_CODES.TIRAMISU
import android.os.Build.VERSION_CODES.UPSIDE_DOWN_CAKE
import android.safetycenter.SafetyEvent
@@ -39,13 +38,13 @@ import android.safetycenter.SafetySourceStatus.IconAction.ICON_TYPE_INFO
import androidx.annotation.RequiresApi
import com.android.modules.utils.build.SdkLevel
import com.android.safetycenter.testing.SafetyCenterTestConfigs.Companion.ACTION_TEST_ACTIVITY
+import com.android.safetycenter.testing.SafetyCenterTestConfigs.Companion.ACTION_TEST_ACTIVITY_EXPORTED
import com.android.safetycenter.testing.SafetyCenterTestConfigs.Companion.SINGLE_SOURCE_ID
import com.android.safetycenter.testing.SafetySourceIntentHandler.Companion.ACTION_DISMISS_ISSUE
import com.android.safetycenter.testing.SafetySourceIntentHandler.Companion.ACTION_RESOLVE_ACTION
import com.android.safetycenter.testing.SafetySourceIntentHandler.Companion.EXTRA_SOURCE_ID
import com.android.safetycenter.testing.SafetySourceIntentHandler.Companion.EXTRA_SOURCE_ISSUE_ACTION_ID
import com.android.safetycenter.testing.SafetySourceIntentHandler.Companion.EXTRA_SOURCE_ISSUE_ID
-import java.lang.IllegalStateException
import kotlin.math.max
/**
@@ -55,16 +54,21 @@ import kotlin.math.max
@RequiresApi(TIRAMISU)
class SafetySourceTestData(private val context: Context) {
- /** A [PendingIntent] that redirects to the [TestActivity] page. */
- val testActivityRedirectPendingIntent =
- createRedirectPendingIntent(context, Intent(ACTION_TEST_ACTIVITY))
-
/**
- * A [PendingIntent] that redirects to the [TestActivity] page, the [Intent] is constructed with
- * the given [identifier].
+ * A [PendingIntent] that redirects to the [TestActivity] page.
+ *
+ * @param explicit whether the returned [PendingIntent] should use an explicit [Intent] (default
+ * [true])
+ * @param identifier the [Intent] identifier (default [null])
*/
- fun testActivityRedirectPendingIntent(identifier: String? = null) =
- createRedirectPendingIntent(context, Intent(ACTION_TEST_ACTIVITY).setIdentifier(identifier))
+ fun createTestActivityRedirectPendingIntent(
+ explicit: Boolean = true,
+ identifier: String? = null
+ ) =
+ createRedirectPendingIntent(
+ context,
+ createTestActivityIntent(context, explicit).setIdentifier(identifier)
+ )
/** A [SafetySourceData] with a [SEVERITY_LEVEL_UNSPECIFIED] [SafetySourceStatus]. */
val unspecified =
@@ -93,7 +97,7 @@ class SafetySourceTestData(private val context: Context) {
SEVERITY_LEVEL_UNSPECIFIED
)
.setEnabled(false)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
.build()
@@ -114,7 +118,7 @@ class SafetySourceTestData(private val context: Context) {
Action.Builder(
INFORMATION_ISSUE_ACTION_ID,
"Review",
- testActivityRedirectPendingIntent
+ createTestActivityRedirectPendingIntent()
)
.build()
)
@@ -136,7 +140,7 @@ class SafetySourceTestData(private val context: Context) {
Action.Builder(
INFORMATION_ISSUE_ACTION_ID,
"Review",
- testActivityRedirectPendingIntent
+ createTestActivityRedirectPendingIntent()
)
.build()
)
@@ -154,7 +158,7 @@ class SafetySourceTestData(private val context: Context) {
"Unspecified summary",
SEVERITY_LEVEL_UNSPECIFIED
)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
.addIssue(informationIssue)
@@ -172,7 +176,7 @@ class SafetySourceTestData(private val context: Context) {
"Unspecified summary",
SEVERITY_LEVEL_UNSPECIFIED
)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
.addIssue(informationIssue)
@@ -183,7 +187,7 @@ class SafetySourceTestData(private val context: Context) {
SafetySourceData.Builder()
.setStatus(
SafetySourceStatus.Builder("Ok title", "Ok summary", SEVERITY_LEVEL_INFORMATION)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
.build()
@@ -209,8 +213,10 @@ class SafetySourceTestData(private val context: Context) {
SafetySourceData.Builder()
.setStatus(
SafetySourceStatus.Builder("Ok title", "Ok summary", SEVERITY_LEVEL_INFORMATION)
- .setPendingIntent(testActivityRedirectPendingIntent)
- .setIconAction(IconAction(ICON_TYPE_INFO, testActivityRedirectPendingIntent))
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
+ .setIconAction(
+ IconAction(ICON_TYPE_INFO, createTestActivityRedirectPendingIntent())
+ )
.build()
)
.build()
@@ -223,8 +229,10 @@ class SafetySourceTestData(private val context: Context) {
SafetySourceData.Builder()
.setStatus(
SafetySourceStatus.Builder("Ok title", "Ok summary", SEVERITY_LEVEL_INFORMATION)
- .setPendingIntent(testActivityRedirectPendingIntent)
- .setIconAction(IconAction(ICON_TYPE_GEAR, testActivityRedirectPendingIntent))
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
+ .setIconAction(
+ IconAction(ICON_TYPE_GEAR, createTestActivityRedirectPendingIntent())
+ )
.build()
)
.build()
@@ -237,7 +245,7 @@ class SafetySourceTestData(private val context: Context) {
SafetySourceData.Builder()
.setStatus(
SafetySourceStatus.Builder("Ok title", "Ok summary", SEVERITY_LEVEL_INFORMATION)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
.addIssue(informationIssue)
@@ -253,7 +261,7 @@ class SafetySourceTestData(private val context: Context) {
SafetySourceData.Builder()
.setStatus(
SafetySourceStatus.Builder("Ok title", "Ok summary", SEVERITY_LEVEL_INFORMATION)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
.addIssue(
@@ -275,7 +283,7 @@ class SafetySourceTestData(private val context: Context) {
"Ok summary",
SEVERITY_LEVEL_INFORMATION
)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
.addIssue(informationIssue)
@@ -289,7 +297,7 @@ class SafetySourceTestData(private val context: Context) {
SafetySourceData.Builder()
.setStatus(
SafetySourceStatus.Builder("Ok title", "Ok summary", SEVERITY_LEVEL_INFORMATION)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
.addIssue(informationIssueWithSubtitle)
@@ -315,7 +323,7 @@ class SafetySourceTestData(private val context: Context) {
Action.Builder(
RECOMMENDATION_ISSUE_ACTION_ID,
"See issue",
- testActivityRedirectPendingIntent
+ createTestActivityRedirectPendingIntent()
)
.apply {
if (confirmationDialog && SdkLevel.isAtLeastU()) {
@@ -383,7 +391,7 @@ class SafetySourceTestData(private val context: Context) {
"Recommendation summary",
SEVERITY_LEVEL_RECOMMENDATION
)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
@@ -467,7 +475,11 @@ class SafetySourceTestData(private val context: Context) {
/** An action that redirects to [TestActivity] */
val testActivityRedirectAction =
- Action.Builder(CRITICAL_ISSUE_ACTION_ID, "Redirect", testActivityRedirectPendingIntent)
+ Action.Builder(
+ CRITICAL_ISSUE_ACTION_ID,
+ "Redirect",
+ createTestActivityRedirectPendingIntent()
+ )
.build()
/** A resolving Critical [Action] that declares a success message */
@@ -505,7 +517,7 @@ class SafetySourceTestData(private val context: Context) {
Action.Builder(
CRITICAL_ISSUE_ACTION_ID,
"Go solve issue",
- testActivityRedirectPendingIntent
+ createTestActivityRedirectPendingIntent()
)
.build()
)
@@ -584,7 +596,7 @@ class SafetySourceTestData(private val context: Context) {
"Critical summary",
SEVERITY_LEVEL_CRITICAL_WARNING
)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
@@ -698,7 +710,7 @@ class SafetySourceTestData(private val context: Context) {
"Critical summary",
SEVERITY_LEVEL_CRITICAL_WARNING
)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
.addIssue(criticalResolvingIssueWithSuccessMessage)
@@ -723,7 +735,7 @@ class SafetySourceTestData(private val context: Context) {
"Critical summary 2",
SEVERITY_LEVEL_CRITICAL_WARNING
)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
.addIssue(criticalRedirectingIssue)
@@ -742,7 +754,7 @@ class SafetySourceTestData(private val context: Context) {
SafetySourceData.Builder()
.setStatus(
SafetySourceStatus.Builder(entryTitle, entrySummary, severityLevel)
- .setPendingIntent(testActivityRedirectPendingIntent)
+ .setPendingIntent(createTestActivityRedirectPendingIntent())
.build()
)
.apply {
@@ -759,7 +771,7 @@ class SafetySourceTestData(private val context: Context) {
Action.Builder(
"action_id",
"Action",
- testActivityRedirectPendingIntent
+ createTestActivityRedirectPendingIntent()
)
.build()
)
@@ -824,41 +836,28 @@ class SafetySourceTestData(private val context: Context) {
return builder.build()
}
- /** Returns a [PendingIntent] that redirects to [intent]. */
- fun createRedirectPendingIntent(
- context: Context,
- intent: Intent,
- inQuietMode: Boolean = false
- ): PendingIntent {
- val explicitIntent = Intent(intent).setPackage(context.packageName)
- val redirectIntent =
- if (intentResolves(context, explicitIntent)) {
- explicitIntent
- } else if (intentResolves(context, intent)) {
- // We have seen some flakiness where implicit intents find multiple receivers
- // and the ResolveActivity pops up. A test cannot handle this, so crash. Most
- // likely the cause is other test's APKs being left hanging around by flaky
- // test infrastructure.
- val intentWithFlag = Intent(intent)
- intentWithFlag.flags =
- intentWithFlag.flags or Intent.FLAG_ACTIVITY_REQUIRE_DEFAULT
- intentWithFlag
- } else if (inQuietMode) {
- explicitIntent
- } else {
- throw IllegalStateException("Intent doesn't resolve")
- }
+ /** Returns an [Intent] that redirects to the [TestActivity] page. */
+ fun createTestActivityIntent(context: Context, explicit: Boolean = true): Intent =
+ if (explicit) {
+ Intent(ACTION_TEST_ACTIVITY).setPackage(context.packageName)
+ } else {
+ val intent = Intent(ACTION_TEST_ACTIVITY_EXPORTED)
+ // We have seen some flakiness where implicit intents find multiple receivers
+ // and the ResolveActivity pops up. A test cannot handle this, so crash. Most
+ // likely the cause is other test's APKs being left hanging around by flaky
+ // test infrastructure.
+ intent.flags = intent.flags or Intent.FLAG_ACTIVITY_REQUIRE_DEFAULT
+ intent
+ }
+
+ /** Returns a [PendingIntent] that redirects to the given [Intent]. */
+ fun createRedirectPendingIntent(context: Context, intent: Intent): PendingIntent {
return PendingIntent.getActivity(
context,
0 /* requestCode */,
- redirectIntent,
+ intent,
PendingIntent.FLAG_IMMUTABLE
)
}
-
- private fun intentResolves(context: Context, intent: Intent): Boolean =
- context.packageManager
- .queryIntentActivities(intent, ResolveInfoFlags.of(0))
- .isNotEmpty()
}
}