I am working on a django application, which need to support multiple languages. This application involves some amount of javascript code. In this javascript code, there are some multi-line strings, which need to be translated.
We have tried this structure:
var $text = gettext('Lorem ipsum dolor sit amet, consectetur adipisicing ' +
'elit, sed do eiusmod tempor incididunt ut labore et ' +
'dolore magna aliqua. Ut enim ad minim veniam, quis ');
This does not work. makemessages
stops at the first +
sign, so in the .po
file it shows up as:
msgid "Lorem ipsum dolor sit amet, consectetur adipisicing "
A bit of searching on the net lead to a style guide, which recommends the format we are already using for multi-line strings. But that style is not supported by makemessages
.
I tried removing the +
characters at the end of the lines. Without the +
characters, makemessages
can find the full string, but it no longer works in the browser.
Does there exist a style for multi-line strings, which is both supported by makemessages
and can be expected to work in all major browsers?
So far I have found that what makemessages
is actually doing is to replace all single-quoted strings with double-quoted strings and runs the result through xgettext
claiming it to be C code.
The reason it doesn't work automatically is that makemessages
doesn't use a real javascript parser. It does a minor transformation and applies a C parser. But in order to concatenate strings in javascript you need a +
character, but in C you must not have any tokens between the strings to be concatenated.
I finally found a workaround, that works:
var $text = gettext('Lorem ipsum dolor sit amet, consectetur adipisicing ' //\
+
'elit, sed do eiusmod tempor incididunt ut labore et ' //\
+
'dolore magna aliqua. Ut enim ad minim veniam, quis ');
The javascript parser in the browser will see //\
as a comment, and find +
characters between each string as needed. When using makemessages
the \
character is parsed as line continuation, and both //\
as well as the +
on the following line is considered to be a single comment. So the parser sees string constants separated by just a comment, and implicit string concatenation is performed.
I found this workaround by accident as I came across this piece of code from a fellow developer:
// IE8 only allows string, identifier and number keys between {}s
var parse_bool = {"null": null, "true": true, "false": false}
parse_bool[undefined] = null
parse_bool[null] = null // using null/true/false *this* way works
parse_bool[true] = true // _______
parse_bool[false] = false // ( WAT?! )
// ¯¯¯¯¯¯¯ o ^__^
var render_bool = {} // o (oo)\_______
render_bool[null] = '--' // (__)\ )\/\
render_bool[true] = gettext('yes') // ||----w |
render_bool[false] = gettext('no') // || ||
When makemessages
was processing this piece of javascript code, it missed the yes
string.