Home | History | Annotate | Download | only in authenticator
      1 /*
      2  * Copyright (C) 2010 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 
     17 package com.example.android.samplesync.authenticator;
     18 
     19 import android.accounts.AbstractAccountAuthenticator;
     20 import android.accounts.Account;
     21 import android.accounts.AccountAuthenticatorResponse;
     22 import android.accounts.AccountManager;
     23 import android.content.Context;
     24 import android.content.Intent;
     25 import android.os.Bundle;
     26 
     27 import com.example.android.samplesync.Constants;
     28 import com.example.android.samplesync.R;
     29 import com.example.android.samplesync.client.NetworkUtilities;
     30 
     31 /**
     32  * This class is an implementation of AbstractAccountAuthenticator for
     33  * authenticating accounts in the com.example.android.samplesync domain.
     34  */
     35 class Authenticator extends AbstractAccountAuthenticator {
     36     // Authentication Service context
     37     private final Context mContext;
     38 
     39     public Authenticator(Context context) {
     40         super(context);
     41         mContext = context;
     42     }
     43 
     44     /**
     45      * {@inheritDoc}
     46      */
     47     @Override
     48     public Bundle addAccount(AccountAuthenticatorResponse response,
     49         String accountType, String authTokenType, String[] requiredFeatures,
     50         Bundle options) {
     51         final Intent intent = new Intent(mContext, AuthenticatorActivity.class);
     52         intent.putExtra(AuthenticatorActivity.PARAM_AUTHTOKEN_TYPE,
     53             authTokenType);
     54         intent.putExtra(AccountManager.KEY_ACCOUNT_AUTHENTICATOR_RESPONSE,
     55             response);
     56         final Bundle bundle = new Bundle();
     57         bundle.putParcelable(AccountManager.KEY_INTENT, intent);
     58         return bundle;
     59     }
     60 
     61     /**
     62      * {@inheritDoc}
     63      */
     64     @Override
     65     public Bundle confirmCredentials(AccountAuthenticatorResponse response,
     66         Account account, Bundle options) {
     67         if (options != null && options.containsKey(AccountManager.KEY_PASSWORD)) {
     68             final String password =
     69                 options.getString(AccountManager.KEY_PASSWORD);
     70             final boolean verified =
     71                 onlineConfirmPassword(account.name, password);
     72             final Bundle result = new Bundle();
     73             result.putBoolean(AccountManager.KEY_BOOLEAN_RESULT, verified);
     74             return result;
     75         }
     76         // Launch AuthenticatorActivity to confirm credentials
     77         final Intent intent = new Intent(mContext, AuthenticatorActivity.class);
     78         intent.putExtra(AuthenticatorActivity.PARAM_USERNAME, account.name);
     79         intent.putExtra(AuthenticatorActivity.PARAM_CONFIRMCREDENTIALS, true);
     80         intent.putExtra(AccountManager.KEY_ACCOUNT_AUTHENTICATOR_RESPONSE,
     81             response);
     82         final Bundle bundle = new Bundle();
     83         bundle.putParcelable(AccountManager.KEY_INTENT, intent);
     84         return bundle;
     85     }
     86 
     87     /**
     88      * {@inheritDoc}
     89      */
     90     @Override
     91     public Bundle editProperties(AccountAuthenticatorResponse response,
     92         String accountType) {
     93         throw new UnsupportedOperationException();
     94     }
     95 
     96     /**
     97      * {@inheritDoc}
     98      */
     99     @Override
    100     public Bundle getAuthToken(AccountAuthenticatorResponse response,
    101         Account account, String authTokenType, Bundle loginOptions) {
    102         if (!authTokenType.equals(Constants.AUTHTOKEN_TYPE)) {
    103             final Bundle result = new Bundle();
    104             result.putString(AccountManager.KEY_ERROR_MESSAGE,
    105                 "invalid authTokenType");
    106             return result;
    107         }
    108         final AccountManager am = AccountManager.get(mContext);
    109         final String password = am.getPassword(account);
    110         if (password != null) {
    111             final boolean verified =
    112                 onlineConfirmPassword(account.name, password);
    113             if (verified) {
    114                 final Bundle result = new Bundle();
    115                 result.putString(AccountManager.KEY_ACCOUNT_NAME, account.name);
    116                 result.putString(AccountManager.KEY_ACCOUNT_TYPE,
    117                     Constants.ACCOUNT_TYPE);
    118                 result.putString(AccountManager.KEY_AUTHTOKEN, password);
    119                 return result;
    120             }
    121         }
    122         // the password was missing or incorrect, return an Intent to an
    123         // Activity that will prompt the user for the password.
    124         final Intent intent = new Intent(mContext, AuthenticatorActivity.class);
    125         intent.putExtra(AuthenticatorActivity.PARAM_USERNAME, account.name);
    126         intent.putExtra(AuthenticatorActivity.PARAM_AUTHTOKEN_TYPE,
    127             authTokenType);
    128         intent.putExtra(AccountManager.KEY_ACCOUNT_AUTHENTICATOR_RESPONSE,
    129             response);
    130         final Bundle bundle = new Bundle();
    131         bundle.putParcelable(AccountManager.KEY_INTENT, intent);
    132         return bundle;
    133     }
    134 
    135     /**
    136      * {@inheritDoc}
    137      */
    138     @Override
    139     public String getAuthTokenLabel(String authTokenType) {
    140         if (authTokenType.equals(Constants.AUTHTOKEN_TYPE)) {
    141             return mContext.getString(R.string.label);
    142         }
    143         return null;
    144 
    145     }
    146 
    147     /**
    148      * {@inheritDoc}
    149      */
    150     @Override
    151     public Bundle hasFeatures(AccountAuthenticatorResponse response,
    152         Account account, String[] features) {
    153         final Bundle result = new Bundle();
    154         result.putBoolean(AccountManager.KEY_BOOLEAN_RESULT, false);
    155         return result;
    156     }
    157 
    158     /**
    159      * Validates user's password on the server
    160      */
    161     private boolean onlineConfirmPassword(String username, String password) {
    162         return NetworkUtilities.authenticate(username, password,
    163             null/* Handler */, null/* Context */);
    164     }
    165 
    166     /**
    167      * {@inheritDoc}
    168      */
    169     @Override
    170     public Bundle updateCredentials(AccountAuthenticatorResponse response,
    171         Account account, String authTokenType, Bundle loginOptions) {
    172         final Intent intent = new Intent(mContext, AuthenticatorActivity.class);
    173         intent.putExtra(AuthenticatorActivity.PARAM_USERNAME, account.name);
    174         intent.putExtra(AuthenticatorActivity.PARAM_AUTHTOKEN_TYPE,
    175             authTokenType);
    176         intent.putExtra(AuthenticatorActivity.PARAM_CONFIRMCREDENTIALS, false);
    177         final Bundle bundle = new Bundle();
    178         bundle.putParcelable(AccountManager.KEY_INTENT, intent);
    179         return bundle;
    180     }
    181 
    182 }
    183