196c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project/*
296c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project * Copyright (C) 2008 The Android Open Source Project
396c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project *
496c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License");
596c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project * you may not use this file except in compliance with the License.
696c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project * You may obtain a copy of the License at
796c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project *
896c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project *      http://www.apache.org/licenses/LICENSE-2.0
996c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project *
1096c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project * Unless required by applicable law or agreed to in writing, software
1196c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS,
1296c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1396c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project * See the License for the specific language governing permissions and
1496c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project * limitations under the License.
1596c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project */
1696c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project
1796c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Projectpackage com.android.email.activity.setup;
1896c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project
199dac94975f31013d4b31ffb15eba27f352b2e758Daisuke Miyakawaimport android.accounts.AccountAuthenticatorResponse;
209dac94975f31013d4b31ffb15eba27f352b2e758Daisuke Miyakawaimport android.accounts.AccountManager;
2196c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Projectimport android.app.Activity;
22d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadlerimport android.app.ActivityManager;
233dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadlerimport android.app.AlertDialog;
243dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadlerimport android.app.Dialog;
253dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadlerimport android.app.DialogFragment;
26fd14496c494a0d38c35c3788c9cc55f1984592e4Andrew Stadlerimport android.app.FragmentTransaction;
27bcff14acf25d3a999b7448e317604e694c204f47Andrew Stadlerimport android.content.Context;
283dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadlerimport android.content.DialogInterface;
2996c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Projectimport android.content.Intent;
303dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadlerimport android.os.AsyncTask;
3196c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Projectimport android.os.Bundle;
323dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadlerimport android.text.Editable;
33d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadlerimport android.text.TextUtils;
343dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadlerimport android.text.TextWatcher;
35d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadlerimport android.util.Log;
367988164ddfdf2837314fa1763614422bcc90867bAndy Stadlerimport android.view.View;
377988164ddfdf2837314fa1763614422bcc90867bAndy Stadlerimport android.view.View.OnClickListener;
387988164ddfdf2837314fa1763614422bcc90867bAndy Stadlerimport android.widget.Button;
393dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadlerimport android.widget.CheckBox;
403dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadlerimport android.widget.EditText;
413dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadlerimport android.widget.TextView;
423dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadlerimport android.widget.Toast;
433dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
446fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blankimport com.android.email.EmailAddressValidator;
456fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blankimport com.android.email.R;
466fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blankimport com.android.email.VendorPolicyLoader;
476fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blankimport com.android.email.activity.ActivityHelper;
486fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blankimport com.android.email.activity.UiUtilities;
496fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blankimport com.android.email.activity.Welcome;
506fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blankimport com.android.email.activity.setup.AccountSettingsUtils.Provider;
516fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blankimport com.android.emailcommon.Logging;
526fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blankimport com.android.emailcommon.provider.Account;
536fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blankimport com.android.emailcommon.provider.EmailContent;
546fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blankimport com.android.emailcommon.provider.HostAuth;
55025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komaloimport com.android.emailcommon.service.SyncWindow;
566fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blankimport com.android.emailcommon.utility.Utility;
57025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komaloimport com.google.common.annotations.VisibleForTesting;
586fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blank
593dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadlerimport java.net.URISyntaxException;
608b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadlerimport java.util.concurrent.Callable;
618b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadlerimport java.util.concurrent.ExecutionException;
628b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadlerimport java.util.concurrent.FutureTask;
6396c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project
6496c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project/**
65fd14496c494a0d38c35c3788c9cc55f1984592e4Andrew Stadler * Prompts the user for the email address and password. Also prompts for "Use this account as
66fd14496c494a0d38c35c3788c9cc55f1984592e4Andrew Stadler * default" if this is the 2nd+ account being set up.
67fd14496c494a0d38c35c3788c9cc55f1984592e4Andrew Stadler *
68fd14496c494a0d38c35c3788c9cc55f1984592e4Andrew Stadler * If the domain is well-known, the account is configured fully and checked immediately
69fd14496c494a0d38c35c3788c9cc55f1984592e4Andrew Stadler * using AccountCheckSettingsFragment.  If this succeeds we proceed directly to AccountSetupOptions.
70fd14496c494a0d38c35c3788c9cc55f1984592e4Andrew Stadler *
71fd14496c494a0d38c35c3788c9cc55f1984592e4Andrew Stadler * If the domain is not known, or the user selects Manual setup, we invoke the
72fd14496c494a0d38c35c3788c9cc55f1984592e4Andrew Stadler * AccountSetupAccountType activity where the user can begin to manually configure the account.
73d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler *
74d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler * === Support for automated testing ==
75d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler * This activity can also be launched directly via ACTION_CREATE_ACCOUNT.  This is intended
76ea4c5642612803753fd221f33bbdf47fd40bc7ddBrett Chabot * only for use by continuous test systems, and is currently only available when
77ea4c5642612803753fd221f33bbdf47fd40bc7ddBrett Chabot * {@link ActivityManager#isRunningInTestHarness()} is set.  To use this mode, you must construct
78ea4c5642612803753fd221f33bbdf47fd40bc7ddBrett Chabot * an intent which contains all necessary information to create the account.  No connection
79ea4c5642612803753fd221f33bbdf47fd40bc7ddBrett Chabot * checking is done, so the account may or may not actually work.  Here is a sample command, for a
80ea4c5642612803753fd221f33bbdf47fd40bc7ddBrett Chabot * gmail account "test_account" with a password of "test_password".
81d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler *
82d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler *      $ adb shell am start -a com.android.email.CREATE_ACCOUNT \
83d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler *          -e EMAIL test_account@gmail.com \
84d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler *          -e USER "Test Account Name" \
85d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler *          -e INCOMING imap+ssl+://test_account:test_password@imap.gmail.com \
86d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler *          -e OUTGOING smtp+ssl+://test_account:test_password@smtp.gmail.com
87d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler *
88d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler * Note: For accounts that require the full email address in the login, encode the @ as %40.
89d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler * Note: Exchange accounts that require device security policies cannot be created automatically.
9096c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project */
91e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blankpublic class AccountSetupBasics extends AccountSetupActivity
923dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        implements OnClickListener, TextWatcher, AccountCheckSettingsFragment.Callbacks {
933dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
943dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private final static boolean ENTER_DEBUG_SCREEN = true;
9596c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project
96d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler    /**
97d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler     * Direct access for forcing account creation
98d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler     * For use by continuous automated test system (e.g. in conjunction with monkey tests)
99d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler     */
100c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo    private static final String ACTION_CREATE_ACCOUNT = "com.android.email.CREATE_ACCOUNT";
101c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo    private static final String EXTRA_FLOW_MODE = "FLOW_MODE";
102c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo    private static final String EXTRA_CREATE_ACCOUNT_EMAIL = "EMAIL";
103c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo    private static final String EXTRA_CREATE_ACCOUNT_USER = "USER";
104c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo    private static final String EXTRA_CREATE_ACCOUNT_INCOMING = "INCOMING";
105c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo    private static final String EXTRA_CREATE_ACCOUNT_OUTGOING = "OUTGOING";
106c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo    private static final Boolean DEBUG_ALLOW_NON_TEST_HARNESS_CREATION = false;
107d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler
108c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo    private static final String STATE_KEY_PROVIDER = "AccountSetupBasics.provider";
1093dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
1103dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    // NOTE: If you change this value, confirm that the new interval exists in arrays.xml
111c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo    private static final int DEFAULT_ACCOUNT_CHECK_INTERVAL = 15;
1123dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
1133dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    // Support for UI
1143dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private TextView mWelcomeView;
1153dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private EditText mEmailView;
1163dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private EditText mPasswordView;
1173dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private CheckBox mDefaultView;
118025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo    private final EmailAddressValidator mEmailValidator = new EmailAddressValidator();
1193dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private Provider mProvider;
1207988164ddfdf2837314fa1763614422bcc90867bAndy Stadler    private Button mManualButton;
1217988164ddfdf2837314fa1763614422bcc90867bAndy Stadler    private Button mNextButton;
1228b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler    private boolean mNextButtonInhibit;
123a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler    private boolean mPaused;
124f020910461908681978a9e0f8f98b748853b0e39Andy Stadler    private boolean mReportAccountAuthenticatorError;
1259dac94975f31013d4b31ffb15eba27f352b2e758Daisuke Miyakawa
1268b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler    // FutureTask to look up the owner
1278b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler    FutureTask<String> mOwnerLookupTask;
1288b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler
129d5059731780b81c91eff85be8830cafad41f3ed1Andy Stadler    public static void actionNewAccount(Activity fromActivity) {
130c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        Intent i = new Intent(fromActivity, AccountSetupBasics.class);
131c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        i.putExtra(EXTRA_FLOW_MODE, SetupData.FLOW_MODE_NORMAL);
132c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        fromActivity.startActivity(i);
13396c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project    }
13496c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project
135bcff14acf25d3a999b7448e317604e694c204f47Andrew Stadler    /**
136e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank     * This generates setup data that can be used to start a self-contained account creation flow
137bcff14acf25d3a999b7448e317604e694c204f47Andrew Stadler     * for exchange accounts.
138bcff14acf25d3a999b7448e317604e694c204f47Andrew Stadler     */
139bcff14acf25d3a999b7448e317604e694c204f47Andrew Stadler    public static Intent actionSetupExchangeIntent(Context context) {
140c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        Intent i = new Intent(context, AccountSetupBasics.class);
141c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        i.putExtra(EXTRA_FLOW_MODE, SetupData.FLOW_MODE_ACCOUNT_MANAGER_EAS);
142c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        return i;
143e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank    }
144e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank
145e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank    /**
146e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank     * This generates setup data that can be used to start a self-contained account creation flow
147e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank     * for pop/imap accounts.
148e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank     */
149e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank    public static Intent actionSetupPopImapIntent(Context context) {
150c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        Intent i = new Intent(context, AccountSetupBasics.class);
151c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        i.putExtra(EXTRA_FLOW_MODE, SetupData.FLOW_MODE_ACCOUNT_MANAGER_POP_IMAP);
152c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        return i;
153bcff14acf25d3a999b7448e317604e694c204f47Andrew Stadler    }
154bcff14acf25d3a999b7448e317604e694c204f47Andrew Stadler
155e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank    public static void actionAccountCreateFinishedAccountFlow(Activity fromActivity) {
156c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        // TODO: handle this case - modifying state on SetupData when instantiating an Intent
157c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        // is not safe, since it's not guaranteed that an Activity will run with the Intent, and
158c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        // information can get lost.
159c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo
160f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank        Intent i= new Intent(fromActivity, AccountSetupBasics.class);
161e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank        // If we're in the "account flow" (from AccountManager), we want to return to the caller
162f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank        // (in the settings app)
163e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank        SetupData.init(SetupData.FLOW_MODE_RETURN_TO_CALLER);
164f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank        i.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
165f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank        fromActivity.startActivity(i);
166f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank    }
167f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank
168e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank    public static void actionAccountCreateFinished(final Activity fromActivity,
169e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank            final long accountId) {
170e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank        Utility.runAsync(new Runnable() {
171e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank           public void run() {
172e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank               Intent i = new Intent(fromActivity, AccountSetupBasics.class);
173e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank               // If we're not in the "account flow" (from AccountManager), we want to show the
174e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank               // message list for the new inbox
175e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank               Account account = Account.restoreAccountWithId(fromActivity, accountId);
176e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank               SetupData.init(SetupData.FLOW_MODE_RETURN_TO_MESSAGE_LIST, account);
177e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank               i.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
178e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank               fromActivity.startActivity(i);
179e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank            }});
180f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank    }
181f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank
18296c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project    @Override
18396c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project    public void onCreate(Bundle savedInstanceState) {
18496c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project        super.onCreate(savedInstanceState);
185cd09545b87979fa6b4337f17b5a001f0ef7b5269Andrew Stadler        ActivityHelper.debugSetWindowFlags(this);
186f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank
187d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler        // Check for forced account creation first, as it comes from an externally-generated
188d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler        // intent and won't have any SetupData prepared.
189d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler        String action = getIntent().getAction();
190d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler        if (ACTION_CREATE_ACCOUNT.equals(action)) {
191d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler            SetupData.init(SetupData.FLOW_MODE_FORCE_CREATE);
192d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler        }
193d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler
194c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        int flowMode = getIntent().getIntExtra(EXTRA_FLOW_MODE, SetupData.FLOW_MODE_UNSPECIFIED);
195c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        if (flowMode != SetupData.FLOW_MODE_UNSPECIFIED) {
196c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo            SetupData.init(flowMode);
197c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        } else {
198c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo            // TODO: get rid of this case. It's not safe to rely on this global static state. It
199c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo            // should be specified in the Intent always.
200c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo            flowMode = SetupData.getFlowMode();
201c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo        }
202c5c44eed77b851e71803b972fb76fd91d5338fefBen Komalo
203e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank        if (flowMode == SetupData.FLOW_MODE_RETURN_TO_CALLER) {
204f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank            // Return to the caller who initiated account creation
205f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank            finish();
206f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank            return;
207e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank        } else if (flowMode == SetupData.FLOW_MODE_RETURN_TO_MESSAGE_LIST) {
208e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank            Account account = SetupData.getAccount();
209e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank            if (account != null && account.mId >= 0) {
210f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank                // Show the message list for the new account
211b98f219cf088fef9288045813c963be070dde9d0Makoto Onuki                Welcome.actionOpenAccountInbox(this, account.mId);
212f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank                finish();
213f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank                return;
214f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank            }
215f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank        }
216f1efd65a5ebac0a2f1e218c0ae6bb8ceb1a19af6Marc Blank
21796c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project        setContentView(R.layout.account_setup_basics);
21817da1767e396b873723d53b2aef93da8aca2c00eMarc Blank
2192fbb3db5d86210d03175ce77ff08c989a96c5864Makoto Onuki        mWelcomeView = (TextView) UiUtilities.getView(this, R.id.instructions);
2202fbb3db5d86210d03175ce77ff08c989a96c5864Makoto Onuki        mEmailView = (EditText) UiUtilities.getView(this, R.id.account_email);
2212fbb3db5d86210d03175ce77ff08c989a96c5864Makoto Onuki        mPasswordView = (EditText) UiUtilities.getView(this, R.id.account_password);
2222fbb3db5d86210d03175ce77ff08c989a96c5864Makoto Onuki        mDefaultView = (CheckBox) UiUtilities.getView(this, R.id.account_default);
2233dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
2243dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        mEmailView.addTextChangedListener(this);
2253dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        mPasswordView.addTextChangedListener(this);
2263dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
2273dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        // If there are one or more accounts already in existence, then display
2283dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        // the "use as default" checkbox (it defaults to hidden).
229bc2eaadde987044027b57d241e635de014bdb8baMakoto Onuki        new DisplayCheckboxTask().executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);
2303dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
2313dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        boolean manualButtonDisplayed = true;
232a75bab550423e0cd0b2d58379d8210ce6c7c7aa9Andrew Stadler        boolean alternateStrings = false;
233e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank        if (flowMode == SetupData.FLOW_MODE_ACCOUNT_MANAGER_EAS) {
2348067b54294356f375521ba3d1e7db3df117b65a4Andrew Stadler            // No need for manual button -> next is appropriate
2353dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            manualButtonDisplayed = false;
2368067b54294356f375521ba3d1e7db3df117b65a4Andrew Stadler            // Swap welcome text for EAS-specific text
237a75bab550423e0cd0b2d58379d8210ce6c7c7aa9Andrew Stadler            alternateStrings = VendorPolicyLoader.getInstance(this).useAlternateExchangeStrings();
238e5c3c98e9a85198e0b023fd25529512baeb88cdbMakoto Onuki            setTitle(alternateStrings
239e5c3c98e9a85198e0b023fd25529512baeb88cdbMakoto Onuki                    ? R.string.account_setup_basics_exchange_title_alternate
2403dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                    : R.string.account_setup_basics_exchange_title);
2413dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            mWelcomeView.setText(alternateStrings
2423dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                    ? R.string.accounts_welcome_exchange_alternate
2433dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                    : R.string.accounts_welcome_exchange);
244bcff14acf25d3a999b7448e317604e694c204f47Andrew Stadler        }
245bcff14acf25d3a999b7448e317604e694c204f47Andrew Stadler
2467988164ddfdf2837314fa1763614422bcc90867bAndy Stadler        // Configure buttons
2472fbb3db5d86210d03175ce77ff08c989a96c5864Makoto Onuki        mManualButton = (Button) UiUtilities.getView(this, R.id.manual_setup);
2482fbb3db5d86210d03175ce77ff08c989a96c5864Makoto Onuki        mNextButton = (Button) UiUtilities.getView(this, R.id.next);
2493dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        mManualButton.setVisibility(manualButtonDisplayed ? View.VISIBLE : View.INVISIBLE);
2507988164ddfdf2837314fa1763614422bcc90867bAndy Stadler        mManualButton.setOnClickListener(this);
2517988164ddfdf2837314fa1763614422bcc90867bAndy Stadler        mNextButton.setOnClickListener(this);
2523dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        // Force disabled until validator notifies otherwise
2533dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        onEnableProceedButtons(false);
2548b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        // Lightweight debounce while Async tasks underway
2558b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        mNextButtonInhibit = false;
2567988164ddfdf2837314fa1763614422bcc90867bAndy Stadler
257f020910461908681978a9e0f8f98b748853b0e39Andy Stadler        // Set aside incoming AccountAuthenticatorResponse, if there was any
258f020910461908681978a9e0f8f98b748853b0e39Andy Stadler        AccountAuthenticatorResponse authenticatorResponse =
2599dac94975f31013d4b31ffb15eba27f352b2e758Daisuke Miyakawa            getIntent().getParcelableExtra(AccountManager.KEY_ACCOUNT_AUTHENTICATOR_RESPONSE);
260f020910461908681978a9e0f8f98b748853b0e39Andy Stadler        SetupData.setAccountAuthenticatorResponse(authenticatorResponse);
261f020910461908681978a9e0f8f98b748853b0e39Andy Stadler        if (authenticatorResponse != null) {
262f020910461908681978a9e0f8f98b748853b0e39Andy Stadler            // When this Activity is called as part of account authentification flow,
263f020910461908681978a9e0f8f98b748853b0e39Andy Stadler            // we are responsible for eventually reporting the result (success or failure) to
264f020910461908681978a9e0f8f98b748853b0e39Andy Stadler            // the account manager.  Most exit paths represent an failed or abandoned setup,
265f020910461908681978a9e0f8f98b748853b0e39Andy Stadler            // so the default is to report the error.  Success will be reported by the code in
266f020910461908681978a9e0f8f98b748853b0e39Andy Stadler            // AccountSetupOptions that commits the finally created account.
267f020910461908681978a9e0f8f98b748853b0e39Andy Stadler            mReportAccountAuthenticatorError = true;
2689dac94975f31013d4b31ffb15eba27f352b2e758Daisuke Miyakawa        }
269d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler
2703dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        // Load fields, but only once
2713dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        String userName = SetupData.getUsername();
2723dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        if (userName != null) {
2733dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            mEmailView.setText(userName);
2743dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            SetupData.setUsername(null);
2753dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
2763dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        String password = SetupData.getPassword();
2773dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        if (userName != null) {
2783dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            mPasswordView.setText(password);
2793dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            SetupData.setPassword(null);
2803dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
2813dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
282d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler        // Handle force account creation immediately (now that fragment is set up)
283d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler        // This is never allowed in a normal user build and will exit immediately.
284d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler        if (SetupData.getFlowMode() == SetupData.FLOW_MODE_FORCE_CREATE) {
285ea4c5642612803753fd221f33bbdf47fd40bc7ddBrett Chabot            if (!DEBUG_ALLOW_NON_TEST_HARNESS_CREATION &&
286ea4c5642612803753fd221f33bbdf47fd40bc7ddBrett Chabot                    !ActivityManager.isRunningInTestHarness()) {
28731d9acbf0623872f9d4a2b3210b5970854b654c7Marc Blank                Log.e(Logging.LOG_TAG,
288ea4c5642612803753fd221f33bbdf47fd40bc7ddBrett Chabot                        "ERROR: Force account create only allowed while in test harness");
289d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler                finish();
290d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler                return;
291d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler            }
292d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler            Intent intent = getIntent();
293d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler            String email = intent.getStringExtra(EXTRA_CREATE_ACCOUNT_EMAIL);
294d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler            String user = intent.getStringExtra(EXTRA_CREATE_ACCOUNT_USER);
295d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler            String incoming = intent.getStringExtra(EXTRA_CREATE_ACCOUNT_INCOMING);
296d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler            String outgoing = intent.getStringExtra(EXTRA_CREATE_ACCOUNT_OUTGOING);
297d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler            if (TextUtils.isEmpty(email) || TextUtils.isEmpty(user) ||
298d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler                    TextUtils.isEmpty(incoming) || TextUtils.isEmpty(outgoing)) {
29931d9acbf0623872f9d4a2b3210b5970854b654c7Marc Blank                Log.e(Logging.LOG_TAG, "ERROR: Force account create requires extras EMAIL, USER, " +
300d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler                        "INCOMING, OUTGOING");
301d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler                finish();
302d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler                return;
303d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler            }
3043dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            forceCreateAccount(email, user, incoming, outgoing);
305d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler            onCheckSettingsComplete(AccountCheckSettingsFragment.CHECK_SETTINGS_OK); // calls finish
306d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler            return;
307d685b469c73c3479c09301da2e65cd7c11fd4aceAndy Stadler        }
3083dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
3093dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        if (savedInstanceState != null && savedInstanceState.containsKey(STATE_KEY_PROVIDER)) {
3103dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            mProvider = (Provider) savedInstanceState.getSerializable(STATE_KEY_PROVIDER);
3113dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
3128b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler
3138b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        // Launch a worker to look up the owner name.  It should be ready well in advance of
3148b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        // the time the user clicks next or manual.
3158b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        mOwnerLookupTask = new FutureTask<String>(mOwnerLookupCallable);
3168b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        Utility.runAsync(mOwnerLookupTask);
31796c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project    }
31896c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project
31943f2321d10a9ec3efd649cd257aee8d88ea87e08Daisuke Miyakawa    @Override
320a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler    public void onPause() {
321a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler        super.onPause();
322a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler        mPaused = true;
323a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler    }
324a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler
325a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler    @Override
326a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler    public void onResume() {
327a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler        super.onResume();
328a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler        mPaused = false;
329a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler    }
330a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler
331a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler    @Override
33243f2321d10a9ec3efd649cd257aee8d88ea87e08Daisuke Miyakawa    public void finish() {
333f020910461908681978a9e0f8f98b748853b0e39Andy Stadler        // If the account manager initiated the creation, and success was not reported,
334f020910461908681978a9e0f8f98b748853b0e39Andy Stadler        // then we assume that we're giving up (for any reason) - report failure.
335f020910461908681978a9e0f8f98b748853b0e39Andy Stadler        if (mReportAccountAuthenticatorError) {
336f020910461908681978a9e0f8f98b748853b0e39Andy Stadler            AccountAuthenticatorResponse authenticatorResponse =
337f020910461908681978a9e0f8f98b748853b0e39Andy Stadler                    SetupData.getAccountAuthenticatorResponse();
338f020910461908681978a9e0f8f98b748853b0e39Andy Stadler            if (authenticatorResponse != null) {
339f020910461908681978a9e0f8f98b748853b0e39Andy Stadler                authenticatorResponse.onError(AccountManager.ERROR_CODE_CANCELED, "canceled");
340f020910461908681978a9e0f8f98b748853b0e39Andy Stadler                SetupData.setAccountAuthenticatorResponse(null);
34143f2321d10a9ec3efd649cd257aee8d88ea87e08Daisuke Miyakawa            }
34243f2321d10a9ec3efd649cd257aee8d88ea87e08Daisuke Miyakawa        }
34343f2321d10a9ec3efd649cd257aee8d88ea87e08Daisuke Miyakawa        super.finish();
34443f2321d10a9ec3efd649cd257aee8d88ea87e08Daisuke Miyakawa    }
34543f2321d10a9ec3efd649cd257aee8d88ea87e08Daisuke Miyakawa
34696c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project    @Override
3473dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    public void onSaveInstanceState(Bundle outState) {
3483dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        super.onSaveInstanceState(outState);
3493dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        if (mProvider != null) {
3503dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            outState.putSerializable(STATE_KEY_PROVIDER, mProvider);
3512731aef45c6f2f9792ae698ebf7d65ca6338a02cAndrew Stadler        }
3522731aef45c6f2f9792ae698ebf7d65ca6338a02cAndrew Stadler    }
3532731aef45c6f2f9792ae698ebf7d65ca6338a02cAndrew Stadler
3542731aef45c6f2f9792ae698ebf7d65ca6338a02cAndrew Stadler    /**
3557988164ddfdf2837314fa1763614422bcc90867bAndy Stadler     * Implements OnClickListener
3568bcb572ccfdac6974c111fe6dfc753a5e0d4e7caAndrew Stadler     */
3578bcb572ccfdac6974c111fe6dfc753a5e0d4e7caAndrew Stadler    @Override
3587988164ddfdf2837314fa1763614422bcc90867bAndy Stadler    public void onClick(View v) {
3597988164ddfdf2837314fa1763614422bcc90867bAndy Stadler        switch (v.getId()) {
360a75bab550423e0cd0b2d58379d8210ce6c7c7aa9Andrew Stadler            case R.id.next:
3618b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                // Simple debounce - just ignore while async checks are underway
3628b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                if (mNextButtonInhibit) {
3638b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                    return;
3648b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                }
3653dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                onNext();
3667988164ddfdf2837314fa1763614422bcc90867bAndy Stadler                break;
367a75bab550423e0cd0b2d58379d8210ce6c7c7aa9Andrew Stadler            case R.id.manual_setup:
3683dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                onManualSetup(false);
3697988164ddfdf2837314fa1763614422bcc90867bAndy Stadler                break;
370a75bab550423e0cd0b2d58379d8210ce6c7c7aa9Andrew Stadler        }
37196c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project    }
37296c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project
373a75bab550423e0cd0b2d58379d8210ce6c7c7aa9Andrew Stadler    /**
3743dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * Implements TextWatcher
375a75bab550423e0cd0b2d58379d8210ce6c7c7aa9Andrew Stadler     */
3763dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    public void afterTextChanged(Editable s) {
3773dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        validateFields();
3783dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    }
3798bcb572ccfdac6974c111fe6dfc753a5e0d4e7caAndrew Stadler
3803dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    /**
3813dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * Implements TextWatcher
3823dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     */
3833dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    public void beforeTextChanged(CharSequence s, int start, int count, int after) {
3843dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    }
3853dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
3863dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    /**
3873dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * Implements TextWatcher
3883dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     */
3893dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    public void onTextChanged(CharSequence s, int start, int before, int count) {
3903dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    }
3913dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
3923dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private void validateFields() {
3933dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        boolean valid = Utility.isTextViewNotEmpty(mEmailView)
3943dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                && Utility.isTextViewNotEmpty(mPasswordView)
3953dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                && mEmailValidator.isValid(mEmailView.getText().toString().trim());
3963dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        onEnableProceedButtons(valid);
397858c2822777f74947e81476125590ad06bfe4803Andy Stadler
398858c2822777f74947e81476125590ad06bfe4803Andy Stadler        // Warn (but don't prevent) if password has leading/trailing spaces
399858c2822777f74947e81476125590ad06bfe4803Andy Stadler        AccountSettingsUtils.checkPasswordSpaces(this, mPasswordView);
4003dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    }
4013dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
4023dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    /**
4038b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler     * Return an existing username if found, or null.  This is the result of the Callable (below).
4043dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     */
4053dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private String getOwnerName() {
4068b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        String result = null;
4078b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        try {
4088b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            result = mOwnerLookupTask.get();
4098b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        } catch (InterruptedException e) {
4108b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        } catch (ExecutionException e) {
4118bcb572ccfdac6974c111fe6dfc753a5e0d4e7caAndrew Stadler        }
4128b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        return result;
41396c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project    }
41496c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project
415da8836a76cd8a6eaa7e3693eeacc6393870b2066Andrew Stadler    /**
4168b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler     * Callable that returns the username (based on other accounts) or null.
4178b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler     */
418025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo    private final Callable<String> mOwnerLookupCallable = new Callable<String>() {
4198b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        public String call() {
4208b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            Context context = AccountSetupBasics.this;
4218b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            String name = null;
4228b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            long defaultId = Account.getDefaultAccountId(context);
4238b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            if (defaultId != -1) {
4248b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                Account account = Account.restoreAccountWithId(context, defaultId);
4258b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                if (account != null) {
4268b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                    name = account.getSenderName();
4278b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                }
4288b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            }
4298b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            return name;
4308b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        }
4318b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler    };
4328b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler
4338b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler    /**
4343dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * Finish the auto setup process, in some cases after showing a warning dialog.
435da8836a76cd8a6eaa7e3693eeacc6393870b2066Andrew Stadler     */
4363dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private void finishAutoSetup() {
4373dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        String email = mEmailView.getText().toString().trim();
438858c2822777f74947e81476125590ad06bfe4803Andy Stadler        String password = mPasswordView.getText().toString();
439040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy
4403dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        try {
44108534762bdded437a7fa0e5e422d311c414e0621Todd Kennedy            mProvider.expandTemplates(email);
4423dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
443040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy            Account account = SetupData.getAccount();
444040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy            HostAuth recvAuth = account.getOrCreateHostAuthRecv(this);
445313586c8eb4e23ceec068b82f3dc0be1c8a7045fBen Komalo            HostAuth.setHostAuthFromString(recvAuth, mProvider.incomingUri);
44608534762bdded437a7fa0e5e422d311c414e0621Todd Kennedy            recvAuth.setLogin(mProvider.incomingUsername, password);
4473dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
448040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy            HostAuth sendAuth = account.getOrCreateHostAuthSend(this);
449313586c8eb4e23ceec068b82f3dc0be1c8a7045fBen Komalo            HostAuth.setHostAuthFromString(sendAuth, mProvider.outgoingUri);
45008534762bdded437a7fa0e5e422d311c414e0621Todd Kennedy            sendAuth.setLogin(mProvider.outgoingUsername, password);
451040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy
452040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy            // Populate the setup data, assuming that the duplicate account check will succeed
453040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy            populateSetupData(getOwnerName(), email, mDefaultView.isChecked());
4543dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
455040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy            // Stop here if the login credentials duplicate an existing account
456040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy            // Launch an Async task to do the work
457bc2eaadde987044027b57d241e635de014bdb8baMakoto Onuki            new DuplicateCheckTask(this, recvAuth.mAddress, mProvider.incomingUsername)
458bc2eaadde987044027b57d241e635de014bdb8baMakoto Onuki                    .executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);
459040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        } catch (URISyntaxException e) {
4603dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            /*
461040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy             * If there is some problem with the URI we give up and go on to manual setup.
462040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy             * Technically speaking, AutoDiscover is OK here, since the user clicked "Next"
463040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy             * to get here. This will not happen in practice because we don't expect to
464040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy             * find any EAS accounts in the providers list.
4653dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler             */
4663dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            onManualSetup(true);
4673dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
46896c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project    }
46996c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project
470bcff14acf25d3a999b7448e317604e694c204f47Andrew Stadler    /**
4718b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler     * Async task that continues the work of finishAutoSetup().  Checks for a duplicate
4728b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler     * account and then either alerts the user, or continues.
4738b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler     */
4748b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler    private class DuplicateCheckTask extends AsyncTask<Void, Void, Account> {
4758b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        private final Context mContext;
4768b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        private final String mCheckHost;
4778b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        private final String mCheckLogin;
4788b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler
4798b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        public DuplicateCheckTask(Context context, String checkHost, String checkLogin) {
4808b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            mContext = context;
4818b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            mCheckHost = checkHost;
4828b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            mCheckLogin = checkLogin;
4838b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            // Prevent additional clicks on the next button during Async lookup
4848b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            mNextButtonInhibit = true;
4858b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        }
4868b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler
4878b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        @Override
4888b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        protected Account doInBackground(Void... params) {
489f5418f1f93b02e7fab9f15eb201800b65510998eMarc Blank            Account account = Utility.findExistingAccount(mContext, -1,
4908b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                    mCheckHost, mCheckLogin);
4918b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            return account;
4928b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        }
4938b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler
4948b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        @Override
4958b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        protected void onPostExecute(Account duplicateAccount) {
4968b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            mNextButtonInhibit = false;
497a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler            // Exit immediately if the user left before we finished
498a97faa25ac3265209b50d4534b4c2b41cd211e5cAndy Stadler            if (mPaused) return;
4998b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            // Show duplicate account warning, or proceed
5008b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            if (duplicateAccount != null) {
5018b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                DuplicateAccountDialogFragment dialogFragment =
5028b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                    DuplicateAccountDialogFragment.newInstance(duplicateAccount.mDisplayName);
5038b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                dialogFragment.show(getFragmentManager(), DuplicateAccountDialogFragment.TAG);
5048b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                return;
5058b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            } else {
5068b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                AccountCheckSettingsFragment checkerFragment =
5078b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                    AccountCheckSettingsFragment.newInstance(
5088b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                        SetupData.CHECK_INCOMING | SetupData.CHECK_OUTGOING, null);
50931e25767918193217c884db72aaa98e50a4957d3Dianne Hackborn                FragmentTransaction transaction = getFragmentManager().beginTransaction();
5108b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                transaction.add(checkerFragment, AccountCheckSettingsFragment.TAG);
5118b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                transaction.addToBackStack("back");
5128b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler                transaction.commit();
5138b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler            }
5148b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler        }
5158b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler    }
5168b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler
5178b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler
5188b5cd2beff18ff525c429f10acfdd78bc1e011bbAndy Stadler    /**
5193dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * When "next" button is clicked
520bcff14acf25d3a999b7448e317604e694c204f47Andrew Stadler     */
5213dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private void onNext() {
5223dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        // Try auto-configuration from XML providers (unless in EAS mode, we can skip it)
5233dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        if (SetupData.getFlowMode() != SetupData.FLOW_MODE_ACCOUNT_MANAGER_EAS) {
5243dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            String email = mEmailView.getText().toString().trim();
5253dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            String[] emailParts = email.split("@");
5263dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            String domain = emailParts[1].trim();
5273dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            mProvider = AccountSettingsUtils.findProviderForDomain(this, domain);
5283dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            if (mProvider != null) {
5293dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                if (mProvider.note != null) {
5303dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                    NoteDialogFragment dialogFragment =
5313dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                            NoteDialogFragment.newInstance(mProvider.note);
5323dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                    dialogFragment.show(getFragmentManager(), NoteDialogFragment.TAG);
5333dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                } else {
5343dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                    finishAutoSetup();
5353dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                }
5363dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                return;
5373dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            }
5383dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
5393dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        // Can't use auto setup (although EAS accounts may still be able to AutoDiscover)
5403dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        onManualSetup(true);
54196c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project    }
54296c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project
54363ab9de1b881bf1496228285511cab213501f404Andrew Stadler    /**
5443dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * When "manual setup" button is clicked
5453dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     *
5463dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * @param allowAutoDiscover - true if the user clicked 'next' and (if the account is EAS)
5473dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * it's OK to use autodiscover.  false to prevent autodiscover and go straight to manual setup.
5483dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * Ignored for IMAP & POP accounts.
54963ab9de1b881bf1496228285511cab213501f404Andrew Stadler     */
5503dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private void onManualSetup(boolean allowAutoDiscover) {
5513dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        String email = mEmailView.getText().toString().trim();
5523dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        String password = mPasswordView.getText().toString();
5533dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        String[] emailParts = email.split("@");
5543dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        String user = emailParts[0].trim();
5553dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        String domain = emailParts[1].trim();
5563dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
5573dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        // Alternate entry to the debug options screen (for devices without a physical keyboard:
5583dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        //  Username: d@d.d
5593dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        //  Password: debug
5603dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        if (ENTER_DEBUG_SCREEN && "d@d.d".equals(email) && "debug".equals(password)) {
5613dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            mEmailView.setText("");
5623dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            mPasswordView.setText("");
5632866284a6d4ee4b368fcaf412c540b21d457e065Ben Komalo            AccountSettings.actionSettingsWithDebug(this);
5643dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            return;
5653dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
5663dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
567040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        Account account = SetupData.getAccount();
568040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        HostAuth recvAuth = account.getOrCreateHostAuthRecv(this);
569040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        recvAuth.setLogin(user, password);
570040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        recvAuth.setConnection("placeholder", domain, HostAuth.PORT_UNKNOWN, HostAuth.FLAG_NONE);
571040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy
572040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        HostAuth sendAuth = account.getOrCreateHostAuthSend(this);
573040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        sendAuth.setLogin(user, password);
574040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        sendAuth.setConnection("placeholder", domain, HostAuth.PORT_UNKNOWN, HostAuth.FLAG_NONE);
5753dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
576040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        populateSetupData(getOwnerName(), email, mDefaultView.isChecked());
5773dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
5782731aef45c6f2f9792ae698ebf7d65ca6338a02cAndrew Stadler        SetupData.setAllowAutodiscover(allowAutoDiscover);
579e6cc662abc0b5fffe223cda5e980b4f05a4e91ddMarc Blank        AccountSetupAccountType.actionSelectAccountType(this);
58096c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project    }
5813dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
5823dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    /**
5833dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * To support continuous testing, we allow the forced creation of accounts.
5843dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * This works in a manner fairly similar to automatic setup, in which the complete server
5853dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * Uri's are available, except that we will also skip checking (as if both checks were true)
5863dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * and all other UI.
5873dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     *
5883dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * @param email The email address for the new account
5893dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * @param user The user name for the new account
5903dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * @param incoming The URI-style string defining the incoming account
5913dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * @param outgoing The URI-style string defining the outgoing account
5923dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     */
5933dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private void forceCreateAccount(String email, String user, String incoming, String outgoing) {
594040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        Account account = SetupData.getAccount();
595040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        try {
596040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy            HostAuth recvAuth = account.getOrCreateHostAuthRecv(this);
597313586c8eb4e23ceec068b82f3dc0be1c8a7045fBen Komalo            HostAuth.setHostAuthFromString(recvAuth, incoming);
598040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy
599040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy            HostAuth sendAuth = account.getOrCreateHostAuthSend(this);
600313586c8eb4e23ceec068b82f3dc0be1c8a7045fBen Komalo            HostAuth.setHostAuthFromString(sendAuth, outgoing);
601040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy
602040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy            populateSetupData(user, email, false);
603040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        } catch (URISyntaxException e) {
604040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy            // If we can't set up the URL, don't continue - account setup pages will fail too
605040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy            Toast.makeText(
606040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy                    this, R.string.account_setup_username_password_toast, Toast.LENGTH_LONG).show();
607040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        }
6083dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    }
6093dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
6103dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    /**
6113dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * Populate SetupData's account with complete setup info.
6123dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     */
613040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy    private void populateSetupData(String senderName, String senderEmail, boolean isDefault) {
6143dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        Account account = SetupData.getAccount();
6153dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        account.setSenderName(senderName);
6163dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        account.setEmailAddress(senderEmail);
6173dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        account.setDisplayName(senderEmail);
6183dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        account.setDefaultAccount(isDefault);
6193dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        SetupData.setDefault(isDefault);        // TODO - why duplicated, if already set in account
6203dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
621040ddf60cfef4aaecf4bfe1f897fce3248d777a4Todd Kennedy        String protocol = account.mHostAuthRecv.mProtocol;
622025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo        setFlagsForProtocol(account, protocol);
623025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo    }
624025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo
625025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo    /**
626025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo     * Sets the account sync, delete, and other misc flags not captured in {@code HostAuth}
627025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo     * information for the specified account based on the protocol type.
628025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo     */
629025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo    @VisibleForTesting
630025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo    static void setFlagsForProtocol(Account account, String protocol) {
6316fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blank        if (HostAuth.SCHEME_IMAP.equals(protocol)) {
6323dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            // Delete policy must be set explicitly, because IMAP does not provide a UI selection
633025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo            // for it.
634f5418f1f93b02e7fab9f15eb201800b65510998eMarc Blank            account.setDeletePolicy(Account.DELETE_POLICY_ON_DELETE);
635025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo            account.mFlags |= Account.FLAGS_SUPPORTS_SEARCH;
6363dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
6373dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
6386fea021e3dbe71aaa93512aba699d1bfda3d520dMarc Blank        if (HostAuth.SCHEME_EAS.equals(protocol)) {
639025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo            account.setDeletePolicy(Account.DELETE_POLICY_ON_DELETE);
6403dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            account.setSyncInterval(Account.CHECK_INTERVAL_PUSH);
641025d29fd4b9dd8351fe2e0428a585cf327ddaca4Ben Komalo            account.setSyncLookback(SyncWindow.SYNC_WINDOW_AUTO);
6423dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        } else {
6433dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            account.setSyncInterval(DEFAULT_ACCOUNT_CHECK_INTERVAL);
6443dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
6453dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    }
6463dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
6473dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    /**
6483dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * Implements AccountCheckSettingsFragment.Callbacks
6493dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     *
6503dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * This is used in automatic setup mode to jump directly down to the options screen.
651f020910461908681978a9e0f8f98b748853b0e39Andy Stadler     *
652f020910461908681978a9e0f8f98b748853b0e39Andy Stadler     * This is the only case where we finish() this activity but account setup is continuing,
653f020910461908681978a9e0f8f98b748853b0e39Andy Stadler     * so we inhibit reporting any error back to the Account manager.
6543dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     */
6553dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    @Override
6563dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    public void onCheckSettingsComplete(int result) {
6573dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        if (result == AccountCheckSettingsFragment.CHECK_SETTINGS_OK) {
6583dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            AccountSetupOptions.actionOptions(this);
659f020910461908681978a9e0f8f98b748853b0e39Andy Stadler            mReportAccountAuthenticatorError = false;
6603dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            finish();
6613dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
6623dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    }
6633dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
6643dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    /**
6653dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * Implements AccountCheckSettingsFragment.Callbacks
6663dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * This is overridden only by AccountSetupExchange
6673dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     */
6683dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    @Override
6693dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    public void onAutoDiscoverComplete(int result, HostAuth hostAuth) {
6703dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        throw new IllegalStateException();
6713dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    }
6723dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
6733dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    /**
6743dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * AsyncTask checks count of accounts and displays "use this account as default" checkbox
6753dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * if there are more than one.
6763dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     */
6773dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private class DisplayCheckboxTask extends AsyncTask<Void, Void, Integer> {
6783dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
6793dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        @Override
6803dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        protected Integer doInBackground(Void... params) {
681f5418f1f93b02e7fab9f15eb201800b65510998eMarc Blank            return EmailContent.count(AccountSetupBasics.this, Account.CONTENT_URI);
6823dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
6833dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
6843dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        @Override
6853dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        protected void onPostExecute(Integer numAccounts) {
6863dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            if (numAccounts > 0) {
6872fbb3db5d86210d03175ce77ff08c989a96c5864Makoto Onuki                Activity a = AccountSetupBasics.this;
6882fbb3db5d86210d03175ce77ff08c989a96c5864Makoto Onuki                UiUtilities.setVisibilitySafe(mDefaultView, View.VISIBLE);
6892fbb3db5d86210d03175ce77ff08c989a96c5864Makoto Onuki                UiUtilities.setVisibilitySafe(a, R.id.account_default_divider_1, View.VISIBLE);
6902fbb3db5d86210d03175ce77ff08c989a96c5864Makoto Onuki                UiUtilities.setVisibilitySafe(a, R.id.account_default_divider_2, View.VISIBLE);
6913dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            }
6923dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
6933dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    }
6943dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
6953dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    private void onEnableProceedButtons(boolean enabled) {
6963dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        mManualButton.setEnabled(enabled);
6973dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        mNextButton.setEnabled(enabled);
6983dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    }
6993dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
7003dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    /**
7013dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     * Dialog fragment to show "setup note" dialog
7023dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler     */
7033dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    public static class NoteDialogFragment extends DialogFragment {
7043dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        private final static String TAG = "NoteDialogFragment";
7053dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
7063dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        // Argument bundle keys
7073dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        private final static String BUNDLE_KEY_NOTE = "NoteDialogFragment.Note";
7083dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
7093dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        /**
7103dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler         * Create the dialog with parameters
7113dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler         */
7123dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        public static NoteDialogFragment newInstance(String note) {
7133dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            NoteDialogFragment f = new NoteDialogFragment();
7143dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            Bundle b = new Bundle();
7153dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            b.putString(BUNDLE_KEY_NOTE, note);
7163dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            f.setArguments(b);
7173dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            return f;
7183dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
7193dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
7203dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        @Override
7213dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        public Dialog onCreateDialog(Bundle savedInstanceState) {
7223dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            Context context = getActivity();
7233dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            final String note = getArguments().getString(BUNDLE_KEY_NOTE);
7243dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler
7253dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler            return new AlertDialog.Builder(context)
72649518bb3605d6c8e3cc4801c452e4f8f63220f44Makoto Onuki                .setIconAttribute(android.R.attr.alertDialogIcon)
7273dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                .setTitle(android.R.string.dialog_alert_title)
7283dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                .setMessage(note)
7293dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                .setPositiveButton(
7303dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                        R.string.okay_action,
7313dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                        new DialogInterface.OnClickListener() {
7323dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                            public void onClick(DialogInterface dialog, int which) {
7333dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                                Activity a = getActivity();
7343dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                                if (a instanceof AccountSetupBasics) {
7353dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                                    ((AccountSetupBasics)a).finishAutoSetup();
7363dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                                }
7373dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                                dismiss();
7383dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                            }
7393dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                        })
7403dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                .setNegativeButton(
7413dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                        context.getString(R.string.cancel_action),
7423dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                        null)
7433dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler                .create();
7443dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler        }
7453dedc8b19172066e45a146f1e5065d7cdc00236aAndy Stadler    }
74696c5af40d639d629267794f4f0338a267ff94ce5The Android Open Source Project}
747