31

angular Universal で Angular の公式国際化ツールを使用しようとしています。これまでのところ、次の手順を使用してクライアント側のレンダリングを変換できます (この回答に感謝https://stackoverflow.com/a/40930110/1110635 ):

テンプレートのドキュメントに記載されているように、「i18n」属性を追加します。

./src/+app/about/about.component.html :

<h1 i18n="H1 of the about component">About</h1>
...

次に実行します:

./node_modules/.bin/ng-xi18n

ベースのmessages.xlfファイルを生成します。

次に、サポートしたいロケールごとにこのファイルを「messages.[locale].xlf」として「locale」フォルダーにコピーします。準備ができたら、コンテンツのエクスポートされた文字列を含む xlf ファイルごとに「 messages.[locale].ts 」を作成します。

./locale/messages.fr.ts:

// TRANSLATION_FR is only for "messages.fr.ts" of course.
// I would create a TRANSLATION_ES const inside "messages.es.ts" for spanish for example.
export const TRANSLATION_FR: string = `<?xml version="1.0" encoding="UTF-8" ?>
<xliff version="1.2" xmlns="urn:oasis:names:tc:xliff:document:1.2">
  <file source-language="en" datatype="plaintext" original="ng2.template">
    <body>
      <trans-unit id="004b222ff9ef9dd4771b777950ca1d0e4cd4348a" datatype="html">
        <source>About</source>
        <target>A propos</target>
        <note priority="1" from="description">H1 of the about component</note>
      </trans-unit>
    </body>
  </file>
</xliff>
`;

最後に、client.tsファイルは次のようになります。

./src/client.ts:

[...]

// i18n
import { TRANSLATIONS, TRANSLATIONS_FORMAT, LOCALE_ID  } from '@angular/core';
import { TRANSLATION_FR } from '../locale/messages.fr';

import { MainModule } from './browser.module';

export const platformRef = platformUniversalDynamic();

// on document ready bootstrap Angular 2
export function main() {
  return platformRef.bootstrapModule(MainModule, {
      providers: [
          {provide: TRANSLATIONS, useValue: TRANSLATION_FR},
          {provide: TRANSLATIONS_FORMAT, useValue: "xlf"},
          {provide: LOCALE_ID, useValue: 'fr'}
      ]
  });
}
bootloader(main);

これは機能し、「クライアント側」アプリケーションを期待どおりに機能させます。「について」は「提案」に置き換えられます。しかし、クライアント側のブートストラップが完了するまでテキストは翻訳されません。

そのため、最初にページに移動すると、約 1 秒間「 About 」が表示されてから、クライアント側で「 A propos」に置き換えられます。

サーバー側で翻訳サービスを実行するだけです。しかし、私はそれを行う方法がわかりません。

私のserver.tsは次のようになります:

./src/server.ts

[...]

// i18n
import { TRANSLATIONS, TRANSLATIONS_FORMAT, LOCALE_ID  } from '@angular/core';
import { TRANSLATION_FR } from '../locale/messages.fr';

const app = express();
const ROOT = path.join(path.resolve(__dirname, '..', 'dist'));

// Express View
app.engine('.html', createEngine({
    ngModule: MainModule,
    providers: [
      /**
       * HERE IS THE IMPORTANT PART.
       * I tried to declare providers but it has no effect.
       */
      {provide: TRANSLATIONS, useValue: TRANSLATION_FR},
      {provide: TRANSLATIONS_FORMAT, useValue: "xlf"},
      {provide: LOCALE_ID, useValue: 'fr'}
    ]
}));
app.set('port', process.env.PORT || 3000);
app.set('views', ROOT);
app.set('view engine', 'html');
[...]

function ngApp(req, res) {
    res.render('index', {
      req,
      res,
      preboot: false,
      baseUrl: '/',
      requestUrl: req.originalUrl,
      originUrl: `http://localhost:${ app.get('port') }`
    });
}
app.get('*', ngApp);

// Server
let server = app.listen(app.get('port'), () => {
    console.log(`Listening on: http://localhost:${server.address().port}`);
});

クライアント側のように、 bootstrapModuleメソッドに直接アクセスすることはできません。「 createEngine」パラメーター オブジェクトのprovidersキーは、元のserver.tsコードに既に存在していました。

私は何が欠けていますか?

4

1 に答える 1