<DKIM> maxage causes loss of local email

Janna Martl janna.martl109 at gmail.com
Sat Mar 7 09:50:33 GMT 2015

Commented/ reorganized as you suggested.

As for the IMAP/timezone issue, a similar issue is discussed in the
thunderbird bug tracker here:


In the end, they're solving a different problem, but they agree that
there is really no reliable way of guessing the IMAP server's internal

Idea: in Base.py __syncmessagesto_delete(), check the time of each
thing in the deletelist to make sure it's not in the "ambiguity zone"
-- i.e. maxage +/- 1 days ago, where we can't tell if a message was
deleted on purpose or it just failed to show up on some list because
of timezone messiness. If it does fall into this range, then ask for
both messagelists from maxage + 1 days ago, instead of maxage days
ago. Now there should be enough information to determine whether the
message was deleted on purpose or not. (Or alternatively, just be
conservative and don't touch things in the ambiguity zone.)

-- J.M.

(I'm not cc'ing Mike Dawson anymore because the emails are bouncing.)
-------------- next part --------------
--- /usr/lib/python2.7/site-packages/offlineimap/folder/Maildir.py	2015-02-28 02:18:19.685320880 -0500
+++ Maildir.py	2015-03-07 04:20:31.413696048 -0500
@@ -31,7 +31,7 @@
 except NameError:
     from sets import Set as set
-from offlineimap import OfflineImapError
+from offlineimap import OfflineImapError, emailutil
 # Find the UID in a message filename
 re_uidmatch = re.compile(',U=(\d+)')
@@ -246,17 +246,36 @@
         filepath = os.path.join(self.getfullname(), filename)
         return os.path.getmtime(filepath)
-    def new_message_filename(self, uid, flags=set()):
+    def new_message_filename(self, uid, flags=set(), rtime=None):
         """Creates a new unique Maildir filename
         :param uid: The UID`None`, or a set of maildir flags
         :param flags: A set of maildir flags
         :returns: String containing unique message filename"""
+        # Prefer internal time (rtime) over retrieval time (_gettimeseq()) for
+        # consistency in the maxage check, which compares times of local mail
+        # (gotten from the filename) to internal times of remote mail.
+        if rtime is None:
+            timeval, timeseq = _gettimeseq()
+        else:
+            timeval, timeseq = rtime, 0
+        def build_filename(timeval, timeseq, pid, hostname, uid, folder_id,
+            infosep, flags):
+            """Compute a new filename with 'time sequence' uniqueness in mind"""
+            filename = '%d_%d.%d.%s,U=%d,FMD5=%s%s2,%s' % \
+                (timeval, timeseq, pid, hostname, uid, folder_id, infosep, flags)
+            for imap_dir in ['cur', 'new', 'tmp']:
+                if os.path.exists(os.path.join(self.getfullname(), imap_dir,
+                        filename)):
+                    # Increase timeseq
+                    return build_filename(timeval, timeseq + 1, pid, hostname,
+                            uid, folder_id, infosep, flags)
+            return filename
-        timeval, timeseq = _gettimeseq()
-        return '%d_%d.%d.%s,U=%d,FMD5=%s%s2,%s' % \
-            (timeval, timeseq, os.getpid(), socket.gethostname(),
-             uid, self._foldermd5, self.infosep, ''.join(sorted(flags)))
+        return build_filename(timeval, timeseq, os.getpid(), socket.gethostname(),
+                 uid, self._foldermd5, self.infosep, ''.join(sorted(flags)))
     def save_to_tmp_file(self, filename, content):
@@ -323,7 +342,10 @@
         # Otherwise, save the message in tmp/ and then call savemessageflags()
         # to give it a permanent home.
         tmpdir = os.path.join(self.getfullname(), 'tmp')
-        messagename = self.new_message_filename(uid, flags)
+        # Make sure rtime is the internal date, so it can be put in the filename
+        if rtime is None:
+            rtime = emailutil.get_message_date(content)
+        messagename = self.new_message_filename(uid, flags, rtime=rtime)
         tmpname = self.save_to_tmp_file(messagename, content)
         if rtime != None:
             os.utime(os.path.join(self.getfullname(), tmpname), (rtime, rtime))
@@ -399,8 +421,10 @@
         oldfilename = self.messagelist[uid]['filename']
         dir_prefix, filename = os.path.split(oldfilename)
         flags = self.getmessageflags(uid)
+        content = self.getmessage(uid)
+        rtime = emailutil.get_message_date(content)
         newfilename = os.path.join(dir_prefix,
-          self.new_message_filename(new_uid, flags))
+          self.new_message_filename(new_uid, flags, rtime=rtime))
         os.rename(os.path.join(self.getfullname(), oldfilename),
                   os.path.join(self.getfullname(), newfilename))
         self.messagelist[new_uid] = self.messagelist[uid]

More information about the OfflineIMAP-project mailing list