我已经通过 Locale::Maketext 使我的网站支持多种语言(或更具体地说是 CatalystX::I18N::Model::Maketext )。
我的 maketext 类在编译时通过从数据库加载词典将其加载到包 var %Lexicon 中。
我想在我的应用程序中为词典添加一个管理界面,但我想不出重新加载词典的方法。我向每个语言环境类添加了一个方法来刷新 %Lexicon 哈希,这在开发中运行良好,但在 fork 服务器 (Starman) 上运行时,它当然只会重新加载该服务器进程中的包 var。
然后我想也许我可以将词典放入缓存中,在需要时可以过期。但是,Locale::Maketext 中的 %Lexicon 散列是在运行时开始时填充的,我不知道如何在每次请求时从缓存中填充它。
我最近的想法是覆盖 Locale::Maketext 的一部分,但我正在寻找任何聪明的想法:)
最佳答案
如果您愿意为某些请求承受轻微的性能损失,您可以在每次调用 maketext()
时检查文件的 md5sum。
例如:
package MyMakeText;
use strict;
use warnings;
use Digest::MD5;
my @PO_FILES = ('exaple.po');
my %FILE_TO_DIGEST;
my $LOCALIZER;
sub maketext {
if (files_have_changed() || !$LOCALIZER) {
$LOCALIZER = get_handle();
}
return $LOCALIZER->maketext(@_);
}
sub files_have_changed {
my $files_have_changed = 0;
for my $po_file (@PO_FILES) {
open(my $fh, '<', $po_file) or die $!;
my $md5sum = Digest::MD5->new->addfile($fh)->hexdigest;
close($fh);
if (!exists $FILE_TO_DIGEST{$po_file} || $FILE_TO_DIGEST{$po_file} ne $md5sum) {
$FILE_TO_DIGEST{$po_file} = $md5sum;
$files_have_changed = 1;
}
}
return $files_have_changed;
}
请注意,这是部分伪代码,因为我不知道您当前是如何构建 Locale::MakeText 对象的,因此我将其留给您填写 get_handle()
.但我认为您可以看到如何包装对 maketext()
的调用以包括检查以查看是否有任何文件更改了它们的内容。
.po
文件通常非常小,最近更改的文件通常会在 Linux 磁盘缓存中,所以我希望这会非常快,尽管所有明显的磁盘读取都是如此。
关于perl - 如何在我的应用程序中动态更改 Maketext 词典?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13397561/