php/wordpress アプリやテーマを国際化/多言語化しよう

WordPress

環境Install

sudo apt-get install gettext

使用方法

テンプレートファイル:potファイルを作成する

#keywordは複数設定できる
xgettext --keyword='__' -o 出力ファイル名 読み込むファイル
xgettext --keyword='__' -o test.pot aaa.php

出力されるファイル

# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.
#
#, fuzzy
msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2021-01-06 11:48+0900\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"Language: \n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=CHARSET\n"
"Content-Transfer-Encoding: 8bit\n"

#: 翻訳されるテキストがある行番号
msgid "翻訳される前のテキスト"
msgstr ""

potファイルからpoファイルを作成する

msginit --locale=言語 --input=読み込むファイル
msginit --locale=ja --input=test.pot
#実行時にメールアドレスを入力するように求められる
#例としてaaa@xxxxx.comと入力

#ユーザが翻訳に関するフィードバックをあなたに送ることができるように,
#新しいメッセージカタログにはあなたの email アドレスを含めてください.
#またこれは, 予期せぬ技術的な問題が発生した場合に管理者があなたに連絡が取れる
#ようにするという目的もあります.

出力

# Japanese translations for PACKAGE package.
# Copyright (C) 2021 THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
#  <aaa@xxxxx.com>, 2021.
#
msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2021-01-06 11:48+0900\n"
"PO-Revision-Date: 2021-01-06 12:02+0900\n"
"Last-Translator:  <aaa@xxxxx.com>\n"
"Language-Team: Japanese\n"
"Language: ja\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=ASCII\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=1; plural=0;\n"

#: 翻訳されるテキストがある行番号
msgid "翻訳される前のテキスト"
msgstr ""

変更項目

#文字コードの変更
#変換に日本語を使うと不正な複数バイトのシーケンスと出てしまうため。
"Content-Type: text/plain; charset=UTF-8\n"

msgid "翻訳される前のテキスト"
msgstr "翻訳したいテキスト"

poファイルをmoファイルに変換する

msgfmt -o 出力ファイル 入力ファイル
msgfmt -o ja.mo ja.po

コンパイルしたmoファイルをpoファイルに戻したい

#コメント行が消えてしまうので少し不便。
msgunfmt xxx.mo

moファイルの更新はどうすればいい?

poファイルは残しておくこと。
新しいソースファイルからpoファイルを出力する工程まで終わらせる

#新しいpoの分が追加される。
msgmerge 古い.po 新しい.po -o 出力先.po
#この処理の後に翻訳テキストを入力すること

wordpressから翻訳ファイルを読み込む

サンプルとして適当に書いてみる

下記の内容のファイルをmoに変換して使う

# Japanese translations for PACKAGE package.
# Copyright (C) 2021 THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
#  <aaa@aaa.com>, 2021.
#
msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2021-01-06 12:23+0900\n"
"PO-Revision-Date: 2021-01-06 12:24+0900\n"
"Last-Translator:  <aaa@aaa.com>\n"
"Language-Team: Japanese\n"
"Language: ja\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=utf-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=1; plural=0;\n"

msgid "test text "
msgstr "テストテキスト"

msgid "aiueo"
msgstr "あいうえお"

msgid "anko"
msgstr "あんこ"

msgid "python"
msgstr "パイソン"

get_locale:現在のローケル情報を取得する

$lang=get_locale()

load_textdomain:moファイルをロードする

load_textdomain( <$domain> , <$mo_file> );

$domain...      任意のドメイン名を決める
$mo_file...     ルートからのファイルパスを指定。URLではない。
返り値...       ロードできた場合はtrue
plugins
└── wordpress_example_mo
    ├── languages
    │   └── ja.mo
    └── wordpress_example_mo.php
$aaa=load_textdomain('test',dirname(__FILE__).'/languages/'.get_locale().'.mo');

if ($aaa == true){
    error_log('true');
}else{
    error_log('false');
}
$aa1 = __('test text ','test');
error_log($aa1);
$aa2 = __('aiueo','test');
error_log($aa2);
$aa3 = __('anko','test');
error_log($aa3);
$aa4 = __('python','test');
error_log($aa4);
[06-Jan-2021 14:23:57 UTC] true
[06-Jan-2021 14:23:57 UTC] テストテキスト
[06-Jan-2021 14:23:57 UTC] あいうえお
[06-Jan-2021 14:23:57 UTC] あんこ
[06-Jan-2021 14:23:57 UTC] パイソン

load_plugin_textdomain:

プラグイン用のmoファイルをロードする

load_plugin_textdomain( <$domain> , [false] , [$plugin_path]=false );

$domain...      domain名
false...        2.7以降推奨されていない。falseでよい。
$plugin_path... moファイルが保存されているディレクトリを指定する。
               読み込まれるファイルは「domain名-ローケル情報.mo」である。
返り値...       moファイルがロードできた場合はtrue
plugins
└── wordpress_example_mo
    ├── languages
    │   └── test-ja.mo
    └── wordpress_example_mo.php
$aaa=load_plugin_textdomain('test',false,basename(dirname(__FILE__)).'/languages');

出力や他共通コードは省略させてもらう。

load_theme_textdomain:

load_theme_textdomain( <$domain> , [$path]=false );

$domain...      ドメイン名を指定
$path... moファイルが保存されているディレクトリを指定する。
返り値...       読み込みに成功すればtrue

どのように読み込まれる?

__():翻訳テキストの取得

__( <$text> , [$domain]='default' );

$text...    英文テキスト。ドメインと言語指定によって変更される。
           翻訳テキストがなければ$textがそのまま返る
$domain...  ドメイン名を指定する。デフォルトではdefaultが指定される

_e():翻訳テキストの表示

_e( <$text> , [$domain]='default' );

小言

配布と更新を考えるのならばpoファイルも残しておきましょう

参考

__ – WordPress私的マニュアル
_e – WordPress私的マニュアル
_x – WordPress私的マニュアル
esc_attr_e – WordPress私的マニュアル

load_plugin_textdomain – WordPress私的マニュアル
load_theme_textdomain – WordPress私的マニュアル