#26645: Errors when running i18n makemessages tests on Windows
--------------------------------------+------------------------------------
Reporter: ramiro | Owner: ramiro
Type: Bug | Status: assigned
Component: Internationalization | Version: master
Severity: Normal | Resolution:
Keywords: windows makemessages | Triage Stage: Accepted
Has patch: 0 | Needs documentation: 0
Needs tests: 0 | Patch needs improvement: 0
Easy pickings: 0 | UI/UX: 0
--------------------------------------+------------------------------------
Comment (by ramiro):
AFAICS what happens on Windows is that by not passing `universal_newlines`
to `subprocess.Popen()` as we are doing since
fa08d27fb714534670b431fde0cd04a17d637585 the in -memory representation of
text content we capture from the standard output of `xgettext(1)`,
`msgmerge(1)`, etc. on this platform contains native line ending sequences
and not simply `\n`.
(All examples below are running the
`i18n.test_extraction.BasicExtractorTests.test_blocktrans_trimmed` test
case)
Blob of text that reaches
`django.core.management.commands.makemessages.write_pot_file()`:
{{{
(Pdb) msgs
u'# SOME DESCRIPTIVE TITLE.\r\n# Copyright (C) YEAR THE PACKAGE\'S
COPYRIGHT HOLDER\r\n# This file is distributed under the same license as
the PACKAGE package.\r\n# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.\r\n#\r\n#,
fuzzy\r\nmsgid ""\r\nmsgstr ""\r\n
}}}
Note the native `\r\n` line ending sequences.
Then, the temporary `.pot` file
(`test\i18n\test_extraction\commands\locale\django.pot`) is written. As we
open it in text mode (we can't open it in either binary or universal
newlines modes because we are passing the ''encoding'' parameter to
``io.open()``) the `\n` sequences are replaced with `\r\n` ones resulting
in lines separated by `\r\r\n`, e.g. (output of `hd(1)` on Linux,
`django.pot` transferred from the Windows system):
{{{
$ hd -n 240 django.pot
00000000 23 20 53 4f 4d 45 20 44 45 53 43 52 49 50 54 49 |# SOME
DESCRIPTI|
00000010 56 45 20 54 49 54 4c 45 2e 0d 0d 0a 23 20 43 6f |VE TITLE....#
Co|
00000020 70 79 72 69 67 68 74 20 28 43 29 20 59 45 41 52 |pyright (C)
YEAR|
00000030 20 54 48 45 20 50 41 43 4b 41 47 45 27 53 20 43 | THE
PACKAGE'S C|
00000040 4f 50 59 52 49 47 48 54 20 48 4f 4c 44 45 52 0d |OPYRIGHT
HOLDER.|
00000050 0d 0a 23 20 54 68 69 73 20 66 69 6c 65 20 69 73 |..# This file
is|
00000060 20 64 69 73 74 72 69 62 75 74 65 64 20 75 6e 64 | distributed
und|
00000070 65 72 20 74 68 65 20 73 61 6d 65 20 6c 69 63 65 |er the same
lice|
00000080 6e 73 65 20 61 73 20 74 68 65 20 50 41 43 4b 41 |nse as the
PACKA|
00000090 47 45 20 70 61 63 6b 61 67 65 2e 0d 0d 0a 23 20 |GE
package....# |
000000a0 46 49 52 53 54 20 41 55 54 48 4f 52 20 3c 45 4d |FIRST AUTHOR
<EM|
000000b0 41 49 4c 40 41 44 44 52 45 53 53 3e 2c 20 59 45 |AIL@ADDRESS>,
YE|
000000c0 41 52 2e 0d 0d 0a 23 0d 0d 0a 23 2c 20 66 75 7a |AR....#...#,
fuz|
000000d0 7a 79 0d 0d 0a 6d 73 67 69 64 20 22 22 0d 0d 0a |zy...msgid
""...|
000000e0 6d 73 67 73 74 72 20 22 22 0d 0d 0a 22 50 72 6f |msgstr
""..."Pro|
}}}
From this stage of the message extraction process onwards:
1. With each update of the on-disk ancillary temporary POT file additional
`\r` chars are accumulated. In the mentioned test case it ends with
`\r\r\r\r\n` line separators.
2. As further `popen_wrapper` calls are performed (i.e. to call
`msgmerge(1)` or `msguniq(1)`), problem 1 above gets carried to the final
`.po` file(s) and somehow results in multiple `\r\n` inserted:
This is the final
`test\i18n\test_extraction\commands\locale\de\LC_MESSAGES\django.po`:
{{{
$ hd -n 312 django.po
00000000 23 20 53 4f 4d 45 20 44 45 53 43 52 49 50 54 49 |# SOME
DESCRIPTI|
00000010 56 45 20 54 49 54 4c 45 2e 0d 0a 22 50 6c 75 72 |VE
TITLE..."Plur|
00000020 61 6c 2d 46 6f 72 6d 73 3a 20 6e 70 6c 75 72 61 |al-Forms:
nplura|
00000030 6c 73 3d 32 3b 20 70 6c 75 72 61 6c 3d 28 6e 20 |ls=2;
plural=(n |
00000040 21 3d 20 31 29 3b 5c 6e 22 0d 0a 0d 0a 0d 0a 0d |!=
1);\n".......|
00000050 0a 23 20 43 6f 70 79 72 69 67 68 74 20 28 43 29 |.# Copyright
(C)|
00000060 20 59 45 41 52 20 54 48 45 20 50 41 43 4b 41 47 | YEAR THE
PACKAG|
00000070 45 27 53 20 43 4f 50 59 52 49 47 48 54 20 48 4f |E'S COPYRIGHT
HO|
00000080 4c 44 45 52 0d 0a 0d 0a 0d 0a 0d 0a 23 20 54 68 |LDER........#
Th|
00000090 69 73 20 66 69 6c 65 20 69 73 20 64 69 73 74 72 |is file is
distr|
000000a0 69 62 75 74 65 64 20 75 6e 64 65 72 20 74 68 65 |ibuted under
the|
000000b0 20 73 61 6d 65 20 6c 69 63 65 6e 73 65 20 61 73 | same license
as|
000000c0 20 74 68 65 20 50 41 43 4b 41 47 45 20 70 61 63 | the PACKAGE
pac|
000000d0 6b 61 67 65 2e 0d 0a 0d 0a 0d 0a 0d 0a 23 20 46
|kage.........# F|
000000e0 49 52 53 54 20 41 55 54 48 4f 52 20 3c 45 4d 41 |IRST AUTHOR
<EMA|
000000f0 49 4c 40 41 44 44 52 45 53 53 3e 2c 20 59 45 41 |IL@ADDRESS>,
YEA|
00000100 52 2e 0d 0a 0d 0a 0d 0a 0d 0a 23 20 0d 0a 0d 0a |R.........#
....|
00000110 0d 0a 0d 0a 23 2c 20 66 75 7a 7a 79 0d 0a 0d 0a |....#,
fuzzy....|
00000120 6d 73 67 69 64 20 22 22 0d 0a 0d 0a 6d 73 67 73 |msgid
""....msgs|
00000130 74 72 20 22 22 0d 0a 0d |tr ""...|
}}}
3. The newly added newlines confuse `copy_plural_forms()` (see above) and
the code in charge setting of the `charset` value on the PO header to
`utf-8`. '''This is what causes the symptom reported by this ticket''':
`django.po:2:47: syntax error -- msgmerge: found 1 fatal error`
#25667 was about the inability to handle error output of `msgfmt(1)` which
is actually invoked from `compilemessages` buf the removal of the
`gettext_popen_wrapper` function (which was the one passing
`universal_newlines` to `subprocess.Popen()`) introduced this unintended
effect.
One possible path would be to re-introduce `universal_newlines` only for
the handling of the gettext tools used by `makemessages` which, unlike the
`compilemenssages`/`msgmft(1)`, do actually spew POT and PO content in-
band; but I'm afraid to do that given the difficulties we've experienced
on this front, see #20271, 6fb9dee470d57882e378247fd2706d5f9867b5f9 and
57202a112a966593857725071ecd652a87c157fb for some examples.
I'm working on an alternate approach. Will update this ticket with the
link to a PR.
--
Ticket URL: <https://code.djangoproject.com/ticket/26645#comment:3>
Django <https://code.djangoproject.com/>
The Web framework for perfectionists with deadlines.
--
You received this message because you are subscribed to the Google Groups
"Django updates" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To post to this group, send email to [email protected].
To view this discussion on the web visit
https://groups.google.com/d/msgid/django-updates/064.5e66df77b375a111735d815b37c2c809%40djangoproject.com.
For more options, visit https://groups.google.com/d/optout.