def _handle_message_delivery_status(self, msg): """ Handle a message of type "message/delivery-status". This is modified from upstream version in that it also removes empty lines in the beginning of each part. :param msg: The message to be handled. :type msg: Message """ # 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.clone(s) g.flatten(part, unixfrom=False) text = s.getvalue() lines = text.split('\n') # Strip off the unnecessary trailing empty line if lines: if lines[0] == '': lines.pop(0) if lines[-1] == '': lines.pop() blocks.append(NL.join(lines)) 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_multipart(self, msg): # The trick here is to write out each part separately, merge the all # together, and then make sure that the boundary we've chosen isn't # present in the payload. msgtexts = [] subparts = msg.get_payload() if subparts is None: subparts = [] elif isinstance(subparts, basestring): # e.g. a non-strict parse of a message with no starting boundary self._fp.write(subparts) return elif not isinstance(subparts, list): # Scalar payload subparts = [subparts] for part in subparts: s = StringIO() g = self.clone(s) g.flatten(part, unixfrom=False) msgtexts.append(s.getvalue()) # BAW: What about boundaries that are wrapped in double-quotes? boundary = msg.get_boundary() if not boundary: # Create a boundary that doesn't appear in any of the # message texts. alltext = NL.join(msgtexts) boundary = _make_boundary(alltext) msg.set_boundary(boundary) # If there's a preamble, write it out, with a trailing CRLF if msg.preamble is not None: if self._mangle_from_: preamble = fcre.sub('>From ', msg.preamble) else: preamble = msg.preamble print >> self._fp, preamble # dash-boundary transport-padding CRLF print >> self._fp, '--' + boundary # body-part if msgtexts: self._fp.write(msgtexts.pop(0)) # *encapsulation # --> delimiter transport-padding # --> CRLF body-part for body_part in msgtexts: # delimiter transport-padding CRLF print >> self._fp, '\n--' + boundary # body-part self._fp.write(body_part) # close-delimiter transport-padding self._fp.write('\n--' + boundary + '--' + NL) if msg.epilogue is not None: if self._mangle_from_: epilogue = fcre.sub('>From ', msg.epilogue) else: epilogue = msg.epilogue self._fp.write(epilogue)
def _handle_multipart(self, msg): """ A multipart handling implementation that addresses issue #14983. This is just a copy of the parent's method which fixes the following bug: http://bugs.python.org/issue14983 (see the line marked with "(***)"). :param msg: The multipart message to be handled. :type msg: email.message.Message """ # The trick here is to write out each part separately, merge them all # together, and then make sure that the boundary we've chosen isn't # present in the payload. msgtexts = [] subparts = msg.get_payload() if subparts is None: subparts = [] elif isinstance(subparts, basestring): # e.g. a non-strict parse of a message with no starting boundary. self._fp.write(subparts) return elif not isinstance(subparts, list): # Scalar payload subparts = [subparts] for part in subparts: s = StringIO() g = self.clone(s) g.flatten(part, unixfrom=False) msgtexts.append(s.getvalue()) # BAW: What about boundaries that are wrapped in double-quotes? boundary = msg.get_boundary() if not boundary: # Create a boundary that doesn't appear in any of the # message texts. alltext = NL.join(msgtexts) boundary = _make_boundary(alltext) msg.set_boundary(boundary) # If there's a preamble, write it out, with a trailing CRLF if msg.preamble is not None: preamble = msg.preamble if self._mangle_from_: preamble = fcre.sub('>From ', msg.preamble) self._fp.write(preamble + '\n') # dash-boundary transport-padding CRLF self._fp.write('--' + boundary + '\n') # body-part if msgtexts: self._fp.write(msgtexts.pop(0)) # *encapsulation # --> delimiter transport-padding # --> CRLF body-part for body_part in msgtexts: # delimiter transport-padding CRLF self._fp.write('\n--' + boundary + '\n') # body-part self._fp.write(body_part) # close-delimiter transport-padding self._fp.write('\n--' + boundary + '--' + '\n') # (***) Solve #14983 if msg.epilogue is not None: self._fp.write('\n') epilogue = msg.epilogue if self._mangle_from_: epilogue = fcre.sub('>From ', msg.epilogue) self._fp.write(epilogue)