From b384e01796fad1293256262e7ab022f176afce9a Mon Sep 17 00:00:00 2001 From: Barry Warsaw Date: Wed, 26 Sep 2001 05:32:41 +0000 Subject: [PATCH] In class Generator: _handle_text(): If the payload is None, then just return (i.e. don't write anything). Subparts of message/delivery-status types will have this property since they are just blocks of headers. Also, when raising the TypeError, include the type of the payload in the error message. _handle_multipart(), _handle_message(): When creating a clone of self, pass in our _mangle_from_ and maxheaderlen flags so the clone has the same behavior. _handle_message_delivery_status(): New method to do the proper printing of message/delivery-status type messages. These have to be handled differently than other message/* types because their payloads are subparts containing just blocks of headers. In class DecodedGenerator: _dispatch(): Skip over multipart/* messages since we don't care about them, and don't want the non-text format to appear in the printed results. --- Lib/email/Generator.py | 37 ++++++++++++++++++++++++++++++++----- 1 file changed, 32 insertions(+), 5 deletions(-) diff --git a/Lib/email/Generator.py b/Lib/email/Generator.py index ca9757f32d9..c31dc803ec7 100644 --- a/Lib/email/Generator.py +++ b/Lib/email/Generator.py @@ -190,8 +190,10 @@ def _split_header(self, text): def _handle_text(self, msg): payload = msg.get_payload() + if payload is None: + return if not isinstance(payload, StringType): - raise TypeError, 'string payload expected' + raise TypeError, 'string payload expected: %s' % type(payload) if self._mangle_from_: payload = fcre.sub('>From ', payload) self._fp.write(payload) @@ -206,7 +208,7 @@ def _handle_multipart(self, msg, isdigest=0): msgtexts = [] for part in msg.get_payload(): s = StringIO() - g = self.__class__(s) + g = self.__class__(s, self._mangle_from_, self.__maxheaderlen) g(part, unixfrom=0) msgtexts.append(s.getvalue()) # Now make sure the boundary we've selected doesn't appear in any of @@ -245,9 +247,30 @@ def _handle_multipart(self, msg, isdigest=0): def _handle_multipart_digest(self, msg): self._handle_multipart(msg, isdigest=1) - def _handle_message_rfc822(self, msg): + def _handle_message_delivery_status(self, msg): + # We can't just write the headers directly to self's file object + # because this will leave an extra newline between the last header + # block and the boundary. Sigh. + blocks = [] + for part in msg.get_payload(): + s = StringIO() + g = self.__class__(s, self._mangle_from_, self.__maxheaderlen) + g(part, unixfrom=0) + text = s.getvalue() + lines = text.split('\n') + # Strip off the unnecessary trailing empty line + if lines and lines[-1] == '': + blocks.append(NL.join(lines[:-1])) + else: + blocks.append(text) + # Now join all the blocks with an empty line. This has the lovely + # effect of separating each block with an empty line, but not adding + # an extra one after the last one. + self._fp.write(NL.join(blocks)) + + def _handle_message(self, msg): s = StringIO() - g = self.__class__(s) + g = self.__class__(s, self._mangle_from_, self.__maxheaderlen) # A message/rfc822 should contain a scalar payload which is another # Message object. Extract that object, stringify it, and write that # out. @@ -292,8 +315,12 @@ def __init__(self, outfp, mangle_from_=1, maxheaderlen=78, fmt=None): def _dispatch(self, msg): for part in msg.walk(): - if part.get_main_type('text') == 'text': + maintype = part.get_main_type('text') + if maintype == 'text': print >> self, part.get_payload(decode=1) + elif maintype == 'multipart': + # Just skip this + pass else: print >> self, self._fmt % { 'type' : part.get_type('[no MIME type]'),