用于代码翻译的 angular-i18n 解决方法? [英] angular-i18n work-around for translations in code?

查看:26
本文介绍了用于代码翻译的 angular-i18n 解决方法?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我们必须等到 Angular 6 的 angular-i18n 才能支持代码中的错误消息翻译等.

对于那些使用 angular-i18n(例如,而不是 ngx-translate)的人,您在此期间在做什么来处理代码中的翻译?我突然想到,如果没有很多字符串,那么一个简单的语言服务可以使用通过语言代码和 id 获取翻译的方法,但我对更优雅和有角度"的东西感兴趣.

我不知道承诺的代码翻译支持会是什么样子,但理想情况下,任何临时解决方案在上线时都可以轻松转换为 angular-i18n 方式.

人们在做什么来处理这个问题?有什么想法吗?

解决方案

这个 polyfill 似乎是目前最好的方法:

https://github.com/ngx-translate/i18n-polyfill

它允许您在 i18n() 函数中包装您想要翻译的任何内容(此 API 可能会在 Angular 的未来版本中保留 - 请参阅此答案底部的我的注释).

polyfill 主要由负责 i18n 的 Angular 团队成员 Olivier Combe 编写:

<小时>

对于 Angular 5,安装时需要 0.2.0 版:

npm install @ngx-translate/i18n-polyfill@0.2.0 --save

对于 Angular 6,获取最新版本 - 当前为 1.0.0:

npm install @ngx-translate/i18n-polyfill@1.0.0 --save

我让 polyfill同时适用于 JIT 和 AOT 编译,适用于 Angular 5(它也适用于 Angular 6).以下是翻译成单一语言所需要做的事情(这是实现这一目标的好方法 - 稍后您可以使用多种语言,我将在下面进一步解释):

<小时>

app.module.ts

将以下导入添加到您的根 Angular 模块:

import { TRANSLATIONS, TRANSLATIONS_FORMAT } from '@angular/core';从'@ngx-translate/i18n-polyfill'导入{I18n};

添加以下常量,并在您的根模块中指定提供者:

//在 import + export 语句之后添加这个//您需要指定翻译文件的位置//这是将用于 .ts 文件中的翻译的翻译文件const translations = require(`raw-loader!../locale/messages.fr.xlf`);@NgModule({ ....供应商:[I18n,{提供:翻译,useValue:翻译},{提供:TRANSLATIONS_FORMAT,useValue:'xlf'},...

<块引用>

使用 AOT 编译的注意事项:如果您使用 AOT 编译来翻译您的模板,翻译 .ts 文件中的消息仍然会在运行时使用 JIT 编译完成(这就是为什么你需要引用 TRANSLATIONSTRANSLATIONS_FORMAT 而不仅仅是在您的构建脚本中指定这些).

<小时>

*.ts

在要提供翻译的 .ts 文件中,添加以下内容:

import { I18n } from '@ngx-translate/i18n-polyfill';构造函数(私有 i18n:I18n){console.log(i18n("这是一个测试 {{myVar}} !", {myVar: "^_^"}));}

这表明您甚至可以在要翻译的消息中包含插值.

您可以像这样使用 i18n 定义(即使用指定翻译源"ID、含义、描述):

this.i18n({value: 'Some message', id: 'Some message id', 意思: '某些消息的含义', description: '某些消息的描述'})

您仍然需要提取消息,您可以使用 ngx-extractor 工具来执行此操作.这在您安装 polyfill 时包含在内,并且我在下面添加了一个示例,说明它在 npm 脚本中的用法.另请参阅 polyfill 页面上的自述文件.

<小时>

多种语言

要支持在多种语言之间切换,您需要为您的翻译提供工厂提供商.polyfill 页面 的自述文件中有详细信息.你需要在你的根模块中使用类似的东西(或者对于 AOT 编译,将 localeFactory 的返回值替换为一个检测你的应用程序当前正在运行的 AOT 编译语言变体的函数):

 导出函数 localeFactory(): string {返回 (window.clientInformation && window.clientInformation.language) ||window.navigator.language;}供应商:[{提供:翻译,useFactory: (locale) =>{语言环境 = 语言环境 ||'恩';//如果没有提供语言环境,则默认为英语return require(`raw-loader!../locale/messages.${locale}.xlf`);},deps:[LOCALE_ID]},{提供:LOCALE_ID,使用工厂:localeFactory},

<小时>

消息提取和xliffmerge

所有这些都与 xliffmerge,这是一个很好的工具,可以自动合并您添加的任何翻译,而不会覆盖现有翻译.Xliffmerge 还可以使用 Google 翻译自动执行翻译(您需要一个 Google 翻译 API 密钥).为此,我按以下顺序进行提取和合并/翻译,之前我进行实际的 AOT 构建:

"extract-i18n-template-messages": "ng xi18n --outputPath=src/locale --i18n-format=xlf","extract-i18n-ts-messages": "ngx-extractor --input=\"src/**/*.ts\" --format=xlf --out-file=src/locale/messages.xlf","generate-new-translations": "xliffmerge --profile xliffmerge.json en fr es de zh"

针对网站特定语言版本的 AOT 构建如下所示:

"build:fr": "ng build --aot --output-path=dist/fr --base-href/fr/--i18nFile=src/locale/messages.fr.xlf --i18nFormat=xlf --locale=fr",

<小时>

这个 polyfill 的当前状态:

本文主要由负责 i18n 的 Angular 团队成员 Olivier Combe 编写.在这个阶段,这是一个推测性"polyfill,用于翻译 .ts 文件中的变量或字符串.它很可能会被 Angular 内置的 API 所取代,该 API 将非常相似,因此稍后升级应该是可以合理管理的.以下是 Github 页面的免责声明:

<块引用>

这个库是一个推测性的 polyfill,这意味着它应该替换未来即将推出的 API.如果 API 不同,将在可能和必要的情况下提供迁移工具.

关于在即将推出的 Angular 6 次要版本中对代码中变量/字符串翻译的支持进行了一些讨论.

以下引用自 Olivier Combe(今年 3 月),摘自 Github 上的以下讨论:

https://github.com/angular/angular/issues/11405

<块引用>

运行时 i18n 的第一个 PR 已合并到 master,以及我们将用于测试功能的 hello world 演示应用程序.有用在运行时,并支持理论上的代码翻译,即使有还没有它的服务.现在它的支持非常少(静态字符串),我们正在努力添加新功能(我会让下周提取工作,然后是带有占位符的动态字符串和变量).之后,我们将提供代码翻译服务.一旦一个新功能完成,它就会被合并到 master 中,你不必等待新的专业.

We have to wait until Angular 6 for angular-i18n to support translations in code for error messages and such.

For those that are using angular-i18n (instead of ngx-translate for instance) what are you doing in the meantime to handle translations in code? It occurs to me that if there are not many strings then a simple language service with methods to get translations by language code and an id would work, but I am interested in something more elegant and "angular".

I do not know what the promised code translations support will look like but any temporary solution would ideally be easily converted to the angular-i18n way when it goes live.

What are people out there doing to handle this issue? Any ideas?

解决方案

This polyfill seems like the best way to go right now:

https://github.com/ngx-translate/i18n-polyfill

It allows you to wrap anything you want to translate in an i18n() function (this API is likely to be preserved in a future release of Angular - see my notes at the bottom of this answer).

The polyfill is mainly written by Olivier Combe, a member of the Angular team responsible for i18n:


For Angular 5, you'll need version 0.2.0 when you install:

npm install @ngx-translate/i18n-polyfill@0.2.0 --save

For Angular 6, get the latest version - currently 1.0.0:

npm install @ngx-translate/i18n-polyfill@1.0.0 --save

I got the polyfill working for both JIT and AOT compilation, for Angular 5 (it will also work for Angular 6). Here's what you need to do to translate to a single language (this is a good way to get this working - you can then get multiple languages working later, which I explain further down):


app.module.ts

Add the following imports to your root Angular module:

import { TRANSLATIONS, TRANSLATIONS_FORMAT } from '@angular/core';
import { I18n } from '@ngx-translate/i18n-polyfill';

add the following constant, and specify the providers in your root module:

// add this after import + export statements
// you need to specify the location for your translations file
// this is the translations file that will be used for translations in .ts files

const translations = require(`raw-loader!../locale/messages.fr.xlf`);

@NgModule({ ....

  providers:
  [
    I18n,
    {provide: TRANSLATIONS, useValue: translations},
    {provide: TRANSLATIONS_FORMAT, useValue: 'xlf'},
    ...

Note on using AOT compilation: If you're using AOT compilation to translate your templates, translation of the messages in .ts files will still be done at runtime using JIT compilation (that's why you need to reference TRANSLATIONS and TRANSLATIONS_FORMAT instead of just specifying these in your build scripts).


*.ts

In the .ts file where you want to provide a translation, add this:

import { I18n } from '@ngx-translate/i18n-polyfill';

constructor(private i18n: I18n) {
    console.log(i18n("This is a test {{myVar}} !", {myVar: "^_^"}));
}

This demonstrates that you can even include interpolations in the messages that you want to translate.

You can use i18n definitions (i.e. using specifying the translation 'source' id, meaning, description) like this:

this.i18n({value: 'Some message', id: 'Some message id', meaning: 'Meaning of some message', description: 'Description of some message'})

You'll still need to extract the messages, and you can use the ngx-extractor tool to do this. This is included when you install the polyfill, and I've added an example below on its usage inside an npm script. See also the readme on the polyfill page.


Multiple languages

To support switching between multiple languages, you'll need a factory provider for your translations. There are details on the readme of the polyfill page. You'll need something like this in your root module (or for AOT compilation, replace the return value for localeFactory with a function that detects which AOT compiled language variant of your app is currently running):

  export function localeFactory(): string {
    return (window.clientInformation && window.clientInformation.language) || window.navigator.language;
  }

  providers:
  [
    {
      provide: TRANSLATIONS,
      useFactory: (locale) => {
        locale = locale || 'en'; // default to english if no locale provided
        return require(`raw-loader!../locale/messages.${locale}.xlf`);
      },
      deps: [LOCALE_ID]
    },
    {
      provide: LOCALE_ID,
      useFactory: localeFactory
    },


Message extraction and xliffmerge

All of this is compatible with xliffmerge, which is a great tool for automatically merging any new translations you add, without overwriting existing translations. Xliffmerge can also automatically perform translations using Google translate (you'll need a Google translate API key). For this to work, I do the extraction and merging/translation in the following order, before I do the actual AOT build:

"extract-i18n-template-messages": "ng xi18n --outputPath=src/locale --i18n-format=xlf",
"extract-i18n-ts-messages": "ngx-extractor --input=\"src/**/*.ts\" --format=xlf --out-file=src/locale/messages.xlf",
"generate-new-translations": "xliffmerge --profile xliffmerge.json en fr es de zh"

The AOT build for a specific language version of the site looks like this:

"build:fr": "ng build --aot --output-path=dist/fr --base-href /fr/ --i18nFile=src/locale/messages.fr.xlf --i18nFormat=xlf --locale=fr",


Current status of this polyfill:

This is mainly written by Olivier Combe, a member of the Angular team responsible for i18n. At this stage this it's a 'speculative' polyfill for translating variables or strings in the .ts file. It's likely to be replaced by an API built into Angular which will be very similar, so upgrading later should be reasonably manageable. Here's the diclaimer from the Github page:

This library is a speculative polyfill, it means that it's supposed to replace an API that is coming in the future. If the API is different, a migration tool will be provided if it's possible and necessary.

There's been some discussion around support in forthcoming minor versions of Angular 6 for translations of variables/strings in code.

Here's a quote from Olivier Combe (from March this year), from the following discussion on Github:

https://github.com/angular/angular/issues/11405

The first PR for runtime i18n has been merged into master, along with a hello world demo app that we will use to test the features. It works at runtime, and support theoretically code translations, even if there is no service for it yet. For now it's very minimal support (static strings), we're working on adding new features (I'll make the extraction work next week, and then dynamic string with placeholders and variables). After that we'll do the service for code translations. As soon as a new feature is finished it gets merged into master, you won't have to wait for a new major.

这篇关于用于代码翻译的 angular-i18n 解决方法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆