blob: 9dee84347ae1f074db3180c73cec2873fea6b4cd [file] [log] [blame]
yoshiki iguchia85c2a02018-01-12 11:28:06 +09001/*
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
Rohan Shah20790b82018-07-02 17:21:04 -070017package com.android.systemui.statusbar.notification.row;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090018
Julia Reynoldsb5867452018-02-28 16:31:35 -050019import static android.app.AppOpsManager.OP_CAMERA;
20import static android.app.AppOpsManager.OP_RECORD_AUDIO;
21import static android.app.AppOpsManager.OP_SYSTEM_ALERT_WINDOW;
Gus Prevas9abc5062018-10-31 16:11:04 -040022import static android.app.NotificationManager.IMPORTANCE_DEFAULT;
Beverly7c1ad5b2019-12-05 17:17:15 -050023import static android.app.NotificationManager.IMPORTANCE_HIGH;
Gus Prevas5a70a4e2018-11-26 17:16:05 -050024import static android.service.notification.NotificationListenerService.Ranking.USER_SENTIMENT_NEGATIVE;
Julia Reynoldsb5867452018-02-28 16:31:35 -050025
Ned Burns60e94592019-09-06 14:47:25 -040026import static com.android.systemui.statusbar.NotificationEntryHelper.modifyRanking;
27
yoshiki iguchia85c2a02018-01-12 11:28:06 +090028import static junit.framework.Assert.assertNotNull;
Kevina5ff1fa2018-08-21 16:35:48 -070029import static junit.framework.Assert.assertNull;
30import static junit.framework.Assert.assertTrue;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090031
32import static org.junit.Assert.assertEquals;
33import static org.junit.Assert.fail;
34import static org.mockito.ArgumentMatchers.any;
35import static org.mockito.ArgumentMatchers.anyBoolean;
36import static org.mockito.ArgumentMatchers.anyInt;
Evan Laird47dc4542019-04-24 15:10:52 -040037import static org.mockito.ArgumentMatchers.anySet;
Rohan Shah524cf7b2018-03-15 14:40:02 -070038import static org.mockito.ArgumentMatchers.eq;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090039import static org.mockito.Mockito.doNothing;
Kevina5ff1fa2018-08-21 16:35:48 -070040import static org.mockito.Mockito.doReturn;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090041import static org.mockito.Mockito.mock;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090042import static org.mockito.Mockito.spy;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090043import static org.mockito.Mockito.times;
Gus Prevas9abc5062018-10-31 16:11:04 -040044import static org.mockito.Mockito.verify;
45import static org.mockito.Mockito.when;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090046
Rohan Shah524cf7b2018-03-15 14:40:02 -070047import android.app.INotificationManager;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090048import android.app.Notification;
49import android.app.NotificationChannel;
Julia Reynoldsb5867452018-02-28 16:31:35 -050050import android.content.Intent;
Steve Elliott46bb2a12020-03-17 11:04:09 -040051import android.content.pm.LauncherApps;
Rohan Shah524cf7b2018-03-15 14:40:02 -070052import android.content.pm.PackageManager;
Steve Elliott46bb2a12020-03-17 11:04:09 -040053import android.content.pm.ShortcutManager;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090054import android.os.Binder;
55import android.os.Handler;
Julia Reynoldsb5867452018-02-28 16:31:35 -050056import android.provider.Settings;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090057import android.service.notification.StatusBarNotification;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090058import android.testing.AndroidTestingRunner;
59import android.testing.TestableLooper;
Julia Reynoldsb5867452018-02-28 16:31:35 -050060import android.util.ArraySet;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090061import android.view.View;
Dave Mankoff5fe07f72019-11-19 22:14:41 -050062import android.view.accessibility.AccessibilityManager;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090063
Brett Chabot84151d92019-02-27 15:37:59 -080064import androidx.test.filters.SmallTest;
65
TreeHugger Robotee8e1ae2019-01-18 19:26:40 +000066import com.android.internal.logging.MetricsLogger;
Will Brockman4567a4c2020-06-21 17:19:50 -040067import com.android.internal.logging.UiEventLogger;
68import com.android.internal.logging.testing.UiEventLoggerFake;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090069import com.android.systemui.SysuiTestCase;
Lyn Hanb5397972020-06-16 11:56:43 -070070import com.android.systemui.bubbles.BubbleController;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090071import com.android.systemui.plugins.statusbar.NotificationMenuRowPlugin;
Evan Laird31ca5472020-04-08 17:45:24 -040072import com.android.systemui.settings.CurrentUserContextTracker;
Lucas Dupind236ee32019-10-08 15:33:59 -070073import com.android.systemui.statusbar.NotificationLockscreenUserManager;
Rohan Shah20790b82018-07-02 17:21:04 -070074import com.android.systemui.statusbar.NotificationPresenter;
Gus Prevas21437b32018-12-05 10:36:13 -050075import com.android.systemui.statusbar.notification.NotificationActivityStarter;
Ned Burns9512e0c2019-05-30 19:36:04 -040076import com.android.systemui.statusbar.notification.VisualStabilityManager;
Ned Burnsf81c4c42019-01-07 14:10:43 -050077import com.android.systemui.statusbar.notification.collection.NotificationEntry;
Beverlye558f1d2020-01-07 16:28:58 -050078import com.android.systemui.statusbar.notification.collection.provider.HighPriorityProvider;
Steve Elliott2304e4a2020-04-01 17:03:41 -040079import com.android.systemui.statusbar.notification.people.PeopleNotificationIdentifier;
Gus Prevas5a70a4e2018-11-26 17:16:05 -050080import com.android.systemui.statusbar.notification.row.NotificationGutsManager.OnSettingsClickListener;
Rohan Shah20790b82018-07-02 17:21:04 -070081import com.android.systemui.statusbar.notification.stack.NotificationStackScrollLayout;
Evan Laird03cf3502019-05-31 16:46:48 -040082import com.android.systemui.statusbar.phone.StatusBar;
Jason Monk297c04e2018-08-23 17:16:59 -040083import com.android.systemui.statusbar.policy.DeviceProvisionedController;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090084
85import org.junit.Before;
Selim Cinek2476ed72019-03-07 13:19:23 -080086import org.junit.Ignore;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090087import org.junit.Rule;
88import org.junit.Test;
89import org.junit.runner.RunWith;
Evan Laird31ca5472020-04-08 17:45:24 -040090import org.mockito.Answers;
Julia Reynoldsb5867452018-02-28 16:31:35 -050091import org.mockito.ArgumentCaptor;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090092import org.mockito.Mock;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090093import org.mockito.junit.MockitoJUnit;
Gus Prevas9abc5062018-10-31 16:11:04 -040094import org.mockito.junit.MockitoRule;
yoshiki iguchia85c2a02018-01-12 11:28:06 +090095
Evan Laird31ca5472020-04-08 17:45:24 -040096import javax.inject.Provider;
97
Rohan Shah524cf7b2018-03-15 14:40:02 -070098/**
99 * Tests for {@link NotificationGutsManager}.
100 */
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900101@SmallTest
102@RunWith(AndroidTestingRunner.class)
Jason Monka716bac2018-12-05 15:48:21 -0500103@TestableLooper.RunWithLooper
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900104public class NotificationGutsManagerTest extends SysuiTestCase {
105 private static final String TEST_CHANNEL_ID = "NotificationManagerServiceTestChannelId";
106
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900107 private NotificationChannel mTestNotificationChannel = new NotificationChannel(
Gus Prevas9abc5062018-10-31 16:11:04 -0400108 TEST_CHANNEL_ID, TEST_CHANNEL_ID, IMPORTANCE_DEFAULT);
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900109 private TestableLooper mTestableLooper;
110 private Handler mHandler;
111 private NotificationTestHelper mHelper;
112 private NotificationGutsManager mGutsManager;
113
114 @Rule public MockitoRule mockito = MockitoJUnit.rule();
TreeHugger Robotee8e1ae2019-01-18 19:26:40 +0000115 @Mock private MetricsLogger mMetricsLogger;
Ned Burns9512e0c2019-05-30 19:36:04 -0400116 @Mock private VisualStabilityManager mVisualStabilityManager;
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900117 @Mock private NotificationPresenter mPresenter;
Gus Prevas21437b32018-12-05 10:36:13 -0500118 @Mock private NotificationActivityStarter mNotificationActivityStarter;
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900119 @Mock private NotificationStackScrollLayout mStackScroller;
120 @Mock private NotificationInfo.CheckSaveListener mCheckSaveListener;
Jason Monk297c04e2018-08-23 17:16:59 -0400121 @Mock private OnSettingsClickListener mOnSettingsClickListener;
122 @Mock private DeviceProvisionedController mDeviceProvisionedController;
Evan Laird03cf3502019-05-31 16:46:48 -0400123 @Mock private StatusBar mStatusBar;
Dave Mankoff5fe07f72019-11-19 22:14:41 -0500124 @Mock private AccessibilityManager mAccessibilityManager;
Beverlye558f1d2020-01-07 16:28:58 -0500125 @Mock private HighPriorityProvider mHighPriorityProvider;
Steve Elliott46bb2a12020-03-17 11:04:09 -0400126 @Mock private INotificationManager mINotificationManager;
127 @Mock private LauncherApps mLauncherApps;
128 @Mock private ShortcutManager mShortcutManager;
Evan Laird18bd6e62019-08-30 16:39:25 -0400129 @Mock private ChannelEditorDialogController mChannelEditorDialogController;
Steve Elliott2304e4a2020-04-01 17:03:41 -0400130 @Mock private PeopleNotificationIdentifier mPeopleNotificationIdentifier;
Evan Laird31ca5472020-04-08 17:45:24 -0400131 @Mock private CurrentUserContextTracker mContextTracker;
Lyn Hanb5397972020-06-16 11:56:43 -0700132 @Mock private BubbleController mBubbleController;
Evan Laird31ca5472020-04-08 17:45:24 -0400133 @Mock(answer = Answers.RETURNS_SELF)
134 private PriorityOnboardingDialogController.Builder mBuilder;
135 private Provider<PriorityOnboardingDialogController.Builder> mProvider = () -> mBuilder;
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900136
137 @Before
138 public void setUp() {
139 mTestableLooper = TestableLooper.get(this);
Beverly1467c9e2020-02-18 13:31:29 -0500140 allowTestableLooperAsMainThread();
Jason Monk297c04e2018-08-23 17:16:59 -0400141 mDependency.injectTestDependency(DeviceProvisionedController.class,
142 mDeviceProvisionedController);
TreeHugger Robotee8e1ae2019-01-18 19:26:40 +0000143 mDependency.injectTestDependency(MetricsLogger.class, mMetricsLogger);
Ned Burns9512e0c2019-05-30 19:36:04 -0400144 mDependency.injectTestDependency(VisualStabilityManager.class, mVisualStabilityManager);
Lyn Hanb5397972020-06-16 11:56:43 -0700145 mDependency.injectTestDependency(BubbleController.class, mBubbleController);
Lucas Dupind236ee32019-10-08 15:33:59 -0700146 mDependency.injectMockDependency(NotificationLockscreenUserManager.class);
Jason Monk6dceace2018-05-15 20:24:07 -0400147 mHandler = Handler.createAsync(mTestableLooper.getLooper());
Kevin Hana7c21be2020-04-01 17:58:35 -0700148 mHelper = new NotificationTestHelper(mContext, mDependency, TestableLooper.get(this));
Dave Mankoff5fe07f72019-11-19 22:14:41 -0500149 when(mAccessibilityManager.isTouchExplorationEnabled()).thenReturn(false);
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900150
Dave Mankoff4dd47fa2019-11-07 10:44:48 -0500151 mGutsManager = new NotificationGutsManager(mContext, mVisualStabilityManager,
Steve Elliott6771f542020-05-26 13:31:10 -0400152 () -> mStatusBar, mHandler, mHandler, mAccessibilityManager, mHighPriorityProvider,
Evan Laird18bd6e62019-08-30 16:39:25 -0400153 mINotificationManager, mLauncherApps, mShortcutManager,
Will Brockman4567a4c2020-06-21 17:19:50 -0400154 mChannelEditorDialogController, mContextTracker, mProvider, mBubbleController,
155 new UiEventLoggerFake());
Kevina5ff1fa2018-08-21 16:35:48 -0700156 mGutsManager.setUpWithPresenter(mPresenter, mStackScroller,
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900157 mCheckSaveListener, mOnSettingsClickListener);
Gus Prevas21437b32018-12-05 10:36:13 -0500158 mGutsManager.setNotificationActivityStarter(mNotificationActivityStarter);
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900159 }
160
161 ////////////////////////////////////////////////////////////////////////////////////////////////
162 // Test methods:
163
164 @Test
165 public void testOpenAndCloseGuts() {
166 NotificationGuts guts = spy(new NotificationGuts(mContext));
167 when(guts.post(any())).thenAnswer(invocation -> {
168 mHandler.post(((Runnable) invocation.getArguments()[0]));
169 return null;
170 });
171
172 // Test doesn't support animation since the guts view is not attached.
Rohan Shah524cf7b2018-03-15 14:40:02 -0700173 doNothing().when(guts).openControls(
174 eq(true) /* shouldDoCircularReveal */,
175 anyInt(),
176 anyInt(),
177 anyBoolean(),
178 any(Runnable.class));
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900179
180 ExpandableNotificationRow realRow = createTestNotificationRow();
181 NotificationMenuRowPlugin.MenuItem menuItem = createTestMenuItem(realRow);
182
183 ExpandableNotificationRow row = spy(realRow);
184 when(row.getWindowToken()).thenReturn(new Binder());
185 when(row.getGuts()).thenReturn(guts);
186
Evan Laird03cf3502019-05-31 16:46:48 -0400187 assertTrue(mGutsManager.openGutsInternal(row, 0, 0, menuItem));
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900188 assertEquals(View.INVISIBLE, guts.getVisibility());
189 mTestableLooper.processAllMessages();
Rohan Shah524cf7b2018-03-15 14:40:02 -0700190 verify(guts).openControls(
191 eq(true),
192 anyInt(),
193 anyInt(),
194 anyBoolean(),
195 any(Runnable.class));
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900196
197 assertEquals(View.VISIBLE, guts.getVisibility());
198 mGutsManager.closeAndSaveGuts(false, false, false, 0, 0, false);
199
200 verify(guts).closeControls(anyBoolean(), anyBoolean(), anyInt(), anyInt(), anyBoolean());
201 verify(row, times(1)).setGutsView(any());
202 }
203
204 @Test
205 public void testChangeDensityOrFontScale() {
206 NotificationGuts guts = spy(new NotificationGuts(mContext));
207 when(guts.post(any())).thenAnswer(invocation -> {
208 mHandler.post(((Runnable) invocation.getArguments()[0]));
209 return null;
210 });
211
212 // Test doesn't support animation since the guts view is not attached.
Rohan Shah524cf7b2018-03-15 14:40:02 -0700213 doNothing().when(guts).openControls(
214 eq(true) /* shouldDoCircularReveal */,
215 anyInt(),
216 anyInt(),
217 anyBoolean(),
218 any(Runnable.class));
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900219
220 ExpandableNotificationRow realRow = createTestNotificationRow();
221 NotificationMenuRowPlugin.MenuItem menuItem = createTestMenuItem(realRow);
222
223 ExpandableNotificationRow row = spy(realRow);
Evan Laird94492852018-10-25 13:43:01 -0400224
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900225 when(row.getWindowToken()).thenReturn(new Binder());
226 when(row.getGuts()).thenReturn(guts);
Evan Lairde55c6012019-03-13 12:54:37 -0400227 doNothing().when(row).ensureGutsInflated();
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900228
Ned Burnsf81c4c42019-01-07 14:10:43 -0500229 NotificationEntry realEntry = realRow.getEntry();
230 NotificationEntry entry = spy(realEntry);
Evan Laird94492852018-10-25 13:43:01 -0400231
232 when(entry.getRow()).thenReturn(row);
233 when(entry.getGuts()).thenReturn(guts);
234
Evan Laird03cf3502019-05-31 16:46:48 -0400235 assertTrue(mGutsManager.openGutsInternal(row, 0, 0, menuItem));
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900236 mTestableLooper.processAllMessages();
Rohan Shah524cf7b2018-03-15 14:40:02 -0700237 verify(guts).openControls(
238 eq(true),
239 anyInt(),
240 anyInt(),
241 anyBoolean(),
242 any(Runnable.class));
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900243
Evan Laird94492852018-10-25 13:43:01 -0400244 // called once by mGutsManager.bindGuts() in mGutsManager.openGuts()
245 verify(row).setGutsView(any());
246
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900247 row.onDensityOrFontScaleChanged();
Evan Laird94492852018-10-25 13:43:01 -0400248 mGutsManager.onDensityOrFontScaleChanged(entry);
249
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900250 mTestableLooper.processAllMessages();
251
252 mGutsManager.closeAndSaveGuts(false, false, false, 0, 0, false);
253
254 verify(guts).closeControls(anyBoolean(), anyBoolean(), anyInt(), anyInt(), anyBoolean());
Evan Laird94492852018-10-25 13:43:01 -0400255
256 // called again by mGutsManager.bindGuts(), in mGutsManager.onDensityOrFontScaleChanged()
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900257 verify(row, times(2)).setGutsView(any());
258 }
259
Julia Reynoldsb5867452018-02-28 16:31:35 -0500260 @Test
261 public void testAppOpsSettingsIntent_camera() {
262 ArraySet<Integer> ops = new ArraySet<>();
263 ops.add(OP_CAMERA);
264 mGutsManager.startAppOpsSettingsActivity("", 0, ops, null);
265 ArgumentCaptor<Intent> captor = ArgumentCaptor.forClass(Intent.class);
Gus Prevas21437b32018-12-05 10:36:13 -0500266 verify(mNotificationActivityStarter, times(1))
267 .startNotificationGutsIntent(captor.capture(), anyInt(), any());
Julia Reynoldsb5867452018-02-28 16:31:35 -0500268 assertEquals(Intent.ACTION_MANAGE_APP_PERMISSIONS, captor.getValue().getAction());
269 }
270
271 @Test
272 public void testAppOpsSettingsIntent_mic() {
273 ArraySet<Integer> ops = new ArraySet<>();
274 ops.add(OP_RECORD_AUDIO);
275 mGutsManager.startAppOpsSettingsActivity("", 0, ops, null);
276 ArgumentCaptor<Intent> captor = ArgumentCaptor.forClass(Intent.class);
Gus Prevas21437b32018-12-05 10:36:13 -0500277 verify(mNotificationActivityStarter, times(1))
278 .startNotificationGutsIntent(captor.capture(), anyInt(), any());
Julia Reynoldsb5867452018-02-28 16:31:35 -0500279 assertEquals(Intent.ACTION_MANAGE_APP_PERMISSIONS, captor.getValue().getAction());
280 }
281
282 @Test
283 public void testAppOpsSettingsIntent_camera_mic() {
284 ArraySet<Integer> ops = new ArraySet<>();
285 ops.add(OP_CAMERA);
286 ops.add(OP_RECORD_AUDIO);
287 mGutsManager.startAppOpsSettingsActivity("", 0, ops, null);
288 ArgumentCaptor<Intent> captor = ArgumentCaptor.forClass(Intent.class);
Gus Prevas21437b32018-12-05 10:36:13 -0500289 verify(mNotificationActivityStarter, times(1))
290 .startNotificationGutsIntent(captor.capture(), anyInt(), any());
Julia Reynoldsb5867452018-02-28 16:31:35 -0500291 assertEquals(Intent.ACTION_MANAGE_APP_PERMISSIONS, captor.getValue().getAction());
292 }
293
294 @Test
295 public void testAppOpsSettingsIntent_overlay() {
296 ArraySet<Integer> ops = new ArraySet<>();
297 ops.add(OP_SYSTEM_ALERT_WINDOW);
298 mGutsManager.startAppOpsSettingsActivity("", 0, ops, null);
299 ArgumentCaptor<Intent> captor = ArgumentCaptor.forClass(Intent.class);
Gus Prevas21437b32018-12-05 10:36:13 -0500300 verify(mNotificationActivityStarter, times(1))
301 .startNotificationGutsIntent(captor.capture(), anyInt(), any());
Bernardo Rufino8fefb942019-11-25 19:51:09 +0000302 assertEquals(Settings.ACTION_MANAGE_APP_OVERLAY_PERMISSION, captor.getValue().getAction());
Julia Reynoldsb5867452018-02-28 16:31:35 -0500303 }
304
305 @Test
306 public void testAppOpsSettingsIntent_camera_mic_overlay() {
307 ArraySet<Integer> ops = new ArraySet<>();
308 ops.add(OP_CAMERA);
309 ops.add(OP_RECORD_AUDIO);
310 ops.add(OP_SYSTEM_ALERT_WINDOW);
311 mGutsManager.startAppOpsSettingsActivity("", 0, ops, null);
312 ArgumentCaptor<Intent> captor = ArgumentCaptor.forClass(Intent.class);
Gus Prevas21437b32018-12-05 10:36:13 -0500313 verify(mNotificationActivityStarter, times(1))
314 .startNotificationGutsIntent(captor.capture(), anyInt(), any());
Julia Reynoldsb5867452018-02-28 16:31:35 -0500315 assertEquals(Settings.ACTION_APPLICATION_DETAILS_SETTINGS, captor.getValue().getAction());
316 }
317
318 @Test
319 public void testAppOpsSettingsIntent_camera_overlay() {
320 ArraySet<Integer> ops = new ArraySet<>();
321 ops.add(OP_CAMERA);
322 ops.add(OP_SYSTEM_ALERT_WINDOW);
323 mGutsManager.startAppOpsSettingsActivity("", 0, ops, null);
324 ArgumentCaptor<Intent> captor = ArgumentCaptor.forClass(Intent.class);
Gus Prevas21437b32018-12-05 10:36:13 -0500325 verify(mNotificationActivityStarter, times(1))
326 .startNotificationGutsIntent(captor.capture(), anyInt(), any());
Julia Reynoldsb5867452018-02-28 16:31:35 -0500327 assertEquals(Settings.ACTION_APPLICATION_DETAILS_SETTINGS, captor.getValue().getAction());
328 }
329
330 @Test
331 public void testAppOpsSettingsIntent_mic_overlay() {
332 ArraySet<Integer> ops = new ArraySet<>();
333 ops.add(OP_RECORD_AUDIO);
334 ops.add(OP_SYSTEM_ALERT_WINDOW);
335 mGutsManager.startAppOpsSettingsActivity("", 0, ops, null);
336 ArgumentCaptor<Intent> captor = ArgumentCaptor.forClass(Intent.class);
Gus Prevas21437b32018-12-05 10:36:13 -0500337 verify(mNotificationActivityStarter, times(1))
338 .startNotificationGutsIntent(captor.capture(), anyInt(), any());
Julia Reynoldsb5867452018-02-28 16:31:35 -0500339 assertEquals(Settings.ACTION_APPLICATION_DETAILS_SETTINGS, captor.getValue().getAction());
340 }
341
Rohan Shah524cf7b2018-03-15 14:40:02 -0700342 @Test
Gus Prevascaed15c2019-01-18 14:19:51 -0500343 public void testInitializeNotificationInfoView_highPriority() throws Exception {
Gus Prevas9abc5062018-10-31 16:11:04 -0400344 NotificationInfo notificationInfoView = mock(NotificationInfo.class);
345 ExpandableNotificationRow row = spy(mHelper.createRow());
Beverly7c1ad5b2019-12-05 17:17:15 -0500346 final NotificationEntry entry = row.getEntry();
347 modifyRanking(entry)
Ned Burns60e94592019-09-06 14:47:25 -0400348 .setUserSentiment(USER_SENTIMENT_NEGATIVE)
Beverly7c1ad5b2019-12-05 17:17:15 -0500349 .setImportance(IMPORTANCE_HIGH)
Ned Burns60e94592019-09-06 14:47:25 -0400350 .build();
Gus Prevas9abc5062018-10-31 16:11:04 -0400351
Beverly7c1ad5b2019-12-05 17:17:15 -0500352 when(row.getIsNonblockable()).thenReturn(false);
Beverlye558f1d2020-01-07 16:28:58 -0500353 when(mHighPriorityProvider.isHighPriority(entry)).thenReturn(true);
Beverly7c1ad5b2019-12-05 17:17:15 -0500354 StatusBarNotification statusBarNotification = entry.getSbn();
Gus Prevas5a70a4e2018-11-26 17:16:05 -0500355 mGutsManager.initializeNotificationInfo(row, notificationInfoView);
Gus Prevas9abc5062018-10-31 16:11:04 -0400356
357 verify(notificationInfoView).bindNotification(
358 any(PackageManager.class),
359 any(INotificationManager.class),
Ned Burns9512e0c2019-05-30 19:36:04 -0400360 eq(mVisualStabilityManager),
Evan Laird18bd6e62019-08-30 16:39:25 -0400361 eq(mChannelEditorDialogController),
Gus Prevas9abc5062018-10-31 16:11:04 -0400362 eq(statusBarNotification.getPackageName()),
363 any(NotificationChannel.class),
Evan Laird47dc4542019-04-24 15:10:52 -0400364 anySet(),
Mady Mellor53162c12019-10-22 17:12:59 -0700365 eq(entry),
Gus Prevas9abc5062018-10-31 16:11:04 -0400366 any(NotificationInfo.OnSettingsClickListener.class),
367 any(NotificationInfo.OnAppSettingsClickListener.class),
Will Brockman4567a4c2020-06-21 17:19:50 -0400368 any(UiEventLogger.class),
Gus Prevas9abc5062018-10-31 16:11:04 -0400369 eq(false),
370 eq(false),
Gus Prevascaed15c2019-01-18 14:19:51 -0500371 eq(true) /* wasShownHighPriority */);
Julia Reynolds35765d82018-08-17 11:39:19 -0400372 }
373
374 @Test
375 public void testInitializeNotificationInfoView_PassesAlongProvisionedState() throws Exception {
376 NotificationInfo notificationInfoView = mock(NotificationInfo.class);
377 ExpandableNotificationRow row = spy(mHelper.createRow());
378 row.setBlockingHelperShowing(false);
Ned Burns47c98f12019-09-06 17:12:07 -0400379 modifyRanking(row.getEntry())
380 .setUserSentiment(USER_SENTIMENT_NEGATIVE)
381 .build();
Julia Reynolds35765d82018-08-17 11:39:19 -0400382 when(row.getIsNonblockable()).thenReturn(false);
Ned Burns1c2b85a42019-11-14 15:37:03 -0500383 StatusBarNotification statusBarNotification = row.getEntry().getSbn();
Mady Mellor53162c12019-10-22 17:12:59 -0700384 NotificationEntry entry = row.getEntry();
385
Jason Monk297c04e2018-08-23 17:16:59 -0400386 when(mDeviceProvisionedController.isDeviceProvisioned()).thenReturn(true);
Julia Reynolds35765d82018-08-17 11:39:19 -0400387
Gus Prevas5a70a4e2018-11-26 17:16:05 -0500388 mGutsManager.initializeNotificationInfo(row, notificationInfoView);
Julia Reynolds35765d82018-08-17 11:39:19 -0400389
390 verify(notificationInfoView).bindNotification(
391 any(PackageManager.class),
392 any(INotificationManager.class),
Ned Burns9512e0c2019-05-30 19:36:04 -0400393 eq(mVisualStabilityManager),
Evan Laird18bd6e62019-08-30 16:39:25 -0400394 eq(mChannelEditorDialogController),
Julia Reynolds35765d82018-08-17 11:39:19 -0400395 eq(statusBarNotification.getPackageName()),
396 any(NotificationChannel.class),
Evan Laird47dc4542019-04-24 15:10:52 -0400397 anySet(),
Mady Mellor53162c12019-10-22 17:12:59 -0700398 eq(entry),
Julia Reynolds35765d82018-08-17 11:39:19 -0400399 any(NotificationInfo.OnSettingsClickListener.class),
400 any(NotificationInfo.OnAppSettingsClickListener.class),
Will Brockman4567a4c2020-06-21 17:19:50 -0400401 any(UiEventLogger.class),
Julia Reynolds35765d82018-08-17 11:39:19 -0400402 eq(true),
403 eq(false),
Gus Prevascaed15c2019-01-18 14:19:51 -0500404 eq(false) /* wasShownHighPriority */);
Gus Prevas894d9152018-11-12 13:51:40 -0500405 }
406
407 @Test
408 public void testInitializeNotificationInfoView_withInitialAction() throws Exception {
409 NotificationInfo notificationInfoView = mock(NotificationInfo.class);
410 ExpandableNotificationRow row = spy(mHelper.createRow());
411 row.setBlockingHelperShowing(true);
Ned Burns47c98f12019-09-06 17:12:07 -0400412 modifyRanking(row.getEntry())
413 .setUserSentiment(USER_SENTIMENT_NEGATIVE)
414 .build();
Gus Prevas894d9152018-11-12 13:51:40 -0500415 when(row.getIsNonblockable()).thenReturn(false);
Ned Burns1c2b85a42019-11-14 15:37:03 -0500416 StatusBarNotification statusBarNotification = row.getEntry().getSbn();
Mady Mellor53162c12019-10-22 17:12:59 -0700417 NotificationEntry entry = row.getEntry();
Gus Prevas894d9152018-11-12 13:51:40 -0500418
Gus Prevas5a70a4e2018-11-26 17:16:05 -0500419 mGutsManager.initializeNotificationInfo(row, notificationInfoView);
Gus Prevas894d9152018-11-12 13:51:40 -0500420
421 verify(notificationInfoView).bindNotification(
422 any(PackageManager.class),
423 any(INotificationManager.class),
Ned Burns9512e0c2019-05-30 19:36:04 -0400424 eq(mVisualStabilityManager),
Evan Laird18bd6e62019-08-30 16:39:25 -0400425 eq(mChannelEditorDialogController),
Gus Prevas894d9152018-11-12 13:51:40 -0500426 eq(statusBarNotification.getPackageName()),
427 any(NotificationChannel.class),
Evan Laird47dc4542019-04-24 15:10:52 -0400428 anySet(),
Mady Mellor53162c12019-10-22 17:12:59 -0700429 eq(entry),
Gus Prevas894d9152018-11-12 13:51:40 -0500430 any(NotificationInfo.OnSettingsClickListener.class),
431 any(NotificationInfo.OnAppSettingsClickListener.class),
Will Brockman4567a4c2020-06-21 17:19:50 -0400432 any(UiEventLogger.class),
Gus Prevas894d9152018-11-12 13:51:40 -0500433 eq(false),
434 eq(false),
Gus Prevascaed15c2019-01-18 14:19:51 -0500435 eq(false) /* wasShownHighPriority */);
Rohan Shah524cf7b2018-03-15 14:40:02 -0700436 }
437
Kevina5ff1fa2018-08-21 16:35:48 -0700438 @Test
439 public void testShouldExtendLifetime() {
440 NotificationGuts guts = new NotificationGuts(mContext);
441 ExpandableNotificationRow row = spy(createTestNotificationRow());
442 doReturn(guts).when(row).getGuts();
Ned Burnsf81c4c42019-01-07 14:10:43 -0500443 NotificationEntry entry = row.getEntry();
Evan Laird94492852018-10-25 13:43:01 -0400444 entry.setRow(row);
Kevina5ff1fa2018-08-21 16:35:48 -0700445 mGutsManager.setExposedGuts(guts);
446
447 assertTrue(mGutsManager.shouldExtendLifetime(entry));
448 }
449
450 @Test
Selim Cinek2476ed72019-03-07 13:19:23 -0800451 @Ignore
Kevine9e938c2018-09-06 13:38:11 -0700452 public void testSetShouldManageLifetime_setShouldManage() {
Ned Burnsf81c4c42019-01-07 14:10:43 -0500453 NotificationEntry entry = createTestNotificationRow().getEntry();
Kevine9e938c2018-09-06 13:38:11 -0700454 mGutsManager.setShouldManageLifetime(entry, true /* shouldManage */);
Kevina5ff1fa2018-08-21 16:35:48 -0700455
Ned Burns00b4b2d2019-10-17 22:09:27 -0400456 assertTrue(entry.getKey().equals(mGutsManager.mKeyToRemoveOnGutsClosed));
Kevina5ff1fa2018-08-21 16:35:48 -0700457 }
458
459 @Test
Kevine9e938c2018-09-06 13:38:11 -0700460 public void testSetShouldManageLifetime_setShouldNotManage() {
Ned Burnsf81c4c42019-01-07 14:10:43 -0500461 NotificationEntry entry = createTestNotificationRow().getEntry();
Ned Burns00b4b2d2019-10-17 22:09:27 -0400462 mGutsManager.mKeyToRemoveOnGutsClosed = entry.getKey();
Kevine9e938c2018-09-06 13:38:11 -0700463 mGutsManager.setShouldManageLifetime(entry, false /* shouldManage */);
Kevina5ff1fa2018-08-21 16:35:48 -0700464
465 assertNull(mGutsManager.mKeyToRemoveOnGutsClosed);
466 }
467
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900468 ////////////////////////////////////////////////////////////////////////////////////////////////
469 // Utility methods:
470
471 private ExpandableNotificationRow createTestNotificationRow() {
472 Notification.Builder nb = new Notification.Builder(mContext,
473 mTestNotificationChannel.getId())
474 .setContentTitle("foo")
475 .setColorized(true)
476 .setFlag(Notification.FLAG_CAN_COLORIZE, true)
477 .setSmallIcon(android.R.drawable.sym_def_app_icon);
478
479 try {
480 ExpandableNotificationRow row = mHelper.createRow(nb.build());
Ned Burns60e94592019-09-06 14:47:25 -0400481 modifyRanking(row.getEntry())
482 .setChannel(mTestNotificationChannel)
483 .build();
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900484 return row;
485 } catch (Exception e) {
486 fail();
487 return null;
488 }
489 }
490
491 private NotificationMenuRowPlugin.MenuItem createTestMenuItem(ExpandableNotificationRow row) {
Steve Elliott2304e4a2020-04-01 17:03:41 -0400492 NotificationMenuRowPlugin menuRow =
493 new NotificationMenuRow(mContext, mPeopleNotificationIdentifier);
Ned Burns1c2b85a42019-11-14 15:37:03 -0500494 menuRow.createMenu(row, row.getEntry().getSbn());
yoshiki iguchia85c2a02018-01-12 11:28:06 +0900495
496 NotificationMenuRowPlugin.MenuItem menuItem = menuRow.getLongpressMenuItem(mContext);
497 assertNotNull(menuItem);
498 return menuItem;
499 }
500}