• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 package com.android.adservices.measurement;
17 
18 import static org.junit.Assert.assertNotNull;
19 import static org.junit.Assert.assertNull;
20 import static org.mockito.ArgumentMatchers.any;
21 import static org.mockito.ArgumentMatchers.eq;
22 import static org.mockito.Mockito.doNothing;
23 import static org.mockito.Mockito.doReturn;
24 import static org.mockito.Mockito.mock;
25 import static org.mockito.Mockito.never;
26 import static org.mockito.Mockito.spy;
27 import static org.mockito.Mockito.times;
28 import static org.mockito.Mockito.verify;
29 
30 import android.content.Context;
31 import android.content.Intent;
32 import android.content.pm.PackageManager;
33 import android.os.IBinder;
34 
35 import androidx.test.core.app.ApplicationProvider;
36 
37 import com.android.adservices.common.AdServicesExtendedMockitoTestCase;
38 import com.android.adservices.service.FlagsFactory;
39 import com.android.adservices.service.common.PackageChangedReceiver;
40 import com.android.adservices.service.consent.AdServicesApiConsent;
41 import com.android.adservices.service.consent.AdServicesApiType;
42 import com.android.adservices.service.consent.ConsentManager;
43 import com.android.adservices.service.measurement.MeasurementServiceImpl;
44 import com.android.compatibility.common.util.TestUtils;
45 import com.android.dx.mockito.inline.extended.ExtendedMockito;
46 import com.android.modules.utils.testing.ExtendedMockitoRule.SpyStatic;
47 
48 import org.junit.Test;
49 import org.mockito.Mock;
50 
51 /** Unit test for {@link com.android.adservices.measurement.MeasurementService}. */
52 @SpyStatic(ConsentManager.class)
53 @SpyStatic(FlagsFactory.class)
54 @SpyStatic(PackageChangedReceiver.class)
55 public final class MeasurementServiceTest extends AdServicesExtendedMockitoTestCase {
56     @Mock private ConsentManager mMockConsentManager;
57     @Mock private MeasurementServiceImpl mSpyServiceImpl;
58     private MeasurementService mSpyService;
59 
60     /** Test kill switch off with consent given */
61     @Test
testBindableMeasurementService_killSwitchOff_gaUxEnabled_consentGiven()62     public void testBindableMeasurementService_killSwitchOff_gaUxEnabled_consentGiven()
63             throws Exception {
64         runWithMocks(
65                 /* killSwitchOff */ false,
66                 /* consentNotifiedState */
67                 /* consentGiven */ true,
68                 () -> {
69                     // Execute
70                     final IBinder binder = onCreateAndOnBindService();
71 
72                     // Verification
73                     assertNotNull(binder);
74                     verify(mMockConsentManager, never()).getConsent();
75                     verify(mMockConsentManager, times(1))
76                             .getConsent(eq(AdServicesApiType.MEASUREMENTS));
77                     ExtendedMockito.verify(
78                             () -> PackageChangedReceiver.enableReceiver(any(Context.class), any()));
79                     assertJobScheduled(/* timesCalled */ 1);
80                 });
81     }
82 
83     /** Test kill switch off with consent revoked */
84     @Test
testBindableMeasurementService_killSwitchOff_gaUxEnabled_consentRevoked()85     public void testBindableMeasurementService_killSwitchOff_gaUxEnabled_consentRevoked()
86             throws Exception {
87         runWithMocks(
88                 /* killSwitchOff */ false,
89                 /* consentNotifiedState */
90                 /* consentRevoked */ false,
91                 () -> {
92                     // Execute
93                     final IBinder binder = onCreateAndOnBindService();
94 
95                     // Verification
96                     assertNotNull(binder);
97                     verify(mMockConsentManager, never()).getConsent();
98                     verify(mMockConsentManager, times(1))
99                             .getConsent(eq(AdServicesApiType.MEASUREMENTS));
100                     assertJobScheduled(/* timesCalled */ 0);
101                 });
102     }
103 
104     /** Test kill switch on */
105     @Test
testBindableMeasurementService_killSwitchOn_gaUxEnabled()106     public void testBindableMeasurementService_killSwitchOn_gaUxEnabled() throws Exception {
107         runWithMocks(
108                 /* killSwitchOn */ true,
109                 /* consentGiven */ true,
110                 () -> {
111                     // Execute
112                     final IBinder binder = onCreateAndOnBindService();
113 
114                     // Verification
115                     assertNull(binder);
116                     verify(mMockConsentManager, never()).getConsent();
117                     verify(mMockConsentManager, never()).getConsent(any());
118                     assertJobScheduled(/* timesCalled */ 0);
119                 });
120     }
121 
getIntentForMeasurementService()122     private Intent getIntentForMeasurementService() {
123         return new Intent(ApplicationProvider.getApplicationContext(), MeasurementService.class);
124     }
125 
onCreateAndOnBindService()126     private IBinder onCreateAndOnBindService() {
127         doReturn(mock(PackageManager.class)).when(mSpyService).getPackageManager();
128         mSpyService.onCreate();
129         return mSpyService.onBind(getIntentForMeasurementService());
130     }
131 
runWithMocks( boolean killSwitchStatus, boolean consentStatus, TestUtils.RunnableWithThrow execute)132     private void runWithMocks(
133             boolean killSwitchStatus, boolean consentStatus, TestUtils.RunnableWithThrow execute)
134             throws Exception {
135         mSpyService = spy(new MeasurementService(mSpyServiceImpl));
136         doReturn(!killSwitchStatus).when(mMockFlags).getMeasurementEnabled();
137 
138         doNothing().when(mSpyServiceImpl).schedulePeriodicJobs(any());
139         ExtendedMockito.doReturn(mMockFlags).when(FlagsFactory::getFlags);
140         ExtendedMockito.doReturn(mMockConsentManager).when(ConsentManager::getInstance);
141 
142         final AdServicesApiConsent mockConsent = mock(AdServicesApiConsent.class);
143         doReturn(consentStatus).when(mockConsent).isGiven();
144 
145         doReturn(mockConsent)
146                 .when(mMockConsentManager)
147                 .getConsent(eq(AdServicesApiType.MEASUREMENTS));
148 
149         ExtendedMockito.doReturn(true)
150                 .when(() -> PackageChangedReceiver.enableReceiver(any(Context.class), any()));
151 
152         // Execute
153         execute.run();
154     }
155 
assertJobScheduled(int timesCalled)156     private void assertJobScheduled(int timesCalled) {
157         verify(mSpyServiceImpl, times(timesCalled)).schedulePeriodicJobs(any());
158     }
159 }
160