Пример #1
0
    def _prepare_message(self, addresses, subject, contents,
                         use_cache, headers):
        """ Prepare a MIME message """
        if self.is_closed:
            raise YagConnectionClosed('Login required again')
        if isinstance(contents, str):
            contents = [contents]
        has_included_images, content_objects = self._prepare_contents(
            contents, use_cache)
        msg = MIMEMultipart()
        if headers is not None:
            # Strangely, msg does not have an update method, so then manually.
            for k, v in headers.items():
                msg[k] = v

        msg_alternative = MIMEMultipart('alternative')
        msg_related = MIMEMultipart('related')
        msg.attach(msg_alternative)
        self._add_subject(msg, subject)
        self._add_recipients(msg, addresses)
        htmlstr = ''
        altstr = []
        if has_included_images:
            msg.preamble = "This message is best displayed using a MIME capable email reader."
        if contents is not None:
            for content_object, content_string in zip(content_objects,
                                                      contents):
                if content_object['main_type'] == 'image':
                    # aliased image {'path' : 'alias'}
                    if (isinstance(content_string, dict) and
                            len(content_string) == 1):
                        for x in content_string:
                            hashed_ref = str(abs(hash(x)))
                            alias = content_string[x]
                        # pylint: disable=undefined-loop-variable
                        content_string = x
                    else:
                        alias = os.path.basename(content_string)
                        hashed_ref = str(abs(hash(alias)))

                    # if string is `inline`, inline, else, attach
                    # pylint: disable=unidiomatic-typecheck
                    if type(content_string) == inline:
                        htmlstr += '<img src="cid:{}" title="{}"/>'.format(
                            hashed_ref, alias)
                        content_object['mime_object'].add_header(
                            'Content-ID', '<{}>'.format(hashed_ref))
                        altstr.append(
                            '-- img {} should be here -- '.format(alias))

                if content_object['encoding'] == 'base64':
                    email.encoders.encode_base64(content_object['mime_object'])
                    msg.attach(content_object['mime_object'])
                else:
                    content_string = content_string.replace('\n', '<br>')
                    htmlstr += '<div>{}</div>'.format(content_string)
                    altstr.append(content_string)

        msg_related.attach(MIMEText(htmlstr, 'html'))
        msg_alternative.attach(MIMEText('\n'.join(altstr)))
        msg_alternative.attach(msg_related)
        return msg
Пример #2
0
    def _prepare_message(self, addresses, subject, contents, attachments,
                         headers):
        """ Prepare a MIME message """
        if self.is_closed:
            raise YagConnectionClosed('Login required again')
        if isinstance(contents, str):
            contents = [contents]
        if isinstance(attachments, str):
            attachments = [attachments]

        # merge contents and attachments for now.
        if attachments is not None:
            for a in attachments:
                if not os.path.isfile(a):
                    raise TypeError("'{}' is not a valid filepath".format(a))
            contents = attachments if contents is None else contents + attachments

        has_included_images, content_objects = self._prepare_contents(contents)
        msg = MIMEMultipart()
        if headers is not None:
            # Strangely, msg does not have an update method, so then manually.
            for k, v in headers.items():
                msg[k] = v

        msg_alternative = MIMEMultipart('alternative')
        msg_related = MIMEMultipart('related')
        msg_related.attach("-- HTML goes here --")
        msg.attach(msg_alternative)
        self._add_subject(msg, subject)
        self._add_recipients_headers(msg, addresses)
        htmlstr = ''
        altstr = []
        if has_included_images:
            msg.preamble = "This message is best displayed using a MIME capable email reader."

        if contents is not None:
            for content_object, content_string in zip(content_objects,
                                                      contents):
                if content_object['main_type'] == 'image':
                    # all image objects need base64 encoding, so do it now
                    email.encoders.encode_base64(content_object['mime_object'])
                    # aliased image {'path' : 'alias'}
                    if isinstance(content_string,
                                  dict) and len(content_string) == 1:
                        for key in content_string:
                            hashed_ref = str(abs(hash(key)))
                            alias = content_string[key]
                        # pylint: disable=undefined-loop-variable
                        content_string = key
                    else:
                        alias = os.path.basename(str(content_string))
                        hashed_ref = str(abs(hash(alias)))

                    # TODO: I should probably remove inline now that there is "attachments"
                    # if string is `inline`, inline, else, attach
                    # pylint: disable=unidiomatic-typecheck
                    if type(content_string) == inline:
                        htmlstr += '<img src="cid:{}" title="{}"/>'.format(
                            hashed_ref, alias)
                        content_object['mime_object'].add_header(
                            'Content-ID', '<{}>'.format(hashed_ref))
                        altstr.append(
                            '-- img {} should be here -- '.format(alias))
                        # inline images should be in related MIME block
                        msg_related.attach(content_object['mime_object'])
                    else:
                        # non-inline images get attached like any other attachment
                        msg.attach(content_object['mime_object'])

                else:
                    if content_object['encoding'] == 'base64':
                        email.encoders.encode_base64(
                            content_object['mime_object'])
                        msg.attach(content_object['mime_object'])
                    else:
                        content_string = content_string.replace('\n', '<br>')
                        htmlstr += '<div>{}</div>'.format(content_string)
                        altstr.append(content_string)

        msg_related.get_payload()[0] = MIMEText(htmlstr,
                                                'html',
                                                _charset=self.encoding)
        msg_alternative.attach(
            MIMEText('\n'.join(altstr), _charset=self.encoding))
        msg_alternative.attach(msg_related)
        return msg