– 對於帳號管理,由接口IAccountManager描述其相關的一組行為
– AccountManagerService是Android的系統服務。它實現瞭接口IAccountManager定義的這一組行為。這些行為的實現依賴應用程序中定義的Authenticator。
– AccountManager是一個面向應用程序開發的組件。它提供一組對應於IAccountManager協議的應用程序接口。這組接口通過Binder機制與系統服務AccountManagerService進行通信,協作完成帳戶相關的操作。同時,AccountManager接收應用程序提供的回調,以此在帳號操作完成之後向應用程序返回對應的結果,同時觸發應用程序層對這個結果的處理。
以addAccount()操作為例,步驟如下:
1. AccountManager初始化一個匿名的AmsTask子類實例。AmsTask是AccountManager的內部類:
[java] private abstract class AmsTask extends FutureTask<Bundle> implements AccountManagerFuture<Bundle> {
final IAccountManagerResponse mResponse;
final Handler mHandler;
final AccountManagerCallback<Bundle> mCallback;
final Activity mActivity;
public AmsTask(Activity activity, Handler handler, AccountManagerCallback<Bundle> callback) {
super(new Callable<Bundle>() {
public Bundle call() throws Exception {
throw new IllegalStateException("this should never be called");
}
});
mHandler = handler;
mCallback = callback;
mActivity = activity;
mResponse = new Response();
}
…
private abstract class AmsTask extends FutureTask<Bundle> implements AccountManagerFuture<Bundle> {
final IAccountManagerResponse mResponse;
final Handler mHandler;
final AccountManagerCallback<Bundle> mCallback;
final Activity mActivity;
public AmsTask(Activity activity, Handler handler, AccountManagerCallback<Bundle> callback) {
super(new Callable<Bundle>() {
public Bundle call() throws Exception {
throw new IllegalStateException("this should never be called");
}
});
mHandler = handler;
mCallback = callback;
mActivity = activity;
mResponse = new Response();
}
…
它是一個FutureTask子類,執行異步的任務,並返回結果。
addAccount()中的匿名子類實現瞭AmsTask.doWork()方法:
[java] public AccountManagerFuture<Bundle> addAccount(final String accountType,
final String authTokenType, final String[] requiredFeatures,
final Bundle addAccountOptions,
final Activity activity, AccountManagerCallback<Bundle> callback, Handler handler) {
…
return new AmsTask(activity, handler, callback) {
public void doWork() throws RemoteException {
mService.addAcount(mResponse, accountType, authTokenType,
requiredFeatures, activity != null, optionsIn);
}
}.start();
}
public AccountManagerFuture<Bundle> addAccount(final String accountType,
final String authTokenType, final String[] requiredFeatures,
final Bundle addAccountOptions,
final Activity activity, AccountManagerCallback<Bundle> callback, Handler handler) {
…
return new AmsTask(activity, handler, callback) {
public void doWork() throws RemoteException {
mService.addAcount(mResponse, accountType, authTokenType,
requiredFeatures, activity != null, optionsIn);
}
}.start();
}
在doWork()方法的實現中,調用AccountManager持有的AccountManagerService的代理對象(mService)向AccountManagerService發起IPC。
2. AccountManger調用AmsTask匿名子類的start()方法啟動任務。
3. start()方法會調用本類的doWork()方法,在這裡就是執行AccountManagerService的addAccount()操作。
4. 根據FutureTask的實現機制,在任務執行的結束時期,會調用本類的done()方法。AmsTask類覆蓋瞭這個方法:
[java] protected void done() {
if (mCallback != null) {
postToHandler(mHandler, mCallback, this);
}
}
protected void done() {
if (mCallback != null) {
postToHandler(mHandler, mCallback, this);
}
}
這裡的實現調用瞭AccountManager.postHandler()方法。看名字就可以猜到,這裡將mCallback回調對象裡面的run()方法傳送給主線程的handler進行調用:
[java] private void postToHandler(Handler handler, final AccountManagerCallback<Bundle> callback,
final AccountManagerFuture<Bundle> future) {
handler = handler == null ? mMainHandler : handler;
handler.post(new Runnable() {
public void run() {
callback.run(future);
}
});
}
private void postToHandler(Handler handler, final AccountManagerCallback<Bundle> callback,
final AccountManagerFuture<Bundle> future) {
handler = handler == null ? mMainHandler : handler;
handler.post(new Runnable() {
public void run() {
callback.run(future);
}
});
}
在這一次調用中,三個參數的來源分別是:
– handler: mHandler,即當前應用的主線程
– callback: 這個由調用AccountManager的應用程序提供
– future: this,即當前AmsTask實例,它實現瞭AccountManagerCallback接口,包含的是跨進成執行添加帳號操作的返回結果,是一個Bundler對象:
** 包含一個Intent實例:表明帳號創建需要啟動其指定的activity來與用戶交互,用戶將提供驗證信息,如用戶名、密碼
** 或者包含已經創建的帳號的名稱和類型
而應用程序將根據這個Bundle裡面封裝的實際內容采取下一步行動。