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 
18 package com.android.systemui.keyguard.data.quickaffordance
19 
20 import android.app.StatusBarManager
21 import android.app.admin.DevicePolicyManager
22 import android.content.Context
23 import android.content.pm.PackageManager
24 import androidx.test.ext.junit.runners.AndroidJUnit4
25 import androidx.test.filters.SmallTest
26 import com.android.systemui.RoboPilotTest
27 import com.android.systemui.SysuiTestCase
28 import com.android.systemui.camera.CameraGestureHelper
29 import com.android.systemui.settings.UserTracker
30 import com.android.systemui.util.mockito.whenever
31 import com.google.common.truth.Truth
32 import kotlinx.coroutines.ExperimentalCoroutinesApi
33 import kotlinx.coroutines.test.StandardTestDispatcher
34 import kotlinx.coroutines.test.TestScope
35 import kotlinx.coroutines.test.runTest
36 import org.junit.Assert.assertEquals
37 import org.junit.Before
38 import org.junit.Test
39 import org.junit.runner.RunWith
40 import org.mockito.Mock
41 import org.mockito.Mockito.verify
42 import org.mockito.MockitoAnnotations
43 
44 @OptIn(ExperimentalCoroutinesApi::class)
45 @SmallTest
46 @RoboPilotTest
47 @RunWith(AndroidJUnit4::class)
48 class CameraQuickAffordanceConfigTest : SysuiTestCase() {
49 
50     @Mock private lateinit var cameraGestureHelper: CameraGestureHelper
51     @Mock private lateinit var context: Context
52     @Mock private lateinit var packageManager: PackageManager
53     @Mock private lateinit var userTracker: UserTracker
54     @Mock private lateinit var devicePolicyManager: DevicePolicyManager
55 
56     private lateinit var underTest: CameraQuickAffordanceConfig
57     private lateinit var testScope: TestScope
58 
59     @Before
60     fun setUp() {
61         MockitoAnnotations.initMocks(this)
62         setLaunchable()
63 
64         val testDispatcher = StandardTestDispatcher()
65         testScope = TestScope(testDispatcher)
66         underTest =
67             CameraQuickAffordanceConfig(
68                 context,
69                 packageManager,
70                 { cameraGestureHelper },
71                 userTracker,
72                 devicePolicyManager,
73                 testDispatcher,
74             )
75     }
76 
77     @Test
78     fun affordanceTriggered_cameraLaunchCalled() {
79         // When
80         val result = underTest.onTriggered(null)
81 
82         // Then
83         verify(cameraGestureHelper)
84             .launchCamera(StatusBarManager.CAMERA_LAUNCH_SOURCE_QUICK_AFFORDANCE)
85         assertEquals(KeyguardQuickAffordanceConfig.OnTriggeredResult.Handled, result)
86     }
87 
88     @Test
89     fun getPickerScreenState_defaultWhenLaunchable() =
90         testScope.runTest {
91             setLaunchable(true)
92 
93             Truth.assertThat(underTest.getPickerScreenState())
94                 .isInstanceOf(KeyguardQuickAffordanceConfig.PickerScreenState.Default::class.java)
95         }
96 
97     @Test
98     fun getPickerScreenState_unavailableWhenCameraAppNotInstalled() =
99         testScope.runTest {
100             setLaunchable(isCameraAppInstalled = false)
101 
102             Truth.assertThat(underTest.getPickerScreenState())
103                 .isEqualTo(KeyguardQuickAffordanceConfig.PickerScreenState.UnavailableOnDevice)
104         }
105 
106     @Test
107     fun getPickerScreenState_unavailableWhenCameraDisabledByAdmin() =
108         testScope.runTest {
109             setLaunchable(isCameraDisabledByDeviceAdmin = true)
110 
111             Truth.assertThat(underTest.getPickerScreenState())
112                 .isEqualTo(KeyguardQuickAffordanceConfig.PickerScreenState.UnavailableOnDevice)
113         }
114 
115     @Test
116     fun getPickerScreenState_unavailableWhenSecureCameraDisabledByAdmin() =
117         testScope.runTest {
118             setLaunchable(isSecureCameraDisabledByDeviceAdmin = true)
119 
120             Truth.assertThat(underTest.getPickerScreenState())
121                 .isEqualTo(KeyguardQuickAffordanceConfig.PickerScreenState.UnavailableOnDevice)
122         }
123 
124     private fun setLaunchable(
125         isCameraAppInstalled: Boolean = true,
126         isCameraDisabledByDeviceAdmin: Boolean = false,
127         isSecureCameraDisabledByDeviceAdmin: Boolean = false,
128     ) {
129         whenever(packageManager.hasSystemFeature(PackageManager.FEATURE_CAMERA_ANY))
130             .thenReturn(isCameraAppInstalled)
131         whenever(devicePolicyManager.getCameraDisabled(null, userTracker.userId))
132             .thenReturn(isCameraDisabledByDeviceAdmin)
133         whenever(devicePolicyManager.getKeyguardDisabledFeatures(null, userTracker.userId))
134             .thenReturn(
135                 if (isSecureCameraDisabledByDeviceAdmin) {
136                     DevicePolicyManager.KEYGUARD_DISABLE_SECURE_CAMERA
137                 } else {
138                     0
139                 }
140             )
141     }
142 }
143