• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2023 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.bluetooth;
18 
19 import static com.google.common.truth.Truth.assertThat;
20 
21 import static org.mockito.ArgumentMatchers.anyInt;
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.spy;
26 import static org.mockito.Mockito.verify;
27 import static org.mockito.Mockito.when;
28 
29 import android.bluetooth.BluetoothAdapter;
30 import android.bluetooth.BluetoothDevice;
31 import android.bluetooth.BluetoothProfile;
32 import android.content.Context;
33 import android.content.res.Resources;
34 import android.graphics.drawable.Drawable;
35 import android.util.Pair;
36 
37 import androidx.test.core.app.ApplicationProvider;
38 
39 import com.android.settings.testutils.shadow.ShadowBluetoothAdapter;
40 import com.android.settingslib.bluetooth.CachedBluetoothDevice;
41 import com.android.settingslib.bluetooth.LocalBluetoothManager;
42 
43 import org.junit.Before;
44 import org.junit.Rule;
45 import org.junit.Test;
46 import org.junit.runner.RunWith;
47 import org.mockito.Answers;
48 import org.mockito.Mock;
49 import org.mockito.junit.MockitoJUnit;
50 import org.mockito.junit.MockitoRule;
51 import org.robolectric.RobolectricTestRunner;
52 import org.robolectric.annotation.Config;
53 import org.robolectric.shadow.api.Shadow;
54 
55 /** Tests for {@link BluetoothDevicePairingDetailBase}. */
56 @RunWith(RobolectricTestRunner.class)
57 @Config(shadows = {ShadowBluetoothAdapter.class})
58 public class BluetoothDevicePairingDetailBaseTest {
59 
60     @Rule
61     public final MockitoRule mockito = MockitoJUnit.rule();
62 
63     public static final String KEY_DEVICE_LIST_GROUP = "test_key";
64 
65     private static final String TEST_DEVICE_ADDRESS = "00:A1:A1:A1:A1:A1";
66     private static final String TEST_DEVICE_ADDRESS_B = "00:B1:B1:B1:B1:B1";
67     private final Context mContext = ApplicationProvider.getApplicationContext();
68 
69     @Mock
70     private Resources mResource;
71     @Mock(answer = Answers.RETURNS_DEEP_STUBS)
72     private LocalBluetoothManager mLocalManager;
73     @Mock
74     private CachedBluetoothDevice mCachedBluetoothDevice;
75     @Mock
76     private Drawable mDrawable;
77     private BluetoothAdapter mBluetoothAdapter;
78     private ShadowBluetoothAdapter mShadowBluetoothAdapter;
79     private BluetoothProgressCategory mAvailableDevicesCategory;
80     private BluetoothDevice mBluetoothDevice;
81     private TestBluetoothDevicePairingDetailBase mFragment;
82 
83     @Before
setUp()84     public void setUp() {
85         mAvailableDevicesCategory = spy(new BluetoothProgressCategory(mContext));
86         mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter();
87         mShadowBluetoothAdapter = Shadow.extract(BluetoothAdapter.getDefaultAdapter());
88         when(mCachedBluetoothDevice.getAddress()).thenReturn(TEST_DEVICE_ADDRESS);
89         final Pair<Drawable, String> pairs = new Pair<>(mDrawable, "fake_device");
90         when(mCachedBluetoothDevice.getDrawableWithDescription()).thenReturn(pairs);
91         mBluetoothDevice = mBluetoothAdapter.getRemoteDevice(TEST_DEVICE_ADDRESS);
92 
93         mFragment = spy(new TestBluetoothDevicePairingDetailBase());
94         when(mFragment.findPreference(KEY_DEVICE_LIST_GROUP)).thenReturn(mAvailableDevicesCategory);
95         doReturn(mContext).when(mFragment).getContext();
96         doReturn(mResource).when(mFragment).getResources();
97         mFragment.mDeviceListGroup = mAvailableDevicesCategory;
98         mFragment.mLocalManager = mLocalManager;
99         mFragment.mBluetoothAdapter = mBluetoothAdapter;
100         mFragment.initPreferencesFromPreferenceScreen();
101 
102     }
103 
104     @Test
startScanning_startScanAndRemoveDevices()105     public void startScanning_startScanAndRemoveDevices() {
106         mFragment.enableScanning();
107 
108         verify(mFragment).startScanning();
109         verify(mAvailableDevicesCategory).removeAll();
110     }
111 
112     @Test
updateContent_stateOn()113     public void updateContent_stateOn() {
114         mFragment.updateContent(BluetoothAdapter.STATE_ON);
115 
116         assertThat(mBluetoothAdapter.isEnabled()).isTrue();
117         verify(mFragment).enableScanning();
118     }
119 
120     @Test
updateContent_stateOff_finish()121     public void updateContent_stateOff_finish() {
122         mFragment.updateContent(BluetoothAdapter.STATE_OFF);
123 
124         verify(mFragment).finish();
125     }
126 
127     @Test
updateBluetooth_bluetoothOff_turnOnBluetooth()128     public void updateBluetooth_bluetoothOff_turnOnBluetooth() {
129         mShadowBluetoothAdapter.setEnabled(false);
130 
131         mFragment.updateBluetooth();
132 
133         assertThat(mBluetoothAdapter.isEnabled()).isTrue();
134     }
135 
136     @Test
updateBluetooth_bluetoothOn_updateState()137     public void updateBluetooth_bluetoothOn_updateState() {
138         mShadowBluetoothAdapter.setEnabled(true);
139         doNothing().when(mFragment).updateContent(anyInt());
140 
141         mFragment.updateBluetooth();
142 
143         verify(mFragment).updateContent(anyInt());
144     }
145 
146     @Test
onBluetoothStateChanged_whenTurnedOnBTShowToast()147     public void onBluetoothStateChanged_whenTurnedOnBTShowToast() {
148         doNothing().when(mFragment).updateContent(anyInt());
149 
150         mFragment.onBluetoothStateChanged(BluetoothAdapter.STATE_ON);
151 
152         verify(mFragment).showBluetoothTurnedOnToast();
153     }
154 
155     @Test
onProfileConnectionStateChanged_deviceInSelectedListAndConnected_finish()156     public void onProfileConnectionStateChanged_deviceInSelectedListAndConnected_finish() {
157         final BluetoothDevice device = mBluetoothAdapter.getRemoteDevice(TEST_DEVICE_ADDRESS_B);
158         mFragment.mSelectedList.add(mBluetoothDevice);
159         mFragment.mSelectedList.add(device);
160 
161         when(mCachedBluetoothDevice.isConnected()).thenReturn(true);
162         when(mCachedBluetoothDevice.getDevice()).thenReturn(device);
163 
164         mFragment.onProfileConnectionStateChanged(mCachedBluetoothDevice,
165                 BluetoothProfile.A2DP, BluetoothAdapter.STATE_CONNECTED);
166 
167         verify(mFragment).finish();
168     }
169 
170     @Test
onProfileConnectionStateChanged_deviceNotInSelectedList_doNothing()171     public void onProfileConnectionStateChanged_deviceNotInSelectedList_doNothing() {
172         final BluetoothDevice device = mBluetoothAdapter.getRemoteDevice(TEST_DEVICE_ADDRESS_B);
173         mFragment.mSelectedList.add(device);
174 
175         when(mCachedBluetoothDevice.isConnected()).thenReturn(true);
176         when(mCachedBluetoothDevice.getDevice()).thenReturn(mBluetoothDevice);
177 
178         mFragment.onProfileConnectionStateChanged(mCachedBluetoothDevice,
179                 BluetoothProfile.A2DP, BluetoothAdapter.STATE_CONNECTED);
180 
181         // not crash
182     }
183 
184     @Test
onProfileConnectionStateChanged_deviceDisconnected_doNothing()185     public void onProfileConnectionStateChanged_deviceDisconnected_doNothing() {
186         final BluetoothDevice device = mBluetoothAdapter.getRemoteDevice(TEST_DEVICE_ADDRESS_B);
187         mFragment.mSelectedList.add(mBluetoothDevice);
188         mFragment.mSelectedList.add(device);
189 
190         when(mCachedBluetoothDevice.isConnected()).thenReturn(false);
191         when(mCachedBluetoothDevice.getDevice()).thenReturn(device);
192 
193         mFragment.onProfileConnectionStateChanged(mCachedBluetoothDevice,
194                 BluetoothProfile.A2DP, BluetoothAdapter.STATE_DISCONNECTED);
195 
196         // not crash
197     }
198 
199     @Test
onProfileConnectionStateChanged_deviceInPreferenceMapAndConnected_removed()200     public void onProfileConnectionStateChanged_deviceInPreferenceMapAndConnected_removed() {
201         final BluetoothDevicePreference preference =
202                 new BluetoothDevicePreference(mContext, mCachedBluetoothDevice,
203                         true, BluetoothDevicePreference.SortType.TYPE_FIFO);
204         final BluetoothDevice device = mBluetoothAdapter.getRemoteDevice(TEST_DEVICE_ADDRESS);
205         mFragment.getDevicePreferenceMap().put(mCachedBluetoothDevice, preference);
206 
207         when(mCachedBluetoothDevice.isConnected()).thenReturn(true);
208         when(mCachedBluetoothDevice.getDevice()).thenReturn(device);
209 
210         mFragment.onProfileConnectionStateChanged(mCachedBluetoothDevice,
211                 BluetoothProfile.A2DP, BluetoothAdapter.STATE_CONNECTED);
212 
213         assertThat(mFragment.getDevicePreferenceMap().size()).isEqualTo(0);
214     }
215 
216     @Test
onProfileConnectionStateChanged_deviceNotInPreferenceMap_doNothing()217     public void onProfileConnectionStateChanged_deviceNotInPreferenceMap_doNothing() {
218         final CachedBluetoothDevice cachedDevice = mock(CachedBluetoothDevice.class);
219         final BluetoothDevicePreference preference =
220                 new BluetoothDevicePreference(mContext, mCachedBluetoothDevice,
221                         true, BluetoothDevicePreference.SortType.TYPE_FIFO);
222         final BluetoothDevice device = mBluetoothAdapter.getRemoteDevice(TEST_DEVICE_ADDRESS);
223         final BluetoothDevice device2 = mBluetoothAdapter.getRemoteDevice(TEST_DEVICE_ADDRESS_B);
224         mFragment.getDevicePreferenceMap().put(mCachedBluetoothDevice, preference);
225 
226         when(mCachedBluetoothDevice.isConnected()).thenReturn(true);
227         when(mCachedBluetoothDevice.getDevice()).thenReturn(device);
228         when(cachedDevice.isConnected()).thenReturn(true);
229         when(cachedDevice.getDevice()).thenReturn(device2);
230         when(cachedDevice.getAddress()).thenReturn(TEST_DEVICE_ADDRESS_B);
231         when(cachedDevice.getIdentityAddress()).thenReturn(TEST_DEVICE_ADDRESS_B);
232 
233         mFragment.onProfileConnectionStateChanged(cachedDevice, BluetoothProfile.A2DP,
234                 BluetoothAdapter.STATE_CONNECTED);
235 
236         // not crash
237     }
238 
239     private static class TestBluetoothDevicePairingDetailBase extends
240             BluetoothDevicePairingDetailBase {
241 
TestBluetoothDevicePairingDetailBase()242         TestBluetoothDevicePairingDetailBase() {
243             super();
244         }
245 
246         @Override
getMetricsCategory()247         public int getMetricsCategory() {
248             return 0;
249         }
250 
251         @Override
getDeviceListKey()252         public String getDeviceListKey() {
253             return KEY_DEVICE_LIST_GROUP;
254         }
255 
256         @Override
getPreferenceScreenResId()257         protected int getPreferenceScreenResId() {
258             return 0;
259         }
260 
261         @Override
getLogTag()262         protected String getLogTag() {
263             return "test_tag";
264         }
265     }
266 }
267