Python实例浅谈之十国际化支持
来源:互联网 发布:网络黄金 编辑:程序博客网 时间:2024/05/01 18:17
一、简介
Python通过gettext模块支持国际化(i18n),可以实现程序的多语言界面的支持。
二、详解
1、Linux下Python的国际化编程
在Linux的操作和C语言的国际化过程是一样的,在需要国际化的字符串前面添加_()即可。
(1)代码:internation.py
第一种:程序中进行实时切换语言,同时输出中文和英文(此处使用第一种方法)
# -*- coding: utf-8 -*-#!/usr/bin/env pythonimport gettextlocale_path = './locale/'#gettext.install('internation', locale_path) # 这条语句会将_()函数自动放到python的内置命名空间中zh_trans = gettext.translation('internation', locale_path, languages=['zh_CN'])en_trans = gettext.translation('internation', locale_path, languages=['en_US'])print "----中文版本----"zh_trans.install()print _("Hello world!")print _("Python is a good Language.")print "----英文版本----"en_trans.install()print _("Hello world!")print _("Python is a good Language.")第二种:根据用户系统的语言配置(系统的环境变量LANGUAGE, LC_ALL, LC_MESSAGES, LANG),自动选择语言。
使用#echo $LANG或#locale查看当前系统语言环境,使用#export LANG="en_US"或#export LANG="zh_CN"设置本shell的语言环境。
# -*- coding: utf-8 -*-import gettextlocale_path = './locale/'# 将域APP_NAME与LOCALE_PATH目录绑定,# 这样gettext函数会在LOCALE_PATH目录下搜索对应语言的二进制APP_NAME.mo文件gettext.bindtextdomain('internation', locale_path)# 声明使用现在的域,可以使用多个域,便可以为同一种语言提供多套翻译,# 本程序只使用了一个域gettext.textdomain('internation')_ = gettext.gettextprint _("Hello world!")print _("Python is a good Language.")(2)生成po文件
xgettext -k_ -o internation.po_en internation.py
xgettext -k_ -o internation.po_zh internation.py(3)翻译(charset设定为utf-8)
英文:
# 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.##, fuzzymsgid ""msgstr """Project-Id-Version: PACKAGE VERSION\n""Report-Msgid-Bugs-To: \n""POT-Creation-Date: 2015-10-08 22:06+0800\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""MIME-Version: 1.0\n""Content-Type: text/plain; charset=UTF-8\n""Content-Transfer-Encoding: 8bit\n"#: internation.py:11 internation.py:16msgid "Hello world!"msgstr "translate:Hello world"#: internation.py:12 internation.py:17msgid "Python is a good Language."msgstr "translate:python is a good Language."中文:
# 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.##, fuzzymsgid ""msgstr """Project-Id-Version: PACKAGE VERSION\n""Report-Msgid-Bugs-To: \n""POT-Creation-Date: 2015-10-08 22:06+0800\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""MIME-Version: 1.0\n""Content-Type: text/plain; charset=utf-8\n""Content-Transfer-Encoding: 8bit\n"#: internation.py:11 internation.py:16msgid "Hello world!"msgstr "您好!"#: internation.py:12 internation.py:17msgid "Python is a good Language."msgstr "Python是一种好语言。"(4)建立翻译文件路径
在主文件目录下建立英文翻译路径./locale/en_US/LC_MESSAGES/和中文翻译路径./locale/zh_CN/LC_MESSAGES/ (对文件层次比较严格)。
(5)生成mo最终文件
msgfmt -o ./locale/en_US/LC_MESSAGES/internation.mo internation.po_en
msgfmt -o ./locale/zh_CN/LC_MESSAGES/internation.mo internation.po_zh(6)运行
2、Window下Python的国际化编程(未测试)
(1)在python安装目录下的./Tools/i18n/(windows下例 D:\Program Files\Python25\Tools\i18n)目录中找到pygettext.py运行,生
成翻译文件模版messages.pot,部分内容修改为charset=gb2312 Content-Transfer-Encoding: utf8,文件改名为lang.po,如下:
# SOME DESCRIPTIVE TITLE.# Copyright (C) YEAR ORGANIZATION# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.#msgid ""msgstr """Project-Id-Version: PACKAGE VERSION\n""POT-Creation-Date: 2007-01-18 09:55+China Standard Time\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""MIME-Version: 1.0\n""Content-Type: text/plain; charset=gb2312\n""Content-Transfer-Encoding: utf8\n""Generated-By: pygettext.py 1.5\n"(2)建立翻译文件路径,在主文件目录下建立中文翻译路径.D:\python-prj\src\locale\cn\LC_MESSAGES(其中src目录是源文件主目录),英文翻译路径D:\python-prj\src\locale\en\LC_MESSAGES(其中src目录是源文件主目录)。
(3)在主文件中引入gettext模块
# -*- coding: utf-8 -*-#!/usr/bin/env pythonimport gettextgettext.install('lang', './locale', unicode=False)gettext.translation('lang', './locale', languages=['cn']).install(True)第四行中lang是翻译文件主名, ./locale是存放翻译文件的路径,第三个参数是是否使用unicode,第五行languages参数指定要使用的语言存放的子目录,这里cn表示使用./locale/cn/LC_MESSAGES/路径下的翻译文件。
注意: # -*- coding: utf-8 -*- 一定要写在前两行,写第三行都不会生效
(4)处理要翻译的字符串:
print _("Hello world!")print _("Python is a good Language.")(5)编写并生成翻译文件,打开上述编辑过的lang.po文件添加翻译文字,形成如下内容:
(也可以直接使用命令:python pygettext.py -a -v -d lang -o lang.po *.py ,然后翻译)
b5. 编写并生成翻译文件,打开步骤1中编辑过的lang.po文件添加翻译文字,形成如下内容:
# SOME DESCRIPTIVE TITLE.# Copyright (C) YEAR ORGANIZATION# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.#msgid ""msgstr """Project-Id-Version: PACKAGE VERSION\n""POT-Creation-Date: 2007-01-18 09:55+China Standard Time\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""MIME-Version: 1.0\n""Content-Type: text/plain; charset=gb2312\n""Content-Transfer-Encoding: utf8\n""Generated-By: pygettext.py 1.5\n"msgid " Hello world!"msgstr "世界你好!"msgid " Python is a good Language."msgstr "Python 是门好语言."将lang.po文件拷贝到./Tools/i18n/目录下,运行命令行窗口,到改目录下键入:msgfmt.py lang.po,生成ang.mo,将该文件拷贝至./locale/cn/LC_MESSAGES/目录下,将步骤1生成的lang.po文件直接生成lang.mo文件拷贝到./locale/en/LC_MESSAGES/目录下,运行程序,看看两个print命令是不是输出了世界你好! Python 是门好语言.,如果将主文件第五行languages参数置为en,则输出是Hello world! Python is a good Language.,因为en目录下lang.mo文件未做任何的翻译,默认字符串不被替换.
上述实现的方法用在界面编程上可以实现中英文界面的切换,需要作个配置文件选择中/英文;或者在主文件开始时先获取操作系统本地语言然后根据获取结果再设置中/英文,这样就可以实现软件语言自适应;如果想实现软件语言在线切换,对于python来说就比较困难了,需要在软件中加入界面刷新机制(不推荐),可以在切换中/英文设置后软件下一次启动生效(软件如Ulipad)。
3、Window下的其他参考
python中对于国际化的字符串,只需要外加_()即可。如: print(_('hello world')),然后根据user选择的语言,创建translation对象,然后调用install方法install_()函数到Python’s builtins namespace。如:
import gettexten_trans = gettext.install('messages', locale='i18n_path', languages=['default_language'])zh_trans = gettext.install('messages', locale'i18n_path', languages=['zh_CH'])print(_('hello world'))zh_trans.install()print(_('hello world'))
而对于web服务中前端页面的国际化支持也非常简单,和python source文档中一样,在需要国际化的字符串前面添加_()即可。然后在render函数中,把当前translation对象传入模板即可。如Tornado render_string的实现:
def render_string(self, template_name, **kwargs): # If no template_path is specified, use the path of the calling file ... ... args = dict( handler=self, request=self.request, current_user=self.current_user, locale=self.locale, _=self.locale.translate, static_url=self.static_url, xsrf_form_html=self.xsrf_form_html, reverse_url=self.application.reverse_url ) args.update(self.ui) args.update(kwargs) return t.generate(**args)
好了,上面搭建好i18n所需要的环境,下面就是准备对语言字符资源了。
python 工具: pygettext msgfmt,其他工具: msgmerge
1. 创建po文档
在当前目录下创建locale文件夹,下面分别建en_US/LC_MESSAGES/ 和 zh_CN/LC_MESSAGES/目录。
在locale下面创建名为 demo.html的文件内容如下:
<html> <head> <title>${_('title')}</title> </head> <body> <a href=''>${_('body')}</a></body></html>然后打开命令行窗口,输入 python pygettext.py -a -v -d messages -o messages.po \*.py \*.html,完成后,在当前目录生成 messages.po 文件,其中的格式内容:
三、总结
(1)国际化的过程还需要细节的完善,widows下还需要调整使用。
(2)可参考:https://docs.python.org/2/library/gettext.html、http://underthehood.blog.51cto.com/2531780/1663604。
(3)若有不足,请留言,在此先感谢!
1 0
- Python实例浅谈之十国际化支持
- Python实例浅谈之国际化支持
- GTK+浅谈之十一国际化多语言支持及发布
- 十、Qt的国际化支持
- Python实例浅谈之七socket编程
- Python实例浅谈之六读写文件
- Python实例浅谈之二自定义异常
- Python实例浅谈之二自定义异常
- Python 国际化(i18n) 支持
- struts2之5--国际化支持
- Spring学习之国际化支持
- Python实例浅谈之八2048游戏(字符界面)
- Python实例浅谈之九使用本地socket文件
- javaee学习之路(十)国际化
- 浅谈国际化
- shell浅谈之十函数
- shell浅谈之十函数
- shell实例浅谈之十检测整数、浮点数和日期数的合法性
- Mybatis框架基础学习(二)
- c++ primer第五版(中文)习题答案 第十章第三节第三小节-lambda捕获和返回
- 连载《一个程序猿的生命周期》- 36、突破失败的自我感悟
- Java EE 请求响应对象
- Dism 错误 3
- Python实例浅谈之十国际化支持
- 《软件测试过程改进》读书笔记
- 求链表中的最大值,节点个数,平均值
- CentOS yum 源的配置与使用
- 关于结构性阅读
- python3.x安装第三方库的解决办法
- 重拾编程之路0
- MySQL学习历程——数据库操作命令
- Python基础(一): 基本介绍