Chromium Code Reviews| OLD | NEW |
|---|---|
| (Empty) | |
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. | |
| 2 // Use of this source code is governed by a BSD-style license that can be | |
| 3 // found in the LICENSE file. | |
| 4 | |
| 5 package org.chromium.device.sensors; | |
| 6 | |
| 7 import static org.junit.Assert.assertEquals; | |
| 8 import static org.junit.Assert.assertNotNull; | |
| 9 import static org.junit.Assert.assertNull; | |
| 10 import static org.mockito.ArgumentMatchers.any; | |
| 11 import static org.mockito.ArgumentMatchers.anyInt; | |
| 12 import static org.mockito.Mockito.doNothing; | |
| 13 import static org.mockito.Mockito.doReturn; | |
| 14 import static org.mockito.Mockito.mock; | |
| 15 import static org.mockito.Mockito.never; | |
| 16 import static org.mockito.Mockito.times; | |
| 17 import static org.mockito.Mockito.verify; | |
| 18 | |
| 19 import android.content.Context; | |
| 20 import android.hardware.Sensor; | |
| 21 import android.hardware.SensorEvent; | |
| 22 import android.hardware.SensorEventListener; | |
| 23 import android.hardware.SensorManager; | |
| 24 import android.os.Handler; | |
| 25 | |
| 26 import org.chromium.base.test.util.Feature; | |
| 27 import org.chromium.mojom.device.mojom.ReportingMode; | |
| 28 import org.chromium.mojom.device.mojom.SensorReadBuffer; | |
| 29 import org.chromium.mojom.device.mojom.SensorType; | |
| 30 import org.chromium.testing.local.LocalRobolectricTestRunner; | |
| 31 | |
| 32 import org.junit.Before; | |
| 33 import org.junit.Test; | |
| 34 import org.junit.runner.RunWith; | |
| 35 import org.mockito.Mock; | |
| 36 import org.mockito.MockitoAnnotations; | |
| 37 import org.robolectric.annotation.Config; | |
| 38 | |
| 39 import java.lang.reflect.Field; | |
| 40 import java.lang.reflect.Modifier; | |
| 41 import java.nio.ByteBuffer; | |
| 42 import java.nio.ByteOrder; | |
| 43 import java.util.ArrayList; | |
| 44 import java.util.List; | |
| 45 | |
| 46 /** | |
| 47 * Unit tests for PlatformSensorProvider | |
| 48 */ | |
| 49 @RunWith(LocalRobolectricTestRunner.class) | |
| 50 @Config(manifest = Config.NONE) | |
| 51 public class PlatformSensorProviderTest { | |
| 52 @Mock | |
| 53 private Context mContext; | |
| 54 @Mock | |
| 55 private SensorManager mSensorManager; | |
| 56 @Mock | |
| 57 private PlatformSensorProvider mPlatformSensorProvider; | |
| 58 private ByteBuffer mSharedBuffer; | |
| 59 private final List<Sensor> mMockSensors = new ArrayList<Sensor>(); | |
| 60 private static final long PLATFORM_SENSOR_ANDROID = 123456789L; | |
| 61 private static final long PLATFORM_SENSOR_TIMESTAMP = 314159265358979L; | |
| 62 private static final double MILLISECONDS_IN_NANOSECOND = 0.000001d; | |
| 63 | |
| 64 @Before | |
| 65 public void setUp() { | |
| 66 MockitoAnnotations.initMocks(this); | |
| 67 doReturn(mSensorManager).when(mContext).getSystemService(Context.SENSOR_ SERVICE); | |
| 68 doReturn(mMockSensors).when(mSensorManager).getSensorList(anyInt()); | |
| 69 doReturn(mSensorManager).when(mPlatformSensorProvider).getSensorManager( ); | |
| 70 doReturn(new Handler()).when(mPlatformSensorProvider).getHandler(); | |
| 71 // By default, allow successful registration of SensorEventListeners. | |
| 72 doReturn(true) | |
| 73 .when(mSensorManager) | |
| 74 .registerListener(any(SensorEventListener.class), any(Sensor.cla ss), anyInt(), | |
| 75 any(Handler.class)); | |
| 76 doNothing().when(mPlatformSensorProvider).sensorStarted(any(PlatformSens or.class)); | |
| 77 doNothing().when(mPlatformSensorProvider).sensorStopped(any(PlatformSens or.class)); | |
| 78 } | |
| 79 | |
| 80 @Test | |
| 81 @Feature({"PlatformSensorProvider"}) | |
| 82 public void testNullSensorManager() { | |
| 83 doReturn(null).when(mContext).getSystemService(Context.SENSOR_SERVICE); | |
| 84 PlatformSensorProvider provider = PlatformSensorProvider.create(mContext ); | |
| 85 PlatformSensor sensor = provider.createSensor(SensorType.AMBIENT_LIGHT); | |
| 86 assertNull(sensor); | |
| 87 } | |
| 88 | |
| 89 @Test | |
| 90 @Feature({"PlatformSensorProvider"}) | |
| 91 public void testSensorNotSupported() { | |
| 92 PlatformSensorProvider provider = PlatformSensorProvider.create(mContext ); | |
| 93 PlatformSensor sensor = provider.createSensor(SensorType.AMBIENT_LIGHT); | |
| 94 assertNull(sensor); | |
| 95 } | |
| 96 | |
| 97 @Test | |
| 98 @Feature({"PlatformSensorProvider"}) | |
| 99 public void testSensorTypeMappings() { | |
| 100 PlatformSensorProvider provider = PlatformSensorProvider.create(mContext ); | |
| 101 provider.createSensor(SensorType.AMBIENT_LIGHT); | |
| 102 verify(mSensorManager).getSensorList(Sensor.TYPE_LIGHT); | |
| 103 provider.createSensor(SensorType.ACCELEROMETER); | |
| 104 verify(mSensorManager).getSensorList(Sensor.TYPE_ACCELEROMETER); | |
| 105 provider.createSensor(SensorType.LINEAR_ACCELERATION); | |
| 106 verify(mSensorManager).getSensorList(Sensor.TYPE_LINEAR_ACCELERATION); | |
| 107 provider.createSensor(SensorType.GYROSCOPE); | |
| 108 verify(mSensorManager).getSensorList(Sensor.TYPE_GYROSCOPE); | |
| 109 provider.createSensor(SensorType.MAGNETOMETER); | |
| 110 verify(mSensorManager).getSensorList(Sensor.TYPE_MAGNETIC_FIELD); | |
| 111 } | |
| 112 | |
| 113 @Test | |
| 114 @Feature({"PlatformSensorProvider"}) | |
| 115 public void testSensorSupported() { | |
| 116 PlatformSensor sensor = createPlatformSensor(50000, Sensor.TYPE_LIGHT, | |
| 117 SensorType.AMBIENT_LIGHT, Sensor.REPORTING_MODE_ON_CHANGE); | |
| 118 assertNotNull(sensor); | |
| 119 } | |
| 120 | |
| 121 @Test | |
| 122 @Feature({"PlatformSensor"}) | |
| 123 public void testSensorStartStop() { | |
|
timvolodine
2016/09/06 17:44:37
- can we have a test with multiple sensors?
- e.g.
shalamov
2016/09/07 13:53:42
Done.
| |
| 124 addMockSensor(50000, Sensor.TYPE_ACCELEROMETER, Sensor.REPORTING_MODE_CO NTINUOUS); | |
| 125 PlatformSensor sensor = | |
| 126 PlatformSensor.create(Sensor.TYPE_ACCELEROMETER, 3, mPlatformSen sorProvider); | |
| 127 assertNotNull(sensor); | |
| 128 | |
| 129 sensor.startSensor(5); | |
| 130 sensor.stopSensor(); | |
| 131 | |
| 132 // Multiple start invocations. | |
| 133 sensor.startSensor(1); | |
| 134 sensor.startSensor(2); | |
| 135 sensor.startSensor(3); | |
| 136 // Same frequency, should not restart sensor | |
| 137 sensor.startSensor(3); | |
| 138 | |
| 139 // Started polling with 5, 1, 2 and 3 Hz frequency. | |
| 140 verify(mPlatformSensorProvider, times(4)).getHandler(); | |
| 141 verify(mPlatformSensorProvider, times(4)).sensorStarted(sensor); | |
| 142 verify(mSensorManager, times(4)) | |
| 143 .registerListener(any(SensorEventListener.class), any(Sensor.cla ss), anyInt(), | |
|
timvolodine
2016/09/06 17:44:37
is it also possible to test that unregisterListene
shalamov
2016/09/07 13:53:42
Done.
| |
| 144 any(Handler.class)); | |
| 145 | |
| 146 sensor.stopSensor(); | |
| 147 sensor.stopSensor(); | |
| 148 verify(mPlatformSensorProvider, times(3)).sensorStopped(sensor); | |
| 149 } | |
| 150 | |
| 151 @Test | |
| 152 @Feature({"PlatformSensor"}) | |
| 153 public void testSensorStartFails() { | |
| 154 addMockSensor(50000, Sensor.TYPE_ACCELEROMETER, Sensor.REPORTING_MODE_CO NTINUOUS); | |
| 155 PlatformSensor sensor = | |
| 156 PlatformSensor.create(Sensor.TYPE_ACCELEROMETER, 3, mPlatformSen sorProvider); | |
| 157 assertNotNull(sensor); | |
| 158 | |
| 159 doReturn(false) | |
| 160 .when(mSensorManager) | |
| 161 .registerListener(any(SensorEventListener.class), any(Sensor.cla ss), anyInt(), | |
| 162 any(Handler.class)); | |
| 163 | |
| 164 sensor.startSensor(5); | |
| 165 verify(mPlatformSensorProvider, times(1)).sensorStarted(sensor); | |
| 166 verify(mPlatformSensorProvider, times(1)).sensorStopped(sensor); | |
| 167 verify(mPlatformSensorProvider, times(1)).getHandler(); | |
| 168 } | |
| 169 | |
| 170 @Test | |
| 171 @Feature({"PlatformSensor"}) | |
| 172 public void testSensorConfiguration() { | |
| 173 // 5Hz min delay | |
| 174 PlatformSensor sensor = createPlatformSensor(200000, Sensor.TYPE_ACCELER OMETER, | |
| 175 SensorType.ACCELEROMETER, Sensor.REPORTING_MODE_CONTINUOUS); | |
| 176 assertEquals(true, sensor.checkSensorConfiguration(5)); | |
| 177 assertEquals(false, sensor.checkSensorConfiguration(6)); | |
| 178 } | |
| 179 | |
| 180 @Test | |
| 181 @Feature({"PlatformSensor"}) | |
| 182 public void testSensorOnChangeReportingMode() { | |
| 183 PlatformSensor sensor = createPlatformSensor(50000, Sensor.TYPE_LIGHT, | |
| 184 SensorType.AMBIENT_LIGHT, Sensor.REPORTING_MODE_ON_CHANGE); | |
| 185 assertEquals(ReportingMode.ON_CHANGE, sensor.getReportingMode()); | |
| 186 } | |
| 187 | |
| 188 @Test | |
| 189 @Feature({"PlatformSensor"}) | |
| 190 public void testSensorNotifierIsNotCalled() | |
| 191 throws NoSuchFieldException, IllegalAccessException { | |
| 192 PlatformSensor sensor = createPlatformSensor(50000, Sensor.TYPE_ACCELERO METER, | |
| 193 SensorType.ACCELEROMETER, Sensor.REPORTING_MODE_CONTINUOUS); | |
| 194 PlatformSensorNotifier mockNotifier = mock(PlatformSensorNotifier.class) ; | |
| 195 initPlatformSensor(sensor, SensorReadBuffer.READ_BUFFER_SIZE, mockNotifi er); | |
| 196 SensorEvent event = createFakeEvent(3); | |
| 197 sensor.onSensorChanged(event); | |
| 198 verify(mockNotifier, never()).sensorReadingChanged(); | |
| 199 } | |
| 200 | |
| 201 @Test | |
| 202 @Feature({"PlatformSensor"}) | |
| 203 public void testSensorBufferFromEvent() throws NoSuchFieldException, Illegal AccessException { | |
|
timvolodine
2016/09/06 17:44:37
what does this test? maybe add a comment?
shalamov
2016/09/07 13:53:42
Added comments.
| |
| 204 PlatformSensor sensor = createPlatformSensor(50000, Sensor.TYPE_LIGHT, | |
| 205 SensorType.AMBIENT_LIGHT, Sensor.REPORTING_MODE_ON_CHANGE); | |
| 206 PlatformSensorNotifier mockNotifier = mock(PlatformSensorNotifier.class) ; | |
| 207 initPlatformSensor(sensor, SensorReadBuffer.READ_BUFFER_SIZE, mockNotifi er); | |
| 208 SensorEvent event = createFakeEvent(1); | |
| 209 sensor.onSensorChanged(event); | |
| 210 // System.out.format("Event values[0] %f", event.values[0]); | |
|
timvolodine
2016/09/06 17:44:37
should this be here?
shalamov
2016/09/07 13:53:42
Done.
| |
| 211 verify(mockNotifier, times(1)).sensorReadingChanged(); | |
| 212 // verify timestamp | |
| 213 assertEquals(MILLISECONDS_IN_NANOSECOND * PLATFORM_SENSOR_TIMESTAMP, | |
| 214 mSharedBuffer.getDouble(), MILLISECONDS_IN_NANOSECOND); | |
| 215 // verify illuminance | |
| 216 assertEquals(1.0d + MILLISECONDS_IN_NANOSECOND, mSharedBuffer.getDouble( ), | |
| 217 MILLISECONDS_IN_NANOSECOND); | |
| 218 } | |
| 219 | |
| 220 @Test | |
| 221 @Feature({"PlatformSensor"}) | |
| 222 public void testSensorInvalidReadingSize() throws NoSuchFieldException, Ille galAccessException { | |
| 223 PlatformSensor sensor = createPlatformSensor(50000, Sensor.TYPE_ACCELERO METER, | |
| 224 SensorType.ACCELEROMETER, Sensor.REPORTING_MODE_CONTINUOUS); | |
| 225 PlatformSensorNotifier mockNotifier = mock(PlatformSensorNotifier.class) ; | |
| 226 initPlatformSensor(sensor, SensorReadBuffer.READ_BUFFER_SIZE, mockNotifi er); | |
| 227 // Accelerometer requires 3 reading values x,y and z, create fake event with 1 reading | |
| 228 // value. | |
| 229 SensorEvent event = createFakeEvent(1); | |
| 230 sensor.onSensorChanged(event); | |
| 231 verify(mockNotifier, times(1)).sensorError(); | |
| 232 } | |
| 233 | |
| 234 @Test | |
| 235 @Feature({"PlatformSensor"}) | |
| 236 public void testSensorInvalidBufferSize() throws NoSuchFieldException, Illeg alAccessException { | |
| 237 PlatformSensor sensor = createPlatformSensor(50000, Sensor.TYPE_ACCELERO METER, | |
| 238 SensorType.ACCELEROMETER, Sensor.REPORTING_MODE_CONTINUOUS); | |
| 239 PlatformSensorNotifier mockNotifier = mock(PlatformSensorNotifier.class) ; | |
| 240 // Create buffer that doesn't have enough capacity to hold sensor readin g values. | |
| 241 initPlatformSensor(sensor, 2, mockNotifier); | |
| 242 SensorEvent event = createFakeEvent(3); | |
| 243 sensor.onSensorChanged(event); | |
| 244 verify(mockNotifier, times(1)).sensorError(); | |
| 245 } | |
| 246 | |
| 247 private SensorEvent createFakeEvent(int readingValuesNum) | |
| 248 throws NoSuchFieldException, IllegalAccessException { | |
| 249 SensorEvent mockEvent = mock(SensorEvent.class); | |
| 250 mockEvent.timestamp = PLATFORM_SENSOR_TIMESTAMP; | |
| 251 float values[] = new float[readingValuesNum]; | |
| 252 for (int i = 0; i < readingValuesNum; ++i) { | |
| 253 values[i] = (float) (i + 1.0f + MILLISECONDS_IN_NANOSECOND); | |
| 254 } | |
| 255 | |
| 256 Field valuesField = SensorEvent.class.getDeclaredField("values"); | |
| 257 valuesField.setAccessible(true); | |
| 258 Field modifiersField = Field.class.getDeclaredField("modifiers"); | |
| 259 modifiersField.setAccessible(true); | |
| 260 modifiersField.setInt(valuesField, valuesField.getModifiers() & ~Modifie r.FINAL); | |
| 261 valuesField.set(mockEvent, values); | |
| 262 return mockEvent; | |
| 263 } | |
| 264 | |
| 265 private void initPlatformSensor( | |
| 266 PlatformSensor sensor, long readingSize, PlatformSensorNotifier noti fier) { | |
| 267 mSharedBuffer = ByteBuffer.allocate((int) readingSize); | |
| 268 mSharedBuffer.order(ByteOrder.nativeOrder()); | |
| 269 sensor.initPlatformSensorAndroid(notifier, PLATFORM_SENSOR_ANDROID, mSha redBuffer); | |
| 270 } | |
| 271 | |
| 272 private void addMockSensor(long minDelayUsec, int sensorType, int reportingM ode) { | |
| 273 mMockSensors.clear(); | |
| 274 Sensor mockSensor = mock(Sensor.class); | |
| 275 doReturn((int) minDelayUsec).when(mockSensor).getMinDelay(); | |
| 276 doReturn(reportingMode).when(mockSensor).getReportingMode(); | |
| 277 doReturn(sensorType).when(mockSensor).getType(); | |
| 278 doReturn(mMockSensors).when(mSensorManager).getSensorList(sensorType); | |
| 279 mMockSensors.add(mockSensor); | |
| 280 } | |
| 281 | |
| 282 private PlatformSensor createPlatformSensor( | |
| 283 long minDelayUsec, int androidSensorType, int mojoSensorType, int re portingMode) { | |
| 284 addMockSensor(minDelayUsec, androidSensorType, reportingMode); | |
| 285 PlatformSensorProvider provider = PlatformSensorProvider.create(mContext ); | |
| 286 return provider.createSensor(mojoSensorType); | |
| 287 } | |
| 288 } | |
| OLD | NEW |