我发送的是附件附件的电子邮件,该附件的文件名很长。为什么它会被换行符损坏,应该删除系统应该知道哪些新行?
from email.mime.text import MIMEText
from email.mime.multipart import MIMEMultipart
from email.mime.application import MIMEApplication
from email.utils import formatdate
msg = MIMEMultipart()
msg['Subject'] = 'subject'
msg['To'] = 'a@example.com'
msg['From'] = 'b@example.com'
msg['Date'] = formatdate(localtime=True)
msg.attach(MIMEText('abc'))
attachment_name = 'abcdefghijklmnopqrstuvwxyz abcdefghijklmnopqrstuvwxyz abcdefghijklmnopqrstuvwxyz abcdefghijklmnopqrstuvwxyz abcdefghijklmnopqrstuvwxyz abcdefghijklmnopqrstuvwxyz.txt'
part = MIMEApplication("sometext", Name=attachment_name)
part['Content-Disposition'] = 'attachment; filename="%s"' % attachment_name
msg.attach(part)
print msg.as_string()
给我:
Content-Type: multipart/mixed; boundary="===============1448866158=="
MIME-Version: 1.0
Subject: subject
To: a@example.com
From: b@example.com
Date: Sat, 20 Jan 2018 13:11:42 -0500
--===============1448866158==
Content-Type: text/plain; charset="us-ascii"
MIME-Version: 1.0
Content-Transfer-Encoding: 7bit
abc
--===============1448866158==
Content-Type: application/octet-stream;
Name="abcdefghijklmnopqrstuvwxyz abcdefghijklmnopqrstuvwxyz
abcdefghijklmnopqrstuvwxyz abcdefghijklmnopqrstuvwxyz
abcdefghijklmnopqrstuvwxyz abcdefghijklmnopqrstuvwxyz.txt"
MIME-Version: 1.0
Content-Transfer-Encoding: base64
Content-Disposition: attachment; filename="abcdefghijklmnopqrstuvwxyz
abcdefghijklmnopqrstuvwxyz abcdefghijklmnopqrstuvwxyz
abcdefghijklmnopqrstuvwxyz abcdefghijklmnopqrstuvwxyz
abcdefghijklmnopqrstuvwxyz.txt"
c29tZXRleHQ=
--===============1448866158==--
答案 0 :(得分:2)
长标头字段的处理在section 2.2.3 of RFC 2822 "Internet Message Format"中定义。该部分在过时的RFC 5322中保持不变。
2.2.3。长标题字段
每个标题字段在逻辑上是包含的单行字符 字段名称,冒号和字段正文。为了方便 但是,为了处理每行的998/78字符限制, 标题字段的字段主体部分可以分成多个 线表示;这被称为“折叠”。一般规则是 这个标准允许折叠白色空间的地方(不是简单的 WSP字符),可以在任何WSP之前插入CRLF。例如, 标题字段:
Subject: This is a test
可以表示为:
Subject: This is a test
注意:虽然结构化的字段主体是以这样的方式定义的 折叠可以发生在许多词汇标记之间(甚至是 在一些词法标记中),折叠应该限制为 将CRLF置于更高级别的句法中断。例如,如果是 字段主体定义为逗号分隔值,建议使用 折叠发生在逗号分隔结构化项目之后 喜欢可以折叠场地的其他地方,即使它 允许在其他地方使用。
从这个折叠的多行表示移动的过程 调用其单行表示的头字段 “展开”。只需删除任何CRLF即可完成展开 WSP紧随其后。每个标题字段应该是 以展开的形式对待进一步的句法和语义 评价。强>
答案 1 :(得分:2)
正如Leon的回答所解释的那样,Python正在实施RFC中定义的折叠算法。
在Python 2中,您可以使用email.generator.Generator
实例来控制最大标头长度;来自the docs:
为了获得更大的灵活性,请实例化Generator实例并直接使用其flatten()方法。例如:
from cStringIO import StringIO
from email.generator import Generator
fp = StringIO()
g = Generator(fp, mangle_from_=False, maxheaderlen=60)
g.flatten(msg)
text = fp.getvalue()
(将maxheaderlen设置为零可以防止在几乎所有情况下折叠长标题行。)
在Python 3.5中,maxheaderlen参数在email.message.Message.as_string
的{{3}}中公开,所以
print(msg.as_string(maxheaderlen=256))
是可能的。默认情况下,maxheaderlen
为零,因此除非提供值,否则不会删除标题行。
在Python 3.6中,maxheaderlen
的{{3}}中显示了email.message.EmailMessage.as_string
(请注意,这是一个不同的类)。 maxheaderlen
现在默认为None
:标题行换行为78个字符,除非指定了值。