1 /*
2  * Copyright (C) 2022 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.systemui.statusbar.pipeline.mobile.domain.interactor
18 
19 import android.telephony.CellSignalStrength
20 import android.telephony.TelephonyManager.NETWORK_TYPE_UNKNOWN
21 import androidx.test.filters.SmallTest
22 import com.android.settingslib.mobile.MobileIconCarrierIdOverrides
23 import com.android.settingslib.mobile.MobileIconCarrierIdOverridesImpl
24 import com.android.settingslib.mobile.TelephonyIcons
25 import com.android.systemui.SysuiTestCase
26 import com.android.systemui.coroutines.collectLastValue
27 import com.android.systemui.statusbar.pipeline.mobile.data.model.DataConnectionState
28 import com.android.systemui.statusbar.pipeline.mobile.data.model.NetworkNameModel
29 import com.android.systemui.statusbar.pipeline.mobile.data.model.ResolvedNetworkType.CarrierMergedNetworkType
30 import com.android.systemui.statusbar.pipeline.mobile.data.model.ResolvedNetworkType.DefaultNetworkType
31 import com.android.systemui.statusbar.pipeline.mobile.data.model.ResolvedNetworkType.OverrideNetworkType
32 import com.android.systemui.statusbar.pipeline.mobile.data.model.SubscriptionModel
33 import com.android.systemui.statusbar.pipeline.mobile.data.repository.FakeMobileConnectionRepository
34 import com.android.systemui.statusbar.pipeline.mobile.domain.interactor.FakeMobileIconsInteractor.Companion.FIVE_G_OVERRIDE
35 import com.android.systemui.statusbar.pipeline.mobile.domain.interactor.FakeMobileIconsInteractor.Companion.FOUR_G
36 import com.android.systemui.statusbar.pipeline.mobile.domain.interactor.FakeMobileIconsInteractor.Companion.THREE_G
37 import com.android.systemui.statusbar.pipeline.mobile.domain.model.NetworkTypeIconModel
38 import com.android.systemui.statusbar.pipeline.mobile.domain.model.SignalIconModel
39 import com.android.systemui.statusbar.pipeline.mobile.util.FakeMobileMappingsProxy
40 import com.android.systemui.util.mockito.any
41 import com.android.systemui.util.mockito.mock
42 import com.android.systemui.util.mockito.whenever
43 import com.google.common.truth.Truth.assertThat
44 import kotlinx.coroutines.ExperimentalCoroutinesApi
45 import kotlinx.coroutines.flow.MutableStateFlow
46 import kotlinx.coroutines.flow.launchIn
47 import kotlinx.coroutines.flow.onEach
48 import kotlinx.coroutines.test.TestScope
49 import kotlinx.coroutines.test.UnconfinedTestDispatcher
50 import kotlinx.coroutines.test.runTest
51 import org.junit.Before
52 import org.junit.Test
53 import org.mockito.ArgumentMatchers.anyInt
54 import org.mockito.ArgumentMatchers.anyString
55 
56 @OptIn(ExperimentalCoroutinesApi::class)
57 @SmallTest
58 class MobileIconInteractorTest : SysuiTestCase() {
59     private lateinit var underTest: MobileIconInteractor
60     private val mobileMappingsProxy = FakeMobileMappingsProxy()
61     private val mobileIconsInteractor = FakeMobileIconsInteractor(mobileMappingsProxy, mock())
62 
63     private val subscriptionModel =
64         MutableStateFlow(
65             SubscriptionModel(
66                 subscriptionId = SUB_1_ID,
67                 carrierName = DEFAULT_NAME,
68             )
69         )
70 
71     private val connectionRepository = FakeMobileConnectionRepository(SUB_1_ID, mock())
72 
73     private val testDispatcher = UnconfinedTestDispatcher()
74     private val testScope = TestScope(testDispatcher)
75 
76     @Before
77     fun setUp() {
78         underTest = createInteractor()
79 
80         mobileIconsInteractor.activeDataConnectionHasDataEnabled.value = true
81         connectionRepository.isInService.value = true
82     }
83 
84     @Test
85     fun gsm_usesGsmLevel() =
86         testScope.runTest {
87             connectionRepository.isGsm.value = true
88             connectionRepository.primaryLevel.value = GSM_LEVEL
89             connectionRepository.cdmaLevel.value = CDMA_LEVEL
90 
91             var latest: Int? = null
92             val job = underTest.signalLevelIcon.onEach { latest = it.level }.launchIn(this)
93 
94             assertThat(latest).isEqualTo(GSM_LEVEL)
95 
96             job.cancel()
97         }
98 
99     @Test
100     fun gsm_alwaysShowCdmaTrue_stillUsesGsmLevel() =
101         testScope.runTest {
102             connectionRepository.isGsm.value = true
103             connectionRepository.primaryLevel.value = GSM_LEVEL
104             connectionRepository.cdmaLevel.value = CDMA_LEVEL
105             mobileIconsInteractor.alwaysUseCdmaLevel.value = true
106 
107             var latest: Int? = null
108             val job = underTest.signalLevelIcon.onEach { latest = it.level }.launchIn(this)
109 
110             assertThat(latest).isEqualTo(GSM_LEVEL)
111 
112             job.cancel()
113         }
114 
115     @Test
116     fun notGsm_level_default_unknown() =
117         testScope.runTest {
118             connectionRepository.isGsm.value = false
119 
120             var latest: Int? = null
121             val job = underTest.signalLevelIcon.onEach { latest = it.level }.launchIn(this)
122 
123             assertThat(latest).isEqualTo(CellSignalStrength.SIGNAL_STRENGTH_NONE_OR_UNKNOWN)
124             job.cancel()
125         }
126 
127     @Test
128     fun notGsm_alwaysShowCdmaTrue_usesCdmaLevel() =
129         testScope.runTest {
130             connectionRepository.isGsm.value = false
131             connectionRepository.primaryLevel.value = GSM_LEVEL
132             connectionRepository.cdmaLevel.value = CDMA_LEVEL
133             mobileIconsInteractor.alwaysUseCdmaLevel.value = true
134 
135             var latest: Int? = null
136             val job = underTest.signalLevelIcon.onEach { latest = it.level }.launchIn(this)
137 
138             assertThat(latest).isEqualTo(CDMA_LEVEL)
139 
140             job.cancel()
141         }
142 
143     @Test
144     fun notGsm_alwaysShowCdmaFalse_usesPrimaryLevel() =
145         testScope.runTest {
146             connectionRepository.isGsm.value = false
147             connectionRepository.primaryLevel.value = GSM_LEVEL
148             connectionRepository.cdmaLevel.value = CDMA_LEVEL
149             mobileIconsInteractor.alwaysUseCdmaLevel.value = false
150 
151             var latest: Int? = null
152             val job = underTest.signalLevelIcon.onEach { latest = it.level }.launchIn(this)
153 
154             assertThat(latest).isEqualTo(GSM_LEVEL)
155 
156             job.cancel()
157         }
158 
159     @Test
160     fun numberOfLevels_comesFromRepo() =
161         testScope.runTest {
162             var latest: Int? = null
163             val job = underTest.signalLevelIcon.onEach { latest = it.numberOfLevels }.launchIn(this)
164 
165             connectionRepository.numberOfLevels.value = 5
166             assertThat(latest).isEqualTo(5)
167 
168             connectionRepository.numberOfLevels.value = 4
169             assertThat(latest).isEqualTo(4)
170 
171             job.cancel()
172         }
173 
174     @Test
175     fun iconGroup_three_g() =
176         testScope.runTest {
177             connectionRepository.resolvedNetworkType.value =
178                 DefaultNetworkType(mobileMappingsProxy.toIconKey(THREE_G))
179 
180             var latest: NetworkTypeIconModel? = null
181             val job = underTest.networkTypeIconGroup.onEach { latest = it }.launchIn(this)
182 
183             assertThat(latest).isEqualTo(NetworkTypeIconModel.DefaultIcon(TelephonyIcons.THREE_G))
184 
185             job.cancel()
186         }
187 
188     @Test
189     fun iconGroup_updates_on_change() =
190         testScope.runTest {
191             connectionRepository.resolvedNetworkType.value =
192                 DefaultNetworkType(mobileMappingsProxy.toIconKey(THREE_G))
193 
194             var latest: NetworkTypeIconModel? = null
195             val job = underTest.networkTypeIconGroup.onEach { latest = it }.launchIn(this)
196 
197             connectionRepository.resolvedNetworkType.value =
198                 DefaultNetworkType(mobileMappingsProxy.toIconKey(FOUR_G))
199 
200             assertThat(latest).isEqualTo(NetworkTypeIconModel.DefaultIcon(TelephonyIcons.FOUR_G))
201 
202             job.cancel()
203         }
204 
205     @Test
206     fun iconGroup_5g_override_type() =
207         testScope.runTest {
208             connectionRepository.resolvedNetworkType.value =
209                 OverrideNetworkType(mobileMappingsProxy.toIconKeyOverride(FIVE_G_OVERRIDE))
210 
211             var latest: NetworkTypeIconModel? = null
212             val job = underTest.networkTypeIconGroup.onEach { latest = it }.launchIn(this)
213 
214             assertThat(latest).isEqualTo(NetworkTypeIconModel.DefaultIcon(TelephonyIcons.NR_5G))
215 
216             job.cancel()
217         }
218 
219     @Test
220     fun iconGroup_default_if_no_lookup() =
221         testScope.runTest {
222             connectionRepository.resolvedNetworkType.value =
223                 DefaultNetworkType(mobileMappingsProxy.toIconKey(NETWORK_TYPE_UNKNOWN))
224 
225             var latest: NetworkTypeIconModel? = null
226             val job = underTest.networkTypeIconGroup.onEach { latest = it }.launchIn(this)
227 
228             assertThat(latest)
229                 .isEqualTo(NetworkTypeIconModel.DefaultIcon(FakeMobileIconsInteractor.DEFAULT_ICON))
230 
231             job.cancel()
232         }
233 
234     @Test
235     fun iconGroup_carrierMerged_usesOverride() =
236         testScope.runTest {
237             connectionRepository.resolvedNetworkType.value = CarrierMergedNetworkType
238 
239             var latest: NetworkTypeIconModel? = null
240             val job = underTest.networkTypeIconGroup.onEach { latest = it }.launchIn(this)
241 
242             assertThat(latest)
243                 .isEqualTo(
244                     NetworkTypeIconModel.DefaultIcon(CarrierMergedNetworkType.iconGroupOverride)
245                 )
246 
247             job.cancel()
248         }
249 
250     @Test
251     fun overrideIcon_usesCarrierIdOverride() =
252         testScope.runTest {
253             val overrides =
254                 mock<MobileIconCarrierIdOverrides>().also {
255                     whenever(it.carrierIdEntryExists(anyInt())).thenReturn(true)
256                     whenever(it.getOverrideFor(anyInt(), anyString(), any())).thenReturn(1234)
257                 }
258 
259             underTest = createInteractor(overrides)
260 
261             connectionRepository.resolvedNetworkType.value =
262                 DefaultNetworkType(mobileMappingsProxy.toIconKey(THREE_G))
263 
264             var latest: NetworkTypeIconModel? = null
265             val job = underTest.networkTypeIconGroup.onEach { latest = it }.launchIn(this)
266 
267             assertThat(latest)
268                 .isEqualTo(NetworkTypeIconModel.OverriddenIcon(TelephonyIcons.THREE_G, 1234))
269 
270             job.cancel()
271         }
272 
273     @Test
274     fun alwaysShowDataRatIcon_matchesParent() =
275         testScope.runTest {
276             var latest: Boolean? = null
277             val job = underTest.alwaysShowDataRatIcon.onEach { latest = it }.launchIn(this)
278 
279             mobileIconsInteractor.alwaysShowDataRatIcon.value = true
280             assertThat(latest).isTrue()
281 
282             mobileIconsInteractor.alwaysShowDataRatIcon.value = false
283             assertThat(latest).isFalse()
284 
285             job.cancel()
286         }
287 
288     @Test
289     fun dataState_connected() =
290         testScope.runTest {
291             var latest: Boolean? = null
292             val job = underTest.isDataConnected.onEach { latest = it }.launchIn(this)
293 
294             connectionRepository.dataConnectionState.value = DataConnectionState.Connected
295 
296             assertThat(latest).isTrue()
297 
298             job.cancel()
299         }
300 
301     @Test
302     fun dataState_notConnected() =
303         testScope.runTest {
304             var latest: Boolean? = null
305             val job = underTest.isDataConnected.onEach { latest = it }.launchIn(this)
306 
307             connectionRepository.dataConnectionState.value = DataConnectionState.Disconnected
308 
309             assertThat(latest).isFalse()
310 
311             job.cancel()
312         }
313 
314     @Test
315     fun isInService_usesRepositoryValue() =
316         testScope.runTest {
317             var latest: Boolean? = null
318             val job = underTest.isInService.onEach { latest = it }.launchIn(this)
319 
320             connectionRepository.isInService.value = true
321 
322             assertThat(latest).isTrue()
323 
324             connectionRepository.isInService.value = false
325 
326             assertThat(latest).isFalse()
327 
328             job.cancel()
329         }
330 
331     @Test
332     fun roaming_isGsm_usesConnectionModel() =
333         testScope.runTest {
334             var latest: Boolean? = null
335             val job = underTest.isRoaming.onEach { latest = it }.launchIn(this)
336 
337             connectionRepository.cdmaRoaming.value = true
338             connectionRepository.isGsm.value = true
339             connectionRepository.isRoaming.value = false
340 
341             assertThat(latest).isFalse()
342 
343             connectionRepository.isRoaming.value = true
344 
345             assertThat(latest).isTrue()
346 
347             job.cancel()
348         }
349 
350     @Test
351     fun roaming_isCdma_usesCdmaRoamingBit() =
352         testScope.runTest {
353             var latest: Boolean? = null
354             val job = underTest.isRoaming.onEach { latest = it }.launchIn(this)
355 
356             connectionRepository.cdmaRoaming.value = false
357             connectionRepository.isGsm.value = false
358             connectionRepository.isRoaming.value = true
359 
360             assertThat(latest).isFalse()
361 
362             connectionRepository.cdmaRoaming.value = true
363             connectionRepository.isGsm.value = false
364             connectionRepository.isRoaming.value = false
365 
366             assertThat(latest).isTrue()
367 
368             job.cancel()
369         }
370 
371     @Test
372     fun roaming_falseWhileCarrierNetworkChangeActive() =
373         testScope.runTest {
374             var latest: Boolean? = null
375             val job = underTest.isRoaming.onEach { latest = it }.launchIn(this)
376 
377             connectionRepository.cdmaRoaming.value = true
378             connectionRepository.isGsm.value = false
379             connectionRepository.isRoaming.value = true
380             connectionRepository.carrierNetworkChangeActive.value = true
381 
382             assertThat(latest).isFalse()
383 
384             connectionRepository.cdmaRoaming.value = true
385             connectionRepository.isGsm.value = true
386 
387             assertThat(latest).isFalse()
388 
389             job.cancel()
390         }
391 
392     @Test
393     fun networkName_usesOperatorAlphaShortWhenNonNullAndRepoIsDefault() =
394         testScope.runTest {
395             var latest: NetworkNameModel? = null
396             val job = underTest.networkName.onEach { latest = it }.launchIn(this)
397 
398             val testOperatorName = "operatorAlphaShort"
399 
400             // Default network name, operator name is non-null, uses the operator name
401             connectionRepository.networkName.value = DEFAULT_NAME_MODEL
402             connectionRepository.operatorAlphaShort.value = testOperatorName
403 
404             assertThat(latest).isEqualTo(NetworkNameModel.IntentDerived(testOperatorName))
405 
406             // Default network name, operator name is null, uses the default
407             connectionRepository.operatorAlphaShort.value = null
408 
409             assertThat(latest).isEqualTo(DEFAULT_NAME_MODEL)
410 
411             // Derived network name, operator name non-null, uses the derived name
412             connectionRepository.networkName.value = DERIVED_NAME_MODEL
413             connectionRepository.operatorAlphaShort.value = testOperatorName
414 
415             assertThat(latest).isEqualTo(DERIVED_NAME_MODEL)
416 
417             job.cancel()
418         }
419 
420     @Test
421     fun networkNameForSubId_usesOperatorAlphaShortWhenNonNullAndRepoIsDefault() =
422         testScope.runTest {
423             var latest: String? = null
424             val job = underTest.carrierName.onEach { latest = it }.launchIn(this)
425 
426             val testOperatorName = "operatorAlphaShort"
427 
428             // Default network name, operator name is non-null, uses the operator name
429             connectionRepository.carrierName.value = DEFAULT_NAME_MODEL
430             connectionRepository.operatorAlphaShort.value = testOperatorName
431 
432             assertThat(latest).isEqualTo(testOperatorName)
433 
434             // Default network name, operator name is null, uses the default
435             connectionRepository.operatorAlphaShort.value = null
436 
437             assertThat(latest).isEqualTo(DEFAULT_NAME)
438 
439             // Derived network name, operator name non-null, uses the derived name
440             connectionRepository.carrierName.value =
441                 NetworkNameModel.SubscriptionDerived(DERIVED_NAME)
442             connectionRepository.operatorAlphaShort.value = testOperatorName
443 
444             assertThat(latest).isEqualTo(DERIVED_NAME)
445 
446             job.cancel()
447         }
448 
449     @Test
450     fun isSingleCarrier_matchesParent() =
451         testScope.runTest {
452             var latest: Boolean? = null
453             val job = underTest.isSingleCarrier.onEach { latest = it }.launchIn(this)
454 
455             mobileIconsInteractor.isSingleCarrier.value = true
456             assertThat(latest).isTrue()
457 
458             mobileIconsInteractor.isSingleCarrier.value = false
459             assertThat(latest).isFalse()
460 
461             job.cancel()
462         }
463 
464     @Test
465     fun isForceHidden_matchesParent() =
466         testScope.runTest {
467             var latest: Boolean? = null
468             val job = underTest.isForceHidden.onEach { latest = it }.launchIn(this)
469 
470             mobileIconsInteractor.isForceHidden.value = true
471             assertThat(latest).isTrue()
472 
473             mobileIconsInteractor.isForceHidden.value = false
474             assertThat(latest).isFalse()
475 
476             job.cancel()
477         }
478 
479     @Test
480     fun isAllowedDuringAirplaneMode_matchesRepo() =
481         testScope.runTest {
482             val latest by collectLastValue(underTest.isAllowedDuringAirplaneMode)
483 
484             connectionRepository.isAllowedDuringAirplaneMode.value = true
485             assertThat(latest).isTrue()
486 
487             connectionRepository.isAllowedDuringAirplaneMode.value = false
488             assertThat(latest).isFalse()
489         }
490 
491     @Test
492     fun iconId_correctLevel_notCutout() =
493         testScope.runTest {
494             connectionRepository.isInService.value = true
495             connectionRepository.primaryLevel.value = 1
496             connectionRepository.setDataEnabled(false)
497 
498             var latest: SignalIconModel? = null
499             val job = underTest.signalLevelIcon.onEach { latest = it }.launchIn(this)
500 
501             assertThat(latest?.level).isEqualTo(1)
502             assertThat(latest?.showExclamationMark).isFalse()
503 
504             job.cancel()
505         }
506 
507     @Test
508     fun icon_usesLevelFromInteractor() =
509         testScope.runTest {
510             connectionRepository.isInService.value = true
511 
512             var latest: SignalIconModel? = null
513             val job = underTest.signalLevelIcon.onEach { latest = it }.launchIn(this)
514 
515             connectionRepository.primaryLevel.value = 3
516             assertThat(latest!!.level).isEqualTo(3)
517 
518             connectionRepository.primaryLevel.value = 1
519             assertThat(latest!!.level).isEqualTo(1)
520 
521             job.cancel()
522         }
523 
524     @Test
525     fun icon_usesNumberOfLevelsFromInteractor() =
526         testScope.runTest {
527             var latest: SignalIconModel? = null
528             val job = underTest.signalLevelIcon.onEach { latest = it }.launchIn(this)
529 
530             connectionRepository.numberOfLevels.value = 5
531             assertThat(latest!!.numberOfLevels).isEqualTo(5)
532 
533             connectionRepository.numberOfLevels.value = 2
534             assertThat(latest!!.numberOfLevels).isEqualTo(2)
535 
536             job.cancel()
537         }
538 
539     @Test
540     fun icon_defaultDataDisabled_showExclamationTrue() =
541         testScope.runTest {
542             mobileIconsInteractor.activeDataConnectionHasDataEnabled.value = false
543 
544             var latest: SignalIconModel? = null
545             val job = underTest.signalLevelIcon.onEach { latest = it }.launchIn(this)
546 
547             assertThat(latest!!.showExclamationMark).isTrue()
548 
549             job.cancel()
550         }
551 
552     @Test
553     fun icon_defaultConnectionFailed_showExclamationTrue() =
554         testScope.runTest {
555             mobileIconsInteractor.isDefaultConnectionFailed.value = true
556 
557             var latest: SignalIconModel? = null
558             val job = underTest.signalLevelIcon.onEach { latest = it }.launchIn(this)
559 
560             assertThat(latest!!.showExclamationMark).isTrue()
561 
562             job.cancel()
563         }
564 
565     @Test
566     fun icon_enabledAndNotFailed_showExclamationFalse() =
567         testScope.runTest {
568             connectionRepository.isInService.value = true
569             mobileIconsInteractor.activeDataConnectionHasDataEnabled.value = true
570             mobileIconsInteractor.isDefaultConnectionFailed.value = false
571 
572             var latest: SignalIconModel? = null
573             val job = underTest.signalLevelIcon.onEach { latest = it }.launchIn(this)
574 
575             assertThat(latest!!.showExclamationMark).isFalse()
576 
577             job.cancel()
578         }
579 
580     @Test
581     fun icon_usesEmptyState_whenNotInService() =
582         testScope.runTest {
583             var latest: SignalIconModel? = null
584             val job = underTest.signalLevelIcon.onEach { latest = it }.launchIn(this)
585 
586             connectionRepository.isInService.value = false
587 
588             assertThat(latest?.level).isEqualTo(0)
589             assertThat(latest?.showExclamationMark).isTrue()
590 
591             // Changing the level doesn't overwrite the disabled state
592             connectionRepository.primaryLevel.value = 2
593             assertThat(latest?.level).isEqualTo(0)
594             assertThat(latest?.showExclamationMark).isTrue()
595 
596             // Once back in service, the regular icon appears
597             connectionRepository.isInService.value = true
598             assertThat(latest?.level).isEqualTo(2)
599             assertThat(latest?.showExclamationMark).isFalse()
600 
601             job.cancel()
602         }
603 
604     @Test
605     fun icon_usesCarrierNetworkState_whenInCarrierNetworkChangeMode() =
606         testScope.runTest {
607             var latest: SignalIconModel? = null
608             val job = underTest.signalLevelIcon.onEach { latest = it }.launchIn(this)
609 
610             connectionRepository.isInService.value = true
611             connectionRepository.carrierNetworkChangeActive.value = true
612             connectionRepository.primaryLevel.value = 1
613             connectionRepository.cdmaLevel.value = 1
614 
615             assertThat(latest!!.level).isEqualTo(1)
616             assertThat(latest!!.carrierNetworkChange).isTrue()
617 
618             // SignalIconModel respects the current level
619             connectionRepository.primaryLevel.value = 2
620 
621             assertThat(latest!!.level).isEqualTo(2)
622             assertThat(latest!!.carrierNetworkChange).isTrue()
623 
624             job.cancel()
625         }
626 
627     private fun createInteractor(
628         overrides: MobileIconCarrierIdOverrides = MobileIconCarrierIdOverridesImpl()
629     ) =
630         MobileIconInteractorImpl(
631             testScope.backgroundScope,
632             mobileIconsInteractor.activeDataConnectionHasDataEnabled,
633             mobileIconsInteractor.alwaysShowDataRatIcon,
634             mobileIconsInteractor.alwaysUseCdmaLevel,
635             mobileIconsInteractor.isSingleCarrier,
636             mobileIconsInteractor.mobileIsDefault,
637             mobileIconsInteractor.defaultMobileIconMapping,
638             mobileIconsInteractor.defaultMobileIconGroup,
639             mobileIconsInteractor.isDefaultConnectionFailed,
640             mobileIconsInteractor.isForceHidden,
641             connectionRepository,
642             context,
643             overrides,
644         )
645 
646     companion object {
647         private const val GSM_LEVEL = 1
648         private const val CDMA_LEVEL = 2
649 
650         private const val SUB_1_ID = 1
651 
652         private val DEFAULT_NAME = "test default name"
653         private val DEFAULT_NAME_MODEL = NetworkNameModel.Default(DEFAULT_NAME)
654         private val DERIVED_NAME = "test derived name"
655         private val DERIVED_NAME_MODEL = NetworkNameModel.IntentDerived(DERIVED_NAME)
656     }
657 }
658