如何创建用于PHP的ICU资源文件?

5
我正在按照BryanH在这里的回答进行操作:使用Intl库中的相当于gettext()的方法?,并尝试使用php-intl实现本地化(翻译),但我遇到了与此人相同的问题:ResourceBundle返回NULL没有任何错误被引发

他提到他使用了一个工具创建了dat文件(我无法弄清楚如何操作),而前一个回答中的人似乎只是使用扩展名为.res的txt文件。

我该如何正确地使用php-intl和ResourceBundle实现本地化,我做错了什么?

目标是有多个包含不同语言的数据文件,以便我可以执行类似于

$t = new Translator();
$t->setResource(new \ResourceBundle('es', 'locales_folder/'));
$t->echo("somestring"); // "el stringo"

和第一篇答案中所说的一样,目标是拥有易于编辑的文件,这样我就可以将它们交给翻译人员进行修复、更新等操作。我意识到我可以通过一个简单的文本文件来实现自定义解决方案,该文件被解析并在第一次请求时保存到内存缓存中,然后持久化并从中提供服务而无需重新读取.dat文件,但我更愿意采用建议的路线。

编辑:为了让它出现在那里——我成功地使用gettext实现了同样的事情,这很容易——除了一个在Linux系统上持续存在的错误(http://www.php.net/manual/en/book.gettext.php#91187) - 但我希望尽可能依赖更现代和全面的intl扩展。

1个回答

9
我可以为您解决有关如何创建和使用 .res 文件的问题,这与 intl PHP 扩展相关,但我没有在生产系统中使用速度和使用方面的经验,您需要自己判断是否可以替代 gettext
在我看来,gettext 的一个很大的好处是附加工具,例如 xgettext 可以提取要翻译的字符串。不过,在您的用例中使用资源可能更加有用。
要生成 .res 文件,您需要使用程序 genrb,它与 ICU 捆绑在一起。 (例如,在 OSX 上安装 ICU 并使用 brew install icu4c请参见此教程)时,您可以在 /usr/local/Cellar/icu4c/*/bin/genrb 找到该工具(将 * 替换为版本号)。)

接下来,您需要为每个语言环境准备一个文件。在本示例中,我们将为两种语言(德语和西班牙语)执行此操作。

$ cat de.txt
de {
    hello { "Hallo" }
}

$ cat es.txt
es {
    hello { "Hola" }
}

$ genrb *.txt
genrb number of files: 2

您现在有2个额外的文件de.reses.res,您现在可以在PHP中访问它们

<?php
foreach (array("de", "es") as $locale) {
    $r = ResourceBundle::create($locale, __DIR__);
    echo $r["hello"], "\n";
}

将输出

Hallo
Hola

因此,您可以将这些*.txt文件交给翻译人员,并使用genrb为PHP做准备。
最后,以下是您尝试编写的类的一个小例子:
<?php
class Translator {
    private $resourceBundle = null;

    public function __construct(\ResourceBundle $r) {
        $this->resourceBundle = $r;
    }

    public function __get($string) {
        return $this->resourceBundle[$string];
    }
}
$t = new Translator(new \ResourceBundle('es', __DIR__));
echo $t->hello;

谢谢,那就可以了。既然这应该是线程安全的,我认为这就是我要找的解决方案。现在我只需要编写自己的字符串提取器,这样就可以运行了。 - Swader
1
如果您能分享您的经验,以及您的字符串提取器(也许您甚至可以开源它),那将非常有用。提前感谢! - akirk
由于poedit可以自动提取gettext,我想我可以给它另一个要查找的模式,比如$t->_($string),这样就可以为这些字符串创建.mo和.po文件。然后我只需要编写一个工具将它们转换为RES格式,这听起来相当容易。我会写一篇关于整个过程的博客文章,并在这里链接它。 - Swader
1
@Swader ICU有将文件转换为和从XLIFF格式转换的工具。也可以通过这种方式进行旋转。我还考虑过将文件转换为和从po、mo、.properties、.rc等格式。 - Steven R. Loomis
没错,这就是我要做的——将po文件转换为res文件,因为poedit可以很好地从项目中提取所有内容。 - Swader

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接