【问题标题】:Django EmailMultiAlternatives and HTML e-mail display in Outlook 2003 on Win2003Django EmailMultiAlternatives 和 HTML 电子邮件在 Win2003 上的 Outlook 2003 中显示
【发布时间】:2010-10-31 21:25:31
【问题描述】:

我在从我的 django 应用程序发送电子邮件时使用 django.core.mail.EmailMultiAlternatives 以确保在电子邮件客户端不支持 HTML 时邮件降级为文本。

这是我的 send_email 方法:

def send_email(self, from_address, to_list, subject, msg_text, msg_html):
        subject=subject.replace('\r','').replace('\n',' ')
        self.msg = EmailMultiAlternatives(subject, msg_text, from_address, to_list)
        self.msg.attach_alternative(msg_html, "text/html")
        self.msg.content_subtype = "html"
        self.msg.send()

它适用于 Gmail、Hotmail 和许多其他电子邮件客户端 - 毫无问题地显示 HTML 内容。但它不会显示在 Win2003 上运行的 Outlook 2003 中的 HTML 内容 - 只是文本版本。

如果我强行将 HTML 放入 EmailMultiAlternatives 调用中,即像这样使用 msg_html instead of msg_text:

self.msg = EmailMultiAlternatives(subject, msg_html, from_address, to_list)

那么它在所有客户端都能正常工作;但这意味着对于不支持 HTML 或(更有可能)禁用对它的支持的客户端没有文本回退。

我认为值得一提的是,电子邮件是在 Mac OS X 上运行的 django 应用程序上生成的(以防它与操作系统之间的行终止符差异有关)。

我看到people using other languages 的 Outlook 也有类似的问题...

我想知道是否有人知道为什么 Outlook 的行为会有所不同,是否有可以在我的代码中应用的简单修复?

【问题讨论】:

    标签: python html django email


    【解决方案1】:

    我没有可用的 Outlook 安装来测试这个,所以我想知道你的函数中第五行的原因。

    self.msg.content_subtype = "html"

    我对多部分电子邮件的内部结构了解不多,但在我的系统上,该行导致邮件的两个部分都具有 text/html 的内容类型。忽略它会在第一部分生成一条消息,其中包含“Content-Type: text/plain”,第二部分是“Content-Type: text/html”。

    无论如何,关于 Java 的问题的答案之一提到将字符集更改为 iso-8859-1。我认为您应该能够使用 django.core.mail 做到这一点。

    EmailMessage 类(EmailMultiAlternatives 继承自该类)有一个名为“encoding”的属性,用于设置要使用的字符集。默认情况下它是 None 因此使用 utf-8 的默认字符集(除非在设置中被覆盖)。

    换句话说,在问题中列出的函数的发送行之前添加如下内容:

    self.msg.content_subtype = "iso-8859-1"

    不幸的是,这只会改变第一部分指定的编码(上面函数中的 msg_text)。附加替代内容的函数似乎没有使用 encoding 属性。我不确定这是不是正确的方法,但我将 EmailMultiAlternatives 子类化以覆盖相关函数,它似乎工作正常。

    class EmailMultiAlternativesWithEncoding(EmailMultiAlternatives):
        def _create_attachment(self, filename, content, mimetype=None):
            """
            Converts the filename, content, mimetype triple into a MIME attachment
            object. Use self.encoding when handling text attachments.
            """
            if mimetype is None:
                mimetype, _ = mimetypes.guess_type(filename)
                if mimetype is None:
                    mimetype = DEFAULT_ATTACHMENT_MIME_TYPE
            basetype, subtype = mimetype.split('/', 1)
            if basetype == 'text':
                encoding = self.encoding or settings.DEFAULT_CHARSET
                attachment = SafeMIMEText(smart_str(content,
                    settings.DEFAULT_CHARSET), subtype, encoding)
                # original text being replaced above (not last argument)
                # attachment = SafeMIMEText(smart_str(content,
                #     settings.DEFAULT_CHARSET), subtype, settings.DEFAULT_CHARSET)
            else:
                # Encode non-text attachments with base64.
                attachment = MIMEBase(basetype, subtype)
                attachment.set_payload(content)
                Encoders.encode_base64(attachment)
            if filename:
                attachment.add_header('Content-Disposition', 'attachment',
                                      filename=filename)
            return attachment

    我不确定“smart_str(content, settings.DEFAULT_CHARSET)”部分是否也应该引用“encoding”而不是“settings.DEFAULT_CHARSET”,但这是消息体处理文本的编写(django.core.mail. EmailMessage.message)。

    正如我所说,我没有 Outlook,因此我无法实际测试 Outlook 方面,但它似乎确实将两个部分的字符集更改为 iso-8859-1。

    【讨论】:

    • 我也没有要测试的 Outlook,但要努力 +1!
    • 你的第一直觉——我不应该搞乱 content_subtype——是正确的。从我的函数中删除它会在 Outlook 2003 和其他电子邮件客户端中正确呈现 HTML。我认为有关发送电子邮件的 Django 文档可能会受益于删除对 content_subtype 的提及或阐明如何使用它。我假设因为 Outlook 可以处理另一种内容类型;我应该使用 content_subtype = 'html'。显然情况并非如此,并且与我试图实现的目标相反。非常感谢您的健全性检查。
    • 不要使用content_subtype = "iso-8859-1"!它只会将 mime 类型设置为 text/iso-8859-1,这显然是无稽之谈,然后您的消息将为空,并带有一个名为 noname 的附件,其中包含实际消息。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-06-07
    • 2021-05-10
    • 2014-01-28
    • 1970-01-01
    • 2016-12-31
    • 2011-03-16
    • 2013-02-05
    相关资源
    最近更新 更多