$ cnpm install @uyun/everest-i18n
Everest 国际化解决方案
这是一个基于 babel
的国际化工具,由 babel
插件和 International
类配合使用。
本方案的工作流程是,通过应用 babel
插件与实例化 International
,在 babel
编译的过程中收集文本信息,并以表格的形式呈现,从而达到便于维护语言文本、减少工作量的目的。
$ unpm install --save @uyun/everest-i18n
添加 @uyun/everest-i18n/babel
至项目的 .babelrc
。启动项目后,插件默认会在项目根目录中生成一个 locales.json
文件。
// .babelrc
{
"plugins": ["@uyun/everest-i18n/babel"]
}
声明一个 International
的实例。
// index.js
import { International } from '@uyun/everest-i18n'
import locales from './locales.json'
// 如果项目中已有其它翻译文本
import zh_CN from './zh_CN.json'
import en_US from './en_US.json'
const intl = new International({
language: 'zh_CN',
locale: locales
// 有多个翻译文本时请使用 locales 字段
locales: [
locales,
{
zh_CN,
en_US
}
]
})
const { i18n } = intl
i18n('text1')
i18n('text2', { name: 'Apple' })
i18n('text3', '文本三')
i18n('text4', '文本四 {name}', { name: 'Bravo' })
以下示例适合需要异步加载 locales
的项目。
// 注意,以下请求是同步的
const locales = $.ajax({
url: '/locales.json',
async: false
}).responseJSON
// 如果是异步请求,确保以下方法在页面渲染之前完成
const intl = new International({
language: 'zh_CN',
locale: locales
})
插件会尽可能地收集 intl.i18n
方法中的 key
和文本,以二维数组的形式写入其中。
// locales.json
[
["key", "zh_CN", "en_US"],
["text1", null, null],
["text2", null, null]
["text3", "文本三", null],
["text4", "文本四 {name}", null]
]
将翻译后的文本填入对应的语言列。
// locales.json
[
["key", "zh_CN", "en_US"],
["text1", "文本一", "Text 1"],
["text2", "文本二 {name}", "Text 2 {name}"],
["text3", "文本三", "Text 3"],
["text4", "文本四 {name}", "Text 4 {name}"]
]
International
的实例会根据语言翻译对应的文本。
// 第 2 步中的例子
i18n('text1') // 文本一
i18n('text2', { name: 'Apple' }) // 文本二 Apple
i18n('text3', '文本三') // 文本三
i18n('text4', '文本四 {name}', { name: 'Bravo' }) // 文本四 Bravo
intl.switch('en_US')
i18n('text1') // Text 1
i18n('text2', { name: 'Apple' }) // Text 2 Apple
i18n('text3', '文本三') // Text 3
i18n('text4', '文本四 {name}', { name: 'Bravo' }) // Text 4 Bravo
@uyun/everest-i18n/babel
设置文本文件的路径,默认 ./locales.json
。
{ "locales": "./static/i18n.json" }
: 设置文本文件到其它路径。// .babelrc
["@uyun/everest-i18n/babel", {
"locales": "./static/i18n.json"
}]
设置文本文件的缩进,默认 2
。
{ "indent": 4 }
: 设置文本文件的缩进为 4。// .babelrc
["@uyun/everest-i18n/babel", {
"indent": 4
}]
// locales.json
[
["key", "zh_CN", "en_US"],
["text", "文本", "Text"],
]
设置文本文件每行的最大长度,默认 80
。
{ "maxLength": 120 }
: 设置文本文件每行的最大长度为 120。// .babelrc
["@uyun/everest-i18n/babel", {
"maxLength": 120
}]
// locales.json
[
["key", "zh_CN", "en_US"],
["text", "文本文本文本文本文本文本文本文本文本文本文本", "Text Text Text Text Text Text Text Text"],
]
设置语言种类集合,决定 locales.json
中的语言顺序,默认 ["zh_CN", "en_US"]
。
{ "languages": ["en_US", "jp_JP", "zh_CN"] }
: 设置语言种类为 "en_US"、"jp_JP" 和 "zh_CN"。// .babelrc
["@uyun/everest-i18n/babel", {
"languages": ["en_US", "jp_JP", "zh_CN"]
}]
// locales.json
[
["key", "en_US", "jp_JP", "zh_CN"],
["text", "Text", "テキスト", "文本"]
// ...
]
设置从 i18n
方法中收集的文本语言,默认 languages
中的第一个语言。
{ "language": "en_US" }
: 设置 "en_US" 为首要语言。// .babelrc
["@uyun/everest-i18n/babel", {
"language": "en_US"
}]
i18n('text', 'Text')
// locales.json
[
["key", "zh_CN", "en_US"],
["text", null, "Text"]
// ...
]
{ "language": "jp_JP" }
: 设置 "jp_JP" 为首要语言。// .babelrc
["@uyun/everest-i18n/babel", {
"languages": ["en_US", "jp_JP", "zh_CN"],
"language": "jp_JP"
}]
i18n('text', 'テキスト')
// locales.json
[
["key", "en_US", "jp_JP", "zh_CN"],
["text", null, "テキスト", null]
// ...
]
设置需要收集 key
和文本的方法别名,默认 ["intl.i18n", "i18n"]
,设置后不会覆盖默认值。
{ "translators": ["$.translate", "__"] }
: 将 $.translate
和 __
方法中的参数作为 key
和文本收集。// .babelrc
["@uyun/everest-i18n/babel", {
"translators": ['$.translate', '__']
}]
const __ = $.translate = intl.i18n
__('text', '文本')
$.translate('text2', '文本 {num}', { num: 1 })
// locales.json
[
["key", "zh_CN", "en_US"],
["text", "文本", null]
["text2", "文本 {num}", null]
// ...
]
International
new International(options)
设置实例化时的语言,必传。
new International({
language: 'zh_CN'
})
设置翻译文本,支援以下两种格式的文本。
// zh_CN.json
{
'text': '文本'
}
// en_US.json
{
'text': 'Text'
}
import { International } from '@uyun/everest-i18n'
import zh_CN from './zh_CN.json'
import en_US from './en_US.json'
const intl = new International({
language: 'zh_CN',
locale: {
zh_CN,
en_US
}
})
// locales.json
[
['key', 'zh_CN', 'en_US'],
['text', '文本', 'Text']
]
import { International } from '@uyun/everest-i18n'
import locales from './locales.json'
const intl = new International({
language: 'zh_CN',
locale: locales
})
当有多个翻译文本时,请使用该字段代替 locale
。
import { International } from '@uyun/everest-i18n'
import locales from './locales.json'
import zh_CN from './zh_CN.json'
import en_US from './en_US.json'
const intl = new International({
language: 'zh_CN',
locales: [
locales,
{
zh_CN,
en_US
}
]
})
既作为翻译文本的方法,也用来收集 key
和文本。i18n
通过 key
进行翻译,因此 text
参数是可选的。对于相同的 key
, 只要传入一次 text
即可,即从第二个 i18n
方法开始,可以不再传入 text
。
// 这个 key 的文本已被收集
intl.i18n('text', '文本') // 文本
// 之后,相同的 key 可以不用再传其它参数
intl.i18n('text') // 文本
对于有插值符的文本,需要在 values
中传入数据。
// 这个 key 的文本已被收集
i18n('text2', '文本 {name}', { name: 'Apple' }) // 文本 Apple
// 之后,相同的 key 可以只传 values
i18n('text2', { name: 'Bravo' }) // 文本 Bravo
此外,也可以始终只在 i18n
方法中传入 key
,最后统一填写语言的翻译文本。
// 这是另一种编程风格,在代码中只出现 `key`
intl.i18n('text')
intl.i18n('text2', { name: 'Apple' })
// locales.json
[
["key", "zh_CN", "en_US"],
["text", null, null]
["text2", null, null]
// ...
]
// 最后在对应的语言列中,统一填写翻译文本
[
["key", "zh_CN", "en_US"],
["text", "文本", "Text"]
["text2", "文本 {name}", "Text {name}"]
// ...
]
切换文本语言。
// locales.json
[
["key", "zh_CN", "en_US"],
["text", "文本", "Text"]
// ...
]
import { International } from '@uyun/everest-i18n'
const intl = new International({
language: 'zh_CN'
})
intl.i18n('text') // '文本'
intl.switch('en_US')
intl.i18n('text') // 'Text'
对于 React
项目,由于 switch
方法本身并不能触发 React
组件的更新,因此执行该方法后需要手动触发组件的重新渲染,参考 forceUpdate。
Copyright 2013 - present © cnpmjs.org