Skip to content
Merged
Show file tree
Hide file tree
Changes from 5 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions Lib/email/message.py
Original file line number Diff line number Diff line change
Expand Up @@ -313,6 +313,8 @@ def get_payload(self, i=None, decode=False):
# If it does happen, turn the string into bytes in a way
# guaranteed not to fail.
bpayload = payload.encode('raw-unicode-escape')
elif isinstance(payload, bytes):
bpayload = payload
if cte == 'quoted-printable':
return quopri.decodestring(bpayload)
elif cte == 'base64':
Expand Down
7 changes: 7 additions & 0 deletions Lib/test/test_email/test_message.py
Original file line number Diff line number Diff line change
Expand Up @@ -1055,6 +1055,13 @@ def test_get_body_malformed(self):
# AttributeError: 'str' object has no attribute 'is_attachment'
m.get_body()

def test_get_bytes_payload_with_quoted_printable_encoding(self):
payload = b'Some payload'
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
def test_get_bytes_payload_with_quoted_printable_encoding(self):
payload = b'Some payload'
def test_get_bytes_payload_with_quoted_printable_encoding(self):
# See https://github.com/python/cpython/issues/134759.
payload = b'Some payload'

This comment was marked as resolved.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can use the following for only using public methods:

        payload = memoryview(b'Some payload')
        m = self._make_message()
        m.add_header('Content-Transfer-Encoding', 'quoted-printable')
        m.set_payload(payload)
        self.assertEqual(m.get_payload(decode=True), payload)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, I was trying to reproduce bug with "public" method .set_payload(). I'm achieved that by passing BytesIO(b"Some payload") buffer but was not sure about correct arg type of .set_payload() (typeshed want object only with the .decode() method), so came up to put bytes directly.

I'll change the way you suggest, no problem :)

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, decode() is not present on memoryview but it's a buffer-like protocol so I think it should be fine. However, this may be a side-effect of the current implementation :) (also, the current implementation only does duck typing, not true isinstance() checks when setting the payload)

m = self._make_message()
m.add_header('Content-Transfer-Encoding', 'quoted-printable')
m._payload = payload
self.assertEqual(m.get_payload(decode=True), payload)


class TestMIMEPart(TestEmailMessageBase, TestEmailBase):
# Doing the full test run here may seem a bit redundant, since the two
Expand Down
1 change: 1 addition & 0 deletions Misc/ACKS
Original file line number Diff line number Diff line change
Expand Up @@ -1054,6 +1054,7 @@ Alexander Lakeev
David Lam
Thomas Lamb
Valerie Lambert
Kliment Lamonov
Peter Lamut
Jean-Baptiste "Jiba" Lamy
Ronan Lamy
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Fix ``UnboundLocalError`` in ``email.message.Message.get_payload``. Patch by Kliment Lamonov.
Loading