From fb8017991c3de0fd3111f47338e4648e1abb586d Mon Sep 17 00:00:00 2001 From: Sebastian Spaeth Date: Mon, 22 Aug 2011 12:21:11 +0200 Subject: [PATCH] Rework undocumented listjoin to create UID sequences This function was badly named and completely undocumented. Rework it to avoid copying the full UID list using an iterator. Make it possible to hand it a list of UIDs as strings rather than implicitely relying on the fact that they are numeric already. Document the code. The behavior off the function itself remained otherwise unchanged. Signed-off-by: Sebastian Spaeth Signed-off-by: Nicolas Sebrecht --- offlineimap/folder/Gmail.py | 2 +- offlineimap/folder/IMAP.py | 2 +- offlineimap/imaputil.py | 44 ++++++++++++++++++------------------- 3 files changed, 23 insertions(+), 25 deletions(-) diff --git a/offlineimap/folder/Gmail.py b/offlineimap/folder/Gmail.py index 7cbff4f..587a00f 100644 --- a/offlineimap/folder/Gmail.py +++ b/offlineimap/folder/Gmail.py @@ -55,7 +55,7 @@ class GmailFolder(IMAPFolder): try: imapobj.select(self.getfullname()) result = imapobj.uid('copy', - imaputil.listjoin(uidlist), + imaputil.uid_sequence(uidlist), self.trash_folder) assert result[0] == 'OK', \ "Bad IMAPlib result: %s" % result[0] diff --git a/offlineimap/folder/IMAP.py b/offlineimap/folder/IMAP.py index 417b80a..80f144d 100644 --- a/offlineimap/folder/IMAP.py +++ b/offlineimap/folder/IMAP.py @@ -626,7 +626,7 @@ class IMAPFolder(BaseFolder): self.ui.flagstoreadonly(self, uidlist, flags) return r = imapobj.uid('store', - imaputil.listjoin(uidlist), + imaputil.uid_sequence(uidlist), operation + 'FLAGS', imaputil.flagsmaildir2imap(flags)) assert r[0] == 'OK', 'Error with store: ' + '. '.join(r[1]) diff --git a/offlineimap/imaputil.py b/offlineimap/imaputil.py index 3905851..b336876 100644 --- a/offlineimap/imaputil.py +++ b/offlineimap/imaputil.py @@ -168,35 +168,33 @@ def flagsmaildir2imap(maildirflaglist): retval.sort() return '(' + ' '.join(retval) + ')' -def listjoin(list): - start = None - end = None - retval = [] +def uid_sequence(uidlist): + """Collapse UID lists into shorter sequence sets - def getlist(start, end): + [1,2,3,4,5,10,12,13] will return "1:5,10,12:13". This function does + not sort the list, and only collapses if subsequent entries form a + range. + :returns: The collapsed UID list as string""" + def getrange(start, end): if start == end: return(str(start)) - else: - return(str(start) + ":" + str(end)) - + return "%s:%s" % (start, end) - for item in list: - if start == None: - # First item. - start = item - end = item - elif item == end + 1: - # An addition to the list. - end = item - else: - # Here on: starting a new list. - retval.append(getlist(start, end)) - start = item - end = item + if not len(uidlist): return '' # Empty list, return + start, end = None, None + retval = [] - if start != None: - retval.append(getlist(start, end)) + for item in iter(uidlist): + item = int(item) + if start == None: # First item + start, end = item, item + elif item == end + 1: # Next item in a range + end = item + else: # Starting a new range + retval.append(getrange(start, end)) + start, end = item, item + retval.append(getrange(start, end)) # Add final range/item return ",".join(retval)