1 /*
2  * Copyright (C) 2016 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.managedprovisioning.analytics;
18 
19 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_ACCOUNT_TO_MIGRATE;
20 import static android.app.admin.DevicePolicyManager.EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME;
21 import static android.app.admin.DevicePolicyManager.MIME_TYPE_PROVISIONING_NFC;
22 
23 import static com.android.managedprovisioning.common.Globals.ACTION_RESUME_PROVISIONING;
24 
25 import static com.google.common.truth.Truth.assertThat;
26 
27 import static org.mockito.Mockito.mock;
28 import static org.mockito.Mockito.when;
29 
30 import android.app.admin.DevicePolicyManager;
31 import android.content.Context;
32 import android.content.Intent;
33 import android.content.pm.PackageManager;
34 import android.nfc.NdefMessage;
35 import android.nfc.NdefRecord;
36 import android.nfc.NfcAdapter;
37 import android.test.AndroidTestCase;
38 import android.test.suitebuilder.annotation.SmallTest;
39 
40 import com.android.managedprovisioning.common.ManagedProvisioningSharedPreferences;
41 
42 import org.mockito.Mock;
43 import org.mockito.MockitoAnnotations;
44 
45 import java.io.ByteArrayOutputStream;
46 import java.util.List;
47 import java.util.Properties;
48 
49 /**
50  * Unit-tests for {@link AnalyticsUtils}.
51  */
52 @SmallTest
53 public class AnalyticsUtilsTest extends AndroidTestCase {
54     private static final String INVALID_PACKAGE_NAME = "invalid-package-name";
55     private static final String VALID_PACKAGE_NAME = "valid-package-name";
56     private static final String VALID_INSTALLER_PACKAGE = "valid-installer-package";
57     private static final String INVALID_PROVISIONING_EXTRA = "invalid-provisioning-extra";
58 
59     @Mock private Context mockContext;
60     @Mock private PackageManager mockPackageManager;
61 
62     @Override
setUp()63     public void setUp() {
64         // this is necessary for mockito to work
65         System.setProperty("dexmaker.dexcache", getContext().getCacheDir().toString());
66 
67         MockitoAnnotations.initMocks(this);
68 
69         when(mockContext.getPackageManager()).thenReturn(mockPackageManager);
70     }
71 
testGetInstallerPackageName_invalidPackage()72     public void testGetInstallerPackageName_invalidPackage() {
73         // WHEN getting installer package name for an invalid package.
74         when(mockPackageManager.getInstallerPackageName(INVALID_PACKAGE_NAME))
75                 .thenThrow(new IllegalArgumentException());
76         // THEN null should be returned and exception should be digested.
77         assertNull(AnalyticsUtils.getInstallerPackageName(mockContext, INVALID_PACKAGE_NAME));
78     }
79 
testGetInstallerPackageName_validPackage()80     public void testGetInstallerPackageName_validPackage() {
81         // WHEN getting installer package name for a valid package.
82         when(mockPackageManager.getInstallerPackageName(VALID_PACKAGE_NAME))
83                 .thenReturn(VALID_INSTALLER_PACKAGE);
84         // THEN valid installer package name should be returned.
85         assertEquals(VALID_INSTALLER_PACKAGE,
86                 AnalyticsUtils.getInstallerPackageName(mockContext, VALID_PACKAGE_NAME));
87     }
88 
testGetAllProvisioningExtras_NullIntent()89     public void testGetAllProvisioningExtras_NullIntent() {
90         // WHEN getting provisioning extras using null Intent.
91         List<String> provisioningExtras = AnalyticsUtils.getAllProvisioningExtras(null);
92         // THEN an empty list of valid provisioning extras should be returned.
93         assertEquals(0, provisioningExtras.size());
94     }
95 
testGetAllProvisioningExtras_ProvisioningResume()96     public void testGetAllProvisioningExtras_ProvisioningResume() {
97         // GIVEN provisioning was resumed
98         Intent intent = new Intent(ACTION_RESUME_PROVISIONING);
99         // WHEN getting provisioning extras using resume provisioning intent.
100         List<String> provisioningExtras = AnalyticsUtils.getAllProvisioningExtras(intent);
101         // THEN an empty list of valid provisioning extras should be returned.
102         assertEquals(0, provisioningExtras.size());
103     }
104 
testGetAllProvisioningExtras_NullBundleExtras()105     public void testGetAllProvisioningExtras_NullBundleExtras() {
106         // GIVEN intent has null extras
107         Intent intent = new Intent(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE);
108         // WHEN getting provisioning extras with null extras
109         List<String> provisioningExtras = AnalyticsUtils.getAllProvisioningExtras(intent);
110         // THEN an empty list of valid provisioning extras should be returned.
111         assertEquals(0, provisioningExtras.size());
112     }
113 
testGetAllProvisioningExtras_NullNfcProperties()114     public void testGetAllProvisioningExtras_NullNfcProperties() throws Exception {
115         // GIVEN intent has null extras
116         Intent intent = new Intent(NfcAdapter.ACTION_NDEF_DISCOVERED);
117         // WHEN getting provisioning extras with null extras
118         List<String> provisioningExtras = AnalyticsUtils.getAllProvisioningExtras(intent);
119         // THEN an empty list of valid provisioning extras should be returned.
120         assertEquals(0, provisioningExtras.size());
121     }
122 
testGetAllProvisioningExtras()123     public void testGetAllProvisioningExtras() {
124         // GIVEN intent with both valid and invalid provisioning extras
125         Intent intent = new Intent(DevicePolicyManager.ACTION_PROVISION_MANAGED_PROFILE);
126         intent.putExtra(EXTRA_PROVISIONING_ACCOUNT_TO_MIGRATE, "");
127         intent.putExtra(INVALID_PROVISIONING_EXTRA, "");
128         intent.putExtra(EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME, "");
129         // WHEN getting provisioning extras using the intent
130         List<String> provisioningExtras = AnalyticsUtils.getAllProvisioningExtras(intent);
131         // THEN a list of valid provisioning extras should be returned.
132         assertEquals(2, provisioningExtras.size());
133         provisioningExtras.contains(EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME);
134         provisioningExtras.contains(EXTRA_PROVISIONING_ACCOUNT_TO_MIGRATE);
135     }
136 
testGetAllProvisioningExtras_Nfc()137     public void testGetAllProvisioningExtras_Nfc() throws Exception {
138         // GIVEN a Nfc intent with both valid and invalid provisioning extras
139         Properties props = new Properties();
140         ByteArrayOutputStream stream = new ByteArrayOutputStream();
141         props.setProperty(INVALID_PROVISIONING_EXTRA, "");
142         props.setProperty(EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME, "");
143         props.store(stream, "NFC provisioning intent" /* data description */);
144 
145         NdefRecord record = NdefRecord.createMime(
146                 DevicePolicyManager.MIME_TYPE_PROVISIONING_NFC,
147                 stream.toByteArray());
148         NdefMessage ndfMsg = new NdefMessage(new NdefRecord[]{record});
149 
150         Intent intent = new Intent(NfcAdapter.ACTION_NDEF_DISCOVERED)
151                 .setType(MIME_TYPE_PROVISIONING_NFC)
152                 .putExtra(NfcAdapter.EXTRA_NDEF_MESSAGES, new NdefMessage[]{ndfMsg});
153 
154         // WHEN getting provisioning extras using the intent
155         List<String> provisioningExtras = AnalyticsUtils.getAllProvisioningExtras(intent);
156         // THEN a list of valid provisioning extras should be returned.
157         assertEquals(1, provisioningExtras.size());
158         provisioningExtras.contains(EXTRA_PROVISIONING_DEVICE_ADMIN_COMPONENT_NAME);
159     }
160 
testGetProvisioningTime_shouldReturnDiff()161     public void testGetProvisioningTime_shouldReturnDiff() {
162         final ManagedProvisioningSharedPreferences mockPrefs =
163                 mock(ManagedProvisioningSharedPreferences.class);
164         when(mockPrefs.getProvisioningStartedTimestamp()).thenReturn(5L);
165 
166         assertThat(AnalyticsUtils.getProvisioningTime(mockPrefs, () -> 20L)).isEqualTo(15L);
167     }
168 
testGetProvisioningTime_shouldReturnZero()169     public void testGetProvisioningTime_shouldReturnZero() {
170         final ManagedProvisioningSharedPreferences mockPrefs =
171                 mock(ManagedProvisioningSharedPreferences.class);
172         when(mockPrefs.getProvisioningStartedTimestamp()).thenReturn(0L);
173 
174         assertThat(AnalyticsUtils.getProvisioningTime(mockPrefs, () -> 20L)).isEqualTo(-1);
175     }
176 }
177