Parse RFC2047 formatted text properly in submission form. Fixes #2465. Commit ready for merge.

- Legacy-Id: 19120
This commit is contained in:
Kesara Rathnayake 2021-06-14 10:46:35 +00:00
parent a83d60dd55
commit 0a645fd486
4 changed files with 38 additions and 3 deletions

View file

@ -16,6 +16,7 @@ from ietf.group.models import Group
from ietf.message.models import Message from ietf.message.models import Message
from ietf.name.models import DraftSubmissionStateName, FormalLanguageName from ietf.name.models import DraftSubmissionStateName, FormalLanguageName
from ietf.utils.accesstoken import generate_random_key, generate_access_token from ietf.utils.accesstoken import generate_random_key, generate_access_token
from ietf.utils.text import parse_unicode
from ietf.utils.models import ForeignKey from ietf.utils.models import ForeignKey
@ -25,7 +26,7 @@ def parse_email_line(line):
email.utils.parseaddr() but return a dictionary email.utils.parseaddr() but return a dictionary
""" """
name, addr = email.utils.parseaddr(line) if '@' in line else (line, '') name, addr = email.utils.parseaddr(line) if '@' in line else (line, '')
return dict(name=name, email=addr) return dict(name=parse_unicode(name), email=addr)
class Submission(models.Model): class Submission(models.Model):
state = ForeignKey(DraftSubmissionStateName) state = ForeignKey(DraftSubmissionStateName)
@ -169,4 +170,4 @@ class SubmissionEmailEvent(SubmissionEvent):
class SubmissionExtResource(ExtResource): class SubmissionExtResource(ExtResource):
submission = ForeignKey(Submission, related_name='external_resources') submission = ForeignKey(Submission, related_name='external_resources')

View file

@ -41,6 +41,7 @@ from ietf.utils import log
from ietf.utils.accesstoken import generate_random_key from ietf.utils.accesstoken import generate_random_key
from ietf.utils.draft import Draft from ietf.utils.draft import Draft
from ietf.utils.mail import is_valid_email from ietf.utils.mail import is_valid_email
from ietf.utils.text import parse_unicode
from ietf.person.name import unidecode_name from ietf.person.name import unidecode_name
@ -886,7 +887,7 @@ def accept_submission(request, submission, autopost=False):
requires_prev_ad_approval = False requires_prev_ad_approval = False
# Partial message for submission event # Partial message for submission event
sub_event_desc = 'Set submitter to \"%s\", replaces to %s' % (submission.submitter, pretty_replaces) sub_event_desc = 'Set submitter to \"%s\", replaces to %s' % (parse_unicode(submission.submitter), pretty_replaces)
docevent_desc = None docevent_desc = None
address_list = [] address_list = []
if requires_ad_approval or requires_prev_ad_approval: if requires_ad_approval or requires_prev_ad_approval:

View file

@ -43,6 +43,7 @@ from ietf.utils.log import unreachable, assertion
from ietf.utils.mail import send_mail_preformatted, send_mail_text, send_mail_mime, outbox, get_payload_text from ietf.utils.mail import send_mail_preformatted, send_mail_text, send_mail_mime, outbox, get_payload_text
from ietf.utils.test_runner import get_template_paths, set_coverage_checking from ietf.utils.test_runner import get_template_paths, set_coverage_checking
from ietf.utils.test_utils import TestCase from ietf.utils.test_utils import TestCase
from ietf.utils.text import parse_unicode
skip_wiki_glue_testing = False skip_wiki_glue_testing = False
skip_message_svn = "" skip_message_svn = ""
@ -506,3 +507,21 @@ class LogUtilTests(TestCase):
settings.SERVER_MODE = 'development' settings.SERVER_MODE = 'development'
assertion('False') assertion('False')
settings.SERVER_MODE = 'test' settings.SERVER_MODE = 'test'
class TestRFC2047Strings(TestCase):
def test_parse_unicode(self):
names = (
('=?utf-8?b?4Yuz4YuK4Ym1IOGJoOGJgOGIiA==?=', 'ዳዊት በቀለ'),
('=?utf-8?b?5Li9IOmDnA==?=', '丽 郜'),
('=?utf-8?b?4KSV4KSu4KWN4KSs4KWL4KScIOCkoeCkvuCksA==?=', 'कम्बोज डार'),
('=?utf-8?b?zpfPgc6szrrOu861zrnOsSDOm865z4zOvc+Ezrc=?=', 'Ηράκλεια Λιόντη'),
('=?utf-8?b?15nXqdeo15DXnCDXqNeV15bXoNek15zXkw==?=', 'ישראל רוזנפלד'),
('=?utf-8?b?5Li95Y2OIOeahw==?=', '丽华 皇'),
('=?utf-8?b?77ul77qu766V77qzIO+tlu+7ru+vvu+6ju+7pw==?=', 'ﻥﺮﮕﺳ ﭖﻮﯾﺎﻧ'),
('=?utf-8?b?77uh77uu77qz77uu76++IO+6su+7tO+7p++6jSDvurDvu6Pvuo7vu6jvr74=?=', 'ﻡﻮﺳﻮﯾ ﺲﻴﻧﺍ ﺰﻣﺎﻨﯾ'),
('=?utf-8?b?ScOxaWdvIFNhbsOnIEliw6HDsWV6IGRlIGxhIFBlw7Fh?=', 'Iñigo Sanç Ibáñez de la Peña'),
('Mart van Oostendorp', 'Mart van Oostendorp'),
('', ''),
)
for encoded_str, unicode in names:
self.assertEqual(unicode, parse_unicode(encoded_str))

View file

@ -2,6 +2,7 @@
# -*- coding: utf-8 -*- # -*- coding: utf-8 -*-
import email
import re import re
import textwrap import textwrap
import unicodedata import unicodedata
@ -193,3 +194,16 @@ def unwrap(s):
def normalize_text(s): def normalize_text(s):
return re.sub(r'[\s\n\r\u2028\u2029]+', ' ', s, flags=re.U).strip() return re.sub(r'[\s\n\r\u2028\u2029]+', ' ', s, flags=re.U).strip()
def parse_unicode(text):
"Decodes unicode string from string encoded according to RFC2047"
decoded_string, charset = email.header.decode_header(text)[0]
if charset is not None:
try:
text = decoded_string.decode(charset)
except UnicodeDecodeError:
pass
else:
text = decoded_string
return text