From ac028f3ccaef4509067862a2ccef9170801113de Mon Sep 17 00:00:00 2001 From: Marc Blank Date: Mon, 21 Sep 2009 15:30:05 -0700 Subject: [PATCH] Only handle mailbox alarms for EAS mailboxes * Fixes #2135238 in which a change to a POP/IMAP mailbox ended up causing a sync of that box as an EAS mailbox * The fix is to check that mailboxes with changes actually belong to an EAS account before trying to sync them Change-Id: I832095ce61665813cbcfb2aa58e45a48db8a34e7 --- .../exchange/EmailSyncAlarmReceiver.java | 12 ++-- src/com/android/exchange/SyncManager.java | 57 +++++++++++++++---- 2 files changed, 54 insertions(+), 15 deletions(-) diff --git a/src/com/android/exchange/EmailSyncAlarmReceiver.java b/src/com/android/exchange/EmailSyncAlarmReceiver.java index 5addf3ffd..4a4486018 100644 --- a/src/com/android/exchange/EmailSyncAlarmReceiver.java +++ b/src/com/android/exchange/EmailSyncAlarmReceiver.java @@ -55,9 +55,13 @@ public class EmailSyncAlarmReceiver extends BroadcastReceiver { ArrayList mailboxesToNotify = new ArrayList(); ContentResolver cr = context.getContentResolver(); int messageCount = 0; + + // Get a selector for EAS accounts (we don't want to sync on changes to POP/IMAP messages) + String selector = SyncManager.getEasAccountSelector(); + // Find all of the deletions - Cursor c = cr.query(Message.DELETED_CONTENT_URI, MAILBOX_DATA_PROJECTION, - null, null, null); + Cursor c = cr.query(Message.DELETED_CONTENT_URI, MAILBOX_DATA_PROJECTION, selector, + null, null); try { // Keep track of which mailboxes to notify; we'll only notify each one once while (c.moveToNext()) { @@ -72,8 +76,8 @@ public class EmailSyncAlarmReceiver extends BroadcastReceiver { } // Now, find changed messages - c = cr.query(Message.UPDATED_CONTENT_URI, MAILBOX_DATA_PROJECTION, - null, null, null); + c = cr.query(Message.UPDATED_CONTENT_URI, MAILBOX_DATA_PROJECTION, selector, + null, null); try { // Keep track of which mailboxes to notify; we'll only notify each one once while (c.moveToNext()) { diff --git a/src/com/android/exchange/SyncManager.java b/src/com/android/exchange/SyncManager.java index 044f29d4e..fa0174a6b 100644 --- a/src/com/android/exchange/SyncManager.java +++ b/src/com/android/exchange/SyncManager.java @@ -149,6 +149,7 @@ public class SyncManager extends Service implements Runnable { "(" + MailboxColumns.TYPE + '=' + Mailbox.TYPE_OUTBOX + " or " + MailboxColumns.SYNC_INTERVAL + "!=" + Mailbox.CHECK_INTERVAL_NEVER + ')' + " and " + MailboxColumns.ACCOUNT_KEY + " in ("; + private static final String ACCOUNT_KEY_IN = MailboxColumns.ACCOUNT_KEY + " in ("; // Offsets into the syncStatus data for EAS that indicate type, exit status, and change count // The format is S:: @@ -372,7 +373,8 @@ public class SyncManager extends Service implements Runnable { class AccountObserver extends ContentObserver { // mAccounts keeps track of Accounts that we care about (EAS for now) AccountList mAccounts = new AccountList(); - String mAccountKeyList = null; + String mSyncableEasMailboxSelector = null; + String mEasAccountSelector = null; public AccountObserver(Handler handler) { super(handler); @@ -397,12 +399,12 @@ public class SyncManager extends Service implements Runnable { } /** - * Returns a String suitable for appending to a where clause that selects for all eas - * accounts. - * @return a String in the form "and accountKey in (a, b, c...)" + * Returns a String suitable for appending to a where clause that selects for all syncable + * mailboxes in all eas accounts + * @return a complex selection string that is not to be cached */ - public String getMailboxWhere() { - if (mAccountKeyList == null) { + public String getSyncableEasMailboxWhere() { + if (mSyncableEasMailboxSelector == null) { StringBuilder sb = new StringBuilder(WHERE_NOT_INTERVAL_NEVER_AND_ACCOUNT_KEY_IN); boolean first = true; for (Account account: mAccounts) { @@ -414,9 +416,32 @@ public class SyncManager extends Service implements Runnable { sb.append(account.mId); } sb.append(')'); - mAccountKeyList = sb.toString(); + mSyncableEasMailboxSelector = sb.toString(); } - return mAccountKeyList; + return mSyncableEasMailboxSelector; + } + + /** + * Returns a String suitable for appending to a where clause that selects for all eas + * accounts. + * @return a String in the form "accountKey in (a, b, c...)" that is not to be cached + */ + public String getAccountKeyWhere() { + if (mEasAccountSelector == null) { + StringBuilder sb = new StringBuilder(ACCOUNT_KEY_IN); + boolean first = true; + for (Account account: mAccounts) { + if (!first) { + sb.append(','); + } else { + first = false; + } + sb.append(account.mId); + } + sb.append(')'); + mEasAccountSelector = sb.toString(); + } + return mEasAccountSelector; } private boolean syncParametersChanged(Account account) { @@ -453,7 +478,8 @@ public class SyncManager extends Service implements Runnable { new android.accounts.Account(account.mEmailAddress, Eas.ACCOUNT_MANAGER_TYPE); AccountManager.get(SyncManager.this).removeAccount(acct, null, null); - mAccountKeyList = null; + mSyncableEasMailboxSelector = null; + mEasAccountSelector = null; } else { // See whether any of our accounts has changed sync interval or window if (syncParametersChanged(account)) { @@ -483,7 +509,8 @@ public class SyncManager extends Service implements Runnable { HostAuth.restoreHostAuthWithId(getContext(), account.mHostAuthKeyRecv); account.mHostAuthRecv = ha; mAccounts.add(account); - mAccountKeyList = null; + mSyncableEasMailboxSelector = null; + mEasAccountSelector = null; } } @@ -617,6 +644,14 @@ public class SyncManager extends Service implements Runnable { } } + static public String getEasAccountSelector() { + if (INSTANCE != null) { + return INSTANCE.mAccountObserver.getAccountKeyWhere(); + } else { + return null; + } + } + private Account getAccountById(long accountId) { return mAccountObserver.mAccounts.getById(accountId); } @@ -1421,7 +1456,7 @@ public class SyncManager extends Service implements Runnable { // Start up threads that need it; use a query which finds eas mailboxes where the // the sync interval is not "never". This is the set of mailboxes that we control Cursor c = getContentResolver().query(Mailbox.CONTENT_URI, Mailbox.CONTENT_PROJECTION, - mAccountObserver.getMailboxWhere(), null, null); + mAccountObserver.getSyncableEasMailboxWhere(), null, null); try { while (c.moveToNext()) {