Allow to provide only a component name prefix to 'am instrument'
Bug: 27831862
Change-Id: I1d57e416c47fc7d9ea212f0002986932663081b8
diff --git a/cmds/am/src/com/android/commands/am/Am.java b/cmds/am/src/com/android/commands/am/Am.java
index 221b2d3..456be02 100644
--- a/cmds/am/src/com/android/commands/am/Am.java
+++ b/cmds/am/src/com/android/commands/am/Am.java
@@ -44,6 +44,7 @@
import android.content.IIntentReceiver;
import android.content.Intent;
import android.content.pm.IPackageManager;
+import android.content.pm.InstrumentationInfo;
import android.content.pm.ParceledListSlice;
import android.content.pm.ResolveInfo;
import android.content.pm.UserInfo;
@@ -96,6 +97,7 @@
private static final int STACK_BOUNDS_INSET = 10;
private IActivityManager mAm;
+ private IPackageManager mPm;
private int mStartFlags = 0;
private boolean mWaitOption = false;
@@ -224,7 +226,8 @@
" --receiver-permission <PERMISSION>: Require receiver to hold permission.\n" +
"\n" +
"am instrument: start an Instrumentation. Typically this target <COMPONENT>\n" +
- " is the form <TEST_PACKAGE>/<RUNNER_CLASS>. Options are:\n" +
+ " is the form <TEST_PACKAGE>/<RUNNER_CLASS> or only <TEST_PACKAGE> if there \n" +
+ " is only one instrumentation. Options are:\n" +
" -r: print raw results (otherwise decode REPORT_KEY_STREAMRESULT). Use with\n" +
" [-e perf true] to generate raw output for performance measurements.\n" +
" -e <NAME> <VALUE>: set argument <NAME> to <VALUE>. For test runners a\n" +
@@ -373,6 +376,12 @@
throw new AndroidException("Can't connect to activity manager; is the system running?");
}
+ mPm = IPackageManager.Stub.asInterface(ServiceManager.getService("package"));
+ if (mPm == null) {
+ System.err.println(NO_SYSTEM_ERROR_CODE);
+ throw new AndroidException("Can't connect to package manager; is the system running?");
+ }
+
String op = nextArgRequired();
if (op.equals("start")) {
@@ -570,13 +579,7 @@
if (intent.getComponent() != null) {
packageName = intent.getComponent().getPackageName();
} else {
- IPackageManager pm = IPackageManager.Stub.asInterface(
- ServiceManager.getService("package"));
- if (pm == null) {
- System.err.println("Error: Package manager not running; aborting");
- return;
- }
- List<ResolveInfo> activities = pm.queryIntentActivities(intent, mimeType, 0,
+ List<ResolveInfo> activities = mPm.queryIntentActivities(intent, mimeType, 0,
mUserId).getList();
if (activities == null || activities.size() <= 0) {
System.err.println("Error: Intent does not match any activities: "
@@ -813,8 +816,44 @@
}
String cnArg = nextArgRequired();
- ComponentName cn = ComponentName.unflattenFromString(cnArg);
- if (cn == null) throw new IllegalArgumentException("Bad component name: " + cnArg);
+
+ ComponentName cn;
+ if (cnArg.contains("/")) {
+ cn = ComponentName.unflattenFromString(cnArg);
+ if (cn == null) throw new IllegalArgumentException("Bad component name: " + cnArg);
+ } else {
+ List<InstrumentationInfo> infos = mPm.queryInstrumentation(null, 0).getList();
+
+ final int numInfos = infos == null ? 0: infos.size();
+ List<ComponentName> cns = new ArrayList<>();
+ for (int i = 0; i < numInfos; i++) {
+ InstrumentationInfo info = infos.get(i);
+
+ ComponentName c = new ComponentName(info.packageName, info.name);
+ if (cnArg.equals(info.packageName)) {
+ cns.add(c);
+ }
+ }
+
+ if (cns.size() == 0) {
+ throw new IllegalArgumentException("No instrumentation found for: " + cnArg);
+ } else if (cns.size() == 1) {
+ cn = cns.get(0);
+ } else {
+ StringBuilder cnsStr = new StringBuilder();
+ final int numCns = cns.size();
+ for (int i = 0; i < numCns; i++) {
+ cnsStr.append(cns.get(i).flattenToString());
+ cnsStr.append(", ");
+ }
+
+ // Remove last ", "
+ cnsStr.setLength(cnsStr.length() - 2);
+
+ throw new IllegalArgumentException("Found multiple instrumentations: "
+ + cnsStr.toString());
+ }
+ }
InstrumentationWatcher watcher = null;
UiAutomationConnection connection = null;