介绍了在GitLab 9.2。
GitLab的国际化< / h1 >介绍了在GitLab 9.2。
对于使用国际化(i18n),GNU gettext它是这个任务中最常用的工具,有很多应用程序可以帮助我们使用它。
设置GitLab开发工具包(GDK)
为了能够工作GitLab社区版项目,您必须下载并配置它GDK.
一旦你准备好了GitLab项目,你就可以开始翻译了。
工具
需要使用的工具如下:
gettext_i18n_rails
这个gem允许我们转换来自模型、视图和控制器的内容。它还允许我们访问以下raketask:rake gettext:找
解析来自Rails应用程序的几乎所有文件,查找已标记为翻译的内容。最后,它用找到的新内容更新PO文件。rake gettext:包
:处理PO文件,生成最终供应用程序使用的二进制MO文件。
gettext_i18n_rails_js
这个gem用于在JavaScript中提供翻译。它提供了以下raketask:rake gettext: po_to_json
:从PO文件中读取内容并生成包含所有可用翻译的JSON文件。
PO编辑器:有多个应用程序可以帮助我们处理PO文件,一个不错的选择是Poedit它适用于macOS、GNU/Linux和Windows。
准备翻译页面
我们基本上有4种类型的文件:
- Ruby文件:基本上是模型和控制器。
- HAML文件:这些是视图文件。
- ERB文件:用于电子邮件模板。
- JavaScript文件:我们主要需要使用Vue模板。
Ruby文件
如果有一个方法或变量可以处理原始字符串,例如:
def你好“Hello world !”结束
或者:
你好=“Hello world !”
您可以很容易地标记要翻译的内容:
def你好_(“Hello world !”)结束
或者:
你好=_(“Hello world !”)
HAML文件
鉴于HAML中的以下内容:
% h1你好世界!
您可以使用以下命令标记要翻译的内容:
% h1=_(“Hello world !”)
ERB文件
鉴于雇员再培训局的内容如下:
<标题>你好世界!< / h1 >
您可以使用以下命令标记要翻译的内容:
<标题>< % =_(“Hello world !”)% >< / h1 >
JavaScript文件
在JavaScript中,我们添加__ ()
(双下划线括号)函数,您可以从~ /地区
文件。例如:
进口{__}从“~ /地区”;常量标签=__(“订阅”);
为了测试JavaScript翻译,您必须将GitLab本地化更改为英语以外的其他语言,并且必须使用bin /耙gettext: po_to_json
或bin /耙gettext:编译
.
动态翻译
有时,解析器在运行时无法找到一些动态翻译bin /耙gettext:找到
.对于这些场景,您可以使用N_
方法.
也有另一种方法翻译来自验证错误的消息.
处理特殊内容
插值
翻译文本中的占位符应与各自源文件的代码样式匹配。例如使用% {created_at}
在Ruby中% {createdAt}
在JavaScript。
在Ruby / HAML:
_(“你好%{名称}”)%{名称:“乔”}= >“你好乔”
在JavaScript中:
进口{__,sprintf}从“~ /地区”;sprintf(__(“你好% {username}”),{用户名:“乔”});// => 'Hello Joe'
默认情况下,
sprintf
转义占位符值。如果你想自己处理,你可以不去假
作为第三个论点。进口{__,sprintf}从“~ /地区”;sprintf(__(“这是%{value}”),{价值:“大胆强劲< > < / >强”});// => '这是<strong>bold</strong>sprintf(__(“这是%{value}”),{价值:“大胆强劲< > < / >强”},假);// => 'This is bold'
复数
在Ruby / HAML:
n_(“苹果”,“苹果”,3.)# =>“苹果”
使用插值:
n_(“有一只老鼠。”,“有%d老鼠。”,大小)%大小# =>当size == 1: '有一只老鼠。'# =>当size == 2时:'有2只老鼠。'
在JavaScript中:
n__(“苹果”,“苹果”,3.)// => '苹果'
使用插值:
n__(“最后一天”,“最后的%d天”,x)// =>当x == 1: 'Last day'// =>当x == 2: 'Last 2 days'
名称空间
有时,您需要在想要翻译的文本中添加一些上下文(如果单词出现在句子中并且/或者单词有歧义)。
在Ruby / HAML:
s_(“OpenedNDaysAgo |打开的)
如果没有找到翻译,它将返回
打开
.在JavaScript中:
s__(“OpenedNDaysAgo |打开的)
注意:应该从翻译中删除名称空间。看到更多细节翻译指南.
日期/时间
- 在JavaScript中:
进口{createDateTimeFormat}从“~ /地区”;常量dateFormat=createDateTimeFormat({一年:“数字”,月:“长”,一天:“数字”});控制台.日志(dateFormat.格式(新日期(“2063-04-05”)))// 2063年4月5日
它利用了Intl。日期TimeFormat
.
最佳实践
分裂的句子
请不要把一个句子分开,因为那样会假设所有语言中的句子语法和结构都是一样的。
例如,下面这个
{{s__(设定的“mrWidget |”)}}{{作者.名字}}{{s__(“mrWidget|在管道成功时自动合并”)}}
应具体化如下:
{{sprintf(s__("mrWidget|由%{author}设置,当管道成功时自动合并"),{作者:作者.名字})}}
如果有疑问,请尝试遵循本文中描述的最佳实践Mozilla开发人员文档.
用新的内容更新PO文件
现在新内容已经标注为翻译,我们需要用以下命令更新PO文件:
bin /耙gettext:找到
该命令将更新地区/ gitlab.pot
文件与新外部化的字符串,并删除任何不再使用的字符串。你应该把这个文件签入。一旦更改在master上,它们将被Crowdin并被翻译。
中存在合并冲突gitlab.pot
文件,您可以删除该文件,并使用相同的命令重新生成该文件。通过查看diff确认您没有意外删除任何字符串。
该命令还更新每种语言的翻译文件:地区/ * / gitlab.po
这些更改可以被丢弃,语言文件将由Crowdin自动更新。
像这样一次把它们全部丢掉:
Git checkout locale/*/ gitlab.po
验证PO文件
为了确保我们的翻译文件是最新的,有一个linter在CI上运行静态分析
的工作。
要在本地检测PO文件中的调整,您可以运行rake gettext:线头
.
linter将考虑以下因素:
- 有效的po文件语法
- 变量的使用
- 只有一个不知名的(
% d
)变量,因为变量的顺序在不同的语言中可能会改变 - 在消息id中使用的所有变量都在转换中使用
- 翻译中不应该使用message-id之外的变量
- 只有一个不知名的(
- 翻译错误。
错误按每个文件和每个消息ID分组:
' locale/zh_HK/gitlab.po '错误:PO-syntax错误SimplePoParser::ParserErrorSyntax错误msgctext中的语法错误msgstr中的语法错误msgstr中的语法错误message_line语法错误在消息文本的双引号字符之后,在行尾之前应该只有空格。{:msgid=>["", "您要删除%{project_name_with_namespace}。\\n", "已删除的项目无法恢复!\\n”,“你真的确定吗?")}SimplePoParser::ParserError' locale/zh_TW/gitlab.po '错误:1管道<%d >使用未知变量:[%d]使用[]:参数太少,无法转换为zh_TW
在这个输出中地区/ zh_HK / gitlab.po
有语法错误。的地区/ zh_TW / gitlab.po
是否在翻译中使用的变量不在带有id的消息中1管道
.
添加新语言
假设您想为一种新语言添加翻译,比如法语。
第一步是注册新语言
lib / gitlab / i18n.rb
:…AVAILABLE_LANGUAGES={…,“fr”= >“法语”}.冻结…
接下来,您需要添加语言:
bin /耙gettext: add_language[法文]
如果您想为特定区域添加新语言,命令类似,您只需要用下划线分隔区域(
_
).例如:bin /耙gettext: add_language [en_GB]
请注意,您需要用大写字母指定区域部分。
现在添加了语言,在路径下创建了一个新目录:
地区/ fr /
.您现在可以开始使用您的PO编辑器来编辑位于:地区/ fr / gitlab.edit.po
.更新完翻译后,你需要处理PO文件以生成二进制MO文件,最后更新包含翻译的JSON文件:
bin /耙gettext:编译
为了看到翻译的内容,我们需要改变我们的首选语言,可以在用户的下找到设置(
/配置文件
).在检查更改是否正确之后,您可以继续提交新文件。例如:
Git添加locale/fr/ app/assets/javascripts/locale/fr/git提交- m“为Cycle Analytics页面添加法语翻译”