Bug in email.generator.BytesGenerator() [was: Why does SMTP.send_message() do from mangling?]
Grant Edwards
grant.b.edwards at gmail.com
Mon Sep 27 00:07:00 EDT 2021
On 2021-09-27, Grant Edwards <grant.b.edwards at gmail.com> wrote:
> Why does SMTP.send_message(msg) do from mangling even though msg's
> policy has mangle_from_ set to False? The msg policy is
> email.policy.SMTP which has mangle_from_ disabled.
>
> One might expect that SMTP.send_message(msg) would use either msg's
> policy or email.policy.SMTP to send the message, but it does neither.
I've been looking at the smtplib.py sources, and the problem appears
to be in this section of send_message():
912 def send_message(self, msg, from_addr=None, to_addrs=None,
913 mail_options=(), rcpt_options=()):
914 """Converts message to a bytestring and passes it to sendmail.
...
963 # Make a local copy so we can delete the bcc headers.
964 msg_copy = copy.copy(msg)
...
977 with io.BytesIO() as bytesmsg:
978 if international:
979 g = email.generator.BytesGenerator(
980 bytesmsg, policy=msg.policy.clone(utf8=True))
981 mail_options = (*mail_options, 'SMTPUTF8', 'BODY=8BITMIME')
982 else:
983 g = email.generator.BytesGenerator(bytesmsg)
984 g.flatten(msg_copy, linesep='\r\n')
985 flatmsg = bytesmsg.getvalue()
If 'international' is Frue, then the BytesGenerator uses msg.policy
with utf8 added, and I don't get the bogus from mangling: the
generator only does from mangling if the message policy has it
enabled.
If 'international' is False, then the generator always does from
mangling regardless of the message's policy.
According to
https://docs.python.org/3/library/email.generator.html#email.generator.BytesGenerator
the default from mangling behavior is _supposed_ to obey the message
policy if (as seen at 983) no policy or mangle_from_ value was
provided to the call to BytesGenerator(). In my tests, it doesn't
actually seem to work that way. AFAICT, the default behavior when no
policy or mangle_from_ value is passed to BytesGenerator() is to
enable from mangling regardless of the message's policy. I belive that
is a bug.
This can be worked around by changing
983 g = email.generator.BytesGenerator(bytesmsg)
to
983 g = email.generator.BytesGenerator(bytesmsg, policy=msg.policy)
Or BytesGenerator() could be fixed...
--
Grant
More information about the Python-list
mailing list