Skip to content

Workaround a race condition when changing email flags during ItemSync

When user changes Item flags (e.g. marks an email as read) while ItemSync is running for the same collection, the flags change is only stored locally in Akonadi and is pending inside ChangeRecorder in the resource (because the resource is busy with ItemSync).

If the ItemSync updates the Item that the user have changed locally, the local flags will get overwritten by the state on the server, effectively reverting the user's change. However, once the ItemSync is done, the resource will replay the flags change to the server, at which point our local database will actually reflect an outdated state (before the flags change) compared to the remote server.

Proper solution would be to implement (finally) server-side change recording, so that the Item merging code could inspect the pending changes and attempt to properly merge the remote and local changes. Right now all we can do is to assume that if the Item has changed while the ItemSync was running that it was flags that have changed and we preserve the local flags state. This won't detect complex scenarios (like when flags change both locally and remotely), but it should cover the most common scenario: marking an email as read while the collection is syncing.

We've only seen this affect IMAP servers that do not support CONDSTORE extension (RFC4551), which sadly includes some large provides like Outlook, because only then the IMAP resource lists all flags in the mailbox. Additionally, the mailbox has to be really huge or the user must have a very slow internet in order to be able to hit the window for the race.

Merge request reports