wallace/__init__.py wallace/module_footer.py wallace/module_resources.py wallace/modules.py

Jeroen van Meeuwen vanmeeuwen at kolabsys.com
Mon Nov 25 17:01:19 CET 2013


 wallace/__init__.py         |   24 ++++++++++++------------
 wallace/module_footer.py    |   11 +++++------
 wallace/module_resources.py |   13 ++++++-------
 wallace/modules.py          |   44 ++++++++++++++++++++++++--------------------
 4 files changed, 47 insertions(+), 45 deletions(-)

New commits:
commit bf10544b4a71929af6593cc2f5002cd547d31a21
Author: Aleksander Machniak <machniak at kolabsys.com>
Date:   Mon Nov 25 17:00:03 2013 +0100

    Address #1627 once and for all, by simply not encoding / decoding the message but instead insert the envelope headers

diff --git a/wallace/__init__.py b/wallace/__init__.py
index 2db963e..0414d53 100644
--- a/wallace/__init__.py
+++ b/wallace/__init__.py
@@ -21,7 +21,6 @@ import asyncore
 import binascii
 from distutils import version
 import grp
-import json
 import multiprocessing
 import os
 import pwd
@@ -246,24 +245,25 @@ class WallaceDaemon(object):
             s.shutdown(1)
             s.close()
 
+    def data_header(self, mailfrom, rcpttos):
+        COMMASPACE = ', '
+        return "X-Kolab-From: " + mailfrom + "\r\n" + \
+                "X-Kolab-To: " + COMMASPACE.join(rcpttos) + "\r\n"
+
     def process_message(self, peer, mailfrom, rcpttos, data):
         """
             We have retrieved the message. This should be as fast as possible,
             and not ever block.
         """
-        inheaders = 1
-
-        data = json.dumps(
-                {
-                        'from': mailfrom,
-                        'to': rcpttos,
-                        'data': data
-                   },
-                ensure_ascii=True,
-                indent=4
-            )
+
+        header = self.data_header(mailfrom, rcpttos)
 
         (fp, filename) = tempfile.mkstemp(dir="/var/spool/pykolab/wallace/")
+
+        # @TODO: and add line separator (\n or \r\n?)
+        # we should make sure there's only one line separator between
+        # kolab headers and the original message (data)
+        os.write(fp, header);
         os.write(fp, data)
         os.close(fp)
 
diff --git a/wallace/module_footer.py b/wallace/module_footer.py
index 2779461..40833a2 100644
--- a/wallace/module_footer.py
+++ b/wallace/module_footer.py
@@ -17,7 +17,6 @@
 # Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
 #
 
-import json
 import os
 import tempfile
 import time
@@ -25,6 +24,7 @@ import time
 from email import message_from_string
 from email.MIMEBase import MIMEBase
 from email.MIMEText import MIMEText
+from email.parser import Parser
 from email.utils import formataddr
 from email.utils import getaddresses
 
@@ -70,8 +70,9 @@ def execute(*args, **kw):
     os.rename(filepath, new_filepath)
     filepath = new_filepath
 
-    _message = json.load(open(filepath, 'r'))
-    message = message_from_string("%s" % (str(_message['data'])))
+    # parse message headers
+    # @TODO: make sure we can use True as the 2nd argument here
+    message = Parser().parse(open(filepath, 'r'), True)
 
     # Possible footer answers are limited to ACCEPT only
     answers = [ 'ACCEPT' ]
@@ -162,10 +163,8 @@ def execute(*args, **kw):
         log.debug("Footer attached.")
         message.add_header("X-Wallace-Footer", "YES")
 
-    _message['data'] = "%s" % (str(message.as_string()))
-
     (fp, new_filepath) = tempfile.mkstemp(dir="/var/spool/pykolab/wallace/footer/ACCEPT")
-    os.write(fp, json.dumps(_message))
+    os.write(fp, message.as_string())
     os.close(fp)
     os.unlink(filepath)
 
diff --git a/wallace/module_resources.py b/wallace/module_resources.py
index b2924fa..7d45216 100644
--- a/wallace/module_resources.py
+++ b/wallace/module_resources.py
@@ -19,7 +19,6 @@
 
 import datetime
 import icalendar
-import json
 import os
 import pytz
 import random
@@ -29,6 +28,7 @@ from urlparse import urlparse
 import urllib
 
 from email import message_from_string
+from email.parser import Parser
 from email.utils import formataddr
 from email.utils import getaddresses
 
@@ -125,10 +125,11 @@ def execute(*args, **kw):
             os.rename(filepath, new_filepath)
             filepath = new_filepath
 
-    _message = json.load(open(filepath, 'r'))
-    log.debug("Loaded message %r" % (_message), level=9)
-    message = message_from_string(str(_message['data']))
-    recipients = _message['to']
+    # parse message headers
+    # @TODO: make sure we can use True as the 2nd argument here
+    message = Parser().parse(open(filepath, 'r'), True)
+
+    recipients = [address for displayname,address in getaddresses(message.get_all('X-Kolab-To'))]
 
     any_itips = False
     any_resources = False
@@ -449,7 +450,6 @@ def itip_events_from_message(message):
     """
         Obtain the iTip payload from email.message <message>
     """
-
     # Placeholder for any itip_events found in the message.
     itip_events = []
 
@@ -461,7 +461,6 @@ def itip_events_from_message(message):
     # document MUST have (...)" but does not state whether an iTip message must
     # therefore also be multipart.
     if message.is_multipart():
-
         # Check each part
         for part in message.walk():
 
diff --git a/wallace/modules.py b/wallace/modules.py
index d256bdb..861da75 100644
--- a/wallace/modules.py
+++ b/wallace/modules.py
@@ -17,7 +17,6 @@
 # Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
 #
 
-import json
 import os
 import sys
 import time
@@ -28,6 +27,7 @@ from email.mime.base import MIMEBase
 from email.mime.message import MIMEMessage
 from email.mime.multipart import MIMEMultipart
 from email.mime.text import MIMEText
+from email.parser import Parser
 from email.utils import COMMASPACE
 from email.utils import formatdate
 from email.utils import formataddr
@@ -120,8 +120,9 @@ def cb_action_HOLD(module, filepath):
 
 def cb_action_DEFER(module, filepath):
     log.info(_("Deferring message in %s (by module %s)") % (filepath, module))
-    message = json.load(open(filepath, 'r'))
-    message = message_from_string(message['data'])
+
+    # parse message headers
+    message = Parser().parse(open(filepath, 'r'), True)
 
     internal_time = parsedate_tz(message.__getitem__('Date'))
     internal_time = time.mktime(internal_time[:9]) + internal_time[9]
@@ -163,14 +164,14 @@ def cb_action_DEFER(module, filepath):
 def cb_action_REJECT(module, filepath):
     log.info(_("Rejecting message in %s (by module %s)") % (filepath, module))
 
-    _message = json.load(open(filepath, 'r'))
-    message = message_from_string(_message['data'])
+    # parse message headers
+    message = Parser().parse(open(filepath, 'r'), True)
 
     envelope_sender = getaddresses(message.get_all('From', []))
 
     recipients = getaddresses(message.get_all('To', [])) + \
             getaddresses(message.get_all('Cc', [])) + \
-            _message['to']
+            getaddresses(message.get_all('X-Kolab-To', []))
 
     _recipients = []
 
@@ -221,6 +222,12 @@ X-Wallace-Result: REJECT
     part.add_header("Content-Description", "Delivery Report")
     msg.attach(part)
 
+    # @TODO: here I'm not sure message will contain the whole body
+    # when we used headersonly argument of Parser().parse() above
+    # delete X-Kolab-* headers
+    del message['X-Kolab-From']
+    del message['X-Kolab-To']
+
     part = MIMEMessage(message)
     part.add_header("Content-Description", "Undelivered Message")
     msg.attach(part)
@@ -251,23 +258,19 @@ X-Wallace-Result: REJECT
 
 def cb_action_ACCEPT(module, filepath):
     log.info(_("Accepting message in %s (by module %s)") % (filepath, module))
-    try:
-        _message = json.load(open(filepath, 'r'))
-        log.debug(_(u"Message JSON loaded: %r") % (_message), level=9)
-    except Exception, errmsg:
-        log.error(_("Error loading message: %r") % (errmsg))
-        return
-
-    try:
-        message = message_from_string(str(_message['data']).replace('\x00',''))
-    except Exception, errmsg:
-        log.error(_("Error parsing message: %r") % (errmsg))
-        return
 
     log.debug(_("Accepting message in: %r") %(filepath), level=8)
 
-    sender = _message['from']
-    recipients = _message['to']
+    # parse message headers
+    message = Parser().parse(open(filepath, 'r'), True)
+
+    sender = [formataddr(x) for x in getaddresses(message.get_all('X-Kolab-From', []))]
+    recipients = [formataddr(x) for x in getaddresses(message.get_all('X-Kolab-To', []))]
+    log.debug(_("recipients: %r") % (recipients))
+
+    # delete X-Kolab-* headers
+    del message['X-Kolab-From']
+    del message['X-Kolab-To']
 
     smtp = smtplib.SMTP("localhost", 10027)
 
@@ -283,6 +286,7 @@ def cb_action_ACCEPT(module, filepath):
                 #   come from (TODO)
                 # - Third, a character return is inserted somewhere. It
                 #   divides the body from the headers - and we don't like (TODO)
+                # @TODO: check if we need Parser().parse() to load the whole message
                 message.as_string()
             )
 




More information about the commits mailing list