From c9f657c744c19be02a6b2190a9f4227fd849a9d9 Mon Sep 17 00:00:00 2001 From: Tomas Roun Date: Sun, 16 Mar 2025 23:46:27 +0100 Subject: [PATCH 1/5] Test pygettext --escape option --- Lib/test/test_tools/i18n_data/escapes.pot | 33 +++++++ Lib/test/test_tools/i18n_data/escapes.py | 10 ++ Lib/test/test_tools/i18n_data/messages.pot | 4 + Lib/test/test_tools/i18n_data/messages.py | 3 + Lib/test/test_tools/test_i18n.py | 109 ++++++++++++++++++++- Tools/i18n/pygettext.py | 2 +- 6 files changed, 159 insertions(+), 2 deletions(-) create mode 100644 Lib/test/test_tools/i18n_data/escapes.pot create mode 100644 Lib/test/test_tools/i18n_data/escapes.py diff --git a/Lib/test/test_tools/i18n_data/escapes.pot b/Lib/test/test_tools/i18n_data/escapes.pot new file mode 100644 index 00000000000000..54a04f4c1907bc --- /dev/null +++ b/Lib/test/test_tools/i18n_data/escapes.pot @@ -0,0 +1,33 @@ +# SOME DESCRIPTIVE TITLE. +# Copyright (C) YEAR ORGANIZATION +# FIRST AUTHOR , YEAR. +# +msgid "" +msgstr "" +"Project-Id-Version: PACKAGE VERSION\n" +"POT-Creation-Date: 2000-01-01 00:00+0000\n" +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" +"Last-Translator: FULL NAME \n" +"Language-Team: LANGUAGE \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Generated-By: pygettext.py 1.5\n" + + +#: escapes.py:4 +msgid "ascii" +msgstr "" + +#: escapes.py:6 +msgid "\304\233 \305\241 \304\215 \305\231" +msgstr "" + +#: escapes.py:8 +msgid "\316\261 \316\262 \316\263 \316\264" +msgstr "" + +#: escapes.py:10 +msgid "\343\204\261 \343\204\262 \343\204\264 \343\204\267" +msgstr "" + diff --git a/Lib/test/test_tools/i18n_data/escapes.py b/Lib/test/test_tools/i18n_data/escapes.py new file mode 100644 index 00000000000000..d742d2eb459c31 --- /dev/null +++ b/Lib/test/test_tools/i18n_data/escapes.py @@ -0,0 +1,10 @@ +import gettext as _ + + +_('ascii') + +_('ě š č ř') + +_('α β γ δ') + +_('ㄱ ㄲ ㄴ ㄷ') diff --git a/Lib/test/test_tools/i18n_data/messages.pot b/Lib/test/test_tools/i18n_data/messages.pot index e8167acfc0742b..e16e200cad7ded 100644 --- a/Lib/test/test_tools/i18n_data/messages.pot +++ b/Lib/test/test_tools/i18n_data/messages.pot @@ -97,3 +97,7 @@ msgid_plural "worlds" msgstr[0] "" msgstr[1] "" +#: messages.py:122 +msgid "α β γ δ" +msgstr "" + diff --git a/Lib/test/test_tools/i18n_data/messages.py b/Lib/test/test_tools/i18n_data/messages.py index 9457bcb8611020..7b67b6fadcdfbf 100644 --- a/Lib/test/test_tools/i18n_data/messages.py +++ b/Lib/test/test_tools/i18n_data/messages.py @@ -117,3 +117,6 @@ def _(x="don't extract me"): # f-strings f"Hello, {_('world')}!" f"Hello, {ngettext('world', 'worlds', 3)}!" + +# non-ascii +_("α β γ δ") diff --git a/Lib/test/test_tools/test_i18n.py b/Lib/test/test_tools/test_i18n.py index 2ba086109d30ab..2616fae1273445 100644 --- a/Lib/test/test_tools/test_i18n.py +++ b/Lib/test/test_tools/test_i18n.py @@ -18,7 +18,8 @@ with imports_under_tool("i18n"): - from pygettext import parse_spec + import pygettext + from pygettext import make_escapes, parse_spec def normalize_POT_file(pot): @@ -517,6 +518,110 @@ def test_parse_keyword_spec(self): self.assertEqual(str(cm.exception), message) +class TestCharacterEscapes(unittest.TestCase): + # Pygettext always escapes the following characters: + special_chars = { + '\\': r'\\', + '\t': r'\t', + '\r': r'\r', + '\n': r'\n', + '\"': r'\"', + } + + def tearDownClass(): + # Reset the global 'escapes' dict to the default + make_escapes(pass_nonascii=True) + + def test_special_chars(self): + # special_chars are always escaped regardless of the + # --escape option + for pass_nonascii in (True, False): + make_escapes(pass_nonascii=pass_nonascii) + with self.subTest(pass_nonascii=pass_nonascii): + for char in self.special_chars: + self.assertEqual(pygettext.escape(char, encoding='utf-8'), + self.special_chars[char]) + + def _char_to_octal_escape(self, char): + """Convert a character to its octal escape representation.""" + return r"\%03o" % ord(char) + + def _octal_escape_to_string(self, escaped): + """Convert an octal escape representation to string.""" + octal_escapes = re.findall(r'\\([0-7]{3})', escaped) + bytestr = bytes([int(n, 8) for n in octal_escapes]) + return bytestr.decode('utf-8') + + def test_not_escaped(self): + """ + Test escaping when the --escape is not used. + + When --escape is not used, only some characters withing the ASCII + range are escaoped. Characters >= 128 are not escaped. + """ + # This is the same as invoking pygettext without + # the --escape option (the default behavior). + make_escapes(pass_nonascii=True) + # The encoding option is not used when --escape is not passed + encoding = 'foo' + + # First 32 characters use octal escapes (except for special chars) + for i in range(32): + char = chr(i) + if char in self.special_chars: + continue + self.assertEqual(pygettext.escape(char, encoding=encoding), + self._char_to_octal_escape(char)) + + # Characters 32-126 are not escaped (except for special chars) + for i in range(32, 127): + char = chr(i) + if char in self.special_chars: + continue + self.assertEqual(pygettext.escape(char, encoding=encoding), char) + + # chr(127) uses octal escape + self.assertEqual(pygettext.escape(chr(127), encoding=encoding), + '\\177') + + # All characters >= 128 are not escaped + for i in range(128, 256): + char = chr(i) + self.assertEqual(pygettext.escape(char, encoding=encoding), char) + + + def test_escaped(self): + """ + Test escaping when --escape is used. + + When --escape is used, all characters are escaped, including + """ + make_escapes(pass_nonascii=False) + encoding = 'utf-8' + + # First 32 characters use octal escapes (except for special chars) + for i in range(32): + char = chr(i) + if char in self.special_chars: + continue + self.assertEqual(pygettext.escape(char, encoding=encoding), + self._char_to_octal_escape(char)) + + # Characters 32-126 are not escaped (except for special chars) + for i in range(32, 127): + char = chr(i) + if char in self.special_chars: + continue + self.assertEqual(pygettext.escape(char, encoding=encoding), char) + + # Characters >= 127 are escaped + for i in range(127, 256): + char = chr(i) + escaped = pygettext.escape(char, encoding=encoding) + decoded_char = self._octal_escape_to_string(escaped) + self.assertEqual(char, decoded_char) + + def extract_from_snapshots(): snapshots = { 'messages.py': (), @@ -526,6 +631,8 @@ def extract_from_snapshots(): 'custom_keywords.py': ('--keyword=foo', '--keyword=nfoo:1,2', '--keyword=pfoo:1c,2', '--keyword=npfoo:1c,2,3', '--keyword=_:1,2'), + # Test escaping non-ASCII characters + 'escapes.py': ('--escape',), } for filename, args in snapshots.items(): diff --git a/Tools/i18n/pygettext.py b/Tools/i18n/pygettext.py index 0ec257020918b1..f0ee2ea386f18f 100755 --- a/Tools/i18n/pygettext.py +++ b/Tools/i18n/pygettext.py @@ -188,7 +188,7 @@ def make_escapes(pass_nonascii): global escapes, escape if pass_nonascii: # Allow non-ascii characters to pass through so that e.g. 'msgid - # "Höhe"' would result not result in 'msgid "H\366he"'. Otherwise we + # "Höhe"' would not result in 'msgid "H\366he"'. Otherwise we # escape any character outside the 32..126 range. mod = 128 escape = escape_ascii From bcd8f0b5894d1ff014b51ecfba0e2432752cfd0e Mon Sep 17 00:00:00 2001 From: Tomas Roun Date: Mon, 31 Mar 2025 21:26:27 +0200 Subject: [PATCH 2/5] Remove extra newline --- Lib/test/test_tools/test_i18n.py | 1 - 1 file changed, 1 deletion(-) diff --git a/Lib/test/test_tools/test_i18n.py b/Lib/test/test_tools/test_i18n.py index 2616fae1273445..56ec78d8427aee 100644 --- a/Lib/test/test_tools/test_i18n.py +++ b/Lib/test/test_tools/test_i18n.py @@ -589,7 +589,6 @@ def test_not_escaped(self): char = chr(i) self.assertEqual(pygettext.escape(char, encoding=encoding), char) - def test_escaped(self): """ Test escaping when --escape is used. From c56f72c74eebaf98f3c967df03254830236f5535 Mon Sep 17 00:00:00 2001 From: Tomas Roun Date: Mon, 31 Mar 2025 21:47:16 +0200 Subject: [PATCH 3/5] Just use escapes.pot for everything --- .../test_tools/i18n_data/ascii-escapes.pot | 51 ++++++++ Lib/test/test_tools/i18n_data/escapes.pot | 34 +++-- Lib/test/test_tools/i18n_data/escapes.py | 24 +++- Lib/test/test_tools/test_i18n.py | 119 ++---------------- 4 files changed, 109 insertions(+), 119 deletions(-) create mode 100644 Lib/test/test_tools/i18n_data/ascii-escapes.pot diff --git a/Lib/test/test_tools/i18n_data/ascii-escapes.pot b/Lib/test/test_tools/i18n_data/ascii-escapes.pot new file mode 100644 index 00000000000000..55d2407f94e5ed --- /dev/null +++ b/Lib/test/test_tools/i18n_data/ascii-escapes.pot @@ -0,0 +1,51 @@ +# SOME DESCRIPTIVE TITLE. +# Copyright (C) YEAR ORGANIZATION +# FIRST AUTHOR , YEAR. +# +msgid "" +msgstr "" +"Project-Id-Version: PACKAGE VERSION\n" +"POT-Creation-Date: 2000-01-01 00:00+0000\n" +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" +"Last-Translator: FULL NAME \n" +"Language-Team: LANGUAGE \n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=UTF-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Generated-By: pygettext.py 1.5\n" + + +#. Special characters that are always escaped in the POT file +#: escapes.py:5 +msgid "" +"\"\t\n" +"\r\\" +msgstr "" + +#. All ascii characters 0-31 +#: escapes.py:8 +msgid "" +"\000\001\002\003\004\005\006\007\010\t\n" +"\013\014\r\016\017\020\021\022\023\024\025\026\027\030\031\032\033\034\035\036\037" +msgstr "" + +#. All ascii characters 32-126 +#: escapes.py:13 +msgid " !\"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\\]^_`abcdefghijklmnopqrstuvwxyz{|}~" +msgstr "" + +#. ascii char 127 +#: escapes.py:17 +msgid "\177" +msgstr "" + +#. characters 128-255 +#: escapes.py:20 +msgid "€‚ƒ„…†‡ˆ‰Š‹ŒŽ‘’“”•–—˜™š›œžŸ ¡¢£¤¥¦§¨©ª«¬­®¯°±²³´µ¶·¸¹º»¼½¾¿ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖרÙÚÛÜÝÞßàáâãäåæçèéêëìíîïðñòóôõö÷øùúûüýþÿ" +msgstr "" + +#. some characters >= 256 +#: escapes.py:26 +msgid "ě š č ř α β γ δ ㄱ ㄲ ㄴ ㄷ" +msgstr "" + diff --git a/Lib/test/test_tools/i18n_data/escapes.pot b/Lib/test/test_tools/i18n_data/escapes.pot index 54a04f4c1907bc..18d72d0d8248a9 100644 --- a/Lib/test/test_tools/i18n_data/escapes.pot +++ b/Lib/test/test_tools/i18n_data/escapes.pot @@ -15,19 +15,37 @@ msgstr "" "Generated-By: pygettext.py 1.5\n" -#: escapes.py:4 -msgid "ascii" +#. Special characters that are always escaped in the POT file +#: escapes.py:5 +msgid "" +"\"\t\n" +"\r\\" msgstr "" -#: escapes.py:6 -msgid "\304\233 \305\241 \304\215 \305\231" +#. All ascii characters 0-31 +#: escapes.py:8 +msgid "" +"\000\001\002\003\004\005\006\007\010\t\n" +"\013\014\r\016\017\020\021\022\023\024\025\026\027\030\031\032\033\034\035\036\037" msgstr "" -#: escapes.py:8 -msgid "\316\261 \316\262 \316\263 \316\264" +#. All ascii characters 32-126 +#: escapes.py:13 +msgid " !\"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\\]^_`abcdefghijklmnopqrstuvwxyz{|}~" +msgstr "" + +#. ascii char 127 +#: escapes.py:17 +msgid "\177" +msgstr "" + +#. characters 128-255 +#: escapes.py:20 +msgid "\302\200\302\201\302\202\302\203\302\204\302\205\302\206\302\207\302\210\302\211\302\212\302\213\302\214\302\215\302\216\302\217\302\220\302\221\302\222\302\223\302\224\302\225\302\226\302\227\302\230\302\231\302\232\302\233\302\234\302\235\302\236\302\237\302\240\302\241\302\242\302\243\302\244\302\245\302\246\302\247\302\250\302\251\302\252\302\253\302\254\302\255\302\256\302\257\302\260\302\261\302\262\302\263\302\264\302\265\302\266\302\267\302\270\302\271\302\272\302\273\302\274\302\275\302\276\302\277\303\200\303\201\303\202\303\203\303\204\303\205\303\206\303\207\303\210\303\211\303\212\303\213\303\214\303\215\303\216\303\217\303\220\303\221\303\222\303\223\303\224\303\225\303\226\303\227\303\230\303\231\303\232\303\233\303\234\303\235\303\236\303\237\303\240\303\241\303\242\303\243\303\244\303\245\303\246\303\247\303\250\303\251\303\252\303\253\303\254\303\255\303\256\303\257\303\260\303\261\303\262\303\263\303\264\303\265\303\266\303\267\303\270\303\271\303\272\303\273\303\274\303\275\303\276\303\277" msgstr "" -#: escapes.py:10 -msgid "\343\204\261 \343\204\262 \343\204\264 \343\204\267" +#. some characters >= 256 +#: escapes.py:26 +msgid "\304\233 \305\241 \304\215 \305\231 \316\261 \316\262 \316\263 \316\264 \343\204\261 \343\204\262 \343\204\264 \343\204\267" msgstr "" diff --git a/Lib/test/test_tools/i18n_data/escapes.py b/Lib/test/test_tools/i18n_data/escapes.py index d742d2eb459c31..03c96b7682258d 100644 --- a/Lib/test/test_tools/i18n_data/escapes.py +++ b/Lib/test/test_tools/i18n_data/escapes.py @@ -1,10 +1,26 @@ import gettext as _ -_('ascii') +# Special characters that are always escaped in the POT file +_('"\t\n\r\\') -_('ě š č ř') +# All ascii characters 0-31 +_('\x00\x01\x02\x03\x04\x05\x06\x07\x08\t\n' + '\x0b\x0c\r\x0e\x0f\x10\x11\x12\x13\x14\x15' + '\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f') -_('α β γ δ') +# All ascii characters 32-126 +_(' !"#$%&\'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ' + '[\\]^_`abcdefghijklmnopqrstuvwxyz{|}~') -_('ㄱ ㄲ ㄴ ㄷ') +# ascii char 127 +_('\x7f') + +# characters 128-255 +_('\x80\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8a\x8b\x8c\x8d\x8e\x8f\x90' + '\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9a\x9b\x9c\x9d\x9e\x9f\xa0' + '¡¢£¤¥¦§¨©ª«¬\xad®¯°±²³´µ¶·¸¹º»¼½¾¿ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖרÙÚÛÜÝÞ' + 'ßàáâãäåæçèéêëìíîïðñòóôõö÷øùúûüýþÿ') + +# some characters >= 256 +_('ě š č ř α β γ δ ㄱ ㄲ ㄴ ㄷ') diff --git a/Lib/test/test_tools/test_i18n.py b/Lib/test/test_tools/test_i18n.py index 56ec78d8427aee..ab7edb7cc135a5 100644 --- a/Lib/test/test_tools/test_i18n.py +++ b/Lib/test/test_tools/test_i18n.py @@ -518,109 +518,6 @@ def test_parse_keyword_spec(self): self.assertEqual(str(cm.exception), message) -class TestCharacterEscapes(unittest.TestCase): - # Pygettext always escapes the following characters: - special_chars = { - '\\': r'\\', - '\t': r'\t', - '\r': r'\r', - '\n': r'\n', - '\"': r'\"', - } - - def tearDownClass(): - # Reset the global 'escapes' dict to the default - make_escapes(pass_nonascii=True) - - def test_special_chars(self): - # special_chars are always escaped regardless of the - # --escape option - for pass_nonascii in (True, False): - make_escapes(pass_nonascii=pass_nonascii) - with self.subTest(pass_nonascii=pass_nonascii): - for char in self.special_chars: - self.assertEqual(pygettext.escape(char, encoding='utf-8'), - self.special_chars[char]) - - def _char_to_octal_escape(self, char): - """Convert a character to its octal escape representation.""" - return r"\%03o" % ord(char) - - def _octal_escape_to_string(self, escaped): - """Convert an octal escape representation to string.""" - octal_escapes = re.findall(r'\\([0-7]{3})', escaped) - bytestr = bytes([int(n, 8) for n in octal_escapes]) - return bytestr.decode('utf-8') - - def test_not_escaped(self): - """ - Test escaping when the --escape is not used. - - When --escape is not used, only some characters withing the ASCII - range are escaoped. Characters >= 128 are not escaped. - """ - # This is the same as invoking pygettext without - # the --escape option (the default behavior). - make_escapes(pass_nonascii=True) - # The encoding option is not used when --escape is not passed - encoding = 'foo' - - # First 32 characters use octal escapes (except for special chars) - for i in range(32): - char = chr(i) - if char in self.special_chars: - continue - self.assertEqual(pygettext.escape(char, encoding=encoding), - self._char_to_octal_escape(char)) - - # Characters 32-126 are not escaped (except for special chars) - for i in range(32, 127): - char = chr(i) - if char in self.special_chars: - continue - self.assertEqual(pygettext.escape(char, encoding=encoding), char) - - # chr(127) uses octal escape - self.assertEqual(pygettext.escape(chr(127), encoding=encoding), - '\\177') - - # All characters >= 128 are not escaped - for i in range(128, 256): - char = chr(i) - self.assertEqual(pygettext.escape(char, encoding=encoding), char) - - def test_escaped(self): - """ - Test escaping when --escape is used. - - When --escape is used, all characters are escaped, including - """ - make_escapes(pass_nonascii=False) - encoding = 'utf-8' - - # First 32 characters use octal escapes (except for special chars) - for i in range(32): - char = chr(i) - if char in self.special_chars: - continue - self.assertEqual(pygettext.escape(char, encoding=encoding), - self._char_to_octal_escape(char)) - - # Characters 32-126 are not escaped (except for special chars) - for i in range(32, 127): - char = chr(i) - if char in self.special_chars: - continue - self.assertEqual(pygettext.escape(char, encoding=encoding), char) - - # Characters >= 127 are escaped - for i in range(127, 256): - char = chr(i) - escaped = pygettext.escape(char, encoding=encoding) - decoded_char = self._octal_escape_to_string(escaped) - self.assertEqual(char, decoded_char) - - def extract_from_snapshots(): snapshots = { 'messages.py': (), @@ -630,13 +527,21 @@ def extract_from_snapshots(): 'custom_keywords.py': ('--keyword=foo', '--keyword=nfoo:1,2', '--keyword=pfoo:1c,2', '--keyword=npfoo:1c,2,3', '--keyword=_:1,2'), - # Test escaping non-ASCII characters - 'escapes.py': ('--escape',), + # == Test character escaping + # Escape ascii and unicode: + 'escapes.py': ('--escape', '--add-comments='), + # Escape only ascii and let unicode pass through: + ('escapes.py', 'ascii-escapes.pot'): ('--add-comments=',), } for filename, args in snapshots.items(): - input_file = DATA_DIR / filename - output_file = input_file.with_suffix('.pot') + if isinstance(filename, tuple): + filename, output_file = filename + output_file = DATA_DIR / output_file + input_file = DATA_DIR / filename + else: + input_file = DATA_DIR / filename + output_file = input_file.with_suffix('.pot') contents = input_file.read_bytes() with temp_cwd(None): Path(input_file.name).write_bytes(contents) From 8651e814c48573fa20789e7fcd3e1adb5041c4c4 Mon Sep 17 00:00:00 2001 From: Tomas Roun Date: Mon, 31 Mar 2025 21:57:24 +0200 Subject: [PATCH 4/5] Clean up --- Lib/test/test_tools/i18n_data/messages.pot | 4 ---- Lib/test/test_tools/i18n_data/messages.py | 3 --- Lib/test/test_tools/test_i18n.py | 3 +-- 3 files changed, 1 insertion(+), 9 deletions(-) diff --git a/Lib/test/test_tools/i18n_data/messages.pot b/Lib/test/test_tools/i18n_data/messages.pot index e16e200cad7ded..e8167acfc0742b 100644 --- a/Lib/test/test_tools/i18n_data/messages.pot +++ b/Lib/test/test_tools/i18n_data/messages.pot @@ -97,7 +97,3 @@ msgid_plural "worlds" msgstr[0] "" msgstr[1] "" -#: messages.py:122 -msgid "α β γ δ" -msgstr "" - diff --git a/Lib/test/test_tools/i18n_data/messages.py b/Lib/test/test_tools/i18n_data/messages.py index 7b67b6fadcdfbf..9457bcb8611020 100644 --- a/Lib/test/test_tools/i18n_data/messages.py +++ b/Lib/test/test_tools/i18n_data/messages.py @@ -117,6 +117,3 @@ def _(x="don't extract me"): # f-strings f"Hello, {_('world')}!" f"Hello, {ngettext('world', 'worlds', 3)}!" - -# non-ascii -_("α β γ δ") diff --git a/Lib/test/test_tools/test_i18n.py b/Lib/test/test_tools/test_i18n.py index ab7edb7cc135a5..66c33077423229 100644 --- a/Lib/test/test_tools/test_i18n.py +++ b/Lib/test/test_tools/test_i18n.py @@ -18,8 +18,7 @@ with imports_under_tool("i18n"): - import pygettext - from pygettext import make_escapes, parse_spec + from pygettext import parse_spec def normalize_POT_file(pot): From 1e05a6bf928bb505065258f959c909a769bd8afb Mon Sep 17 00:00:00 2001 From: Tomas Roun Date: Tue, 1 Apr 2025 22:47:14 +0200 Subject: [PATCH 5/5] Simplify tests --- Lib/test/test_tools/i18n_data/ascii-escapes.pot | 10 +++++----- Lib/test/test_tools/i18n_data/escapes.pot | 10 +++++----- Lib/test/test_tools/i18n_data/escapes.py | 11 ++++------- 3 files changed, 14 insertions(+), 17 deletions(-) diff --git a/Lib/test/test_tools/i18n_data/ascii-escapes.pot b/Lib/test/test_tools/i18n_data/ascii-escapes.pot index 55d2407f94e5ed..f8e0f53b256934 100644 --- a/Lib/test/test_tools/i18n_data/ascii-escapes.pot +++ b/Lib/test/test_tools/i18n_data/ascii-escapes.pot @@ -39,13 +39,13 @@ msgstr "" msgid "\177" msgstr "" -#. characters 128-255 +#. some characters in the 128-255 range #: escapes.py:20 -msgid "€‚ƒ„…†‡ˆ‰Š‹ŒŽ‘’“”•–—˜™š›œžŸ ¡¢£¤¥¦§¨©ª«¬­®¯°±²³´µ¶·¸¹º»¼½¾¿ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖרÙÚÛÜÝÞßàáâãäåæçèéêëìíîïðñòóôõö÷øùúûüýþÿ" +msgid "€   ÿ" msgstr "" -#. some characters >= 256 -#: escapes.py:26 -msgid "ě š č ř α β γ δ ㄱ ㄲ ㄴ ㄷ" +#. some characters >= 256 encoded as 2, 3 and 4 bytes, respectively +#: escapes.py:23 +msgid "α ㄱ 𓂀" msgstr "" diff --git a/Lib/test/test_tools/i18n_data/escapes.pot b/Lib/test/test_tools/i18n_data/escapes.pot index 18d72d0d8248a9..4dfac0f451ddcf 100644 --- a/Lib/test/test_tools/i18n_data/escapes.pot +++ b/Lib/test/test_tools/i18n_data/escapes.pot @@ -39,13 +39,13 @@ msgstr "" msgid "\177" msgstr "" -#. characters 128-255 +#. some characters in the 128-255 range #: escapes.py:20 -msgid "\302\200\302\201\302\202\302\203\302\204\302\205\302\206\302\207\302\210\302\211\302\212\302\213\302\214\302\215\302\216\302\217\302\220\302\221\302\222\302\223\302\224\302\225\302\226\302\227\302\230\302\231\302\232\302\233\302\234\302\235\302\236\302\237\302\240\302\241\302\242\302\243\302\244\302\245\302\246\302\247\302\250\302\251\302\252\302\253\302\254\302\255\302\256\302\257\302\260\302\261\302\262\302\263\302\264\302\265\302\266\302\267\302\270\302\271\302\272\302\273\302\274\302\275\302\276\302\277\303\200\303\201\303\202\303\203\303\204\303\205\303\206\303\207\303\210\303\211\303\212\303\213\303\214\303\215\303\216\303\217\303\220\303\221\303\222\303\223\303\224\303\225\303\226\303\227\303\230\303\231\303\232\303\233\303\234\303\235\303\236\303\237\303\240\303\241\303\242\303\243\303\244\303\245\303\246\303\247\303\250\303\251\303\252\303\253\303\254\303\255\303\256\303\257\303\260\303\261\303\262\303\263\303\264\303\265\303\266\303\267\303\270\303\271\303\272\303\273\303\274\303\275\303\276\303\277" +msgid "\302\200 \302\240 \303\277" msgstr "" -#. some characters >= 256 -#: escapes.py:26 -msgid "\304\233 \305\241 \304\215 \305\231 \316\261 \316\262 \316\263 \316\264 \343\204\261 \343\204\262 \343\204\264 \343\204\267" +#. some characters >= 256 encoded as 2, 3 and 4 bytes, respectively +#: escapes.py:23 +msgid "\316\261 \343\204\261 \360\223\202\200" msgstr "" diff --git a/Lib/test/test_tools/i18n_data/escapes.py b/Lib/test/test_tools/i18n_data/escapes.py index 03c96b7682258d..900bd97a70fdba 100644 --- a/Lib/test/test_tools/i18n_data/escapes.py +++ b/Lib/test/test_tools/i18n_data/escapes.py @@ -16,11 +16,8 @@ # ascii char 127 _('\x7f') -# characters 128-255 -_('\x80\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8a\x8b\x8c\x8d\x8e\x8f\x90' - '\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9a\x9b\x9c\x9d\x9e\x9f\xa0' - '¡¢£¤¥¦§¨©ª«¬\xad®¯°±²³´µ¶·¸¹º»¼½¾¿ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖרÙÚÛÜÝÞ' - 'ßàáâãäåæçèéêëìíîïðñòóôõö÷øùúûüýþÿ') +# some characters in the 128-255 range +_('\x80 \xa0 ÿ') -# some characters >= 256 -_('ě š č ř α β γ δ ㄱ ㄲ ㄴ ㄷ') +# some characters >= 256 encoded as 2, 3 and 4 bytes, respectively +_('α ㄱ 𓂀')