1 /*
2  * Copyright (C) 2018 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.settings.print;
18 
19 import static androidx.lifecycle.Lifecycle.Event.ON_START;
20 import static androidx.lifecycle.Lifecycle.Event.ON_STOP;
21 
22 import static com.android.settings.core.BasePreferenceController.AVAILABLE;
23 import static com.android.settings.core.BasePreferenceController.UNSUPPORTED_ON_DEVICE;
24 
25 import static com.google.common.truth.Truth.assertThat;
26 
27 import static org.mockito.Mockito.mock;
28 import static org.mockito.Mockito.never;
29 import static org.mockito.Mockito.spy;
30 import static org.mockito.Mockito.verify;
31 import static org.mockito.Mockito.when;
32 
33 import android.content.Context;
34 import android.content.pm.PackageManager;
35 import android.os.UserManager;
36 import android.print.PrintJob;
37 import android.print.PrintJobInfo;
38 import android.print.PrintManager;
39 import android.printservice.PrintServiceInfo;
40 
41 import androidx.lifecycle.LifecycleOwner;
42 
43 import com.android.settings.R;
44 import com.android.settingslib.RestrictedPreference;
45 import com.android.settingslib.core.lifecycle.Lifecycle;
46 
47 import org.junit.Before;
48 import org.junit.Test;
49 import org.junit.runner.RunWith;
50 import org.mockito.Mock;
51 import org.mockito.Mockito;
52 import org.mockito.MockitoAnnotations;
53 import org.robolectric.RobolectricTestRunner;
54 import org.robolectric.RuntimeEnvironment;
55 import org.robolectric.util.ReflectionHelpers;
56 
57 import java.util.ArrayList;
58 import java.util.List;
59 
60 @RunWith(RobolectricTestRunner.class)
61 public class PrintSettingsPreferenceControllerTest {
62 
63     @Mock
64     private PrintManager mPrintManager;
65     @Mock
66     private UserManager mUserManager;
67     @Mock
68     private RestrictedPreference mPreference;
69     @Mock
70     private PackageManager mPackageManager;
71 
72     private Context mContext;
73     private PrintSettingPreferenceController mController;
74     private LifecycleOwner mLifecycleOwner;
75     private Lifecycle mLifecycle;
76 
77     @Before
setUp()78     public void setUp() {
79         MockitoAnnotations.initMocks(this);
80         mContext = spy(RuntimeEnvironment.application);
81         when(mContext.getSystemService(Context.USER_SERVICE)).thenReturn(mUserManager);
82         mPreference = spy(new RestrictedPreference(mContext));
83         mController = new PrintSettingPreferenceController(mContext);
84         mLifecycleOwner = () -> mLifecycle;
85         mLifecycle = new Lifecycle(mLifecycleOwner);
86         ReflectionHelpers.setField(mController, "mPrintManager", mPrintManager);
87         ReflectionHelpers.setField(mController, "mPackageManager", mPackageManager);
88         mLifecycle.addObserver(mController);
89     }
90 
91     @Test
onStartStop_shouldRegisterPrintStateListener()92     public void onStartStop_shouldRegisterPrintStateListener() {
93         mLifecycle.handleLifecycleEvent(ON_START);
94         mLifecycle.handleLifecycleEvent(ON_STOP);
95 
96         verify(mPrintManager).addPrintJobStateChangeListener(mController);
97         verify(mPrintManager).removePrintJobStateChangeListener(mController);
98     }
99 
100     @Test
onStartStop_printManagerIsNull_doNothing()101     public void onStartStop_printManagerIsNull_doNothing() {
102         ReflectionHelpers.setField(mController, "mPrintManager", null);
103 
104         mLifecycle.handleLifecycleEvent(ON_START);
105         mLifecycle.handleLifecycleEvent(ON_STOP);
106 
107         verify(mPrintManager, never()).addPrintJobStateChangeListener(mController);
108         verify(mPrintManager, never()).removePrintJobStateChangeListener(mController);
109     }
110 
111     @Test
updateState_hasActiveJob_shouldSetSummaryToNumberOfJobs()112     public void updateState_hasActiveJob_shouldSetSummaryToNumberOfJobs() {
113         final List<PrintJob> printJobs = new ArrayList<>();
114         final PrintJob job = mock(PrintJob.class, Mockito.RETURNS_DEEP_STUBS);
115         printJobs.add(job);
116         when(job.getInfo().getState()).thenReturn(PrintJobInfo.STATE_STARTED);
117         when(mPrintManager.getPrintJobs()).thenReturn(printJobs);
118 
119         mController.updateState(mPreference);
120 
121         assertThat(mPreference.getSummary())
122                 .isEqualTo(mContext.getResources()
123                         .getQuantityString(R.plurals.print_jobs_summary, 1, 1));
124     }
125 
126     @Test
updateState_shouldSetSummaryToNumberOfPrintServices()127     public void updateState_shouldSetSummaryToNumberOfPrintServices() {
128         final List<PrintServiceInfo> printServices = mock(List.class);
129         when(printServices.isEmpty()).thenReturn(false);
130         when(printServices.size()).thenReturn(2);
131         // 2 services
132         when(mPrintManager.getPrintServices(PrintManager.ENABLED_SERVICES))
133                 .thenReturn(printServices);
134 
135         mController.updateState(mPreference);
136 
137         assertThat(mPreference.getSummary())
138                 .isEqualTo(mContext.getResources()
139                         .getQuantityString(R.plurals.print_settings_summary, 2, 2));
140 
141         // No service
142         when(mPrintManager.getPrintServices(PrintManager.ENABLED_SERVICES)).thenReturn(null);
143 
144         mController.updateState(mPreference);
145 
146         assertThat(mPreference.getSummary())
147                 .isEqualTo(mContext.getString(R.string.print_settings_summary_no_service));
148     }
149 
150     @Test
updateState_shouldCheckRestriction()151     public void updateState_shouldCheckRestriction() {
152         mController.updateState(mPreference);
153         verify(mPreference).checkRestrictionAndSetDisabled(UserManager.DISALLOW_PRINTING);
154     }
155 
156     @Test
getAvailabilityStatus_hasFeature_returnsAvailable()157     public void getAvailabilityStatus_hasFeature_returnsAvailable() {
158         when(mPackageManager.hasSystemFeature(PackageManager.FEATURE_PRINTING))
159                 .thenReturn(true);
160 
161         assertThat(mController.getAvailabilityStatus()).isEqualTo(AVAILABLE);
162     }
163 
164     @Test
getAvailabilityStatus_noFeature_returnsUnsupported()165     public void getAvailabilityStatus_noFeature_returnsUnsupported() {
166         when(mPackageManager.hasSystemFeature(PackageManager.FEATURE_PRINTING))
167                 .thenReturn(false);
168 
169         assertThat(mController.getAvailabilityStatus()).isEqualTo(UNSUPPORTED_ON_DEVICE);
170     }
171 
172     @Test
getAvailabilityStatus_printManagerIsNull_returnsUnsupported()173     public void getAvailabilityStatus_printManagerIsNull_returnsUnsupported() {
174         ReflectionHelpers.setField(mController, "mPrintManager", null);
175         when(mPackageManager.hasSystemFeature(PackageManager.FEATURE_PRINTING))
176                 .thenReturn(true);
177 
178         assertThat(mController.getAvailabilityStatus()).isEqualTo(UNSUPPORTED_ON_DEVICE);
179     }
180 }
181