#19063: partially fix set_payload handling of non-ASCII string input.

This is a backward compatible partial fix, the complete fix requires raising
an error instead of accepting the invalid input, so the real fix is only
suitable for 3.4.
This commit is contained in:
R David Murray 2013-12-11 16:34:34 -05:00
parent 31a655411a
commit d5c4c7411a
4 changed files with 63 additions and 11 deletions

View file

@ -275,9 +275,19 @@ class Message:
Optional charset sets the message's default character set. See
set_charset() for details.
"""
if isinstance(payload, bytes):
payload = payload.decode('ascii', 'surrogateescape')
self._payload = payload
if hasattr(payload, 'encode'):
if charset is None:
# We should check for ASCII-only here, but we can't do that
# for backward compatibility reasons. Fixed in 3.4.
self._payload = payload
return
if not isinstance(charset, Charset):
charset = Charset(charset)
payload = payload.encode(charset.output_charset)
if hasattr(payload, 'decode'):
self._payload = payload.decode('ascii', 'surrogateescape')
else:
self._payload = payload
if charset is not None:
self.set_charset(charset)
@ -316,7 +326,15 @@ class Message:
try:
cte(self)
except TypeError:
self._payload = charset.body_encode(self._payload)
# This if is for backward compatibility and will be removed
# in 3.4 when the ascii check is added to set_payload.
payload = self._payload
if payload:
try:
payload = payload.encode('ascii', 'surrogateescape')
except UnicodeError:
payload = payload.encode(charset.output_charset)
self._payload = charset.body_encode(payload)
self.add_header('Content-Transfer-Encoding', cte)
def get_charset(self):