fix(email): Try to parse bad email address headers

This commit is contained in:
Corentin Forler 2024-09-03 10:39:06 +02:00
parent 8dd14c4ba8
commit 2ba199349c
No known key found for this signature in database
2 changed files with 15 additions and 2 deletions

View file

@ -10,6 +10,7 @@ import poplib
import re
import ssl
from contextlib import suppress
from email.errors import HeaderParseError
from email.header import decode_header
import _socket
@ -440,11 +441,19 @@ class Email:
self.from_real_name = parse_addr(_from_email)[0] if "@" in _from_email else _from_email
@staticmethod
def decode_email(email):
def decode_email(email: bytes | str | None) -> str | None:
if not email:
return
email = frappe.as_unicode(email).replace('"', " ").replace("'", " ")
try:
parts = decode_header(email)
except HeaderParseError:
# Fallback: grab just the email addresses
emails = re.findall(r"(<.*?>)", email)
return ", ".join(emails)
decoded = ""
for part, encoding in decode_header(frappe.as_unicode(email).replace('"', " ").replace("'", " ")):
for part, encoding in parts:
if encoding:
decoded += part.decode(encoding, "replace")
else:

View file

@ -201,6 +201,10 @@ Reply-To: test2_@erpnext.com
)
self.assertIn("user@example.com", mail)
def test_poorly_encoded_messages2(self):
mail = Email.decode_email(" =?UTF-8?B?X\xe0\xe0Y?= <xy@example.com>")
self.assertIn("xy@example.com", mail)
def fixed_column_width(string, chunk_size):
parts = [string[0 + i : chunk_size + i] for i in range(0, len(string), chunk_size)]