1 /* 2 * Copyright (C) 2017 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); you may not 5 * use this file except in compliance with the License. You may obtain a copy of 6 * 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, WITHOUT 12 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the 13 * License for the specific language governing permissions and limitations under 14 * the License. 15 */ 16 package com.android.launcher3.util.rule; 17 18 import static androidx.test.platform.app.InstrumentationRegistry.getInstrumentation; 19 20 import static com.android.launcher3.tapl.TestHelpers.getLauncherInMyProcess; 21 22 import android.content.ComponentName; 23 import android.content.pm.ActivityInfo; 24 import android.os.Process; 25 26 import androidx.annotation.Nullable; 27 import androidx.test.uiautomator.UiDevice; 28 29 import com.android.systemui.shared.system.PackageManagerWrapper; 30 31 import org.junit.Assert; 32 import org.junit.rules.TestRule; 33 import org.junit.runner.Description; 34 import org.junit.runners.model.Statement; 35 36 import java.util.ArrayList; 37 38 /** 39 * Test rule which executes a shell command at the start of the test. 40 */ 41 public class ShellCommandRule implements TestRule { 42 private final String mCmd; 43 private final String mRevertCommand; 44 private final boolean mCheckSuccess; 45 private final Runnable mAdditionalChecks; 46 ShellCommandRule(String cmd, @Nullable String revertCommand, boolean checkSuccess, Runnable additionalChecks)47 public ShellCommandRule(String cmd, @Nullable String revertCommand, boolean checkSuccess, 48 Runnable additionalChecks) { 49 mCmd = cmd; 50 mRevertCommand = revertCommand; 51 mCheckSuccess = checkSuccess; 52 mAdditionalChecks = additionalChecks; 53 } 54 ShellCommandRule(String cmd, @Nullable String revertCommand)55 public ShellCommandRule(String cmd, @Nullable String revertCommand) { 56 this(cmd, revertCommand, false, null); 57 } 58 59 @Override apply(Statement base, Description description)60 public Statement apply(Statement base, Description description) { 61 return new Statement() { 62 @Override 63 public void evaluate() throws Throwable { 64 final String result = 65 UiDevice.getInstance(getInstrumentation()).executeShellCommand(mCmd); 66 if (mCheckSuccess) { 67 Assert.assertTrue( 68 "Failed command: " + mCmd + ", result: " + result, 69 "Success".equals(result.replaceAll("\\s", ""))); 70 } 71 if (mAdditionalChecks != null) mAdditionalChecks.run(); 72 try { 73 base.evaluate(); 74 } finally { 75 if (mRevertCommand != null) { 76 final String revertResult = UiDevice.getInstance( 77 getInstrumentation()).executeShellCommand(mRevertCommand); 78 if (mCheckSuccess) { 79 Assert.assertTrue( 80 "Failed command: " + mRevertCommand 81 + ", result: " + revertResult, 82 "Success".equals(result.replaceAll("\\s", ""))); 83 } 84 } 85 } 86 } 87 }; 88 } 89 90 /** 91 * Grants the launcher permission to bind widgets. 92 */ 93 public static ShellCommandRule grantWidgetBind() { 94 return new ShellCommandRule(String.format("appwidget grantbind --package %s --user %d", 95 getInstrumentation().getTargetContext().getPackageName(), 96 Process.myUserHandle().getIdentifier()), null); 97 } 98 99 /** 100 * Sets the target launcher as default launcher. 101 */ 102 public static ShellCommandRule setDefaultLauncher() { 103 final ActivityInfo launcher = getLauncherInMyProcess(); 104 return new ShellCommandRule(getLauncherCommand(launcher), null, true, () -> 105 Assert.assertEquals("Setting default launcher failed", 106 new ComponentName(launcher.packageName, launcher.name) 107 .flattenToString(), 108 PackageManagerWrapper.getInstance().getHomeActivities(new ArrayList<>()) 109 .flattenToString())); 110 } 111 112 public static String getLauncherCommand(ActivityInfo launcher) { 113 return String.format("cmd package set-home-activity --user %d %s", 114 Process.myUserHandle().getIdentifier(), 115 new ComponentName(launcher.packageName, launcher.name).flattenToString()); 116 } 117 118 /** 119 * Disables heads up notification for the duration of the test 120 */ 121 public static ShellCommandRule disableHeadsUpNotification() { 122 return new ShellCommandRule("settings put global heads_up_notifications_enabled 0", 123 "settings put global heads_up_notifications_enabled 1"); 124 } 125 } 126