Python 3 smtplib 使用 unicode 字符发送

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1429147/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-11-03 22:14:36  来源:igfitidea点击:

Python 3 smtplib send with unicode characters

pythonemailunicodepython-3.xsmtplib

提问by foosion

I'm having a problem emailing unicode characters using smtplib in Python 3. This fails in 3.1.1, but works in 2.5.4:

我在 Python 3 中使用 smtplib 发送 unicode 字符时遇到问题。这在 3.1.1 中失败,但在 2.5.4 中有效:

  import smtplib
  from email.mime.text import MIMEText

  sender = to = '[email protected]'
  server = 'smtp.DEF.com'
  msg = MIMEText('10')
  msg['Subject'] = 'Hello'
  msg['From'] = sender
  msg['To'] = to
  s = smtplib.SMTP(server)
  s.sendmail(sender, [to], msg.as_string())
  s.quit()

I tried an example from the docs, which also failed. http://docs.python.org/3.1/library/email-examples.html, the Send the contents of a directory as a MIME message example

我尝试了文档中的一个示例,但也失败了。 http://docs.python.org/3.1/library/email-examples.html,将目录的内容作为 MIME 消息发送示例

Any suggestions?

有什么建议?

回答by Alex Martelli

The key is in the docs:

关键在文档中

class email.mime.text.MIMEText(_text, _subtype='plain', _charset='us-ascii')

A subclass of MIMENonMultipart, the MIMEText class is used to create MIME objects of major type text. _text is the string for the payload. _subtype is the minor type and defaults to plain. _charset is the character set of the text and is passed as a parameter to the MIMENonMultipart constructor; it defaults to us-ascii. No guessing or encoding is performed on the text data.

MIMEText 类是 MIMENonMultipart 的子类,用于创建主要类型文本的 MIME 对象。_text 是负载的字符串。_subtype 是次要类型,默认为普通类型。_charset 是文本的字符集,作为参数传递给 MIMENonMultipart 构造函数;它默认为 us-ascii。不对文本数据进行猜测或编码。

So what you need is clearly, notmsg = MIMEText('10'), but rather:

所以你需要的显然不是msg = MIMEText('10'),而是:

msg = MIMEText('10'.encode('utf-8'), _charset='utf-8')

While not all that clearly documented, sendmailneeds a byte-string, not a Unicode one (that's what the SMTP protocol specifies); look to what msg.as_string()looks like for each of the two ways of building it -- given the "no guessing or encoding", your way still has that euro character in there (and no way for sendmail to turn it into a bytestring), mine doesn't (and utf-8 is clearly specified throughout).

尽管没有明确记录,sendmail需要一个字节字符串,而不是 Unicode 字符串(这是 SMTP 协议指定的内容);查看msg.as_string()构建它的两种方式中的每一种的外观 - 鉴于“不猜测或编码”,您的方式仍然有欧元字符(并且 sendmail 无法将其转换为字节串),我的没有't(并且在整个过程中都明确指定了 utf-8)。

回答by SilentGhost

_charsetparameter of MIMETextdefaults to us-asciiaccording to the docs. Since is not from us-ascii set it isn't working.

_charset根据docsMIMEText默认参数。由于不是来自 us-ascii 集,因此无法正常工作。us-ascii

example in the docs that you've tried clearly states:

您尝试过的文档中的示例明确指出:

For this example, assume that the text file contains only ASCII characters.

对于此示例,假设文本文件仅包含 ASCII 字符。

You could use .get_charsetmethod on your message to investigate the charset, there is incidentally .set_charsetas well.

您可以.get_charset在您的消息中使用方法来调查字符集,顺便说一下.set_charset

回答by Paul D. Waite

Gus Mueller had a similar issue: http://bugs.python.org/issue4403

Gus Mueller 有一个类似的问题:http: //bugs.python.org/issue4403