• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2024 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.phone.satellite.entitlement;
18 
19 import static com.android.libraries.entitlement.ServiceEntitlementException.ERROR_HTTP_STATUS_NOT_SUCCESS;
20 import static com.android.phone.satellite.entitlement.SatelliteEntitlementResult.SATELLITE_ENTITLEMENT_STATUS_DISABLED;
21 import static com.android.phone.satellite.entitlement.SatelliteEntitlementResult.SATELLITE_ENTITLEMENT_STATUS_ENABLED;
22 
23 import static org.junit.Assert.assertNotNull;
24 import static org.junit.Assert.assertNull;
25 import static org.junit.Assert.assertTrue;
26 import static org.mockito.ArgumentMatchers.any;
27 import static org.mockito.ArgumentMatchers.anyBoolean;
28 import static org.mockito.ArgumentMatchers.anyInt;
29 import static org.mockito.ArgumentMatchers.anyList;
30 import static org.mockito.ArgumentMatchers.anyVararg;
31 import static org.mockito.Mockito.clearInvocations;
32 import static org.mockito.Mockito.doAnswer;
33 import static org.mockito.Mockito.doReturn;
34 import static org.mockito.Mockito.eq;
35 import static org.mockito.Mockito.mock;
36 import static org.mockito.Mockito.never;
37 import static org.mockito.Mockito.reset;
38 import static org.mockito.Mockito.spy;
39 import static org.mockito.Mockito.times;
40 import static org.mockito.Mockito.verify;
41 import static org.mockito.Mockito.when;
42 
43 import android.content.Context;
44 import android.net.ConnectivityManager;
45 import android.net.Network;
46 import android.net.NetworkCapabilities;
47 import android.net.wifi.WifiInfo;
48 import android.os.Handler;
49 import android.os.HandlerThread;
50 import android.os.Looper;
51 import android.os.Message;
52 import android.os.PersistableBundle;
53 import android.telephony.CarrierConfigManager;
54 import android.telephony.TelephonyManager;
55 import android.testing.TestableLooper;
56 import android.util.Log;
57 import android.util.Pair;
58 
59 import androidx.annotation.NonNull;
60 import androidx.test.ext.junit.runners.AndroidJUnit4;
61 
62 import com.android.TelephonyTestBase;
63 import com.android.internal.telephony.ExponentialBackoff;
64 import com.android.internal.telephony.satellite.SatelliteController;
65 import com.android.internal.telephony.subscription.SubscriptionManagerService;
66 import com.android.libraries.entitlement.ServiceEntitlementException;
67 
68 import org.junit.After;
69 import org.junit.Before;
70 import org.junit.Test;
71 import org.junit.runner.RunWith;
72 import org.mockito.Mock;
73 import org.mockito.MockitoAnnotations;
74 import org.mockito.invocation.InvocationOnMock;
75 import org.mockito.stubbing.Answer;
76 
77 import java.lang.reflect.Field;
78 import java.util.ArrayList;
79 import java.util.Arrays;
80 import java.util.HashMap;
81 import java.util.List;
82 import java.util.Map;
83 import java.util.concurrent.Executor;
84 import java.util.concurrent.TimeUnit;
85 
86 @RunWith(AndroidJUnit4.class)
87 public class SatelliteEntitlementControllerTest extends TelephonyTestBase {
88     private static final String TAG = "SatelliteEntitlementControllerTest";
89     private static final int SUB_ID = 0;
90     private static final int SUB_ID_2 = 1;
91     private static final int[] ACTIVE_SUB_ID = {SUB_ID};
92     private static final int DEFAULT_QUERY_REFRESH_DAY = 7;
93     private static final List<String> PLMN_ALLOWED_LIST = Arrays.asList("31026", "302820");
94     private static final List<String> PLMN_BARRED_LIST = Arrays.asList("12345", "98765");
95     private static final List<String> EMPTY_PLMN_LIST = new ArrayList<>();
96     private static final int CMD_START_QUERY_ENTITLEMENT = 1;
97     private static final int CMD_RETRY_QUERY_ENTITLEMENT = 2;
98     private static final int CMD_SIM_REFRESH = 3;
99     private static final int MAX_RETRY_COUNT = 5;
100     @Mock
101     CarrierConfigManager mCarrierConfigManager;
102     @Mock
103     ConnectivityManager mConnectivityManager;
104     @Mock Network mNetwork;
105     @Mock TelephonyManager mTelephonyManager;
106     @Mock SubscriptionManagerService mMockSubscriptionManagerService;
107     @Mock SatelliteEntitlementApi mSatelliteEntitlementApi;
108     @Mock SatelliteEntitlementResult mSatelliteEntitlementResult;
109     @Mock SatelliteController mSatelliteController;
110     private PersistableBundle mCarrierConfigBundle;
111     private TestSatelliteEntitlementController mSatelliteEntitlementController;
112     private Handler mHandler;
113     private TestableLooper mTestableLooper;
114     private List<Pair<Executor, CarrierConfigManager.CarrierConfigChangeListener>>
115             mCarrierConfigChangedListenerList = new ArrayList<>();
116     @Before
setUp()117     public void setUp() throws Exception {
118         super.setUp();
119         MockitoAnnotations.initMocks(this);
120 
121         replaceInstance(SubscriptionManagerService.class, "sInstance", null,
122                 mMockSubscriptionManagerService);
123         replaceInstance(SatelliteController.class, "sInstance", null, mSatelliteController);
124 
125         HandlerThread handlerThread = new HandlerThread("SatelliteEntitlementController");
126         handlerThread.start();
127         mHandler = new Handler(handlerThread.getLooper()) {
128             @Override
129             public void handleMessage(Message msg) {
130             }
131         };
132         mTestableLooper = new TestableLooper(mHandler.getLooper());
133         doReturn(Context.TELEPHONY_SERVICE).when(mContext).getSystemServiceName(
134                 TelephonyManager.class);
135         doReturn(mTelephonyManager).when(mContext).getSystemService(Context.TELEPHONY_SERVICE);
136         doReturn(mTelephonyManager).when(mTelephonyManager).createForSubscriptionId(anyInt());
137         doReturn(Context.CARRIER_CONFIG_SERVICE).when(mContext).getSystemServiceName(
138                 CarrierConfigManager.class);
139         doReturn(mCarrierConfigManager).when(mContext).getSystemService(
140                 Context.CARRIER_CONFIG_SERVICE);
141         doAnswer(invocation -> {
142             Executor executor = invocation.getArgument(0);
143             CarrierConfigManager.CarrierConfigChangeListener listener = invocation.getArgument(1);
144             mCarrierConfigChangedListenerList.add(new Pair<>(executor, listener));
145             return null;
146         }).when(mCarrierConfigManager).registerCarrierConfigChangeListener(
147                 any(Executor.class),
148                 any(CarrierConfigManager.CarrierConfigChangeListener.class));
149         mCarrierConfigBundle = new PersistableBundle();
150         mCarrierConfigBundle.putInt(
151                 CarrierConfigManager.KEY_SATELLITE_ENTITLEMENT_STATUS_REFRESH_DAYS_INT,
152                 DEFAULT_QUERY_REFRESH_DAY);
153         mCarrierConfigBundle.putBoolean(
154                 CarrierConfigManager.KEY_SATELLITE_ENTITLEMENT_SUPPORTED_BOOL, true);
155         doReturn(mCarrierConfigBundle)
156                 .when(mCarrierConfigManager).getConfigForSubId(anyInt(), anyVararg());
157         doReturn(Context.CONNECTIVITY_SERVICE).when(mContext).getSystemServiceName(
158                 ConnectivityManager.class);
159         doReturn(mConnectivityManager).when(mContext).getSystemService(
160                 Context.CONNECTIVITY_SERVICE);
161         doReturn(mNetwork).when(mConnectivityManager).getActiveNetwork();
162         doReturn(ACTIVE_SUB_ID).when(mMockSubscriptionManagerService).getActiveSubIdList(true);
163         mSatelliteEntitlementController = new TestSatelliteEntitlementController(mContext,
164                 mHandler.getLooper(), mSatelliteEntitlementApi);
165         mSatelliteEntitlementController = spy(mSatelliteEntitlementController);
166         doReturn(mSatelliteEntitlementResult).when(
167                 mSatelliteEntitlementApi).checkEntitlementStatus();
168     }
169 
170     @After
tearDown()171     public void tearDown() throws Exception {
172         super.tearDown();
173     }
174 
175     @Test
testShouldStartQueryEntitlement()176     public void testShouldStartQueryEntitlement() throws Exception {
177         logd("testShouldStartQueryEntitlement");
178         doReturn(ACTIVE_SUB_ID).when(mMockSubscriptionManagerService).getActiveSubIdList(true);
179 
180         // Verify don't start the query when KEY_SATELLITE_ENTITLEMENT_SUPPORTED_BOOL is false.
181         mCarrierConfigBundle.putBoolean(
182                 CarrierConfigManager.KEY_SATELLITE_ENTITLEMENT_SUPPORTED_BOOL, false);
183         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
184 
185         verify(mSatelliteEntitlementApi, never()).checkEntitlementStatus();
186         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
187                 anyBoolean(), anyList(), anyList(), any());
188 
189         mCarrierConfigBundle.putBoolean(
190                 CarrierConfigManager.KEY_SATELLITE_ENTITLEMENT_SUPPORTED_BOOL, true);
191         // Verify don't start the query when Internet is disconnected.
192         clearInvocationsForMock();
193         setInternetConnected(false);
194         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
195 
196         verify(mSatelliteEntitlementApi, never()).checkEntitlementStatus();
197         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
198                 anyBoolean(), anyList(), anyList(), any());
199 
200         setInternetConnected(true);
201         // Verify don't start the query when last query refresh time is not expired.
202         setLastQueryTime(System.currentTimeMillis());
203         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
204 
205         verify(mSatelliteEntitlementApi, never()).checkEntitlementStatus();
206         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
207                 anyBoolean(), anyList(), anyList(), any());
208 
209         setLastQueryTime(0L);
210         // Verify don't start the query when retry count is reached max
211         setLastQueryTime(0L);
212         Map<Integer, Integer> mRetryCountPerSub = new HashMap<>();
213         mRetryCountPerSub.put(SUB_ID, MAX_RETRY_COUNT);
214         replaceInstance(SatelliteEntitlementController.class, "mRetryCountPerSub",
215                 mSatelliteEntitlementController, mRetryCountPerSub);
216         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
217 
218         verify(mSatelliteEntitlementApi, never()).checkEntitlementStatus();
219         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
220                 anyBoolean(), anyList(), anyList(), any());
221 
222         replaceInstance(SatelliteEntitlementController.class, "mRetryCountPerSub",
223                 mSatelliteEntitlementController, new HashMap<>());
224 
225         // Verify don't start the query when query is in progressed.
226         Map<Integer, Boolean> mIsEntitlementInProgressPerSub = new HashMap<>();
227         mIsEntitlementInProgressPerSub.put(SUB_ID, true);
228         replaceInstance(SatelliteEntitlementController.class, "mIsEntitlementInProgressPerSub",
229                 mSatelliteEntitlementController, mIsEntitlementInProgressPerSub);
230         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
231 
232         verify(mSatelliteEntitlementApi, never()).checkEntitlementStatus();
233         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
234                 anyBoolean(), anyList(), anyList(), any());
235 
236         replaceInstance(SatelliteEntitlementController.class, "mIsEntitlementInProgressPerSub",
237                 mSatelliteEntitlementController, new HashMap<>());
238         // Verify the query starts when ShouldStartQueryEntitlement returns true.
239         doReturn(mSatelliteEntitlementResult).when(
240                 mSatelliteEntitlementApi).checkEntitlementStatus();
241         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, PLMN_ALLOWED_LIST,
242                 PLMN_BARRED_LIST);
243         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
244 
245         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
246         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(anyInt(),
247                 anyBoolean(), anyList(), anyList(), any());
248     }
249 
250     @Test
testCheckSatelliteEntitlementStatus()251     public void testCheckSatelliteEntitlementStatus() throws Exception {
252         logd("testCheckSatelliteEntitlementStatus");
253         setIsQueryAvailableTrue();
254         // Verify don't call the checkSatelliteEntitlementStatus when getActiveSubIdList is empty.
255         doReturn(new int[]{}).when(mMockSubscriptionManagerService).getActiveSubIdList(true);
256         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
257 
258         verify(mSatelliteEntitlementApi, never()).checkEntitlementStatus();
259         // Verify don't call the updateSatelliteEntitlementStatus.
260         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
261                 anyBoolean(), anyList(), anyList(), any());
262 
263         // Verify call the checkSatelliteEntitlementStatus with invalid response.
264         setIsQueryAvailableTrue();
265         doReturn(mSatelliteEntitlementResult).when(
266                 mSatelliteEntitlementApi).checkEntitlementStatus();
267         replaceInstance(SatelliteEntitlementController.class,
268                 "mSatelliteEntitlementResultPerSub", mSatelliteEntitlementController,
269                 new HashMap<>());
270         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
271 
272         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
273         // Verify call the updateSatelliteEntitlementStatus with satellite service is disabled
274         // , empty PLMNAllowed and empty PLMNBarred.
275         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID),
276                 eq(false), eq(EMPTY_PLMN_LIST), eq(EMPTY_PLMN_LIST), any());
277 
278         // Verify call the checkSatelliteEntitlementStatus with the subscribed result.
279         clearInvocationsForMock();
280         setIsQueryAvailableTrue();
281         doReturn(mSatelliteEntitlementResult).when(
282                 mSatelliteEntitlementApi).checkEntitlementStatus();
283         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, PLMN_ALLOWED_LIST,
284                 PLMN_BARRED_LIST);
285         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
286 
287         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
288         // Verify call the updateSatelliteEntitlementStatus with satellite service is enable,
289         // availablePLMNAllowedList and availablePLMNBarredList.
290         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID), eq(true),
291                 eq(PLMN_ALLOWED_LIST), eq(PLMN_BARRED_LIST), any());
292 
293         // Change subId and verify call the updateSatelliteEntitlementStatus with satellite
294         // service is enable, availablePLMNAllowedList and availablePLMNBarredList
295         clearInvocationsForMock();
296         doReturn(new int[]{SUB_ID_2}).when(mMockSubscriptionManagerService).getActiveSubIdList(
297                 true);
298         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
299 
300         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
301         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID_2), eq(true),
302                 eq(PLMN_ALLOWED_LIST), eq(PLMN_BARRED_LIST), any());
303 
304         // Verify call the updateSatelliteEntitlementStatus with satellite service is enable,
305         // availablePLMNAllowedList and empty plmn barred list.
306         clearInvocationsForMock();
307         setIsQueryAvailableTrue();
308         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, PLMN_ALLOWED_LIST,
309                 new ArrayList<>());
310         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
311 
312         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
313         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID), eq(true),
314                 eq(PLMN_ALLOWED_LIST), eq(EMPTY_PLMN_LIST), any());
315 
316         // Verify call the updateSatelliteEntitlementStatus with satellite service is enable,
317         // empty PLMNAllowedList and PLMNBarredList.
318         clearInvocationsForMock();
319         setIsQueryAvailableTrue();
320         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, new ArrayList<>(),
321                 new ArrayList<>());
322         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
323 
324         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
325         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID), eq(true),
326                 eq(EMPTY_PLMN_LIST), eq(EMPTY_PLMN_LIST), any());
327 
328         // Verify call the updateSatelliteEntitlementStatus with satellite service is enable,
329         // empty PLMNAllowedList and availablePLMNBarredList.
330         clearInvocationsForMock();
331         setIsQueryAvailableTrue();
332         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, new ArrayList<>(),
333                 PLMN_BARRED_LIST);
334         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
335 
336         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
337         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID), eq(true),
338                 eq(EMPTY_PLMN_LIST), eq(PLMN_BARRED_LIST), any());
339     }
340 
341     @Test
testCheckSatelliteEntitlementStatusWhenInternetConnected()342     public void testCheckSatelliteEntitlementStatusWhenInternetConnected() throws Exception {
343         logd("testCheckSatelliteEntitlementStatusWhenInternetConnected");
344         ConnectivityManager.NetworkCallback networkCallback =
345                 (ConnectivityManager.NetworkCallback) getValue("mNetworkCallback");
346         Network mockNetwork = mock(Network.class);
347 
348         // Verify the called the checkSatelliteEntitlementStatus when Internet is connected.
349         setInternetConnected(true);
350         setLastQueryTime(0L);
351         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, PLMN_ALLOWED_LIST,
352                 PLMN_BARRED_LIST);
353 
354         networkCallback.onAvailable(mockNetwork);
355         mTestableLooper.processAllMessages();
356 
357         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
358         // Verify call the updateSatelliteEntitlementStatus with satellite service is available.
359         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID), eq(true),
360                 eq(PLMN_ALLOWED_LIST), eq(PLMN_BARRED_LIST), any());
361     }
362 
363     @Test
testCheckSatelliteEntitlementStatusWhenCarrierConfigChanged()364     public void testCheckSatelliteEntitlementStatusWhenCarrierConfigChanged() throws Exception {
365         logd("testCheckSatelliteEntitlementStatusWhenCarrierConfigChanged");
366         // Verify the called the checkSatelliteEntitlementStatus when CarrierConfigChanged
367         // occurred and Internet is connected.
368         setInternetConnected(true);
369         setLastQueryTime(0L);
370         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, PLMN_ALLOWED_LIST,
371                 PLMN_BARRED_LIST);
372         triggerCarrierConfigChanged();
373 
374         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
375         // Verify call the updateSatelliteEntitlementStatus with satellite service is available.
376         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID), eq(true),
377                 eq(PLMN_ALLOWED_LIST), eq(PLMN_BARRED_LIST), any());
378     }
379 
380     @Test
testCheckWhenStartCmdIsReceivedDuringRetry()381     public void testCheckWhenStartCmdIsReceivedDuringRetry() throws Exception {
382         logd("testCheckWhenStartCmdIsReceivedDuringRetry");
383         // Verify that start cmd is ignored and retry is performed up to 5 times when start cmd
384         // occurs during retries.
385         setIsQueryAvailableTrue();
386         set503RetryAfterResponse();
387         Map<Integer, Integer> retryCountPerSub =
388                 (Map<Integer, Integer>) getValue("mRetryCountPerSub");
389 
390         // Verify that the first query.
391         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
392         mTestableLooper.processAllMessages();
393         verify(mSatelliteEntitlementApi, times(1)).checkEntitlementStatus();
394         // Verify that the retry count is 0 after receiving a 503 with retry-after header in
395         // response.
396         assertTrue(retryCountPerSub.getOrDefault(SUB_ID, 0) == 0);
397 
398         // Verify that the retry count is 1 for the second query when receiving a 503 with
399         // retry-after header in response.
400         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
401         mTestableLooper.processAllMessages();
402         verify(mSatelliteEntitlementApi, times(2)).checkEntitlementStatus();
403         assertTrue(retryCountPerSub.get(SUB_ID) == 1);
404 
405         // Verify that the retry count is 2 for the third query when receiving a 503 with
406         // retry-after header in response.
407         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
408         mTestableLooper.processAllMessages();
409         verify(mSatelliteEntitlementApi, times(3)).checkEntitlementStatus();
410         assertTrue(retryCountPerSub.get(SUB_ID) == 2);
411 
412         // Verify that start CMD is ignored during retries.
413         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
414         mTestableLooper.processAllMessages();
415         verify(mSatelliteEntitlementApi, times(3)).checkEntitlementStatus();
416         assertTrue(retryCountPerSub.get(SUB_ID) == 2);
417 
418         // Verify that the retry count is 3 for the forth query when receiving a 503 with
419         // retry-after header in response.
420         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
421         mTestableLooper.processAllMessages();
422         verify(mSatelliteEntitlementApi, times(4)).checkEntitlementStatus();
423         assertTrue(retryCountPerSub.get(SUB_ID) == 3);
424 
425         // Verify that the retry count is 4 for the fifth query when receiving a 503 with
426         // retry-after header in response.
427         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
428         mTestableLooper.processAllMessages();
429         verify(mSatelliteEntitlementApi, times(5)).checkEntitlementStatus();
430         assertTrue(retryCountPerSub.get(SUB_ID) == 4);
431 
432         // Verify that start CMD is ignored during retries.
433         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
434         mTestableLooper.processAllMessages();
435         verify(mSatelliteEntitlementApi, times(5)).checkEntitlementStatus();
436         assertTrue(retryCountPerSub.get(SUB_ID) == 4);
437 
438         // Verify that the retry count is 5 for the sixth query when receiving a 503 with
439         // retry-after header in response.
440         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
441         mTestableLooper.processAllMessages();
442         verify(mSatelliteEntitlementApi, times(6)).checkEntitlementStatus();
443         assertNull(retryCountPerSub.get(SUB_ID));
444 
445         // Verify only called onSatelliteEntitlementStatusUpdated once.
446         verify(mSatelliteController, times(1)).onSatelliteEntitlementStatusUpdated(eq(SUB_ID),
447                 eq(false), eq(EMPTY_PLMN_LIST), eq(EMPTY_PLMN_LIST), any());
448 
449         // Verify that the query is not restarted after reaching the maximum retry count even if
450         // a start cmd is received.
451         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
452         mTestableLooper.processAllMessages();
453         verify(mSatelliteEntitlementApi, times(6)).checkEntitlementStatus();
454         assertNull(retryCountPerSub.get(SUB_ID));
455 
456         // Verify that the query is not restarted after reaching the maximum retry count even if
457         // a start cmd is received.
458         sendMessage(CMD_RETRY_QUERY_ENTITLEMENT, SUB_ID);
459         mTestableLooper.processAllMessages();
460         verify(mSatelliteEntitlementApi, times(6)).checkEntitlementStatus();
461         assertNull(retryCountPerSub.get(SUB_ID));
462     }
463 
464     @Test
testCheckAfterInternetConnectionChangedDuringRetry()465     public void testCheckAfterInternetConnectionChangedDuringRetry() throws Exception {
466         logd("testCheckAfterInternetConnectionChangedDuringRetry");
467         // Verify that the retry count is maintained even when internet connection is lost and
468         // connected during retries, and that up to 5 retries are performed.
469         setIsQueryAvailableTrue();
470         set503RetryAfterResponse();
471         Map<Integer, Integer> retryCountPerSub =
472                 (Map<Integer, Integer>) getValue("mRetryCountPerSub");
473 
474         // Verify that the first query.
475         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
476         mTestableLooper.processAllMessages();
477         verify(mSatelliteEntitlementApi, times(1)).checkEntitlementStatus();
478         // Verify that the retry count is 0 after receiving a 503 with retry-after header in
479         // response.
480         assertTrue(retryCountPerSub.getOrDefault(SUB_ID, 0) == 0);
481 
482         // Verify that the retry count is 1 for the second query when receiving a 503 with
483         // retry-after header in response.
484         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
485         mTestableLooper.processAllMessages();
486         verify(mSatelliteEntitlementApi, times(2)).checkEntitlementStatus();
487         assertTrue(retryCountPerSub.get(SUB_ID) == 1);
488 
489         // Verify that no query is executed and the retry count does not increase when internet
490         // connection is lost during the second retry.
491         setInternetConnected(false);
492         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
493         mTestableLooper.processAllMessages();
494         verify(mSatelliteEntitlementApi, times(2)).checkEntitlementStatus();
495         assertTrue(retryCountPerSub.get(SUB_ID) == 1);
496 
497         // Verify that the query is started when internet connection is restored and that the
498         // retry count does not increase.
499         setInternetConnected(true);
500         logd("internet connected again");
501         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
502         mTestableLooper.processAllMessages();
503         verify(mSatelliteEntitlementApi, times(3)).checkEntitlementStatus();
504         assertTrue(retryCountPerSub.get(SUB_ID) == 1);
505 
506         // Verify that the retry count is increases after received a 503 with retry-after header
507         // in response.
508         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
509         mTestableLooper.processAllMessages();
510         verify(mSatelliteEntitlementApi, times(4)).checkEntitlementStatus();
511         assertTrue(retryCountPerSub.get(SUB_ID) == 2);
512 
513         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
514         mTestableLooper.processAllMessages();
515         verify(mSatelliteEntitlementApi, times(5)).checkEntitlementStatus();
516         assertTrue(retryCountPerSub.get(SUB_ID) == 3);
517 
518         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
519         mTestableLooper.processAllMessages();
520         verify(mSatelliteEntitlementApi, times(6)).checkEntitlementStatus();
521         assertTrue(retryCountPerSub.get(SUB_ID) == 4);
522 
523         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
524         mTestableLooper.processAllMessages();
525         verify(mSatelliteEntitlementApi, times(7)).checkEntitlementStatus();
526         assertNull(retryCountPerSub.get(SUB_ID));
527 
528         // Verify that the query is not restarted after reaching the maximum retry count even if
529         // a start cmd is received.
530         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
531         mTestableLooper.processAllMessages();
532         verify(mSatelliteEntitlementApi, times(7)).checkEntitlementStatus();
533         assertNull(retryCountPerSub.get(SUB_ID));
534 
535         // Verify that the query is not restarted after reaching the maximum retry count even if
536         // a retry cmd is received.
537         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
538         mTestableLooper.processAllMessages();
539         verify(mSatelliteEntitlementApi, times(7)).checkEntitlementStatus();
540         assertNull(retryCountPerSub.get(SUB_ID));
541 
542         // Verify only called onSatelliteEntitlementStatusUpdated once.
543         verify(mSatelliteController, times(1)).onSatelliteEntitlementStatusUpdated(eq(SUB_ID),
544                 eq(false), eq(EMPTY_PLMN_LIST), eq(EMPTY_PLMN_LIST), any());
545     }
546 
547     @Test
testStartQueryEntitlementStatus_error500()548     public void testStartQueryEntitlementStatus_error500() throws Exception {
549         logd("testStartQueryEntitlementStatus_error500");
550         setIsQueryAvailableTrue();
551         Map<Integer, Integer> retryCountPerSub =
552                 (Map<Integer, Integer>) getValue("mRetryCountPerSub");
553         setErrorResponse(500);
554 
555         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
556         mTestableLooper.processAllMessages();
557         verify(mSatelliteEntitlementApi, times(1)).checkEntitlementStatus();
558         assertNull(retryCountPerSub.get(SUB_ID));
559         verify(mSatelliteController, times(1)).onSatelliteEntitlementStatusUpdated(eq(SUB_ID),
560                 eq(false), eq(EMPTY_PLMN_LIST), eq(EMPTY_PLMN_LIST), any());
561     }
562 
563     @Test
testStartQueryEntitlementStatus_error503_retrySuccess()564     public void testStartQueryEntitlementStatus_error503_retrySuccess() throws Exception {
565         logd("testStartQueryEntitlementStatus_error503_retrySuccess");
566         setIsQueryAvailableTrue();
567         set503RetryAfterResponse();
568         Map<Integer, Integer> retryCountPerSub =
569                 (Map<Integer, Integer>) getValue("mRetryCountPerSub");
570 
571         // Verify that the first query.
572         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
573         mTestableLooper.processAllMessages();
574         verify(mSatelliteEntitlementApi, times(1)).checkEntitlementStatus();
575         assertNull(retryCountPerSub.get(SUB_ID));
576 
577         // Verify whether the query has been retried and verify called
578         // onSatelliteEntitlementStatusUpdated after receive a success case.
579         doReturn(mSatelliteEntitlementResult).when(
580                 mSatelliteEntitlementApi).checkEntitlementStatus();
581         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, PLMN_ALLOWED_LIST,
582                 PLMN_BARRED_LIST);
583         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
584         mTestableLooper.processAllMessages();
585         verify(mSatelliteEntitlementApi, times(2)).checkEntitlementStatus();
586         assertNull(retryCountPerSub.get(SUB_ID));
587         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID), eq(true),
588                 eq(PLMN_ALLOWED_LIST), eq(PLMN_BARRED_LIST), any());
589     }
590 
591     @Test
testStartQueryEntitlementStatus_otherError_retrySuccess()592     public void testStartQueryEntitlementStatus_otherError_retrySuccess() throws Exception {
593         logd("testStartQueryEntitlementStatus_otherError_retrySuccess");
594         setIsQueryAvailableTrue();
595         Map<Integer, Integer> retryCountPerSub =
596                 (Map<Integer, Integer>) getValue("mRetryCountPerSub");
597         Map<Integer, Boolean> isEntitlementInProgressPerSub =
598                 (Map<Integer, Boolean>) getValue("mIsEntitlementInProgressPerSub");
599         Map<Integer, ExponentialBackoff> exponentialBackoffPerSub =
600                 (Map<Integer, ExponentialBackoff>) getValue("mExponentialBackoffPerSub");
601         setErrorResponse(400);
602 
603         // Verify start the exponentialBackoff.
604         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
605         mTestableLooper.processAllMessages();
606         verify(mSatelliteEntitlementApi, times(1)).checkEntitlementStatus();
607         assertNull(retryCountPerSub.get(SUB_ID));
608         assertTrue(isEntitlementInProgressPerSub.get(SUB_ID));
609         assertNotNull(exponentialBackoffPerSub.get(SUB_ID));
610         // Verify don't call the onSatelliteEntitlementStatusUpdated.
611         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
612                 anyBoolean(), anyList(), anyList(), any());
613 
614         // Verify the retry in progress.
615         sendMessage(CMD_RETRY_QUERY_ENTITLEMENT, SUB_ID);
616         mTestableLooper.processAllMessages();
617         verify(mSatelliteEntitlementApi, times(2)).checkEntitlementStatus();
618         assertTrue(retryCountPerSub.get(SUB_ID) == 1);
619         // Verify don't call the onSatelliteEntitlementStatusUpdated.
620         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
621                 anyBoolean(), anyList(), anyList(), any());
622 
623         // Received the 200 response, Verify call the onSatelliteEntitlementStatusUpdated.
624         setIsQueryAvailableTrue();
625         doReturn(mSatelliteEntitlementResult).when(
626                 mSatelliteEntitlementApi).checkEntitlementStatus();
627         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, PLMN_ALLOWED_LIST,
628                 PLMN_BARRED_LIST);
629 
630         sendMessage(CMD_RETRY_QUERY_ENTITLEMENT, SUB_ID);
631         mTestableLooper.processAllMessages();
632         verify(mSatelliteEntitlementApi, times(3)).checkEntitlementStatus();
633         assertTrue(retryCountPerSub.get(SUB_ID) == 1);
634         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID), eq(true),
635                 eq(PLMN_ALLOWED_LIST), eq(PLMN_BARRED_LIST), any());
636     }
637 
638     @Test
testSatelliteEntitlementSupportedChangedFromSupportToNotSupport()639     public void testSatelliteEntitlementSupportedChangedFromSupportToNotSupport() throws Exception {
640         logd("testSatelliteEntitlementSupportedChangedFromSupportToNotSupport");
641         setIsQueryAvailableTrue();
642 
643         // KEY_SATELLITE_ENTITLEMENT_SUPPORTED_BOOL changed from Support(entitlement status
644         // disabled) to not support.
645         doReturn(mSatelliteEntitlementResult).when(
646                 mSatelliteEntitlementApi).checkEntitlementStatus();
647         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_DISABLED, EMPTY_PLMN_LIST,
648                 EMPTY_PLMN_LIST);
649         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
650         mTestableLooper.processAllMessages();
651 
652         // Verify call the onSatelliteEntitlementStatusUpdated - entitlement status false
653         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
654         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(anyInt(),
655                 eq(false), eq(EMPTY_PLMN_LIST), eq(EMPTY_PLMN_LIST), any());
656 
657         // Verify call the onSatelliteEntitlementStatusUpdated - entitlement status true
658         mCarrierConfigBundle.putBoolean(
659                 CarrierConfigManager.KEY_SATELLITE_ENTITLEMENT_SUPPORTED_BOOL, false);
660         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
661         mTestableLooper.processAllMessages();
662 
663         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(anyInt(),
664                 eq(true), eq(EMPTY_PLMN_LIST), eq(EMPTY_PLMN_LIST), any());
665 
666         // KEY_SATELLITE_ENTITLEMENT_SUPPORTED_BOOL changed from Support(entitlement status
667         // enabled) to not support.
668         mCarrierConfigBundle.putBoolean(
669                 CarrierConfigManager.KEY_SATELLITE_ENTITLEMENT_SUPPORTED_BOOL, true);
670         doReturn(mSatelliteEntitlementResult).when(
671                 mSatelliteEntitlementApi).checkEntitlementStatus();
672         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, PLMN_ALLOWED_LIST,
673                 PLMN_BARRED_LIST);
674         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
675         mTestableLooper.processAllMessages();
676 
677         // Verify call the onSatelliteEntitlementStatusUpdated - entitlement status true.
678         verify(mSatelliteEntitlementApi, times(2)).checkEntitlementStatus();
679         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(anyInt(),
680                 eq(true), eq(PLMN_ALLOWED_LIST), eq(PLMN_BARRED_LIST), any());
681 
682         // Verify not call the onSatelliteEntitlementStatusUpdated.
683         clearInvocationsForMock();
684         mCarrierConfigBundle.putBoolean(
685                 CarrierConfigManager.KEY_SATELLITE_ENTITLEMENT_SUPPORTED_BOOL, false);
686         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
687         mTestableLooper.processAllMessages();
688 
689         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
690                 eq(true), eq(EMPTY_PLMN_LIST), eq(EMPTY_PLMN_LIST), any());
691     }
692 
693     @Test
testStartQueryEntitlementStatus_refreshStatus()694     public void testStartQueryEntitlementStatus_refreshStatus() throws Exception {
695         logd("testStartQueryEntitlementStatus_refreshStatus");
696         setIsQueryAvailableTrue();
697         mCarrierConfigBundle.putInt(
698                 CarrierConfigManager.KEY_SATELLITE_ENTITLEMENT_STATUS_REFRESH_DAYS_INT, 1);
699 
700         // Verify start query and success.
701         doReturn(mSatelliteEntitlementResult).when(
702                 mSatelliteEntitlementApi).checkEntitlementStatus();
703         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, PLMN_ALLOWED_LIST,
704                 PLMN_BARRED_LIST);
705         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
706         mTestableLooper.processAllMessages();
707 
708         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
709         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(anyInt(),
710                 anyBoolean(), anyList(), anyList(), any());
711 
712         // After move to the refresh time, verify the query started and success.
713         setLastQueryTime(System.currentTimeMillis() - TimeUnit.DAYS.toMillis(1) - 1000);
714         mTestableLooper.moveTimeForward(TimeUnit.DAYS.toMillis(1));
715         mTestableLooper.processAllMessages();
716 
717         verify(mSatelliteEntitlementApi, times(2)).checkEntitlementStatus();
718         verify(mSatelliteController, times(2)).onSatelliteEntitlementStatusUpdated(anyInt(),
719                 anyBoolean(), anyList(), anyList(), any());
720     }
721 
722     @Test
testStartQueryEntitlementStatus_internetDisconnectedAndConnectedAgain()723     public void testStartQueryEntitlementStatus_internetDisconnectedAndConnectedAgain()
724             throws Exception {
725         logd("testStartQueryEntitlementStatus_internetDisconnectedAndConnectedAgain");
726         setIsQueryAvailableTrue();
727 
728         // Verify the query does not start if there is no internet connection.
729         setInternetConnected(false);
730         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
731         mTestableLooper.processAllMessages();
732 
733         verify(mSatelliteEntitlementApi, never()).checkEntitlementStatus();
734         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
735                 anyBoolean(), anyList(), anyList(), any());
736 
737         // Verify the query start and success after internet connected.
738         setInternetConnected(true);
739         doReturn(mSatelliteEntitlementResult).when(
740                 mSatelliteEntitlementApi).checkEntitlementStatus();
741         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, PLMN_ALLOWED_LIST,
742                 PLMN_BARRED_LIST);
743         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
744         mTestableLooper.processAllMessages();
745 
746         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
747         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID), eq(true),
748                 eq(PLMN_ALLOWED_LIST), eq(PLMN_BARRED_LIST), any());
749     }
750 
751     @Test
testStartQueryEntitlementStatus_error503_error500()752     public void testStartQueryEntitlementStatus_error503_error500() throws Exception {
753         logd("testStartQueryEntitlementStatus_error503_error500");
754         setIsQueryAvailableTrue();
755         set503RetryAfterResponse();
756 
757         // Verify that the first query was triggered and that onSatelliteEntitlementStatusUpdated
758         // was not called after received a 503 error.
759         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
760         mTestableLooper.processAllMessages();
761         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
762         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
763                 anyBoolean(), anyList(), anyList(), any());
764 
765         // Verify whether the second query has been triggered and whether
766         // onSatelliteEntitlementStatusUpdated has been called after received the 500 error.
767         reset(mSatelliteEntitlementApi);
768         setErrorResponse(500);
769         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
770         mTestableLooper.processAllMessages();
771         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
772         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID),
773                 eq(false), eq(EMPTY_PLMN_LIST), eq(EMPTY_PLMN_LIST), any());
774     }
775 
776     @Test
testStartQueryEntitlementStatus_error503_otherError()777     public void testStartQueryEntitlementStatus_error503_otherError() throws Exception {
778         logd("testStartQueryEntitlementStatus_error503_otherError");
779         setIsQueryAvailableTrue();
780         set503RetryAfterResponse();
781 
782         // Verify that the first query was triggered and that onSatelliteEntitlementStatusUpdated
783         // was not called after received a 503 error.
784         sendMessage(CMD_START_QUERY_ENTITLEMENT, SUB_ID);
785         mTestableLooper.processAllMessages();
786         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
787         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
788                 anyBoolean(), anyList(), anyList(), any());
789 
790         // Verify whether the second query was triggered and onSatelliteEntitlementStatusUpdated
791         // was not called after received a 503 error without valid retry-after header.
792         reset(mSatelliteEntitlementApi);
793         setErrorResponse(503);
794         mTestableLooper.moveTimeForward(TimeUnit.SECONDS.toMillis(1));
795         mTestableLooper.processAllMessages();
796         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
797         verify(mSatelliteController, never()).onSatelliteEntitlementStatusUpdated(anyInt(),
798                 anyBoolean(), anyList(), anyList(), any());
799 
800         // Verify whether the third query was triggered and onSatelliteEntitlementStatusUpdated
801         // was called after received a success case.
802         doReturn(mSatelliteEntitlementResult).when(
803                 mSatelliteEntitlementApi).checkEntitlementStatus();
804         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, PLMN_ALLOWED_LIST,
805                 PLMN_BARRED_LIST);
806         mTestableLooper.moveTimeForward(TimeUnit.MINUTES.toMillis(10));
807         mTestableLooper.processAllMessages();
808 
809         verify(mSatelliteEntitlementApi, times(2)).checkEntitlementStatus();
810         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(eq(SUB_ID), eq(true),
811                 eq(PLMN_ALLOWED_LIST), eq(PLMN_BARRED_LIST), any());
812     }
813 
814     @Test
testStartQueryEntitlementStatus_AfterSimRefresh()815     public void testStartQueryEntitlementStatus_AfterSimRefresh() throws Exception {
816         logd("testStartQueryEntitlementStatus_AfterSimRefresh");
817         setIsQueryAvailableTrue();
818 
819         // Verify the first query complete.
820         doReturn(mSatelliteEntitlementResult).when(
821                 mSatelliteEntitlementApi).checkEntitlementStatus();
822         setSatelliteEntitlementResult(SATELLITE_ENTITLEMENT_STATUS_ENABLED, PLMN_ALLOWED_LIST,
823                 PLMN_BARRED_LIST);
824         mSatelliteEntitlementController.handleCmdStartQueryEntitlement();
825 
826         verify(mSatelliteEntitlementApi).checkEntitlementStatus();
827         verify(mSatelliteController).onSatelliteEntitlementStatusUpdated(anyInt(),
828                 anyBoolean(), anyList(), anyList(), any());
829 
830         // SIM_REFRESH event occurred before expired the query refresh timer, verify the start
831         // the query.
832         sendMessage(CMD_SIM_REFRESH, SUB_ID);
833         mTestableLooper.moveTimeForward(TimeUnit.MINUTES.toMillis(10));
834         mTestableLooper.processAllMessages();
835 
836         verify(mSatelliteEntitlementApi, times(2)).checkEntitlementStatus();
837         verify(mSatelliteController, times(2)).onSatelliteEntitlementStatusUpdated(anyInt(),
838                 anyBoolean(), anyList(), anyList(), any());
839     }
840 
triggerCarrierConfigChanged()841     private void triggerCarrierConfigChanged() {
842         for (Pair<Executor, CarrierConfigManager.CarrierConfigChangeListener> pair
843                 : mCarrierConfigChangedListenerList) {
844             pair.first.execute(() -> pair.second.onCarrierConfigChanged(
845                     /*slotIndex*/ 0, /*subId*/ SUB_ID, /*carrierId*/ 0, /*specificCarrierId*/ 0)
846             );
847         }
848         mTestableLooper.processAllMessages();
849     }
850 
triggerCarrierConfigChanged(int subId)851     private void triggerCarrierConfigChanged(int subId) {
852         for (Pair<Executor, CarrierConfigManager.CarrierConfigChangeListener> pair
853                 : mCarrierConfigChangedListenerList) {
854             pair.first.execute(() -> pair.second.onCarrierConfigChanged(
855                     /*slotIndex*/ 0, /*subId*/ subId, /*carrierId*/ 0, /*specificCarrierId*/ 0)
856             );
857         }
858         mTestableLooper.processAllMessages();
859     }
860 
clearInvocationsForMock()861     private void clearInvocationsForMock() {
862         clearInvocations(mSatelliteEntitlementApi);
863         clearInvocations(mSatelliteController);
864     }
865 
setIsQueryAvailableTrue()866     private void setIsQueryAvailableTrue() throws Exception {
867         doReturn(ACTIVE_SUB_ID).when(mMockSubscriptionManagerService).getActiveSubIdList(true);
868         mCarrierConfigBundle.putBoolean(
869                 CarrierConfigManager.KEY_SATELLITE_ENTITLEMENT_SUPPORTED_BOOL, true);
870         replaceInstance(SatelliteEntitlementController.class, "mRetryCountPerSub",
871                 mSatelliteEntitlementController, new HashMap<>());
872         replaceInstance(SatelliteEntitlementController.class, "mIsEntitlementInProgressPerSub",
873                 mSatelliteEntitlementController, new HashMap<>());
874         setInternetConnected(true);
875         setLastQueryTime(0L);
876         replaceInstance(SatelliteEntitlementController.class,
877                 "mSatelliteEntitlementResultPerSub", mSatelliteEntitlementController,
878                 new HashMap<>());
879         replaceInstance(SatelliteEntitlementController.class,
880                 "mSubIdPerSlot", mSatelliteEntitlementController, new HashMap<>());
881     }
882 
setInternetConnected(boolean connected)883     private void setInternetConnected(boolean connected) {
884         NetworkCapabilities networkCapabilities = new NetworkCapabilities.Builder().build();
885 
886         if (connected) {
887             networkCapabilities = new NetworkCapabilities.Builder()
888                     .addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
889                     .setTransportInfo(mock(WifiInfo.class))
890                     .build();
891         }
892         doReturn(networkCapabilities).when(mConnectivityManager).getNetworkCapabilities(mNetwork);
893     }
894 
setSatelliteEntitlementResult(int entitlementStatus, List<String> plmnAllowedList, List<String> plmnBarredList)895     private void setSatelliteEntitlementResult(int entitlementStatus,
896             List<String> plmnAllowedList, List<String> plmnBarredList) {
897         doReturn(entitlementStatus).when(mSatelliteEntitlementResult).getEntitlementStatus();
898         doReturn(plmnAllowedList).when(mSatelliteEntitlementResult).getAllowedPLMNList();
899         doReturn(plmnBarredList).when(mSatelliteEntitlementResult).getBarredPLMNList();
900     }
901 
setLastQueryTime(Long lastQueryTime)902     private void setLastQueryTime(Long lastQueryTime) throws Exception {
903         Map<Integer, Long> lastQueryTimePerSub = new HashMap<>();
904         replaceInstance(SatelliteEntitlementController.class, "mLastQueryTimePerSub",
905                 mSatelliteEntitlementController, lastQueryTimePerSub);
906         lastQueryTimePerSub.put(SUB_ID, lastQueryTime);
907     }
908 
set503RetryAfterResponse()909     private void set503RetryAfterResponse() throws Exception {
910         when(mSatelliteEntitlementApi.checkEntitlementStatus()).thenAnswer(
911                 new Answer() {
912                     @Override
913                     public Object answer(InvocationOnMock invocation) throws Throwable {
914                         throw new ServiceEntitlementException(
915                                 ERROR_HTTP_STATUS_NOT_SUCCESS, 503, "1", "503 occurred");
916                     }
917                 }
918         );
919     }
920 
setErrorResponse(int errorCode)921     private void setErrorResponse(int errorCode) throws Exception {
922         when(mSatelliteEntitlementApi.checkEntitlementStatus()).thenAnswer(
923                 new Answer() {
924                     @Override
925                     public Object answer(InvocationOnMock invocation) throws Throwable {
926                         throw new ServiceEntitlementException(
927                                 ERROR_HTTP_STATUS_NOT_SUCCESS, errorCode, "",
928                                 errorCode + " occurred");
929                     }
930                 }
931         );
932     }
933 
sendMessage(int what, int subId)934     private void sendMessage(int what, int subId) {
935         mSatelliteEntitlementController.handleMessage(mHandler.obtainMessage(what, subId, 0));
936     }
937 
getValue(String originalObjectName)938     private Object getValue(String originalObjectName) throws Exception {
939         Field field = SatelliteEntitlementController.class.getDeclaredField(originalObjectName);
940         field.setAccessible(true);
941         return field.get(mSatelliteEntitlementController);
942     }
943 
944     public static class TestSatelliteEntitlementController extends SatelliteEntitlementController {
945         private SatelliteEntitlementApi mInjectSatelliteEntitlementApi;
946 
TestSatelliteEntitlementController(@onNull Context context, @NonNull Looper looper, SatelliteEntitlementApi api)947         TestSatelliteEntitlementController(@NonNull Context context, @NonNull Looper looper,
948                 SatelliteEntitlementApi api) {
949             super(context, looper);
950             mInjectSatelliteEntitlementApi = api;
951         }
952 
953         @Override
getSatelliteEntitlementApi(int subId)954         public SatelliteEntitlementApi getSatelliteEntitlementApi(int subId) {
955             logd("getSatelliteEntitlementApi");
956             return mInjectSatelliteEntitlementApi;
957         }
958     }
959 
logd(String log)960     private static void logd(String log) {
961         Log.d(TAG, log);
962     }
963 }
964