• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2018 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 
17 package com.android.settings.network;
18 
19 import static android.telephony.SignalStrength.NUM_SIGNAL_STRENGTH_BINS;
20 import static android.telephony.SignalStrength.SIGNAL_STRENGTH_GOOD;
21 import static android.telephony.SignalStrength.SIGNAL_STRENGTH_GREAT;
22 import static android.telephony.SignalStrength.SIGNAL_STRENGTH_NONE_OR_UNKNOWN;
23 import static android.telephony.SignalStrength.SIGNAL_STRENGTH_POOR;
24 import static android.telephony.SubscriptionManager.INVALID_SUBSCRIPTION_ID;
25 
26 import static com.google.common.truth.Truth.assertThat;
27 
28 import static org.mockito.ArgumentMatchers.any;
29 import static org.mockito.ArgumentMatchers.anyBoolean;
30 import static org.mockito.ArgumentMatchers.anyInt;
31 import static org.mockito.ArgumentMatchers.eq;
32 import static org.mockito.Mockito.doReturn;
33 import static org.mockito.Mockito.mock;
34 import static org.mockito.Mockito.spy;
35 import static org.mockito.Mockito.times;
36 import static org.mockito.Mockito.verify;
37 import static org.mockito.Mockito.when;
38 
39 import android.app.Activity;
40 import android.content.Context;
41 import android.content.Intent;
42 import android.graphics.drawable.Drawable;
43 import android.graphics.drawable.LayerDrawable;
44 import android.net.ConnectivityManager;
45 import android.net.Network;
46 import android.net.NetworkCapabilities;
47 import android.provider.Settings;
48 import android.telephony.SignalStrength;
49 import android.telephony.SubscriptionInfo;
50 import android.telephony.SubscriptionManager;
51 import android.telephony.TelephonyManager;
52 
53 import com.android.settings.R;
54 import com.android.settingslib.core.lifecycle.Lifecycle;
55 import com.android.settingslib.graph.SignalDrawable;
56 
57 import org.junit.After;
58 import org.junit.Before;
59 import org.junit.Test;
60 import org.junit.runner.RunWith;
61 import org.mockito.ArgumentCaptor;
62 import org.mockito.Mock;
63 import org.mockito.MockitoAnnotations;
64 import org.robolectric.Robolectric;
65 import org.robolectric.RobolectricTestRunner;
66 import org.robolectric.annotation.Config;
67 import org.robolectric.shadows.ShadowSubscriptionManager;
68 
69 import java.util.ArrayList;
70 import java.util.Arrays;
71 import java.util.List;
72 
73 import androidx.lifecycle.LifecycleOwner;
74 import androidx.preference.Preference;
75 import androidx.preference.PreferenceCategory;
76 import androidx.preference.PreferenceScreen;
77 
78 @RunWith(RobolectricTestRunner.class)
79 @Config(shadows = ShadowSubscriptionManager.class)
80 public class SubscriptionsPreferenceControllerTest {
81     private static final String KEY = "preference_group";
82 
83     @Mock
84     private PreferenceScreen mScreen;
85     @Mock
86     private PreferenceCategory mPreferenceCategory;
87     @Mock
88     private SubscriptionManager mSubscriptionManager;
89     @Mock
90     private ConnectivityManager mConnectivityManager;
91     @Mock
92     private TelephonyManager mTelephonyManager;
93     @Mock
94     private Network mActiveNetwork;
95     @Mock
96     private NetworkCapabilities mCapabilities;
97     @Mock
98     private Drawable mSignalStrengthIcon;
99 
100     private Context mContext;
101     private LifecycleOwner mLifecycleOwner;
102     private Lifecycle mLifecycle;
103     private SubscriptionsPreferenceController mController;
104     private int mOnChildUpdatedCount;
105     private SubscriptionsPreferenceController.UpdateListener mUpdateListener;
106 
107     @Before
setUp()108     public void setUp() {
109         MockitoAnnotations.initMocks(this);
110         mContext = spy(Robolectric.setupActivity(Activity.class));
111         mLifecycleOwner = () -> mLifecycle;
112         mLifecycle = new Lifecycle(mLifecycleOwner);
113         when(mContext.getSystemService(SubscriptionManager.class)).thenReturn(mSubscriptionManager);
114         when(mContext.getSystemService(ConnectivityManager.class)).thenReturn(mConnectivityManager);
115         when(mContext.getSystemService(TelephonyManager.class)).thenReturn(mTelephonyManager);
116         when(mConnectivityManager.getActiveNetwork()).thenReturn(mActiveNetwork);
117         when(mConnectivityManager.getNetworkCapabilities(mActiveNetwork)).thenReturn(mCapabilities);
118         when(mTelephonyManager.createForSubscriptionId(anyInt())).thenReturn(mTelephonyManager);
119         when(mScreen.findPreference(eq(KEY))).thenReturn(mPreferenceCategory);
120         when(mPreferenceCategory.getContext()).thenReturn(mContext);
121         mOnChildUpdatedCount = 0;
122         mUpdateListener = () -> mOnChildUpdatedCount++;
123 
124         mController = spy(
125                 new SubscriptionsPreferenceController(mContext, mLifecycle, mUpdateListener,
126                         KEY, 5));
127         doReturn(mSignalStrengthIcon).when(mController).getIcon(anyInt(), anyInt(), anyBoolean());
128     }
129 
130     @After
tearDown()131     public void tearDown() {
132         SubscriptionUtil.setActiveSubscriptionsForTesting(null);
133     }
134 
135     @Test
isAvailable_oneSubscription_availableFalse()136     public void isAvailable_oneSubscription_availableFalse() {
137         setupMockSubscriptions(1);
138         assertThat(mController.isAvailable()).isFalse();
139     }
140 
141     @Test
isAvailable_twoSubscriptions_availableTrue()142     public void isAvailable_twoSubscriptions_availableTrue() {
143         setupMockSubscriptions(2);
144         assertThat(mController.isAvailable()).isTrue();
145     }
146 
147     @Test
isAvailable_fiveSubscriptions_availableTrue()148     public void isAvailable_fiveSubscriptions_availableTrue() {
149         setupMockSubscriptions(5);
150         assertThat(mController.isAvailable()).isTrue();
151     }
152 
153     @Test
isAvailable_airplaneModeOn_availableFalse()154     public void isAvailable_airplaneModeOn_availableFalse() {
155         setupMockSubscriptions(2);
156         assertThat(mController.isAvailable()).isTrue();
157         Settings.Global.putInt(mContext.getContentResolver(), Settings.Global.AIRPLANE_MODE_ON, 1);
158         assertThat(mController.isAvailable()).isFalse();
159     }
160 
161     @Test
onAirplaneModeChanged_airplaneModeTurnedOn_eventFired()162     public void onAirplaneModeChanged_airplaneModeTurnedOn_eventFired() {
163         setupMockSubscriptions(2);
164         mController.onResume();
165         mController.displayPreference(mScreen);
166         assertThat(mController.isAvailable()).isTrue();
167 
168         final int updateCountBeforeModeChange = mOnChildUpdatedCount;
169         Settings.Global.putInt(mContext.getContentResolver(), Settings.Global.AIRPLANE_MODE_ON, 1);
170         mController.onAirplaneModeChanged(true);
171         assertThat(mController.isAvailable()).isFalse();
172         assertThat(mOnChildUpdatedCount).isEqualTo(updateCountBeforeModeChange + 1);
173     }
174 
175     @Test
onAirplaneModeChanged_airplaneModeTurnedOff_eventFired()176     public void onAirplaneModeChanged_airplaneModeTurnedOff_eventFired() {
177         Settings.Global.putInt(mContext.getContentResolver(), Settings.Global.AIRPLANE_MODE_ON, 1);
178         setupMockSubscriptions(2);
179         mController.onResume();
180         mController.displayPreference(mScreen);
181         assertThat(mController.isAvailable()).isFalse();
182 
183         final int updateCountBeforeModeChange = mOnChildUpdatedCount;
184         Settings.Global.putInt(mContext.getContentResolver(), Settings.Global.AIRPLANE_MODE_ON, 0);
185         mController.onAirplaneModeChanged(false);
186         assertThat(mController.isAvailable()).isTrue();
187         assertThat(mOnChildUpdatedCount).isEqualTo(updateCountBeforeModeChange + 1);
188     }
189 
190     @Test
onSubscriptionsChanged_countBecameTwo_eventFired()191     public void onSubscriptionsChanged_countBecameTwo_eventFired() {
192         final List<SubscriptionInfo> subs = setupMockSubscriptions(2);
193         SubscriptionUtil.setActiveSubscriptionsForTesting(subs.subList(0, 1));
194         mController.onResume();
195         mController.displayPreference(mScreen);
196         assertThat(mController.isAvailable()).isFalse();
197 
198         final int updateCountBeforeSubscriptionChange = mOnChildUpdatedCount;
199         SubscriptionUtil.setActiveSubscriptionsForTesting(subs);
200         mController.onSubscriptionsChanged();
201         assertThat(mController.isAvailable()).isTrue();
202         assertThat(mOnChildUpdatedCount).isEqualTo(updateCountBeforeSubscriptionChange + 1);
203     }
204 
205     @Test
onSubscriptionsChanged_countBecameOne_eventFiredAndPrefsRemoved()206     public void onSubscriptionsChanged_countBecameOne_eventFiredAndPrefsRemoved() {
207         final List<SubscriptionInfo> subs = setupMockSubscriptions(2);
208         mController.onResume();
209         mController.displayPreference(mScreen);
210         assertThat(mController.isAvailable()).isTrue();
211         verify(mPreferenceCategory, times(2)).addPreference(any(Preference.class));
212 
213         final int updateCountBeforeSubscriptionChange = mOnChildUpdatedCount;
214         SubscriptionUtil.setActiveSubscriptionsForTesting(subs.subList(0, 1));
215         mController.onSubscriptionsChanged();
216         assertThat(mController.isAvailable()).isFalse();
217         assertThat(mOnChildUpdatedCount).isEqualTo(updateCountBeforeSubscriptionChange + 1);
218 
219         verify(mPreferenceCategory, times(2)).removePreference(any(Preference.class));
220     }
221 
222     @Test
onSubscriptionsChanged_subscriptionReplaced_preferencesChanged()223     public void onSubscriptionsChanged_subscriptionReplaced_preferencesChanged() {
224         final List<SubscriptionInfo> subs = setupMockSubscriptions(3);
225 
226         // Start out with only sub1 and sub2.
227         SubscriptionUtil.setActiveSubscriptionsForTesting(subs.subList(0, 2));
228         mController.onResume();
229         mController.displayPreference(mScreen);
230         final ArgumentCaptor<Preference> captor = ArgumentCaptor.forClass(Preference.class);
231         verify(mPreferenceCategory, times(2)).addPreference(captor.capture());
232         assertThat(captor.getAllValues().size()).isEqualTo(2);
233         assertThat(captor.getAllValues().get(0).getTitle()).isEqualTo("sub1");
234         assertThat(captor.getAllValues().get(1).getTitle()).isEqualTo("sub2");
235 
236         // Now replace sub2 with sub3, and make sure the old preference was removed and the new
237         // preference was added.
238         final int updateCountBeforeSubscriptionChange = mOnChildUpdatedCount;
239         SubscriptionUtil.setActiveSubscriptionsForTesting(Arrays.asList(subs.get(0), subs.get(2)));
240         mController.onSubscriptionsChanged();
241         assertThat(mController.isAvailable()).isTrue();
242         assertThat(mOnChildUpdatedCount).isEqualTo(updateCountBeforeSubscriptionChange + 1);
243 
244         verify(mPreferenceCategory).removePreference(captor.capture());
245         assertThat(captor.getValue().getTitle()).isEqualTo("sub2");
246         verify(mPreferenceCategory, times(3)).addPreference(captor.capture());
247         assertThat(captor.getValue().getTitle()).isEqualTo("sub3");
248     }
249 
250 
251     /**
252      * Helper to create a specified number of subscriptions, display them, and then click on one and
253      * verify that the intent fires and has the right subscription id extra.
254      *
255      * @param subscriptionCount the number of subscriptions
256      * @param selectedPrefIndex index of the subscription to click on
257      */
runPreferenceClickTest(final int subscriptionCount, final int selectedPrefIndex)258     private void runPreferenceClickTest(final int subscriptionCount, final int selectedPrefIndex) {
259         final List<SubscriptionInfo> subs = setupMockSubscriptions(subscriptionCount);
260         mController.displayPreference(mScreen);
261         final ArgumentCaptor<Preference> prefCaptor = ArgumentCaptor.forClass(Preference.class);
262         verify(mPreferenceCategory, times(subscriptionCount)).addPreference(prefCaptor.capture());
263         final List<Preference> prefs = prefCaptor.getAllValues();
264         final Preference pref = prefs.get(selectedPrefIndex);
265         pref.getOnPreferenceClickListener().onPreferenceClick(pref);
266         final ArgumentCaptor<Intent> intentCaptor = ArgumentCaptor.forClass(Intent.class);
267         verify(mContext).startActivity(intentCaptor.capture());
268         final Intent intent = intentCaptor.getValue();
269         assertThat(intent).isNotNull();
270         assertThat(intent.hasExtra(Settings.EXTRA_SUB_ID)).isTrue();
271         final int subIdFromIntent = intent.getIntExtra(Settings.EXTRA_SUB_ID,
272                 INVALID_SUBSCRIPTION_ID);
273         assertThat(subIdFromIntent).isEqualTo(
274                 subs.get(selectedPrefIndex).getSubscriptionId());
275     }
276 
277     @Test
twoPreferences_firstPreferenceClicked_correctIntentFires()278     public void twoPreferences_firstPreferenceClicked_correctIntentFires() {
279         runPreferenceClickTest(2, 0);
280     }
281 
282     @Test
twoPreferences_secondPreferenceClicked_correctIntentFires()283     public void twoPreferences_secondPreferenceClicked_correctIntentFires() {
284         runPreferenceClickTest(2, 1);
285     }
286 
287     @Test
threePreferences_secondPreferenceClicked_correctIntentFires()288     public void threePreferences_secondPreferenceClicked_correctIntentFires() {
289         runPreferenceClickTest(3, 1);
290     }
291 
292     @Test
threePreferences_thirdPreferenceClicked_correctIntentFires()293     public void threePreferences_thirdPreferenceClicked_correctIntentFires() {
294         runPreferenceClickTest(3, 2);
295     }
296 
297     @Test
getSummary_twoSubsOneDefaultForEverythingDataActive()298     public void getSummary_twoSubsOneDefaultForEverythingDataActive() {
299         setupMockSubscriptions(2);
300 
301         ShadowSubscriptionManager.setDefaultSmsSubscriptionId(11);
302         ShadowSubscriptionManager.setDefaultVoiceSubscriptionId(11);
303         when(mTelephonyManager.isDataEnabled()).thenReturn(true);
304         when(mCapabilities.hasTransport(NetworkCapabilities.TRANSPORT_CELLULAR)).thenReturn(true);
305 
306         assertThat(mController.getSummary(11, true)).isEqualTo(
307                 mContext.getString(R.string.default_for_calls_and_sms) + System.lineSeparator()
308                         + mContext.getString(R.string.mobile_data_active));
309 
310         assertThat(mController.getSummary(22, false)).isEqualTo(
311                 mContext.getString(R.string.subscription_available));
312     }
313 
314     @Test
getSummary_twoSubsOneDefaultForEverythingDataNotActive()315     public void getSummary_twoSubsOneDefaultForEverythingDataNotActive() {
316         setupMockSubscriptions(2, 1, true);
317 
318         ShadowSubscriptionManager.setDefaultSmsSubscriptionId(1);
319         ShadowSubscriptionManager.setDefaultVoiceSubscriptionId(1);
320 
321         assertThat(mController.getSummary(1, true)).isEqualTo(
322                 mContext.getString(R.string.default_for_calls_and_sms) + System.lineSeparator()
323                         + mContext.getString(R.string.default_for_mobile_data));
324 
325         assertThat(mController.getSummary(2, false)).isEqualTo(
326                 mContext.getString(R.string.subscription_available));
327     }
328 
329     @Test
getSummary_twoSubsOneDefaultForEverythingDataDisabled()330     public void getSummary_twoSubsOneDefaultForEverythingDataDisabled() {
331         setupMockSubscriptions(2);
332 
333         ShadowSubscriptionManager.setDefaultVoiceSubscriptionId(1);
334         ShadowSubscriptionManager.setDefaultSmsSubscriptionId(1);
335 
336         assertThat(mController.getSummary(1, true)).isEqualTo(
337                 mContext.getString(R.string.default_for_calls_and_sms) + System.lineSeparator()
338                         + mContext.getString(R.string.mobile_data_off));
339 
340         assertThat(mController.getSummary(2, false)).isEqualTo(
341                 mContext.getString(R.string.subscription_available));
342     }
343 
344     @Test
getSummary_twoSubsOneForCallsAndDataOneForSms()345     public void getSummary_twoSubsOneForCallsAndDataOneForSms() {
346         setupMockSubscriptions(2, 1, true);
347 
348         ShadowSubscriptionManager.setDefaultSmsSubscriptionId(2);
349         ShadowSubscriptionManager.setDefaultVoiceSubscriptionId(1);
350 
351         assertThat(mController.getSummary(1, true)).isEqualTo(
352                 mContext.getString(R.string.default_for_calls) + System.lineSeparator()
353                         + mContext.getString(R.string.default_for_mobile_data));
354 
355         assertThat(mController.getSummary(2, false)).isEqualTo(
356                 mContext.getString(R.string.default_for_sms));
357     }
358 
359     @Test
setIcon_nullStrength_noCrash()360     public void setIcon_nullStrength_noCrash() {
361         final List<SubscriptionInfo> subs = setupMockSubscriptions(2);
362         setMockSubSignalStrength(subs, 0, -1);
363         final Preference pref = mock(Preference.class);
364 
365         mController.setIcon(pref, 1, true /* isDefaultForData */);
366         verify(mController).getIcon(eq(0), eq(NUM_SIGNAL_STRENGTH_BINS), eq(true));
367     }
368 
369     @Test
setIcon_noSignal_correctLevels()370     public void setIcon_noSignal_correctLevels() {
371         final List<SubscriptionInfo> subs = setupMockSubscriptions(2, 1, true);
372         setMockSubSignalStrength(subs, 0, SIGNAL_STRENGTH_NONE_OR_UNKNOWN);
373         setMockSubSignalStrength(subs, 1, SIGNAL_STRENGTH_NONE_OR_UNKNOWN);
374         setMockSubDataEnabled(subs, 0, true);
375         final Preference pref = mock(Preference.class);
376 
377         mController.setIcon(pref, 1, true /* isDefaultForData */);
378         verify(mController).getIcon(eq(0), eq(NUM_SIGNAL_STRENGTH_BINS), eq(false));
379 
380         mController.setIcon(pref, 2, false /* isDefaultForData */);
381         verify(mController).getIcon(eq(0), eq(NUM_SIGNAL_STRENGTH_BINS), eq(true));
382     }
383 
384     @Test
setIcon_noSignal_withInflation_correctLevels()385     public void setIcon_noSignal_withInflation_correctLevels() {
386         final List<SubscriptionInfo> subs = setupMockSubscriptions(2, 1, true);
387         setMockSubSignalStrength(subs, 0, SIGNAL_STRENGTH_NONE_OR_UNKNOWN);
388         setMockSubSignalStrength(subs, 1, SIGNAL_STRENGTH_NONE_OR_UNKNOWN);
389         final Preference pref = mock(Preference.class);
390         doReturn(true).when(mController).shouldInflateSignalStrength(anyInt());
391 
392         mController.setIcon(pref, 1, true /* isDefaultForData */);
393         verify(mController).getIcon(eq(1), eq(NUM_SIGNAL_STRENGTH_BINS + 1), eq(false));
394 
395         mController.setIcon(pref, 2, false /* isDefaultForData */);
396         verify(mController).getIcon(eq(1), eq(NUM_SIGNAL_STRENGTH_BINS + 1), eq(true));
397     }
398 
399     @Test
setIcon_greatSignal_correctLevels()400     public void setIcon_greatSignal_correctLevels() {
401         final List<SubscriptionInfo> subs = setupMockSubscriptions(2, 1, true);
402         setMockSubSignalStrength(subs, 0, SIGNAL_STRENGTH_GREAT);
403         setMockSubSignalStrength(subs, 1, SIGNAL_STRENGTH_GREAT);
404         final Preference pref = mock(Preference.class);
405 
406         mController.setIcon(pref, 1, true /* isDefaultForData */);
407         verify(mController).getIcon(eq(4), eq(NUM_SIGNAL_STRENGTH_BINS), eq(false));
408 
409         mController.setIcon(pref, 2, false /* isDefaultForData */);
410         verify(mController).getIcon(eq(4), eq(NUM_SIGNAL_STRENGTH_BINS), eq(true));
411     }
412 
413     @Test
onSignalStrengthChanged_subTwoGoesFromGoodToGreat_correctLevels()414     public void onSignalStrengthChanged_subTwoGoesFromGoodToGreat_correctLevels() {
415         final List<SubscriptionInfo> subs = setupMockSubscriptions(2);
416         setMockSubSignalStrength(subs, 0, SIGNAL_STRENGTH_POOR);
417         setMockSubSignalStrength(subs, 1, SIGNAL_STRENGTH_GOOD);
418 
419         mController.onResume();
420         mController.displayPreference(mScreen);
421 
422         // Now change the signal strength for the 2nd subscription from Good to Great
423         setMockSubSignalStrength(subs, 1, SIGNAL_STRENGTH_GREAT);
424         mController.onSignalStrengthChanged();
425 
426         final ArgumentCaptor<Integer> level = ArgumentCaptor.forClass(Integer.class);
427         verify(mController, times(4)).getIcon(level.capture(), eq(NUM_SIGNAL_STRENGTH_BINS),
428                 eq(true));
429         assertThat(level.getAllValues().get(0)).isEqualTo(1);
430         assertThat(level.getAllValues().get(1)).isEqualTo(3); // sub2, first time
431         assertThat(level.getAllValues().get(2)).isEqualTo(1);
432         assertThat(level.getAllValues().get(3)).isEqualTo(4); // sub2, after change
433     }
434 
435     @Test
displayPreference_mobileDataOff_bothSubsHaveCutOut()436     public void displayPreference_mobileDataOff_bothSubsHaveCutOut() {
437         setupMockSubscriptions(2, 1, false);
438 
439         mController.onResume();
440         mController.displayPreference(mScreen);
441 
442         verify(mController, times(2)).getIcon(eq(SIGNAL_STRENGTH_GOOD),
443                 eq(NUM_SIGNAL_STRENGTH_BINS), eq(true));
444     }
445 
446     @Test
displayPreference_mobileDataOn_onlyNonDefaultSubHasCutOut()447     public void displayPreference_mobileDataOn_onlyNonDefaultSubHasCutOut() {
448         final List<SubscriptionInfo> subs = setupMockSubscriptions(2, 1, true);
449         setMockSubSignalStrength(subs, 1, SIGNAL_STRENGTH_POOR);
450 
451         mController.onResume();
452         mController.displayPreference(mScreen);
453 
454         verify(mController).getIcon(eq(SIGNAL_STRENGTH_GOOD), eq(NUM_SIGNAL_STRENGTH_BINS),
455                 eq(false));
456         verify(mController).getIcon(eq(SIGNAL_STRENGTH_POOR), eq(NUM_SIGNAL_STRENGTH_BINS),
457                 eq(true));
458     }
459 
460 
461     @Test
onMobileDataEnabledChange_mobileDataTurnedOff_bothSubsHaveCutOut()462     public void onMobileDataEnabledChange_mobileDataTurnedOff_bothSubsHaveCutOut() {
463         final List<SubscriptionInfo> subs = setupMockSubscriptions(2, 1, true);
464 
465         mController.onResume();
466         mController.displayPreference(mScreen);
467 
468         setMockSubDataEnabled(subs, 0, false);
469         mController.onMobileDataEnabledChange();
470 
471         final ArgumentCaptor<Boolean> cutOutCaptor = ArgumentCaptor.forClass(Boolean.class);
472         verify(mController, times(4)).getIcon(eq(SIGNAL_STRENGTH_GOOD),
473                 eq(NUM_SIGNAL_STRENGTH_BINS), cutOutCaptor.capture());
474         assertThat(cutOutCaptor.getAllValues().get(0)).isEqualTo(false); // sub1, first time
475         assertThat(cutOutCaptor.getAllValues().get(1)).isEqualTo(true);
476         assertThat(cutOutCaptor.getAllValues().get(2)).isEqualTo(true); // sub1, second time
477         assertThat(cutOutCaptor.getAllValues().get(3)).isEqualTo(true);
478     }
479 
setupMockSubscriptions(int count)480     private List<SubscriptionInfo> setupMockSubscriptions(int count) {
481         return setupMockSubscriptions(count, 0, true);
482     }
483 
484     /** Helper method to setup several mock active subscriptions. The generated subscription id's
485      * start at 1.
486      *
487      * @param count How many subscriptions to create
488      * @param defaultDataSubId The subscription id of the default data subscription - pass
489      *                         INVALID_SUBSCRIPTION_ID if there should not be one
490      * @param mobileDataEnabled Whether mobile data should be considered enabled for the default
491      *                          data subscription
492      */
setupMockSubscriptions(int count, int defaultDataSubId, boolean mobileDataEnabled)493     private List<SubscriptionInfo> setupMockSubscriptions(int count, int defaultDataSubId,
494             boolean mobileDataEnabled) {
495         if (defaultDataSubId != INVALID_SUBSCRIPTION_ID) {
496             ShadowSubscriptionManager.setDefaultDataSubscriptionId(defaultDataSubId);
497         }
498         final ArrayList<SubscriptionInfo> infos = new ArrayList<>();
499         for (int i = 0; i < count; i++) {
500             final int subscriptionId = i + 1;
501             final SubscriptionInfo info = mock(SubscriptionInfo.class);
502             final TelephonyManager mgrForSub = mock(TelephonyManager.class);
503             final SignalStrength signalStrength = mock(SignalStrength.class);
504 
505             if (subscriptionId == defaultDataSubId) {
506                 when(mgrForSub.isDataEnabled()).thenReturn(mobileDataEnabled);
507             }
508             when(info.getSubscriptionId()).thenReturn(i + 1);
509             when(info.getDisplayName()).thenReturn("sub" + (i + 1));
510             doReturn(mgrForSub).when(mTelephonyManager).createForSubscriptionId(eq(subscriptionId));
511             when(mgrForSub.getSignalStrength()).thenReturn(signalStrength);
512             when(signalStrength.getLevel()).thenReturn(SIGNAL_STRENGTH_GOOD);
513 
514             infos.add(info);
515         }
516         SubscriptionUtil.setActiveSubscriptionsForTesting(infos);
517         return infos;
518     }
519 
520     /**
521      * Helper method to set the signal strength returned for a mock subscription
522      * @param subs The list of subscriptions
523      * @param index The index in of the subscription in |subs| to change
524      * @param level The signal strength level to return for the subscription. Pass -1 to force
525      *              return of a null SignalStrength object for the subscription.
526      */
setMockSubSignalStrength(List<SubscriptionInfo> subs, int index, int level)527     private void setMockSubSignalStrength(List<SubscriptionInfo> subs, int index, int level) {
528         final TelephonyManager mgrForSub =
529                 mTelephonyManager.createForSubscriptionId(subs.get(index).getSubscriptionId());
530         if (level == -1) {
531             when(mgrForSub.getSignalStrength()).thenReturn(null);
532         } else {
533             final SignalStrength signalStrength = mgrForSub.getSignalStrength();
534             when(signalStrength.getLevel()).thenReturn(level);
535         }
536     }
537 
setMockSubDataEnabled(List<SubscriptionInfo> subs, int index, boolean enabled)538     private void setMockSubDataEnabled(List<SubscriptionInfo> subs, int index, boolean enabled) {
539         final TelephonyManager mgrForSub =
540                 mTelephonyManager.createForSubscriptionId(subs.get(index).getSubscriptionId());
541         when(mgrForSub.isDataEnabled()).thenReturn(enabled);
542     }
543 }
544