diff options
author | Fred Quintana <fredq@google.com> | 2010-03-23 17:57:03 -0700 |
---|---|---|
committer | Fred Quintana <fredq@google.com> | 2010-03-24 10:37:40 -0700 |
commit | fb084400d6afa6443a421117fbcaee0265d38fb6 (patch) | |
tree | 941a318a87f111e3950453551ad2cbe1d5a36476 /core/java/android/content/SyncStorageEngine.java | |
parent | 49de491379fc56960d00ff6c52472fe1a7d907a7 (diff) | |
download | frameworks_base-fb084400d6afa6443a421117fbcaee0265d38fb6.zip frameworks_base-fb084400d6afa6443a421117fbcaee0265d38fb6.tar.gz frameworks_base-fb084400d6afa6443a421117fbcaee0265d38fb6.tar.bz2 |
fix bug where sync settings set lost upon upgrade from donut and eclair
to froyo
- intepret a missing syncavble attribute from donut as "unsynced"
rather than the traditional "true"
- copy the sync settings from the authorities "contacts" and "calendar"
to "com.android.contacts" and "com.android.calendar" if the latter
don't already have settings
- delay the database cleanup until after boot completed, which will give
the GoogleLoginService accounts migration code a chance to run; this
was causing all the settings to get removed upon a donut to froyo upgrade
Change-Id: I8795e97ba0c9b930d1a50784229ca9ab15dff9d2
http://b/issue?id=2531359
Diffstat (limited to 'core/java/android/content/SyncStorageEngine.java')
-rw-r--r-- | core/java/android/content/SyncStorageEngine.java | 81 |
1 files changed, 70 insertions, 11 deletions
diff --git a/core/java/android/content/SyncStorageEngine.java b/core/java/android/content/SyncStorageEngine.java index 03e606f..daad95c 100644 --- a/core/java/android/content/SyncStorageEngine.java +++ b/core/java/android/content/SyncStorageEngine.java @@ -122,7 +122,15 @@ public class SyncStorageEngine extends Handler { private static final boolean SYNC_ENABLED_DEFAULT = false; // the version of the accounts xml file format - private static final int ACCOUNTS_VERSION = 1; + private static final int ACCOUNTS_VERSION = 2; + + private static HashMap<String, String> sAuthorityRenames; + + static { + sAuthorityRenames = new HashMap<String, String>(); + sAuthorityRenames.put("contacts", "com.android.contacts"); + sAuthorityRenames.put("calendar", "com.android.calendar"); + } public static class PendingOperation { final Account account; @@ -1281,7 +1289,9 @@ public class SyncStorageEngine extends Handler { private void removeAuthorityLocked(Account account, String authorityName) { AccountInfo accountInfo = mAccounts.get(account); if (accountInfo != null) { - if (accountInfo.authorities.remove(authorityName) != null) { + final AuthorityInfo authorityInfo = accountInfo.authorities.remove(authorityName); + if (authorityInfo != null) { + mAuthorities.remove(authorityInfo.ident); writeAccountInfoLocked(); } } @@ -1407,11 +1417,61 @@ public class SyncStorageEngine extends Handler { } } + if (maybeMigrateSettingsForRenamedAuthorities()) { + writeNeeded = true; + } + if (writeNeeded) { writeAccountInfoLocked(); } } + /** + * some authority names have changed. copy over their settings and delete the old ones + * @return true if a change was made + */ + private boolean maybeMigrateSettingsForRenamedAuthorities() { + boolean writeNeeded = false; + + ArrayList<AuthorityInfo> authoritiesToRemove = new ArrayList<AuthorityInfo>(); + final int N = mAuthorities.size(); + for (int i=0; i<N; i++) { + AuthorityInfo authority = mAuthorities.valueAt(i); + // skip this authority if it isn't one of the renamed ones + final String newAuthorityName = sAuthorityRenames.get(authority.authority); + if (newAuthorityName == null) { + continue; + } + + // remember this authority so we can remove it later. we can't remove it + // now without messing up this loop iteration + authoritiesToRemove.add(authority); + + // this authority isn't enabled, no need to copy it to the new authority name since + // the default is "disabled" + if (!authority.enabled) { + continue; + } + + // if we already have a record of this new authority then don't copy over the settings + if (getAuthorityLocked(authority.account, newAuthorityName, "cleanup") != null) { + continue; + } + + AuthorityInfo newAuthority = getOrCreateAuthorityLocked(authority.account, + newAuthorityName, -1 /* ident */, false /* doWrite */); + newAuthority.enabled = true; + writeNeeded = true; + } + + for (AuthorityInfo authorityInfo : authoritiesToRemove) { + removeAuthorityLocked(authorityInfo.account, authorityInfo.authority); + writeNeeded = true; + } + + return writeNeeded; + } + private AuthorityInfo parseAuthority(XmlPullParser parser, int version) { AuthorityInfo authority = null; int id = -1; @@ -1424,14 +1484,15 @@ public class SyncStorageEngine extends Handler { Log.e(TAG, "the id of the authority is null", e); } if (id >= 0) { + String authorityName = parser.getAttributeValue(null, "authority"); + String enabled = parser.getAttributeValue(null, "enabled"); + String syncable = parser.getAttributeValue(null, "syncable"); String accountName = parser.getAttributeValue(null, "account"); String accountType = parser.getAttributeValue(null, "type"); if (accountType == null) { accountType = "com.google"; + syncable = "unknown"; } - String authorityName = parser.getAttributeValue(null, "authority"); - String enabled = parser.getAttributeValue(null, "enabled"); - String syncable = parser.getAttributeValue(null, "syncable"); authority = mAuthorities.get(id); if (DEBUG_FILE) Log.v(TAG, "Adding authority: account=" + accountName + " auth=" + authorityName @@ -1456,7 +1517,7 @@ public class SyncStorageEngine extends Handler { authority.syncable = -1; } else { authority.syncable = - (syncable == null || Boolean.parseBoolean(enabled)) ? 1 : 0; + (syncable == null || Boolean.parseBoolean(syncable)) ? 1 : 0; } } else { Log.w(TAG, "Failure adding authority: account=" @@ -1546,13 +1607,11 @@ public class SyncStorageEngine extends Handler { out.attribute(null, "account", authority.account.name); out.attribute(null, "type", authority.account.type); out.attribute(null, "authority", authority.authority); - if (!authority.enabled) { - out.attribute(null, "enabled", "false"); - } + out.attribute(null, "enabled", Boolean.toString(authority.enabled)); if (authority.syncable < 0) { out.attribute(null, "syncable", "unknown"); - } else if (authority.syncable == 0) { - out.attribute(null, "syncable", "false"); + } else { + out.attribute(null, "syncable", Boolean.toString(authority.syncable != 0)); } for (Pair<Bundle, Long> periodicSync : authority.periodicSyncs) { out.startTag(null, "periodicSync"); |