Shell Scriptを多言語化する 【 Linux 豆知識 】

Arch Linux

みなさんこんにちはmk419です。一週間ぶりですね。
今回は久しぶりの技術系?の記事になります。

スポンサーリンク

gettext

今回使用するツールです。
Arch Linux場合は下記のコマンドで簡単にインストールできます。(多分入ってるはず)

sudo pacman -S gettext

今回はシェルスクリプトで使いますが、C, C++, C#, Python, PHP, JavaScript などで対応しています。

実際に作ってみる

スクリプトの準備

今回使用するスクリプトは下記のものです。”hellow-world.sh”として保存してください。

#!/usr/bin/env bash
source "/usr/bin/gettext.sh"

TEXTDOMAIN="hello-world"
export TEXTDOMAIN

TEXTDOMAINDIR="$(pwd)/locale"
export TEXTDOMAINDIR

echo "$(eval_gettext "Hello, World!")"

ではコードを一行ずつ見ていきましょう。
1行目はBashを呼び出すための呪文です。詳しく知りたい人は”シェバン”でググると色々出てきます。
2行目はgettextをシェルスクリプトで使うための呪文です。Pythonでいう”import”みたいなものです。
4行目はmoファイル(poファイルをバイナリ化したもの)の名前を指定しています。
7行目はmoファイルがあるディレクトリを指定しています。絶対パスで指定してください。
5、8行目は環境変数を上書きしています。
10行目は”Hello, World!”を出力する部分です。

この状態で一回実行してみましょう。

Hello, World!

poファイルとかmoファイルとかを作ってないのでそのまま出力されます。

poファイルの準備

poファイルを置くディレクトリを用意

mkdir po

poファイルのテンプレートになるpotファイルを作成

xgettext -o po/hello-world.pot hello-world.sh

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

msginit -i po/hello-world.pot -l ja -o po/ja.po

そして”po/ja.po”をお好きなエディターで開きます。
VimでもEmacsでもNanoでもVSCodeでもAtomでもOKです。

msgid "Hello, World!"
msgstr ""

どこかにこんな感じの行があるはずなので、これを下記のように変更

msgid "Hello, World!"
msgstr "こんにちは世界!"

(なんかダサい・・・)

このままpoをmoに変換するとエラーが出てしまうので、下記の行を

"Content-Type: text/plain; charset=ASCII\n"

このように変更

"Content-Type: text/plain; charset=UTF-8\n"

moファイルの準備

moファイルを置くディレクトリを作成

mkdir -p locale/ja/LC_MESSAGES

moファイルの作成

msgfmt po/ja.po -o locale/ja/LC_MESSAGES/hello-world.mo

実行

それでは実行してみましょう。

こんにちは世界!

日本語化に成功しました!

応用

今までのコードだと一つ問題点があります。変数の処理です。
例えば”I’m 17 years old.”という文を翻訳したい場合に、”私は17歳です。”って書けば問題ないですが、もし”17″を”18″とか”20″とかに変えたい場合にいちいち翻訳を用意するのは面倒です。

そこで今回は”echo”ではなく”printf”を使って解決してみましょう。

スクリプトの改変

さっき書いたスクリプトを再利用します。
以下のコードを追記してください。

printf "$(eval_gettext "I am %s years old.")\n" "17"

“%s”に”17″を代入し、”\n”で改行しています。

この状態で実行すると、

こんにちは世界!
I am 17 years old.

こんな感じになるはずです。

poファイルの更新

既存のテンプレートを上書き

xgettext -o po/hello-world.pot hello-world.sh

テンプレートから”po/ja.po”にマージ

msgmerge -U po/ja.po po/hello-world.pot

下記のコードを

msgid "I am %s years old."
msgstr ""

以下のように変更

msgid "I am %s years old."
msgstr "私は%s歳です。"

moファイルの更新

既存のmoファイルを上書き

msgfmt po/ja.po -o locale/ja/LC_MESSAGES/hello-world.mo

実行

こんな感じになります。

こんにちは世界!
私は17歳です。

やったね!

終わりに

gettextの使い方をマスターすれば、世界中のOSSに日本語訳をプルリクできるようになるので覚えておいて損はないと個人的には思っています。

プルリクエストお願いします()
https://github.com/FascodeNet/alterlinux-doc

コメント

タイトルとURLをコピーしました