1 /*
2  * Copyright (C) 2017 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 package com.android.emergency.edit;
17 
18 import static androidx.test.espresso.Espresso.onView;
19 import static androidx.test.espresso.Espresso.openActionBarOverflowOrOptionsMenu;
20 import static androidx.test.espresso.action.ViewActions.click;
21 import static androidx.test.espresso.matcher.ViewMatchers.withText;
22 
23 import static com.google.common.truth.Truth.assertThat;
24 import static com.google.common.truth.Truth.assertWithMessage;
25 
26 import android.app.Dialog;
27 import android.app.Instrumentation;
28 import android.content.ComponentName;
29 import android.content.Context;
30 import android.content.Intent;
31 import android.content.IntentFilter;
32 import android.content.pm.PackageManager;
33 import android.net.Uri;
34 import android.provider.ContactsContract;
35 
36 import androidx.preference.Preference;
37 import androidx.preference.PreferenceGroup;
38 import androidx.preference.PreferenceManager;
39 import androidx.test.InstrumentationRegistry;
40 import androidx.test.runner.AndroidJUnit4;
41 
42 import com.android.emergency.ContactTestUtils;
43 import com.android.emergency.PreferenceKeys;
44 import com.android.emergency.R;
45 import com.android.emergency.preferences.EmergencyContactsPreference;
46 import com.android.emergency.preferences.EmergencyEditTextPreference;
47 import com.android.emergency.preferences.EmergencyListPreference;
48 import com.android.emergency.util.PreferenceUtils;
49 
50 import org.junit.After;
51 import org.junit.Before;
52 import org.junit.Test;
53 import org.junit.runner.RunWith;
54 
55 /** Unit tests for {@link EditInfoActivity}. */
56 @RunWith(AndroidJUnit4.class)
57 public final class EditInfoActivityTest {
58     private Instrumentation mInstrumentation;
59     private Context mTargetContext;
60 
61     @Before
setUp()62     public void setUp() {
63         mInstrumentation = InstrumentationRegistry.getInstrumentation();
64         mTargetContext = mInstrumentation.getTargetContext();
65         // In case a previous test crashed or failed, clear any previous shared preference value.
66         PreferenceManager.getDefaultSharedPreferences(mTargetContext).edit().clear().commit();
67     }
68 
69     @After
tearDown()70     public void tearDown() {
71         PreferenceManager.getDefaultSharedPreferences(mTargetContext).edit().clear().commit();
72     }
73 
74     @Test
testInitialState()75     public void testInitialState() {
76         EditInfoActivity activity = startEditInfoActivity();
77         EditInfoFragment fragment = (EditInfoFragment) activity.getFragment();
78         PreferenceGroup medicalInfoParent = fragment.getMedicalInfoParent();
79 
80         // Because the initial state of each preference is empty, the edit activity removes the
81         // preference. As a result, we expect them all to be null.
82         for (String key : PreferenceKeys.KEYS_EDIT_EMERGENCY_INFO) {
83             assertWithMessage(key).that((Preference) medicalInfoParent.findPreference(key))
84                     .isNull();
85         }
86         EmergencyContactsPreference emergencyContactsPreference =
87                 (EmergencyContactsPreference) fragment.findPreference(
88                         PreferenceKeys.KEY_EMERGENCY_CONTACTS);
89         assertThat(emergencyContactsPreference).isNotNull();
90         assertThat(emergencyContactsPreference.getPreferenceCount()).isEqualTo(0);
91 
92         final PackageManager packageManager = mTargetContext.getPackageManager();
93         final String packageName = mTargetContext.getPackageName();
94         final ComponentName componentName = new ComponentName(
95                 packageName,
96                 packageName + PreferenceUtils.SETTINGS_SUGGESTION_ACTIVITY_ALIAS);
97         assertThat(packageManager.getComponentEnabledSetting(componentName))
98                 .isEqualTo(PackageManager.COMPONENT_ENABLED_STATE_ENABLED);
99     }
100 
101     @Test
testClearAllPreferences()102     public void testClearAllPreferences() {
103         PreferenceManager.getDefaultSharedPreferences(mTargetContext).edit().putString(
104                 PreferenceKeys.KEY_ADDRESS, "Home").commit();
105         PreferenceManager.getDefaultSharedPreferences(mTargetContext).edit().putString(
106                 PreferenceKeys.KEY_BLOOD_TYPE, "A+").commit();
107         PreferenceManager.getDefaultSharedPreferences(mTargetContext).edit().putString(
108                 PreferenceKeys.KEY_ALLERGIES, "Peanuts").commit();
109         PreferenceManager.getDefaultSharedPreferences(mTargetContext).edit().putString(
110                 PreferenceKeys.KEY_MEDICATIONS, "Aspirin").commit();
111         PreferenceManager.getDefaultSharedPreferences(mTargetContext).edit().putString(
112                 PreferenceKeys.KEY_MEDICAL_CONDITIONS, "Asthma").commit();
113         PreferenceManager.getDefaultSharedPreferences(mTargetContext).edit().putString(
114                 PreferenceKeys.KEY_ORGAN_DONOR, "Yes").commit();
115 
116         final Uri contactUri = ContactTestUtils
117                 .createContact(mTargetContext.getContentResolver(), "Michael", "789");
118         PreferenceManager.getDefaultSharedPreferences(mTargetContext)
119                 .edit().putString(PreferenceKeys.KEY_EMERGENCY_CONTACTS, contactUri.toString())
120                 .commit();
121 
122         final PackageManager packageManager = mTargetContext.getPackageManager();
123         final String packageName = mTargetContext.getPackageName();
124         final ComponentName componentName = new ComponentName(
125                 packageName,
126                 packageName + PreferenceUtils.SETTINGS_SUGGESTION_ACTIVITY_ALIAS);
127         // With emergency info settings present, the settings suggestion should be disabled.
128         assertThat(packageManager.getComponentEnabledSetting(componentName))
129                 .isEqualTo(PackageManager.COMPONENT_ENABLED_STATE_DISABLED);
130 
131         EditInfoActivity activity = startEditInfoActivity();
132         EditInfoFragment fragment = (EditInfoFragment) activity.getFragment();
133 
134         final EmergencyEditTextPreference addressPreference =
135                 (EmergencyEditTextPreference) fragment.getMedicalInfoPreference(
136                         PreferenceKeys.KEY_ADDRESS);
137         final EmergencyListPreference bloodTypePreference =
138                 (EmergencyListPreference) fragment.getMedicalInfoPreference(
139                         PreferenceKeys.KEY_BLOOD_TYPE);
140         final EmergencyEditTextPreference allergiesPreference =
141                 (EmergencyEditTextPreference) fragment.getMedicalInfoPreference(
142                         PreferenceKeys.KEY_ALLERGIES);
143         final EmergencyEditTextPreference medicationsPreference =
144                 (EmergencyEditTextPreference) fragment.getMedicalInfoPreference(
145                         PreferenceKeys.KEY_MEDICATIONS);
146         final EmergencyEditTextPreference medicalConditionsPreference =
147                 (EmergencyEditTextPreference) fragment.getMedicalInfoPreference(
148                         PreferenceKeys.KEY_MEDICAL_CONDITIONS);
149         final EmergencyListPreference organDonorPreference =
150                 (EmergencyListPreference) fragment.getMedicalInfoPreference(
151                         PreferenceKeys.KEY_ORGAN_DONOR);
152         final EmergencyContactsPreference emergencyContactsPreference =
153                 (EmergencyContactsPreference) fragment.findPreference(
154                         PreferenceKeys.KEY_EMERGENCY_CONTACTS);
155 
156         String unknownAddress = activity.getResources().getString(R.string.unknown_address);
157         String unknownBloodType = activity.getResources().getString(R.string.unknown_blood_type);
158         String unknownAllergies = activity.getResources().getString(R.string.unknown_allergies);
159         String unknownMedications = activity.getResources().getString(R.string.unknown_medications);
160         String unknownMedicalConditions =
161                 activity.getResources().getString(R.string.unknown_medical_conditions);
162         String unknownOrganDonor = activity.getResources().getString(R.string.unknown_organ_donor);
163 
164         assertThat(addressPreference.getSummary()).isNotEqualTo(unknownAddress);
165         assertThat(bloodTypePreference.getSummary()).isNotEqualTo(unknownBloodType);
166         assertThat(allergiesPreference.getSummary()).isNotEqualTo(unknownAllergies);
167         assertThat(medicationsPreference.getSummary()).isNotEqualTo(unknownMedications);
168         assertThat(medicalConditionsPreference.getSummary()).isNotEqualTo(unknownMedicalConditions);
169         assertThat(organDonorPreference.getSummary()).isNotEqualTo(unknownOrganDonor);
170         assertThat(emergencyContactsPreference.getEmergencyContacts()).hasSize(1);
171         assertThat(emergencyContactsPreference.getPreferenceCount()).isEqualTo(1);
172 
173         EditInfoActivity.ClearAllDialogFragment clearAllDialogFragment =
174                 (EditInfoActivity.ClearAllDialogFragment) activity.getFragmentManager()
175                         .findFragmentByTag(EditInfoActivity.TAG_CLEAR_ALL_DIALOG);
176         assertThat(clearAllDialogFragment).isNull();
177 
178         openActionBarOverflowOrOptionsMenu(mTargetContext);
179         onView(withText(R.string.clear_all)).perform(click());
180 
181         final EditInfoActivity.ClearAllDialogFragment clearAllDialogFragmentAfterwards =
182                 (EditInfoActivity.ClearAllDialogFragment) activity.getFragmentManager()
183                         .findFragmentByTag(EditInfoActivity.TAG_CLEAR_ALL_DIALOG);
184 
185         assertThat(clearAllDialogFragmentAfterwards).isNotNull();
186         Dialog clearAllDialog = clearAllDialogFragmentAfterwards.getDialog();
187         assertThat(clearAllDialog).isNotNull();
188         assertThat(clearAllDialog.isShowing()).isTrue();
189 
190         onView(withText(R.string.clear)).perform(click());
191 
192         // After the clear all the preferences dialog is confirmed, the preferences values are
193         // reloaded, and the existing object references are updated in-place.
194         assertThat(addressPreference.getSummary()).isNull();
195         assertThat(bloodTypePreference.getSummary().toString()).isEqualTo(unknownBloodType);
196         assertThat(allergiesPreference.getSummary()).isNull();
197         assertThat(medicationsPreference.getSummary()).isNull();
198         assertThat(medicalConditionsPreference.getSummary()).isNull();
199         assertThat(organDonorPreference.getSummary()).isEqualTo(unknownOrganDonor);
200         assertThat(emergencyContactsPreference.getEmergencyContacts()).isEmpty();
201         assertThat(emergencyContactsPreference.getPreferenceCount()).isEqualTo(0);
202 
203         // The preference values are not displayed, being empty.
204         PreferenceGroup medicalInfoParent = fragment.getMedicalInfoParent();
205         for (String key : PreferenceKeys.KEYS_EDIT_EMERGENCY_INFO) {
206             assertWithMessage(key).that((Preference) medicalInfoParent.findPreference(key))
207                     .isNull();
208         }
209 
210         // Now that the settings have been cleared, the settings suggestion should reappear.
211         assertThat(packageManager.getComponentEnabledSetting(componentName))
212                 .isEqualTo(PackageManager.COMPONENT_ENABLED_STATE_ENABLED);
213 
214         assertThat(ContactTestUtils
215                 .deleteContact(activity.getContentResolver(), "Michael", "789")).isTrue();
216     }
217 
218     @Test
testAddContactPreference()219     public void testAddContactPreference() throws Throwable {
220         EditInfoActivity activity = startEditInfoActivity();
221         EditInfoFragment fragment = (EditInfoFragment) activity.getFragment();
222 
223         Preference addContactPreference =
224                 fragment.findPreference(PreferenceKeys.KEY_ADD_EMERGENCY_CONTACT);
225         assertThat(addContactPreference).isNotNull();
226 
227         IntentFilter intentFilter = new IntentFilter(Intent.ACTION_PICK);
228         intentFilter.addDataType(ContactsContract.CommonDataKinds.Phone.CONTENT_TYPE);
229         Instrumentation.ActivityMonitor activityMonitor =
230                 mInstrumentation.addMonitor(intentFilter, null, true /* block */);
231 
232         addContactPreference
233                 .getOnPreferenceClickListener().onPreferenceClick(addContactPreference);
234         assertThat(mInstrumentation.checkMonitorHit(activityMonitor, 1 /* minHits */)).isTrue();
235     }
236 
startEditInfoActivity()237     private EditInfoActivity startEditInfoActivity() {
238         final Intent editActivityIntent = new Intent(mTargetContext, EditInfoActivity.class);
239         return (EditInfoActivity) mInstrumentation.startActivitySync(editActivityIntent);
240     }
241 }
242