1 /* 2 * Copyright (C) 2020 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.server.usage; 18 19 import static com.android.dx.mockito.inline.extended.ExtendedMockito.doNothing; 20 import static com.android.dx.mockito.inline.extended.ExtendedMockito.mockitoSession; 21 import static com.android.dx.mockito.inline.extended.ExtendedMockito.spyOn; 22 23 import static org.junit.Assert.assertNull; 24 import static org.junit.Assert.fail; 25 import static org.mockito.ArgumentMatchers.any; 26 import static org.mockito.ArgumentMatchers.anyInt; 27 import static org.mockito.Mockito.mock; 28 29 import android.app.ActivityManager; 30 import android.app.IActivityManager; 31 import android.app.usage.UsageEvents; 32 import android.app.usage.UsageStatsManagerInternal; 33 import android.content.Context; 34 import android.os.RemoteException; 35 36 import androidx.test.runner.AndroidJUnit4; 37 38 import com.android.server.LocalServices; 39 40 import org.junit.After; 41 import org.junit.Before; 42 import org.junit.Test; 43 import org.junit.runner.RunWith; 44 import org.mockito.Mock; 45 import org.mockito.MockitoSession; 46 import org.mockito.quality.Strictness; 47 48 import java.util.concurrent.CountDownLatch; 49 import java.util.concurrent.TimeUnit; 50 51 @RunWith(AndroidJUnit4.class) 52 public class UsageStatsServiceTest { 53 private static final long TIMEOUT = 5000; 54 55 private UsageStatsService mService; 56 57 private MockitoSession mMockingSession; 58 @Mock 59 private Context mContext; 60 61 private static class TestInjector extends UsageStatsService.Injector { getAppStandbyController(Context context)62 AppStandbyInternal getAppStandbyController(Context context) { 63 return mock(AppStandbyInternal.class); 64 } 65 } 66 67 @Before setUp()68 public void setUp() { 69 mMockingSession = mockitoSession() 70 .initMocks(this) 71 .strictness(Strictness.LENIENT) 72 .startMocking(); 73 IActivityManager activityManager = ActivityManager.getService(); 74 spyOn(activityManager); 75 try { 76 doNothing().when(activityManager).registerUidObserver(any(), anyInt(), anyInt(), any()); 77 } catch (RemoteException e) { 78 fail("registerUidObserver threw exception: " + e.getMessage()); 79 } 80 mService = new UsageStatsService(mContext, new TestInjector()); 81 spyOn(mService); 82 doNothing().when(mService).publishBinderServices(); 83 mService.onStart(); 84 } 85 86 @After tearDown()87 public void tearDown() { 88 if (mMockingSession != null) { 89 mMockingSession.finishMocking(); 90 } 91 } 92 93 @Test testUsageEventListener()94 public void testUsageEventListener() throws Exception { 95 TestUsageEventListener listener = new TestUsageEventListener(); 96 UsageStatsManagerInternal usmi = LocalServices.getService(UsageStatsManagerInternal.class); 97 usmi.registerListener(listener); 98 99 UsageEvents.Event event = new UsageEvents.Event(UsageEvents.Event.CONFIGURATION_CHANGE, 10); 100 usmi.reportEvent("com.android.test", 10, event.getEventType()); 101 listener.setExpectation(10, event); 102 listener.mCountDownLatch.await(TIMEOUT, TimeUnit.MILLISECONDS); 103 104 usmi.unregisterListener(listener); 105 listener.reset(); 106 107 usmi.reportEvent("com.android.test", 0, UsageEvents.Event.CHOOSER_ACTION); 108 Thread.sleep(TIMEOUT); 109 assertNull(listener.mLastReceivedEvent); 110 } 111 112 private static class TestUsageEventListener implements 113 UsageStatsManagerInternal.UsageEventListener { 114 UsageEvents.Event mLastReceivedEvent; 115 int mLastReceivedUserId; 116 UsageEvents.Event mExpectedEvent; 117 int mExpectedUserId; 118 CountDownLatch mCountDownLatch; 119 120 @Override onUsageEvent(int userId, UsageEvents.Event event)121 public void onUsageEvent(int userId, UsageEvents.Event event) { 122 mLastReceivedUserId = userId; 123 mLastReceivedEvent = event; 124 if (mCountDownLatch != null && userId == mExpectedUserId 125 && event.getEventType() == mExpectedEvent.getEventType()) { 126 mCountDownLatch.countDown(); 127 } 128 } 129 setExpectation(int userId, UsageEvents.Event event)130 private void setExpectation(int userId, UsageEvents.Event event) { 131 mExpectedUserId = userId; 132 mExpectedEvent = event; 133 mCountDownLatch = new CountDownLatch(1); 134 } 135 reset()136 private void reset() { 137 mLastReceivedUserId = mExpectedUserId = -1; 138 mLastReceivedEvent = mExpectedEvent = null; 139 mCountDownLatch = null; 140 } 141 } 142 } 143