Merge "add option --user to Bmgr.java"
diff --git a/cmds/bmgr/src/com/android/commands/bmgr/Bmgr.java b/cmds/bmgr/src/com/android/commands/bmgr/Bmgr.java
index a826ec7..3723fce 100644
--- a/cmds/bmgr/src/com/android/commands/bmgr/Bmgr.java
+++ b/cmds/bmgr/src/com/android/commands/bmgr/Bmgr.java
@@ -17,6 +17,7 @@
package com.android.commands.bmgr;
import android.annotation.IntDef;
+import android.annotation.UserIdInt;
import android.app.backup.BackupManager;
import android.app.backup.BackupManagerMonitor;
import android.app.backup.BackupProgress;
@@ -29,6 +30,7 @@
import android.app.backup.ISelectBackupTransportCallback;
import android.app.backup.RestoreSet;
import android.content.ComponentName;
+import android.content.Context;
import android.content.pm.IPackageManager;
import android.content.pm.PackageInfo;
import android.os.Bundle;
@@ -37,8 +39,10 @@
import android.os.SystemClock;
import android.os.UserHandle;
import android.util.ArraySet;
+import android.util.Slog;
import com.android.internal.annotations.GuardedBy;
+import com.android.internal.annotations.VisibleForTesting;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
@@ -49,20 +53,34 @@
import java.util.Set;
import java.util.concurrent.CountDownLatch;
-public final class Bmgr {
- IBackupManager mBmgr;
- IRestoreSession mRestore;
+/**
+ * Adb shell command for {@link android.app.backup.IBackupManager}.
+ */
+public class Bmgr {
+ public static final String TAG = "Bmgr";
- static final String BMGR_NOT_RUNNING_ERR =
+ private final IBackupManager mBmgr;
+ private IRestoreSession mRestore;
+
+ private static final String BMGR_NOT_RUNNING_ERR =
"Error: Could not access the Backup Manager. Is the system running?";
- static final String TRANSPORT_NOT_RUNNING_ERR =
+ private static final String TRANSPORT_NOT_RUNNING_ERR =
"Error: Could not access the backup transport. Is the system running?";
- static final String PM_NOT_RUNNING_ERR =
+ private static final String PM_NOT_RUNNING_ERR =
"Error: Could not access the Package Manager. Is the system running?";
private String[] mArgs;
private int mNextArg;
+ @VisibleForTesting
+ Bmgr(IBackupManager bmgr) {
+ mBmgr = bmgr;
+ }
+
+ Bmgr() {
+ mBmgr = IBackupManager.Stub.asInterface(ServiceManager.getService(Context.BACKUP_SERVICE));
+ }
+
public static void main(String[] args) {
try {
new Bmgr().run(args);
@@ -78,71 +96,73 @@
return;
}
- if (!isBmgrActive()) {
+ mArgs = args;
+ mNextArg = 0;
+ int userId = parseUserId();
+ String op = nextArg();
+ Slog.v(TAG, "Running " + op + " for user:" + userId);
+
+ if (!isBmgrActive(userId)) {
return;
}
- mArgs = args;
- String op = args[0];
- mNextArg = 1;
-
if ("enabled".equals(op)) {
- doEnabled();
+ doEnabled(userId);
return;
}
if ("enable".equals(op)) {
- doEnable();
+ doEnable(userId);
return;
}
if ("run".equals(op)) {
- doRun();
+ doRun(userId);
return;
}
if ("backup".equals(op)) {
- doBackup();
+ doBackup(userId);
return;
}
if ("init".equals(op)) {
- doInit();
+ doInit(userId);
return;
}
if ("list".equals(op)) {
- doList();
+ doList(userId);
return;
}
if ("restore".equals(op)) {
- doRestore();
+ doRestore(userId);
return;
}
if ("transport".equals(op)) {
- doTransport();
+ doTransport(userId);
return;
}
if ("wipe".equals(op)) {
- doWipe();
+ doWipe(userId);
return;
}
if ("fullbackup".equals(op)) {
- doFullTransportBackup();
+ doFullTransportBackup(userId);
return;
}
if ("backupnow".equals(op)) {
- doBackupNow();
+ doBackupNow(userId);
return;
}
if ("cancel".equals(op)) {
- doCancel();
+ doCancel(userId);
return;
}
@@ -155,15 +175,14 @@
showUsage();
}
- private boolean isBmgrActive() {
- mBmgr = IBackupManager.Stub.asInterface(ServiceManager.getService("backup"));
+ boolean isBmgrActive(@UserIdInt int userId) {
if (mBmgr == null) {
System.err.println(BMGR_NOT_RUNNING_ERR);
return false;
}
try {
- if (!mBmgr.isBackupServiceActive(UserHandle.USER_SYSTEM)) {
+ if (!mBmgr.isBackupServiceActive(userId)) {
System.err.println(BMGR_NOT_RUNNING_ERR);
return false;
}
@@ -180,7 +199,7 @@
return enabled ? "enabled" : "disabled";
}
- private void doEnabled() {
+ private void doEnabled(@UserIdInt int userId) {
try {
boolean isEnabled = mBmgr.isBackupEnabled();
System.out.println("Backup Manager currently "
@@ -191,7 +210,7 @@
}
}
- private void doEnable() {
+ private void doEnable(@UserIdInt int userId) {
String arg = nextArg();
if (arg == null) {
showUsage();
@@ -211,7 +230,7 @@
}
}
- private void doRun() {
+ void doRun(@UserIdInt int userId) {
try {
mBmgr.backupNow();
} catch (RemoteException e) {
@@ -220,7 +239,7 @@
}
}
- private void doBackup() {
+ private void doBackup(@UserIdInt int userId) {
String pkg = nextArg();
if (pkg == null) {
showUsage();
@@ -235,7 +254,7 @@
}
}
- private void doFullTransportBackup() {
+ private void doFullTransportBackup(@UserIdInt int userId) {
System.out.println("Performing full transport backup");
String pkg;
@@ -354,8 +373,8 @@
}
}
- private void backupNowAllPackages(boolean nonIncrementalBackup, @Monitor int monitorState) {
- int userId = UserHandle.USER_SYSTEM;
+ private void backupNowAllPackages(@UserIdInt int userId, boolean nonIncrementalBackup,
+ @Monitor int monitorState) {
IPackageManager mPm =
IPackageManager.Stub.asInterface(ServiceManager.getService("package"));
if (mPm == null) {
@@ -379,11 +398,13 @@
System.err.println(e.toString());
System.err.println(BMGR_NOT_RUNNING_ERR);
}
- backupNowPackages(Arrays.asList(filteredPackages), nonIncrementalBackup, monitorState);
+ backupNowPackages(userId, Arrays.asList(filteredPackages), nonIncrementalBackup,
+ monitorState);
}
}
private void backupNowPackages(
+ @UserIdInt int userId,
List<String> packages, boolean nonIncrementalBackup, @Monitor int monitorState) {
int flags = 0;
if (nonIncrementalBackup) {
@@ -412,7 +433,7 @@
}
}
- private void doBackupNow() {
+ private void doBackupNow(@UserIdInt int userId) {
String pkg;
boolean backupAll = false;
boolean nonIncrementalBackup = false;
@@ -439,20 +460,20 @@
if (allPkgs.size() == 0) {
System.out.println("Running " + (nonIncrementalBackup ? "non-" : "") +
"incremental backup for all packages.");
- backupNowAllPackages(nonIncrementalBackup, monitor);
+ backupNowAllPackages(userId, nonIncrementalBackup, monitor);
} else {
System.err.println("Provide only '--all' flag or list of packages.");
}
} else if (allPkgs.size() > 0) {
System.out.println("Running " + (nonIncrementalBackup ? "non-" : "") +
"incremental backup for " + allPkgs.size() +" requested packages.");
- backupNowPackages(allPkgs, nonIncrementalBackup, monitor);
+ backupNowPackages(userId, allPkgs, nonIncrementalBackup, monitor);
} else {
System.err.println("Provide '--all' flag or list of packages.");
}
}
- private void doCancel() {
+ private void doCancel(@UserIdInt int userId) {
String arg = nextArg();
if ("backups".equals(arg)) {
try {
@@ -467,7 +488,7 @@
System.err.println("Unknown command.");
}
- private void doTransport() {
+ private void doTransport(@UserIdInt int userId) {
try {
String which = nextArg();
if (which == null) {
@@ -531,7 +552,7 @@
}
}
- private void doWipe() {
+ private void doWipe(@UserIdInt int userId) {
String transport = nextArg();
if (transport == null) {
showUsage();
@@ -563,7 +584,7 @@
}
}
- private void doInit() {
+ private void doInit(@UserIdInt int userId) {
ArraySet<String> transports = new ArraySet<>();
String transport;
while ((transport = nextArg()) != null) {
@@ -586,7 +607,7 @@
}
}
- private void doList() {
+ private void doList(@UserIdInt int userId) {
String arg = nextArg(); // sets, transports, packages set#
if ("transports".equals(arg)) {
doListTransports();
@@ -603,8 +624,6 @@
if ("sets".equals(arg)) {
doListRestoreSets();
- } else if ("transports".equals(arg)) {
- doListTransports();
}
mRestore.endRestoreSession();
@@ -717,7 +736,7 @@
}
}
- private void doRestore() {
+ private void doRestore(@UserIdInt int userId) {
String arg = nextArg();
if (arg == null) {
showUsage();
@@ -830,8 +849,18 @@
return arg;
}
+ private int parseUserId() {
+ String arg = nextArg();
+ if ("--user".equals(arg)) {
+ return UserHandle.parseUserArg(nextArg());
+ } else {
+ mNextArg--;
+ return UserHandle.USER_SYSTEM;
+ }
+ }
+
private static void showUsage() {
- System.err.println("usage: bmgr [backup|restore|list|transport|run]");
+ System.err.println("usage: bmgr [--user <userId>] [backup|restore|list|transport|run]");
System.err.println(" bmgr backup PACKAGE");
System.err.println(" bmgr enable BOOL");
System.err.println(" bmgr enabled");
@@ -847,6 +876,10 @@
System.err.println(" bmgr cancel backups");
System.err.println(" bmgr init TRANSPORT...");
System.err.println("");
+ System.err.println("The '--user' option specifies the user on which the operation is run.");
+ System.err.println("It must be the first argument before the operation.");
+ System.err.println("The default value is 0 which is the system user.");
+ System.err.println("");
System.err.println("The 'backup' command schedules a backup pass for the named package.");
System.err.println("Note that the backup pass will effectively be a no-op if the package");
System.err.println("does not actually have changed data to store.");
diff --git a/services/robotests/Android.mk b/services/robotests/Android.mk
index 565152c..6f10ed5 100644
--- a/services/robotests/Android.mk
+++ b/services/robotests/Android.mk
@@ -26,6 +26,7 @@
LOCAL_PRIVILEGED_MODULE := true
LOCAL_STATIC_JAVA_LIBRARIES := \
+ bmgrlib \
services.backup \
services.core \
services.net
diff --git a/services/robotests/src/com/android/commands/bmgr/BmgrTest.java b/services/robotests/src/com/android/commands/bmgr/BmgrTest.java
new file mode 100644
index 0000000..1705f5b
--- /dev/null
+++ b/services/robotests/src/com/android/commands/bmgr/BmgrTest.java
@@ -0,0 +1,63 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.commands.bmgr;
+
+import static org.mockito.Mockito.verify;
+
+import android.app.backup.IBackupManager;
+import android.os.UserHandle;
+import android.platform.test.annotations.Presubmit;
+
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.Mock;
+import org.mockito.MockitoAnnotations;
+import org.robolectric.RobolectricTestRunner;
+
+/** Unit tests for {@link com.android.commands.bmgr.Bmgr}. */
+@RunWith(RobolectricTestRunner.class)
+@Presubmit
+public class BmgrTest {
+ @Mock private IBackupManager mBackupManager;
+ private Bmgr mBmgr;
+
+ /** Common setup run before each test method. */
+ @Before
+ public void setUp() throws Exception {
+ MockitoAnnotations.initMocks(this);
+ mBmgr = new Bmgr(mBackupManager);
+ }
+
+ /**
+ * Test that bmgr uses the default user {@link UserHandle.USER_SYSTEM} if no user is specified.
+ */
+ @Test
+ public void testRun_whenUserNotSpecified_callsBackupManagerAsSystemUser() throws Exception {
+ mBmgr.run(new String[] {"run"});
+
+ verify(mBackupManager).isBackupServiceActive(UserHandle.USER_SYSTEM);
+ }
+
+ /** Test that bmgr uses the specified user if an user is specified. */
+ @Test
+ public void testRun_whenUserSpecified_callsBackupManagerAsSpecifiedUser() throws Exception {
+ mBmgr.run(new String[] {"--user", "10"});
+
+ verify(mBackupManager).isBackupServiceActive(10);
+ }
+}