Merge "Fix crash in non-indexable keys collection" into pi-dev
diff --git a/src/com/android/settings/display/AmbientDisplayAlwaysOnPreferenceController.java b/src/com/android/settings/display/AmbientDisplayAlwaysOnPreferenceController.java
index e0efaac..5de49bb 100644
--- a/src/com/android/settings/display/AmbientDisplayAlwaysOnPreferenceController.java
+++ b/src/com/android/settings/display/AmbientDisplayAlwaysOnPreferenceController.java
@@ -47,6 +47,9 @@
@Override
public int getAvailabilityStatus() {
+ if (mConfig == null) {
+ mConfig = new AmbientDisplayConfiguration(mContext);
+ }
return isAvailable(mConfig) ? AVAILABLE : DISABLED_UNSUPPORTED;
}
diff --git a/src/com/android/settings/display/AmbientDisplayNotificationsPreferenceController.java b/src/com/android/settings/display/AmbientDisplayNotificationsPreferenceController.java
index ab769e1..9cff088 100644
--- a/src/com/android/settings/display/AmbientDisplayNotificationsPreferenceController.java
+++ b/src/com/android/settings/display/AmbientDisplayNotificationsPreferenceController.java
@@ -81,6 +81,9 @@
@Override
public int getAvailabilityStatus() {
+ if (mConfig == null) {
+ mConfig = new AmbientDisplayConfiguration(mContext);
+ }
return mConfig.pulseOnNotificationAvailable() ? AVAILABLE : DISABLED_UNSUPPORTED;
}
diff --git a/src/com/android/settings/search/SettingsSearchIndexablesProvider.java b/src/com/android/settings/search/SettingsSearchIndexablesProvider.java
index 3ef1b85..b9134e5 100644
--- a/src/com/android/settings/search/SettingsSearchIndexablesProvider.java
+++ b/src/com/android/settings/search/SettingsSearchIndexablesProvider.java
@@ -41,6 +41,7 @@
import static android.provider.SearchIndexablesContract.INDEXABLES_XML_RES_COLUMNS;
import static android.provider.SearchIndexablesContract.NON_INDEXABLES_KEYS_COLUMNS;
import static android.provider.SearchIndexablesContract.SITE_MAP_COLUMNS;
+
import static com.android.settings.dashboard.DashboardFragmentRegistry.CATEGORY_KEY_TO_PARENT_MAP;
import android.content.Context;
@@ -63,7 +64,16 @@
import java.util.List;
public class SettingsSearchIndexablesProvider extends SearchIndexablesProvider {
+
public static final boolean DEBUG = false;
+
+ /**
+ * Flag for a system property which checks if we should crash if there are issues in the
+ * indexing pipeline.
+ */
+ public static final String SYSPROP_CRASH_ON_ERROR =
+ "debug.com.android.settings.search.crash_on_error";
+
private static final String TAG = "SettingsSearchProvider";
private static final Collection<String> INVALID_KEYS;
@@ -183,7 +193,23 @@
final long startTime = System.currentTimeMillis();
Indexable.SearchIndexProvider provider = DatabaseIndexingUtils.getSearchIndexProvider(
clazz);
- List<String> providerNonIndexableKeys = provider.getNonIndexableKeys(context);
+
+ List<String> providerNonIndexableKeys;
+ try {
+ providerNonIndexableKeys = provider.getNonIndexableKeys(context);
+ } catch (Exception e) {
+ // Catch a generic crash. In the absence of the catch, the background thread will
+ // silently fail anyway, so we aren't losing information by catching the exception.
+ // We crash when the system property exists so that we can test if crashes need to
+ // be fixed.
+ // The gain is that if there is a crash in a specific controller, we don't lose all
+ // non-indexable keys, but we can still find specific crashes in development.
+ if (System.getProperty(SYSPROP_CRASH_ON_ERROR) != null) {
+ throw new RuntimeException(e);
+ }
+ Log.e(TAG, "Error trying to get non-indexable keys from: " + clazz.getName() , e);
+ continue;
+ }
if (providerNonIndexableKeys == null || providerNonIndexableKeys.isEmpty()) {
if (DEBUG) {
diff --git a/tests/unit/src/com/android/settings/search/SettingsSearchIndexablesProviderTest.java b/tests/unit/src/com/android/settings/search/SettingsSearchIndexablesProviderTest.java
index aed94a0..3659fdb 100644
--- a/tests/unit/src/com/android/settings/search/SettingsSearchIndexablesProviderTest.java
+++ b/tests/unit/src/com/android/settings/search/SettingsSearchIndexablesProviderTest.java
@@ -21,11 +21,13 @@
import android.content.Context;
import android.database.Cursor;
import android.net.Uri;
+import android.platform.test.annotations.Presubmit;
import android.provider.SearchIndexablesContract;
import android.support.test.InstrumentationRegistry;
import android.support.test.filters.SmallTest;
import android.support.test.runner.AndroidJUnit4;
+import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
@@ -36,12 +38,16 @@
private Context mContext;
-
@Before
public void setUp() {
mContext = InstrumentationRegistry.getTargetContext();
}
+ @After
+ public void cleanUp() {
+ System.clearProperty(SettingsSearchIndexablesProvider.SYSPROP_CRASH_ON_ERROR);
+ }
+
@Test
public void testSiteMapPairsFetched() {
final Uri uri = Uri.parse("content://" + mContext.getPackageName() + "/" +
@@ -59,4 +65,21 @@
.isNotEmpty();
}
}
+
+ /**
+ * All {@link Indexable.SearchIndexProvider} should collect a list of non-indexable keys
+ * without crashing. This test enables crashing of individual providers in the indexing pipeline
+ * and checks that there are no crashes.
+ */
+ @Test
+ @Presubmit
+ public void nonIndexableKeys_shouldNotCrash() {
+ // Allow crashes in the indexing pipeline.
+ System.setProperty(SettingsSearchIndexablesProvider.SYSPROP_CRASH_ON_ERROR,
+ "enabled");
+
+ final Uri uri = Uri.parse("content://" + mContext.getPackageName() + "/" +
+ SearchIndexablesContract.NON_INDEXABLES_KEYS_PATH);
+ mContext.getContentResolver().query(uri, null, null, null, null);
+ }
}