我正在编写一个包含我需要翻译的文本反馈的库。

我将以下行放在我在应用程序中导入的_config.py模块中:

import gettext, os, sys
pathname = os.path.dirname(sys.argv[0])
localdir = os.path.abspath(pathname) + "/locale"
gettext.install("messages", localdir)

我在./locale/lang_LANG/LC_MESSAGES中有* .mo文件,我将_()函数应用于所有需要翻译的字符串。

现在我刚为用户添加了一个功能,据说是程序员,可以创建自己的消息。我不希望他关心底层的实现,所以我希望他成为苹果公司,让它变得像以下那样直截了当:

lib_object.message = "My message"

我使用了属性来使它干净,但是如果我的用户想要翻译他自己的代码(使用我的代码)并做类似的事情会怎么样:

import gettext, os, sys
pathname = os.path.dirname(sys.argv[0])
localdir = os.path.abspath(pathname) + "/locale"
gettext.install("user_app", localdir)

lib_object.message = _("My message")

这是一个问题吗?如果不打扰我的用户,我该怎么做才能避免麻烦?

有帮助吗?

解决方案

您可以使用基于类的gettext api来隔离消息目录。这也是 python gettext文档中推荐的内容。

缺点是您或其他开发人员必须使用gettext方法或在本地范围内定义 _()方法,绑定到特定的gettext类。具有自己的字符串目录的类的示例:

import gettext

class MyClass(object):
    def __init__(self, locale_for_instance):
        self.lang = gettext.translation("appname", localedir, \
                                         locale=locale_for_instance)

    def some_method(self, arg):
        return self.lang.gettext("You called some method")

    def other_method(self, arg): # does the same thing
        _ = self.lang.gettext
        return _("You called some method")

你可以坚持在装饰器中添加 _()的代码,所以需要它的所有方法都带有 @with_local_gettext

之类的前缀

(注意,我没有测试过以上可能,但它应该工作得很好(tm))

如果目标是不打扰您的用户(并且他不是很好),我猜您可以在代码中使用基于类的方法,并让用户使用全局方法。

其他提示

你只能gettext.install()一次。一般来说,它对于库工作来说是无用的 - 如果调用它的模块负责整个程序,gettext.install()只会做正确的事情,因为它只会为你提供一个目录来加载。库代码应该做类似于Mailman所做的事情:拥有自己的gettext(包装器)包装器,传递该模块的正确参数,然后在每个想要使用它的模块中将其作为“_”导入。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top