AbstractSyncService.java revision e714bb9d153cfe13a7f0932e7d67ea08fa5a1d98
1c5afb16430a145f20d7c887e45f47b38687054daMarc Blank/* 2c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Copyright (C) 2008-2009 Marc Blank 3c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Licensed to The Android Open Source Project. 4c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * 5c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Licensed under the Apache License, Version 2.0 (the "License"); 6c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * you may not use this file except in compliance with the License. 7c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * You may obtain a copy of the License at 8c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * 9c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * http://www.apache.org/licenses/LICENSE-2.0 10c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * 11c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Unless required by applicable law or agreed to in writing, software 12c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * distributed under the License is distributed on an "AS IS" BASIS, 13c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * See the License for the specific language governing permissions and 15c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * limitations under the License. 16c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 17c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 18c5afb16430a145f20d7c887e45f47b38687054daMarc Blankpackage com.android.emailsync; 19c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 20c5afb16430a145f20d7c887e45f47b38687054daMarc Blankimport android.content.Context; 21c5afb16430a145f20d7c887e45f47b38687054daMarc Blankimport android.net.ConnectivityManager; 22c5afb16430a145f20d7c887e45f47b38687054daMarc Blankimport android.net.NetworkInfo; 23c5afb16430a145f20d7c887e45f47b38687054daMarc Blankimport android.os.Bundle; 24c5afb16430a145f20d7c887e45f47b38687054daMarc Blankimport android.util.Log; 25c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 26e714bb9d153cfe13a7f0932e7d67ea08fa5a1d98Marc Blankimport com.android.emailcommon.provider.Account; 27e714bb9d153cfe13a7f0932e7d67ea08fa5a1d98Marc Blankimport com.android.emailcommon.provider.HostAuth; 28e714bb9d153cfe13a7f0932e7d67ea08fa5a1d98Marc Blankimport com.android.emailcommon.provider.Mailbox; 29e714bb9d153cfe13a7f0932e7d67ea08fa5a1d98Marc Blank 30c5afb16430a145f20d7c887e45f47b38687054daMarc Blankimport java.util.concurrent.LinkedBlockingQueue; 31c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 32c5afb16430a145f20d7c887e45f47b38687054daMarc Blank/** 33c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Base class for all protocol services SyncManager (extends Service, implements 34c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Runnable) instantiates subclasses to run a sync (either timed, or push, or 35c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * mail placed in outbox, etc.) EasSyncService is currently implemented; my goal 36c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * would be to move IMAP to this structure when it comes time to introduce push 37c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * functionality. 38c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 39c5afb16430a145f20d7c887e45f47b38687054daMarc Blankpublic abstract class AbstractSyncService implements Runnable { 40c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 41c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public String TAG = "AbstractSyncService"; 42c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 43c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static final int SECONDS = 1000; 44c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static final int MINUTES = 60*SECONDS; 45c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static final int HOURS = 60*MINUTES; 46c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static final int DAYS = 24*HOURS; 47c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 48c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static final int CONNECT_TIMEOUT = 30*SECONDS; 49c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static final int NETWORK_WAIT = 15*SECONDS; 50c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 51c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static final int EXIT_DONE = 0; 52c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static final int EXIT_IO_ERROR = 1; 53c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static final int EXIT_LOGIN_FAILURE = 2; 54c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static final int EXIT_EXCEPTION = 3; 55c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static final int EXIT_SECURITY_FAILURE = 4; 56c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static final int EXIT_ACCESS_DENIED = 5; 57c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 58c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public Mailbox mMailbox; 59c5afb16430a145f20d7c887e45f47b38687054daMarc Blank protected long mMailboxId; 60c5afb16430a145f20d7c887e45f47b38687054daMarc Blank protected int mExitStatus = EXIT_EXCEPTION; 61dba0b20d955d88831ce94d96dbdadc49dba4761aMarc Blank protected String mExitReason; 62c5afb16430a145f20d7c887e45f47b38687054daMarc Blank protected String mMailboxName; 63c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public Account mAccount; 64c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public Context mContext; 65c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public int mChangeCount = 0; 66c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public volatile int mSyncReason = 0; 67c5afb16430a145f20d7c887e45f47b38687054daMarc Blank protected volatile boolean mStop = false; 68c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public volatile Thread mThread; 69c5afb16430a145f20d7c887e45f47b38687054daMarc Blank protected final Object mSynchronizer = new Object(); 70c5afb16430a145f20d7c887e45f47b38687054daMarc Blank // Whether or not the sync service is valid (usable) 71c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public boolean mIsValid = true; 72c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 73c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public boolean mUserLog = true; // STOPSHIP 74c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public boolean mFileLog = false; 75c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 76c5afb16430a145f20d7c887e45f47b38687054daMarc Blank protected volatile long mRequestTime = 0; 77c5afb16430a145f20d7c887e45f47b38687054daMarc Blank protected LinkedBlockingQueue<Request> mRequestQueue = new LinkedBlockingQueue<Request>(); 78c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 79c5afb16430a145f20d7c887e45f47b38687054daMarc Blank /** 80c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Sent by SyncManager to request that the service stop itself cleanly 81c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 82c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public abstract void stop(); 83c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 84c5afb16430a145f20d7c887e45f47b38687054daMarc Blank /** 85c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Sent by SyncManager to indicate that an alarm has fired for this service, and that its 86c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * pending (network) operation has timed out. The service is NOT automatically stopped, 87c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * although the behavior is service dependent. 88c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * 89c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * @return true if the operation was stopped normally; false if the thread needed to be 90c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * interrupted. 91c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 92c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public abstract boolean alarm(); 93c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 94c5afb16430a145f20d7c887e45f47b38687054daMarc Blank /** 95c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Sent by SyncManager to request that the service reset itself cleanly; the meaning of this 96c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * operation is service dependent. 97c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 98c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public abstract void reset(); 99c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 100c5afb16430a145f20d7c887e45f47b38687054daMarc Blank /** 101c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Called to validate an account; abstract to allow each protocol to do what 102c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * is necessary. For consistency with the Email app's original 103c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * functionality, success is indicated by a failure to throw an Exception 104c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * (ugh). Parameters are self-explanatory 105c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * 106c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * @param hostAuth 107c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * @return a Bundle containing a result code and, depending on the result, a PolicySet or an 108c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * error message 109c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 110c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public abstract Bundle validateAccount(HostAuth hostAuth, Context context); 111c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 112c5afb16430a145f20d7c887e45f47b38687054daMarc Blank /** 113c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Called to clear the syncKey for the calendar associated with this service; this is necessary 114c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * because changes to calendar sync state cause a reset of data. 115c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 116c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public abstract void resetCalendarSyncKey(); 117c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 118c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public AbstractSyncService(Context _context, Mailbox _mailbox) { 119c5afb16430a145f20d7c887e45f47b38687054daMarc Blank mContext = _context; 120c5afb16430a145f20d7c887e45f47b38687054daMarc Blank mMailbox = _mailbox; 121c5afb16430a145f20d7c887e45f47b38687054daMarc Blank mMailboxId = _mailbox.mId; 122c5afb16430a145f20d7c887e45f47b38687054daMarc Blank mMailboxName = _mailbox.mServerId; 123c5afb16430a145f20d7c887e45f47b38687054daMarc Blank mAccount = Account.restoreAccountWithId(_context, _mailbox.mAccountKey); 124c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 125c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 126c5afb16430a145f20d7c887e45f47b38687054daMarc Blank // Will be required when subclasses are instantiated by name 127c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public AbstractSyncService(String prefix) { 128c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 129c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 130c5afb16430a145f20d7c887e45f47b38687054daMarc Blank /** 131c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * The UI can call this static method to perform account validation. This method wraps each 132c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * protocol's validateAccount method. Arguments are self-explanatory, except where noted. 133c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * 134c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * @param klass the protocol class (EasSyncService.class for example) 135c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * @param hostAuth 136c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * @param context 137c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * @return a Bundle containing a result code and, depending on the result, a PolicySet or an 138c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * error message 139c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 140c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static Bundle validate(Class<? extends AbstractSyncService> klass, 141c5afb16430a145f20d7c887e45f47b38687054daMarc Blank HostAuth hostAuth, Context context) { 142c5afb16430a145f20d7c887e45f47b38687054daMarc Blank AbstractSyncService svc; 143c5afb16430a145f20d7c887e45f47b38687054daMarc Blank try { 144c5afb16430a145f20d7c887e45f47b38687054daMarc Blank svc = klass.newInstance(); 145c5afb16430a145f20d7c887e45f47b38687054daMarc Blank return svc.validateAccount(hostAuth, context); 146c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } catch (IllegalAccessException e) { 147c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } catch (InstantiationException e) { 148c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 149c5afb16430a145f20d7c887e45f47b38687054daMarc Blank return null; 150c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 151c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 152c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public static class ValidationResult { 153c5afb16430a145f20d7c887e45f47b38687054daMarc Blank static final int NO_FAILURE = 0; 154c5afb16430a145f20d7c887e45f47b38687054daMarc Blank static final int CONNECTION_FAILURE = 1; 155c5afb16430a145f20d7c887e45f47b38687054daMarc Blank static final int VALIDATION_FAILURE = 2; 156c5afb16430a145f20d7c887e45f47b38687054daMarc Blank static final int EXCEPTION = 3; 157c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 158c5afb16430a145f20d7c887e45f47b38687054daMarc Blank static final ValidationResult succeeded = new ValidationResult(true, NO_FAILURE, null); 159c5afb16430a145f20d7c887e45f47b38687054daMarc Blank boolean success; 160c5afb16430a145f20d7c887e45f47b38687054daMarc Blank int failure = NO_FAILURE; 161c5afb16430a145f20d7c887e45f47b38687054daMarc Blank String reason = null; 162c5afb16430a145f20d7c887e45f47b38687054daMarc Blank Exception exception = null; 163c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 164c5afb16430a145f20d7c887e45f47b38687054daMarc Blank ValidationResult(boolean _success, int _failure, String _reason) { 165c5afb16430a145f20d7c887e45f47b38687054daMarc Blank success = _success; 166c5afb16430a145f20d7c887e45f47b38687054daMarc Blank failure = _failure; 167c5afb16430a145f20d7c887e45f47b38687054daMarc Blank reason = _reason; 168c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 169c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 170c5afb16430a145f20d7c887e45f47b38687054daMarc Blank ValidationResult(boolean _success) { 171c5afb16430a145f20d7c887e45f47b38687054daMarc Blank success = _success; 172c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 173c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 174c5afb16430a145f20d7c887e45f47b38687054daMarc Blank ValidationResult(Exception e) { 175c5afb16430a145f20d7c887e45f47b38687054daMarc Blank success = false; 176c5afb16430a145f20d7c887e45f47b38687054daMarc Blank failure = EXCEPTION; 177c5afb16430a145f20d7c887e45f47b38687054daMarc Blank exception = e; 178c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 179c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 180c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public boolean isSuccess() { 181c5afb16430a145f20d7c887e45f47b38687054daMarc Blank return success; 182c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 183c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 184c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public String getReason() { 185c5afb16430a145f20d7c887e45f47b38687054daMarc Blank return reason; 186c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 187c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 188c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 189c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public boolean isStopped() { 190c5afb16430a145f20d7c887e45f47b38687054daMarc Blank return mStop; 191c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 192c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 193c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public Object getSynchronizer() { 194c5afb16430a145f20d7c887e45f47b38687054daMarc Blank return mSynchronizer; 195c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 196c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 197c5afb16430a145f20d7c887e45f47b38687054daMarc Blank /** 198c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Convenience methods to do user logging (i.e. connection activity). Saves a bunch of 199c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * repetitive code. 200c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 201c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public void userLog(String string, int code, String string2) { 202c5afb16430a145f20d7c887e45f47b38687054daMarc Blank if (mUserLog) { 203c5afb16430a145f20d7c887e45f47b38687054daMarc Blank userLog(string + code + string2); 204c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 205c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 206c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 207c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public void userLog(String string, int code) { 208c5afb16430a145f20d7c887e45f47b38687054daMarc Blank if (mUserLog) { 209c5afb16430a145f20d7c887e45f47b38687054daMarc Blank userLog(string + code); 210c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 211c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 212c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 213c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public void userLog(String str, Exception e) { 214c5afb16430a145f20d7c887e45f47b38687054daMarc Blank if (mUserLog) { 215c5afb16430a145f20d7c887e45f47b38687054daMarc Blank Log.e(TAG, str, e); 216c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } else { 217c5afb16430a145f20d7c887e45f47b38687054daMarc Blank Log.e(TAG, str + e); 218c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 219c5afb16430a145f20d7c887e45f47b38687054daMarc Blank if (mFileLog) { 220c5afb16430a145f20d7c887e45f47b38687054daMarc Blank FileLogger.log(e); 221c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 222c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 223c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 224c5afb16430a145f20d7c887e45f47b38687054daMarc Blank /** 225c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Standard logging for EAS. 226c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * If user logging is active, we concatenate any arguments and log them using Log.d 227c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * We also check for file logging, and log appropriately 228c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * @param strings strings to concatenate and log 229c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 230c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public void userLog(String ...strings) { 231c5afb16430a145f20d7c887e45f47b38687054daMarc Blank if (mUserLog) { 232c5afb16430a145f20d7c887e45f47b38687054daMarc Blank String logText; 233c5afb16430a145f20d7c887e45f47b38687054daMarc Blank if (strings.length == 1) { 234c5afb16430a145f20d7c887e45f47b38687054daMarc Blank logText = strings[0]; 235c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } else { 236c5afb16430a145f20d7c887e45f47b38687054daMarc Blank StringBuilder sb = new StringBuilder(64); 237c5afb16430a145f20d7c887e45f47b38687054daMarc Blank for (String string: strings) { 238c5afb16430a145f20d7c887e45f47b38687054daMarc Blank sb.append(string); 239c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 240c5afb16430a145f20d7c887e45f47b38687054daMarc Blank logText = sb.toString(); 241c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 242c5afb16430a145f20d7c887e45f47b38687054daMarc Blank Log.d(TAG, logText); 243c5afb16430a145f20d7c887e45f47b38687054daMarc Blank if (mFileLog) { 244c5afb16430a145f20d7c887e45f47b38687054daMarc Blank FileLogger.log(TAG, logText); 245c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 246c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 247c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 248c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 249c5afb16430a145f20d7c887e45f47b38687054daMarc Blank /** 250c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Error log is used for serious issues that should always be logged 251c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * @param str the string to log 252c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 253c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public void errorLog(String str) { 254c5afb16430a145f20d7c887e45f47b38687054daMarc Blank Log.e(TAG, str); 255c5afb16430a145f20d7c887e45f47b38687054daMarc Blank if (mFileLog) { 256c5afb16430a145f20d7c887e45f47b38687054daMarc Blank FileLogger.log(TAG, str); 257c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 258c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 259c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 260c5afb16430a145f20d7c887e45f47b38687054daMarc Blank /** 261c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Waits for up to 10 seconds for network connectivity; returns whether or not there is 262c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * network connectivity. 263c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * 264c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * @return whether there is network connectivity 265c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 266c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public boolean hasConnectivity() { 267c5afb16430a145f20d7c887e45f47b38687054daMarc Blank ConnectivityManager cm = 268c5afb16430a145f20d7c887e45f47b38687054daMarc Blank (ConnectivityManager)mContext.getSystemService(Context.CONNECTIVITY_SERVICE); 269c5afb16430a145f20d7c887e45f47b38687054daMarc Blank int tries = 0; 270c5afb16430a145f20d7c887e45f47b38687054daMarc Blank while (tries++ < 1) { 271c5afb16430a145f20d7c887e45f47b38687054daMarc Blank // Use the same test as in ExchangeService#waitForConnectivity 272c5afb16430a145f20d7c887e45f47b38687054daMarc Blank // TODO: Create common code for this test in emailcommon 273c5afb16430a145f20d7c887e45f47b38687054daMarc Blank NetworkInfo info = cm.getActiveNetworkInfo(); 274c5afb16430a145f20d7c887e45f47b38687054daMarc Blank if (info != null) { 275c5afb16430a145f20d7c887e45f47b38687054daMarc Blank return true; 276c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 277c5afb16430a145f20d7c887e45f47b38687054daMarc Blank try { 278c5afb16430a145f20d7c887e45f47b38687054daMarc Blank Thread.sleep(10*SECONDS); 279c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } catch (InterruptedException e) { 280c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 281c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 282c5afb16430a145f20d7c887e45f47b38687054daMarc Blank return false; 283c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 284c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 285c5afb16430a145f20d7c887e45f47b38687054daMarc Blank /** 286c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Request handling (common functionality) 287c5afb16430a145f20d7c887e45f47b38687054daMarc Blank * Can be overridden if desired 288c5afb16430a145f20d7c887e45f47b38687054daMarc Blank */ 289c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 290c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public void addRequest(Request req) { 291e714bb9d153cfe13a7f0932e7d67ea08fa5a1d98Marc Blank if (!mRequestQueue.contains(req)) { 292e714bb9d153cfe13a7f0932e7d67ea08fa5a1d98Marc Blank mRequestQueue.offer(req); 293e714bb9d153cfe13a7f0932e7d67ea08fa5a1d98Marc Blank } 294c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 295c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 296c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public void removeRequest(Request req) { 297c5afb16430a145f20d7c887e45f47b38687054daMarc Blank mRequestQueue.remove(req); 298c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 299c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 300c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public boolean hasPendingRequests() { 301c5afb16430a145f20d7c887e45f47b38687054daMarc Blank return !mRequestQueue.isEmpty(); 302c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 303c5afb16430a145f20d7c887e45f47b38687054daMarc Blank 304c5afb16430a145f20d7c887e45f47b38687054daMarc Blank public void clearRequests() { 305c5afb16430a145f20d7c887e45f47b38687054daMarc Blank mRequestQueue.clear(); 306c5afb16430a145f20d7c887e45f47b38687054daMarc Blank } 307c5afb16430a145f20d7c887e45f47b38687054daMarc Blank} 308