makemessages 命令搜索要翻译的文件并调用(x)gettext utility 以提取标记为要翻译的字符串。根据您告诉它使用django 还是djangojs --domain,它的行为会有所不同。
当使用django 域时,它会通过django.utils.translation.templatize 运行非.py 文件以“将Django 模板变成xgettext 可以理解的东西”)。它基本上将整个文件转换为XXXXX,除了词法分析器确定与gettext相关的部分,它保持行号不变,等等。
>>> from django.utils.translation import templatize
>>> content = """This is a {% trans "test" %}!
... {# Translators: these comments remain intact for translators #}
... {% blocktrans %}Only applies to --domain=django and non-.py files {% endblocktrans %}
...
... Everything else is {# ignored #}
... {% trans "EOM" %}
... :)"""
>>> print(templatize(content))
XXXX XX X gettext(u'test') X
# Translators: these comments remain intact for translators
gettext(u'Only applies to --domain=django and non-.py files ') SSSS SSSSSSS SS SSSSSSSSSSSSSSS SSS SSSSSSS SSSSS
XXXXXXXXXX XXXX XX
gettext(u'EOM')
XX
>>>
因此,对于大多数非 Python、非 Django 模板文件,这将消除您的可翻译内容。
当使用djangojs 域时,Django 不会对文件执行任何此类预处理。 (对于早于0.18.3 的gettext 版本,makemessages 将调用django.utils.jslex.prepare_js_for_gettext,这会稍微不那么激进,如果需要,只需调整任何转义/正则表达式语法。
如果你运行makemessages -a -d djangojs -e "js,vue",Django 将告诉xgettext 使用--language=JavaScript 和一定数量的额外--keyword 配置来解析你的.js 和.vue 文件以支持gettext_noop、gettext_lazy等(gettext 默认为 keywordspec 的 _, gettext, dgettext:2, dcgettext:2, ngettext:1,2, dngettext:2,3, pgettext:1c,2, dpgettext:2c,3 为 JavaScript)。 makemessages 也将传递 --from-code=UTF-8 和 --add-comments=Translators 参数。
然后交给gettext根据这些规范进行解析,并根据--language指定的文件自己理解。
因此,使用makemessages 翻译.txt、.xml 等文件的最佳选择是使用djangojs 域并查看gettext 基于--language=JavaScript 得到什么,所以你会标记你的字符串就像你对 JavaScript 一样。
或者对于 Jinja2 模板等,您可以使用替代解决方案,例如 Babel's Message Extraction
或者您甚至可以customize makemessages 根据您的要求将不同的参数传递给gettext。
所以对于您的 Vue 示例...
如果您的 .vue 文件在 javascript 代码部分中包含对 gettext 的调用(默认解析似乎无法识别模板属性中的 gettext 调用等),您应该会发现 makemessages 将提取这些用于翻译的字符串(compilemessages 将在编辑.po 文件后生成所需的二进制文件)。
然后为了在代码运行时查看翻译,您需要使用Django JavaScript Catalog,因此请确保在代码中包含<script type="text/javascript" src="{% url 'javascript-catalog' %}"></script> 之类的内容,以便gettext 等函数实际存在。 (听起来您已经得到了这个,但为了完整起见包括在内。)
在您的 .vue 文件中,您可以使用以下内容:
<script> // trick to ensure xgettext doesn't omit the code below: </closetag>
data(){
const _ = gettext;
// gettext default JavaScript keywordspec includes "_" shortcut
// and should extract the strings below by default
// -- or you could just use gettext('my string') directly
return {
heading: _('This is my translatable heading'),
button_text: _('Click here'),
}
}
</script>
<template>
<h1>{{ heading }}</h1>
<button type="button">{{ button_text }}</button>
</template>
-- 字符串应该根据 Django 翻译机制当前激活的语言进行翻译。