blob: 7181c6117f911f173bc829ca2689593adb60c428 [file] [log] [blame]
Christopher Tate80202c82010-01-25 19:37:47 -08001/*
2 * Copyright (C) 2010 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
Christopher Tate45281862010-03-05 15:46:30 -080017package android.app.backup;
Christopher Tate80202c82010-01-25 19:37:47 -080018
Christopher Tate45281862010-03-05 15:46:30 -080019import android.app.backup.RestoreObserver;
20import android.app.backup.RestoreSet;
21import android.app.backup.IRestoreObserver;
22import android.app.backup.IRestoreSession;
Christopher Tate80202c82010-01-25 19:37:47 -080023import android.content.Context;
24import android.os.Handler;
Christopher Tated3cd3592010-02-01 15:31:09 -080025import android.os.Message;
Christopher Tate80202c82010-01-25 19:37:47 -080026import android.os.RemoteException;
27import android.util.Log;
28
29/**
Christopher Tate9c3cee92010-03-25 16:06:43 -070030 * Interface for managing a restore session.
31 * @hide
Christopher Tate80202c82010-01-25 19:37:47 -080032 */
33public class RestoreSession {
34 static final String TAG = "RestoreSession";
35
36 final Context mContext;
37 IRestoreSession mBinder;
38 RestoreObserverWrapper mObserver = null;
39
40 /**
41 * Ask the current transport what the available restore sets are.
42 *
Christopher Tate2d449afe2010-03-29 19:14:24 -070043 * @param observer a RestoreObserver object whose restoreSetsAvailable() method will
44 * be called on the application's main thread in order to supply the results of
45 * the restore set lookup by the backup transport. This parameter must not be
46 * null.
47 * @return Zero on success, nonzero on error. The observer's restoreSetsAvailable()
48 * method will only be called if this method returned zero.
Christopher Tate80202c82010-01-25 19:37:47 -080049 */
Christopher Tate2d449afe2010-03-29 19:14:24 -070050 public int getAvailableRestoreSets(RestoreObserver observer) {
51 int err = -1;
52 RestoreObserverWrapper obsWrapper = new RestoreObserverWrapper(mContext, observer);
Christopher Tate80202c82010-01-25 19:37:47 -080053 try {
Christopher Tate2d449afe2010-03-29 19:14:24 -070054 err = mBinder.getAvailableRestoreSets(obsWrapper);
Christopher Tate80202c82010-01-25 19:37:47 -080055 } catch (RemoteException e) {
56 Log.d(TAG, "Can't contact server to get available sets");
Christopher Tate80202c82010-01-25 19:37:47 -080057 }
Christopher Tate2d449afe2010-03-29 19:14:24 -070058 return err;
Christopher Tate80202c82010-01-25 19:37:47 -080059 }
60
61 /**
62 * Restore the given set onto the device, replacing the current data of any app
63 * contained in the restore set with the data previously backed up.
64 *
Christopher Tate84725812010-02-04 15:52:40 -080065 * <p>Callers must hold the android.permission.BACKUP permission to use this method.
66 *
Christopher Tate80202c82010-01-25 19:37:47 -080067 * @return Zero on success; nonzero on error. The observer will only receive
68 * progress callbacks if this method returned zero.
Kenny Root7951eaa2010-02-17 13:55:17 -080069 * @param token The token from {@link #getAvailableRestoreSets()} corresponding to
Christopher Tate80202c82010-01-25 19:37:47 -080070 * the restore set that should be used.
Christopher Tate84725812010-02-04 15:52:40 -080071 * @param observer If non-null, this binder points to an object that will receive
72 * progress callbacks during the restore operation.
Christopher Tate80202c82010-01-25 19:37:47 -080073 */
Christopher Tate84725812010-02-04 15:52:40 -080074 public int restoreAll(long token, RestoreObserver observer) {
Christopher Tate80202c82010-01-25 19:37:47 -080075 int err = -1;
76 if (mObserver != null) {
Christopher Tate84725812010-02-04 15:52:40 -080077 Log.d(TAG, "restoreAll() called during active restore");
Christopher Tate80202c82010-01-25 19:37:47 -080078 return -1;
79 }
80 mObserver = new RestoreObserverWrapper(mContext, observer);
81 try {
Christopher Tate84725812010-02-04 15:52:40 -080082 err = mBinder.restoreAll(token, mObserver);
Christopher Tate80202c82010-01-25 19:37:47 -080083 } catch (RemoteException e) {
Christopher Tate84725812010-02-04 15:52:40 -080084 Log.d(TAG, "Can't contact server to restore");
85 }
86 return err;
87 }
88
89 /**
Christopher Tate284f1bb2011-07-07 14:31:18 -070090 * Restore select packages from the given set onto the device, replacing the
91 * current data of any app contained in the set with the data previously
92 * backed up.
93 *
94 * <p>Callers must hold the android.permission.BACKUP permission to use this method.
95 *
96 * @return Zero on success, nonzero on error. The observer will only receive
97 * progress callbacks if this method returned zero.
98 * @param token The token from {@link getAvailableRestoreSets()} corresponding to
99 * the restore set that should be used.
100 * @param observer If non-null, this binder points to an object that will receive
101 * progress callbacks during the restore operation.
102 * @param packages The set of packages for which to attempt a restore. Regardless of
103 * the contents of the actual back-end dataset named by {@code token}, only
104 * applications mentioned in this list will have their data restored.
105 *
106 * @hide
107 */
108 public int restoreSome(long token, RestoreObserver observer, String[] packages) {
109 int err = -1;
110 if (mObserver != null) {
111 Log.d(TAG, "restoreAll() called during active restore");
112 return -1;
113 }
114 mObserver = new RestoreObserverWrapper(mContext, observer);
115 try {
116 err = mBinder.restoreSome(token, mObserver, packages);
117 } catch (RemoteException e) {
118 Log.d(TAG, "Can't contact server to restore packages");
119 }
120 return err;
121 }
122
123 /**
Christopher Tate84725812010-02-04 15:52:40 -0800124 * Restore a single application from backup. The data will be restored from the
125 * current backup dataset if the given package has stored data there, or from
126 * the dataset used during the last full device setup operation if the current
127 * backup dataset has no matching data. If no backup data exists for this package
128 * in either source, a nonzero value will be returned.
129 *
130 * @return Zero on success; nonzero on error. The observer will only receive
131 * progress callbacks if this method returned zero.
132 * @param packageName The name of the package whose data to restore. If this is
133 * not the name of the caller's own package, then the android.permission.BACKUP
134 * permission must be held.
135 * @param observer If non-null, this binder points to an object that will receive
136 * progress callbacks during the restore operation.
137 */
138 public int restorePackage(String packageName, RestoreObserver observer) {
139 int err = -1;
140 if (mObserver != null) {
141 Log.d(TAG, "restorePackage() called during active restore");
142 return -1;
143 }
144 mObserver = new RestoreObserverWrapper(mContext, observer);
145 try {
146 err = mBinder.restorePackage(packageName, mObserver);
147 } catch (RemoteException e) {
148 Log.d(TAG, "Can't contact server to restore package");
Christopher Tate80202c82010-01-25 19:37:47 -0800149 }
150 return err;
151 }
152
153 /**
154 * End this restore session. After this method is called, the RestoreSession
155 * object is no longer valid.
156 *
157 * <p><b>Note:</b> The caller <i>must</i> invoke this method to end the restore session,
Kenny Root7951eaa2010-02-17 13:55:17 -0800158 * even if {@link #restorePackage(String, RestoreObserver)} failed.
Christopher Tate80202c82010-01-25 19:37:47 -0800159 */
160 public void endRestoreSession() {
161 try {
162 mBinder.endRestoreSession();
163 } catch (RemoteException e) {
164 Log.d(TAG, "Can't contact server to get available sets");
165 } finally {
166 mBinder = null;
167 }
168 }
169
170 /*
171 * Nonpublic implementation here
172 */
173
174 RestoreSession(Context context, IRestoreSession binder) {
175 mContext = context;
176 mBinder = binder;
177 }
178
179 /*
180 * We wrap incoming binder calls with a private class implementation that
Christopher Tate44a27902010-01-27 17:15:49 -0800181 * redirects them into main-thread actions. This serializes the restore
Christopher Tate80202c82010-01-25 19:37:47 -0800182 * progress callbacks nicely within the usual main-thread lifecycle pattern.
183 */
184 private class RestoreObserverWrapper extends IRestoreObserver.Stub {
185 final Handler mHandler;
186 final RestoreObserver mAppObserver;
187
Christopher Tated3cd3592010-02-01 15:31:09 -0800188 static final int MSG_RESTORE_STARTING = 1;
189 static final int MSG_UPDATE = 2;
190 static final int MSG_RESTORE_FINISHED = 3;
Christopher Tate2d449afe2010-03-29 19:14:24 -0700191 static final int MSG_RESTORE_SETS_AVAILABLE = 4;
Christopher Tated3cd3592010-02-01 15:31:09 -0800192
Christopher Tate80202c82010-01-25 19:37:47 -0800193 RestoreObserverWrapper(Context context, RestoreObserver appObserver) {
Christopher Tated3cd3592010-02-01 15:31:09 -0800194 mHandler = new Handler(context.getMainLooper()) {
195 @Override
196 public void handleMessage(Message msg) {
197 switch (msg.what) {
198 case MSG_RESTORE_STARTING:
199 mAppObserver.restoreStarting(msg.arg1);
200 break;
201 case MSG_UPDATE:
Christopher Tate9c3cee92010-03-25 16:06:43 -0700202 mAppObserver.onUpdate(msg.arg1, (String)msg.obj);
Christopher Tated3cd3592010-02-01 15:31:09 -0800203 break;
204 case MSG_RESTORE_FINISHED:
205 mAppObserver.restoreFinished(msg.arg1);
206 break;
Christopher Tate2d449afe2010-03-29 19:14:24 -0700207 case MSG_RESTORE_SETS_AVAILABLE:
208 mAppObserver.restoreSetsAvailable((RestoreSet[])msg.obj);
209 break;
Christopher Tated3cd3592010-02-01 15:31:09 -0800210 }
211 }
212 };
Christopher Tate80202c82010-01-25 19:37:47 -0800213 mAppObserver = appObserver;
214 }
215
Christopher Tated3cd3592010-02-01 15:31:09 -0800216 // Binder calls into this object just enqueue on the main-thread handler
Christopher Tate2d449afe2010-03-29 19:14:24 -0700217 public void restoreSetsAvailable(RestoreSet[] result) {
218 mHandler.sendMessage(
219 mHandler.obtainMessage(MSG_RESTORE_SETS_AVAILABLE, result));
220 }
221
Christopher Tate80202c82010-01-25 19:37:47 -0800222 public void restoreStarting(int numPackages) {
Christopher Tated3cd3592010-02-01 15:31:09 -0800223 mHandler.sendMessage(
224 mHandler.obtainMessage(MSG_RESTORE_STARTING, numPackages, 0));
Christopher Tate80202c82010-01-25 19:37:47 -0800225 }
226
Christopher Tate9c3cee92010-03-25 16:06:43 -0700227 public void onUpdate(int nowBeingRestored, String currentPackage) {
Christopher Tated3cd3592010-02-01 15:31:09 -0800228 mHandler.sendMessage(
Christopher Tate9c3cee92010-03-25 16:06:43 -0700229 mHandler.obtainMessage(MSG_UPDATE, nowBeingRestored, 0, currentPackage));
Christopher Tate80202c82010-01-25 19:37:47 -0800230 }
231
232 public void restoreFinished(int error) {
Christopher Tated3cd3592010-02-01 15:31:09 -0800233 mHandler.sendMessage(
234 mHandler.obtainMessage(MSG_RESTORE_FINISHED, error, 0));
Christopher Tate80202c82010-01-25 19:37:47 -0800235 }
236 }
237}