前言

课程设计总是Flask开发。。网站经常要求双语翻译,开发中英文两份html自然是最麻烦的方法,而babel库的使用就是一个熟练工。本文将详细总结使用flask_babel库进行多语种切换的方法,以英文切换成中文为例。


一、安装flask_babel

我使用的编译器是pycharm, 在虚拟环境终端pip install flask_babel,稍等片刻即下载成功。


二、在flask项目应用babel

这里用一个常见的例子,以下代码出自app.py,即flask项目的启动文件。

from flask import Flask, render_template, requestfrom flask_babel import Babel, gettext as _app = Flask(__name__)
app.config['BABEL_DEFAULT_LOCALE'] = 'en'
app.config['BABEL_DEFAULT_TIMEZONE'] = 'UTC'babel = Babel(app)@babel.localeselector
def get_locale():return request.accept_languages.best_match(['zh', 'en'])@app.route('/')
def hello():day = _("Saturday")return render_template('index.html', day=day)if __name__ == '__main__':app.debug = Trueapp.run()

下面分步骤详细解释:

  1. 从 flask_babel 引入 Babel 模块和 gettext 函数,由于 gettext 函数被引用的次数太多了,为了方便手写,一般将其重命名为 “_”
  2. 设置babel默认的地区语言和区时(可不设置)
    app.config['BABEL_DEFAULT_LOCALE'] = 'en'
    app.config['BABEL_DEFAULT_TIMEZONE'] = 'UTC'
    
  3. 初始化 babel 应用
    babel = Babel(app)
    
  4. 定义一个函数来实现地区语言选择
    使用babel库自带的@babel.localeselector来修饰函数,此函数会在所有路由函数运行前执行。 request.accept_languages.best_match([‘zh’, ‘en’])函数会调用当前浏览器的默认语言,然后将其设置为当前语言。例如下图的情况,此函数返回值为“zh_CN”

三、生成翻译模板

  1. 把所有需要翻译的html中的文字用{{ _( " 翻译文字") }}框起来,别忘前面的下划线

    这是一项十分繁琐的工作,在pycharm可以先用鼠标选中待翻译文字,然后按住shift的同时按两下"{"(左花括号),再按一下"("(左括号),再按一下"(左引号),最后再左括号前面加下划线即可
  2. 在 app.py 的同级目录创建一个叫 babel.cfg 的文件,内容如下
    [python: **.py]
    [jinja2: **/templates/**.html]
    extensions=jinja2.ext.autoescape,jinja2.ext.with_
    

    目录可以根据实际情况修改,例如**/templates/news/**只翻译news里的所有html.

  3. 在终端执行输入以下代码生成翻译模板,即提取所有框起来的文字
    pybabel extract -F babel.cfg -o messages.pot .
    

    执行完后会在app.py同级目录下产生一个新文件messages.pot,其中含有所有需要翻译的文字空白模板,此文件不需要任何操作!

  4. 在终端输入一下代码, 创建中文翻译
    pybabel init -i messages.pot -d translations -l zh_CN
    

    此时会在app.py同级目录产生一个新的translation文件夹,结构如下。LC开头的文件夹下还有一个名为message.po的文件。

  5. 手动添加翻译
    是的你没有看错!还是需要手动翻译!
    在message.po中,msgid对应的是提取出的待翻译的词,msgstr是需要我们手动填入的翻译结果。 我们需要做的就是把所有词对应翻译好。
  6. 在终端执行以下命令,编译翻译结果
    pybabel compile -d translations
    

    执行完后会生成一个messages.mo的编译文件,此文件生成即代表翻译结束!


四、运行flask项目

大功告成,此时运行flask项目,虽然我们默认的babel地区语言是‘en’英文,但get_locale函数会获取到我们的浏览器推荐语言,返回"zh_CN",所以页面将会呈现中文翻译。


五、翻译的更新或修改

很简单,如果需要增加翻译,首先去相应的html用之前相同的方法把需要翻译的内容框起来。然后重新执行一次翻译模板提取语句:

 pybabel extract -F babel.cfg -o messages.pot .

message.pot文件会更新, 此时再执行一次翻译更新语句:

 pybabel update -i messages.pot -d translations

此命令可以将之前的翻译合并到新的文件中,此时translation文件夹中的messages.po文件会更新,在其中将需要添加的翻译补充上,或是将需要修改的翻译修改即可

最后再次执行编译语句,更新完成!

 pybabel compile -d translations

六、翻译套路总结

固定套路:flask_babel配置好以后

  1. pybabel extract -F babel.cfg -o messages.pot . 提取翻译模板
  2. pybabel init -i messages.pot -d translations -l zh 生成需要翻译成的语言模板
  3. 在对应文件夹中修改messages.po 添加相应翻译
  4. pybabel compile -d translations 编译生成翻译文件

修改翻译套路 (如果没有添加 1、2、3可省略):

  1. 添加或改变html中框起来的文字
  2. pybabel extract -F babel.cfg -o messages.pot . 重新提取翻译模板
  3. pybabel update -i messages.pot -d translations 合并更新翻译
  4. 在对应文件夹中编辑messages.po 添加或修改相应翻译
  5. pybabel compile -d translations 重新编译生成翻译文件

拓展:在页面中实现手动切换语言

这里简单介绍我采用的思路,我们的页面右上角有一个select下拉框(如下),用于点击切换语言。在某一页点击后,整个页面的语言就会切换,已中英切换为例。

  1. 首先给select下选框添加一个id,方便定位

  2. 之后修改get_locale函数并且新建一个函数set_locale ,代码如下

    set_locale函数是点击切换语言后,利用ajax调用的函数。它会首先获取前端传递过来的语言,然后判断语言,利用response给页面设置一个cookie,用来标识当前页面应该翻译成的语言。

    get_locale函数中获取前面设置的cookie值,然后返回cookie值中的语言,zh_CN或en,也就是设置当前babel的语言

    @babel.localeselector
    def get_locale():cookie = request.cookies.get('locale')if cookie in ['zh_CN', 'en']:return cookiereturn request.accept_languages.best_match(app.config.get('BABEL_DEFAULT_LOCALE'))# 没有cookie时,默认为 en@app.route("/set_locale")
    def set_locale():lang = request.args.get("language")response = make_response(jsonify(message=lang))if lang == 'English':refresh()response.set_cookie('locale', 'en')return responseif lang == '汉语':refresh()response.set_cookie('locale', 'zh_CN')return responsereturn jsonify({"data": "success"})
    
  3. js代码,设置select下拉框的change函数,一旦当前选择改变(切换语言),就用ajax调用上面的set_locale函数。

    <script>$("#language_switch").change(function(){$.ajax({url: '/set_locale',type: 'GET',data:{"language": $(this).val()},success: function (ret) {location.reload();}})});
    </script>
    
  4. 下拉框改变后,右上角显示的语言也需要改变。例如点击汉语,右上角就需要一直显示汉语。一般需要用js来实现动态改变。这里有个小技巧可以将English和汉语都用{{ _(" ") }}框起来进行翻译,English翻译成汉语,汉语翻译成中文,这样就实现了动态改变!


部分效果图



踩坑总结

  1. 在更新翻译时,有的词汇框起来后,提取后但并没有在messages.po中发现,一般是因为#, fuzzy关键字。此关键字我的理解是它会判断出一些重复的字词,然后将其按照你之前的翻译进行自动翻译。但有时会不准确(经常。。) 如以下图片中,原文和自动翻译不符。删掉这一行(红色框起来的部分)即可。

  2. 课设开发时需要使用git,我为了防止代码在merge时出问题,一般会将整个项目文件夹复制备份。这种情况下,我有时会遇到执行pybabel extract -F babel.cfg -o messages.pot . 提取命令没有反应的情况。多次观察后发现,我在源项目中执行这个语句,结果在备份文件夹中新建了messages.po文件。目前为止原因,可能是它会自动寻找路径,但由于我两份项目文件夹是复制,它就找错了根目录。

  3. 遇到特殊符号,例如原文或翻译中带有单引号’或双引号"等,要用转义字符反斜杠\进行转义,否则会报错。

  4. 大段文字直接框选即可,不用担心行间空格,没有影响。

  5. 字符等建议不框起来,只框纯文字部分,这样后面翻译也好操作。例如“单位:$”,只需按照{{ _(“单位”) }}操作即可。

  6. 极少数情况下设置好zh_CN语言页面却没有翻译,那么可以将上面的zh_CN改成zh_Hans_CN用同样的方法生成文件夹进行翻译。但据我观察zh_CN生成的messages.po文件中自动标识的语言也是zh_Hans_CN,所以此问题可能一般不会遇见。

最后推荐另一篇好文Flask-Babel实现国际化,欢迎大家交流指正!

一文搞懂利用Flask-Babel实现网页多语言翻译切换相关推荐

  1. 一文搞懂HMM(隐马尔可夫模型)-Viterbi algorithm

    ***一文搞懂HMM(隐马尔可夫模型)*** 简单来说,熵是表示物质系统状态的一种度量,用它老表征系统的无序程度.熵越大,系统越无序,意味着系统结构和运动的不确定和无规则:反之,,熵越小,系统越有序, ...

  2. 一文搞懂AWS EC2, IGW, RT, NAT, SG 基础篇下

    B站实操视频更新 跟着拉面学习AWS--EC2, IGW, RT, NAT, SG 简介 长文多图预警,看结论可以直接拖到"总结"部分 本文承接上一篇文章介绍以下 AWS 基础概念 ...

  3. 一文搞懂 Traefik2.1 的使用

    原文链接:一文搞懂 Traefik2.1 的使用 一文搞懂 Traefik2.1 的使用 核心概念 安装 ACME 中间件 灰度发布 流量复制 TCP 简单 TCP 服务 带 TLS 证书的 TCP ...

  4. 一文搞懂 Cocos Creator 3.0 坐标转换原理

    一文搞懂 Cocos Creator 3.0 坐标转换原理 屏幕坐标 UI 触点坐标 UI 多分辨率适配方案 UI 触点获取 不同坐标之间的转换 屏幕坐标与 3D 节点世界坐标互转 3D 节点之间的坐 ...

  5. 一文搞懂BN、LN、IN、GN的区别

    一文搞懂BN.LN.IN.GN的区别 批归一化(BN)已经成为许多先进深度学习模型的重要组成部分,特别是在计算机视觉领域.它通过批处理中计算的平均值和方差来规范化层输入,因此得名.要使BN工作,批大小 ...

  6. 一文搞懂如何使用ArcGIS API for Python训练深度学习模型

    一文搞懂如何使用ArcGIS API for Python训练深度学习模型 文章目录 一文搞懂如何使用ArcGIS API for Python训练深度学习模型 写在前面 一.ArcGIS API f ...

  7. 网络知识扫盲,一文搞懂 DNS

    在找工作面试的过程中,面试官非常喜欢考察基础知识,除了数据结构与算法之外,网络知识也是一个非常重要的考察对象. 而网络知识,通常是很抽象,不容易理解的,有很多同学就在这里裁了跟头.为了更好地通过面试, ...

  8. 【显卡】一文搞懂显卡

    [显卡]一文搞懂显卡 文章目录 [显卡]一文搞懂显卡 1. 前言介绍 1.1 CPU和显卡的区别 1.1.1 作用不同 1.1.2 结构不同 1.1.3 应用场景不同 1.2 三个著名的显卡公司 2. ...

  9. 一文搞懂极大似然估计

    极大似然估计,通俗理解来说,就是利用已知的样本结果信息,反推最具有可能(最大概率)导致这些样本结果出现的模型参数值! 换句话说,极大似然估计提供了一种给定观察数据来评估模型参数的方法,即:" ...

  10. 计算机科学与技术要机械硬盘,机械硬盘避坑大法:一文搞懂PMR和SMR有什么区别...

    原标题:机械硬盘避坑大法:一文搞懂PMR和SMR有什么区别 存储市场上一直存在固态硬盘(SSD)和机械硬盘(HDD)的竞争.论综合性能,SSD远高于HDD,是大家选购存储设备时的理想选择.早期消费级S ...

最新文章

  1. 酷狗kuGoo 2007 和 flex有冲突
  2. 实现BFS之“营救”
  3. 排序算法有哪些_超强整理,科班算法岗的秋招之路
  4. android 弹窗in,Android监听程序处于INACTIVITY(未操作状态)时间并作出相应的操作
  5. zabbix数据库分表的实现
  6. fat32文件系统详细介绍_文件系统介绍
  7. 阿里云免费证书SSL下载及安装
  8. 使用Laravel和Vue.js2.5进行服务器端渲染
  9. 模拟一个简单的购房商贷月供计算器,按照总利息和每月还款金额
  10. html桌面共享文件夹,win7共享文件夹在哪? win7和win10怎么共享文件夹
  11. BaiduMap SDK-Location自定义定位图标
  12. manjaro xfce 环境配置
  13. 《和平精英》新模式,玩法竟跟《使命召唤》和《王牌战士》类似?
  14. Nature子刊:教你零基础开展微生物组数据分析和可视化
  15. WormHole是一个简单、易用的api管理平台,支持dubbo服务调用
  16. 优化问题-目标函数确定
  17. 如何使用eclipse开发单片机程序
  18. git删除未监视的文件(untracked files)命令用法
  19. classList属性配合内置方法add()、remove()、toggle(),添加或删除某个类,以此改变CSS样式
  20. java 继承、super、this、抽象类

热门文章

  1. grafana 中国地图 echarts
  2. device-monitoring-studio(串口监控软件)的使用方法
  3. Flash制作(简单)电子相册
  4. 计算机机房综合布线方案,计算机网络设备施工方案(不含综合布线)(word版)
  5. 灵悟礼品网上专卖店Sprint计划
  6. jsp论文参考文献(2020最新)
  7. Grails集成Quartz插件实现定时任务(Job)
  8. 小试牛刀——搭建一个周报管理系统
  9. kali新手入门教学(16)--如何在校园网下使用桥接模式上网
  10. 安卓没有第三方rec获取root教程,成功率90%