1 /* 2 * Copyright (C) 2017 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.internal.app; 18 19 import static org.mockito.ArgumentMatchers.any; 20 import static org.mockito.ArgumentMatchers.anyInt; 21 import static org.mockito.Mockito.mock; 22 import static org.mockito.Mockito.when; 23 24 import android.app.usage.UsageStatsManager; 25 import android.content.Context; 26 import android.content.Intent; 27 import android.content.pm.PackageManager; 28 import android.content.pm.ResolveInfo; 29 import android.os.Bundle; 30 import android.os.UserHandle; 31 32 import com.android.internal.app.AbstractMultiProfilePagerAdapter.CrossProfileIntentsChecker; 33 import com.android.internal.app.AbstractMultiProfilePagerAdapter.MyUserIdProvider; 34 import com.android.internal.app.AbstractMultiProfilePagerAdapter.QuietModeManager; 35 import com.android.internal.app.chooser.TargetInfo; 36 37 import java.util.List; 38 import java.util.function.Function; 39 40 /* 41 * Simple wrapper around chooser activity to be able to initiate it under test 42 */ 43 public class ResolverWrapperActivity extends ResolverActivity { 44 static final OverrideData sOverrides = new OverrideData(); 45 private UsageStatsManager mUsm; 46 ResolverWrapperActivity()47 public ResolverWrapperActivity() { 48 super(/* isIntentPicker= */ true); 49 } 50 51 @Override createResolverListAdapter(Context context, List<Intent> payloadIntents, Intent[] initialIntents, List<ResolveInfo> rList, boolean filterLastUsed, UserHandle userHandle)52 public ResolverListAdapter createResolverListAdapter(Context context, 53 List<Intent> payloadIntents, Intent[] initialIntents, List<ResolveInfo> rList, 54 boolean filterLastUsed, UserHandle userHandle) { 55 return new ResolverWrapperAdapter(context, payloadIntents, initialIntents, rList, 56 filterLastUsed, createListController(userHandle), this); 57 } 58 59 @Override createMyUserIdProvider()60 protected MyUserIdProvider createMyUserIdProvider() { 61 if (sOverrides.mMyUserIdProvider != null) { 62 return sOverrides.mMyUserIdProvider; 63 } 64 return super.createMyUserIdProvider(); 65 } 66 67 @Override createCrossProfileIntentsChecker()68 protected CrossProfileIntentsChecker createCrossProfileIntentsChecker() { 69 if (sOverrides.mCrossProfileIntentsChecker != null) { 70 return sOverrides.mCrossProfileIntentsChecker; 71 } 72 return super.createCrossProfileIntentsChecker(); 73 } 74 75 @Override createQuietModeManager()76 protected QuietModeManager createQuietModeManager() { 77 if (sOverrides.mQuietModeManager != null) { 78 return sOverrides.mQuietModeManager; 79 } 80 return super.createQuietModeManager(); 81 } 82 getAdapter()83 ResolverWrapperAdapter getAdapter() { 84 return (ResolverWrapperAdapter) mMultiProfilePagerAdapter.getActiveListAdapter(); 85 } 86 getPersonalListAdapter()87 ResolverListAdapter getPersonalListAdapter() { 88 return ((ResolverListAdapter) mMultiProfilePagerAdapter.getAdapterForIndex(0)); 89 } 90 getWorkListAdapter()91 ResolverListAdapter getWorkListAdapter() { 92 if (mMultiProfilePagerAdapter.getInactiveListAdapter() == null) { 93 return null; 94 } 95 return ((ResolverListAdapter) mMultiProfilePagerAdapter.getAdapterForIndex(1)); 96 } 97 98 @Override isVoiceInteraction()99 public boolean isVoiceInteraction() { 100 if (sOverrides.isVoiceInteraction != null) { 101 return sOverrides.isVoiceInteraction; 102 } 103 return super.isVoiceInteraction(); 104 } 105 106 @Override safelyStartActivity(TargetInfo cti)107 public void safelyStartActivity(TargetInfo cti) { 108 if (sOverrides.onSafelyStartCallback != null && 109 sOverrides.onSafelyStartCallback.apply(cti)) { 110 return; 111 } 112 super.safelyStartActivity(cti); 113 } 114 115 @Override createListController(UserHandle userHandle)116 protected ResolverListController createListController(UserHandle userHandle) { 117 if (userHandle == UserHandle.SYSTEM) { 118 when(sOverrides.resolverListController.getUserHandle()).thenReturn(UserHandle.SYSTEM); 119 return sOverrides.resolverListController; 120 } 121 when(sOverrides.workResolverListController.getUserHandle()).thenReturn(userHandle); 122 return sOverrides.workResolverListController; 123 } 124 125 @Override getPackageManager()126 public PackageManager getPackageManager() { 127 if (sOverrides.createPackageManager != null) { 128 return sOverrides.createPackageManager.apply(super.getPackageManager()); 129 } 130 return super.getPackageManager(); 131 } 132 getCurrentUserHandle()133 protected UserHandle getCurrentUserHandle() { 134 return mMultiProfilePagerAdapter.getCurrentUserHandle(); 135 } 136 137 @Override getWorkProfileUserHandle()138 protected UserHandle getWorkProfileUserHandle() { 139 return sOverrides.workProfileUserHandle; 140 } 141 142 @Override startActivityAsUser(Intent intent, Bundle options, UserHandle user)143 public void startActivityAsUser(Intent intent, Bundle options, UserHandle user) { 144 super.startActivityAsUser(intent, options, user); 145 } 146 147 /** 148 * We cannot directly mock the activity created since instrumentation creates it. 149 * <p> 150 * Instead, we use static instances of this object to modify behavior. 151 */ 152 static class OverrideData { 153 @SuppressWarnings("Since15") 154 public Function<PackageManager, PackageManager> createPackageManager; 155 public Function<TargetInfo, Boolean> onSafelyStartCallback; 156 public ResolverListController resolverListController; 157 public ResolverListController workResolverListController; 158 public Boolean isVoiceInteraction; 159 public UserHandle workProfileUserHandle; 160 public Integer myUserId; 161 public boolean hasCrossProfileIntents; 162 public boolean isQuietModeEnabled; 163 public QuietModeManager mQuietModeManager; 164 public MyUserIdProvider mMyUserIdProvider; 165 public CrossProfileIntentsChecker mCrossProfileIntentsChecker; 166 reset()167 public void reset() { 168 onSafelyStartCallback = null; 169 isVoiceInteraction = null; 170 createPackageManager = null; 171 resolverListController = mock(ResolverListController.class); 172 workResolverListController = mock(ResolverListController.class); 173 workProfileUserHandle = null; 174 myUserId = null; 175 hasCrossProfileIntents = true; 176 isQuietModeEnabled = false; 177 178 mQuietModeManager = new QuietModeManager() { 179 @Override 180 public boolean isQuietModeEnabled(UserHandle workProfileUserHandle) { 181 return isQuietModeEnabled; 182 } 183 184 @Override 185 public void requestQuietModeEnabled(boolean enabled, 186 UserHandle workProfileUserHandle) { 187 isQuietModeEnabled = enabled; 188 } 189 190 @Override 191 public void markWorkProfileEnabledBroadcastReceived() { 192 } 193 194 @Override 195 public boolean isWaitingToEnableWorkProfile() { 196 return false; 197 } 198 }; 199 200 mMyUserIdProvider = new MyUserIdProvider() { 201 @Override 202 public int getMyUserId() { 203 return myUserId != null ? myUserId : UserHandle.myUserId(); 204 } 205 }; 206 207 mCrossProfileIntentsChecker = mock(CrossProfileIntentsChecker.class); 208 when(mCrossProfileIntentsChecker.hasCrossProfileIntents(any(), anyInt(), anyInt())) 209 .thenAnswer(invocation -> hasCrossProfileIntents); 210 } 211 } 212 } 213