summaryrefslogtreecommitdiff
path: root/src/leap/mail/imap/messages.py
diff options
context:
space:
mode:
authorKali Kaneko <kali@leap.se>2014-02-11 01:45:20 -0400
committerKali Kaneko <kali@leap.se>2014-02-17 11:39:48 -0400
commitf869b7eecab67d07a23dfb8b2931b3844f7523e3 (patch)
tree42aded16d0059ffa0636540d0a4b8a9a4f0eb7ed /src/leap/mail/imap/messages.py
parent4338368aa2ba0efaee742e9000e21b81af34d3db (diff)
fine grained locks for puts
Diffstat (limited to 'src/leap/mail/imap/messages.py')
-rw-r--r--src/leap/mail/imap/messages.py35
1 files changed, 23 insertions, 12 deletions
diff --git a/src/leap/mail/imap/messages.py b/src/leap/mail/imap/messages.py
index 8b6d3f3..de5dd1f 100644
--- a/src/leap/mail/imap/messages.py
+++ b/src/leap/mail/imap/messages.py
@@ -88,6 +88,13 @@ def try_unique_query(curried):
logger.exception("Unhandled error %r" % exc)
+"""
+A dictionary that keeps one lock per mbox and uid.
+"""
+# XXX too much overhead?
+fdoc_locks = defaultdict(lambda: defaultdict(lambda: threading.Lock()))
+
+
class LeapMessage(fields, MailParser, MBoxParser):
"""
The main representation of a message.
@@ -102,8 +109,6 @@ class LeapMessage(fields, MailParser, MBoxParser):
implements(imap4.IMessage)
- flags_lock = threading.Lock()
-
def __init__(self, soledad, uid, mbox, collection=None, container=None):
"""
Initializes a LeapMessage.
@@ -129,6 +134,9 @@ class LeapMessage(fields, MailParser, MBoxParser):
self.__chash = None
self.__bdoc = None
+ from twisted.internet import reactor
+ self.reactor = reactor
+
# XXX make these properties public
@property
@@ -238,20 +246,21 @@ class LeapMessage(fields, MailParser, MBoxParser):
:type mode: int
"""
leap_assert(isinstance(flags, tuple), "flags need to be a tuple")
- log.msg('setting flags: %s (%s)' % (self._uid, flags))
+ #log.msg('setting flags: %s (%s)' % (self._uid, flags))
- doc = self.fdoc
- if not doc:
- logger.warning(
- "Could not find FDOC for %s:%s while setting flags!" %
- (self._mbox, self._uid))
- return
+ mbox, uid = self._mbox, self._uid
APPEND = 1
REMOVE = -1
SET = 0
- with self.flags_lock:
+ with fdoc_locks[mbox][uid]:
+ doc = self.fdoc
+ if not doc:
+ logger.warning(
+ "Could not find FDOC for %r:%s while setting flags!" %
+ (mbox, uid))
+ return
current = doc.content[self.FLAGS_KEY]
if mode == APPEND:
newflags = tuple(set(tuple(current) + flags))
@@ -733,6 +742,9 @@ class MessageCollection(WithMsgFields, IndexedDB, MailParser, MBoxParser):
# ensure that we have a recent-flags and a hdocs-sec doc
self._get_or_create_rdoc()
+ from twisted.internet import reactor
+ self.reactor = reactor
+
def _get_empty_doc(self, _type=FLAGS_DOC):
"""
Returns an empty doc for storing different message parts.
@@ -877,7 +889,7 @@ class MessageCollection(WithMsgFields, IndexedDB, MailParser, MBoxParser):
uid when the adding succeed.
:rtype: deferred
"""
- logger.debug('adding message')
+ logger.debug('Adding message')
if flags is None:
flags = tuple()
leap_assert_type(flags, tuple)
@@ -921,7 +933,6 @@ class MessageCollection(WithMsgFields, IndexedDB, MailParser, MBoxParser):
msg = self.get_msg_by_uid(uid)
# TODO this cannot be deferred, this has to block.
- #reactor.callLater(0, msg.setFlags, (fields.DELETED_FLAG,), -1)
msg.setFlags((fields.DELETED_FLAG,), -1)
reactor.callLater(0, observer.callback, uid)
return