Python:使用pyinstaller打包含有gettext locales语言环境的项目

如何使用 pyinstaller 打包使用了 gettext 本地化的项目,最终只生成一个 exe 文件

最近在用 pyhton 做一个图片处理的小工具,顺便接触了一下 gettext,用来实现本地化化中英文转换。项目主要结构如下:

.
|--src # 源码
|  |--package1
|  |--package2
|  |--locales # 本地化文件
|  |  |--en # 英文
|  |  |  |--LC_MESSAGES
|  |  |     |--en.mo
|  |  |--zh # 中文
|  |    |--LC_MESSAGES
|  |       |--en.mo
|  |--GUI.py # 界面
|  |--main.py # 主程序

直接使用 pyinstaller -F src\main.py 命令进行打包,打包后运行在 dist 文件夹中生成的 main.exe 会报错。原因是 gettext 找不到本地化文件。但如果试着将 locales 文件夹复制到 main.exe 的目录下程序能正常运行,说明 pyinstaller 在打包时不会将 locales 文件夹打包进去。

复制 locales 文件夹到可执行文件目录下固然可以运行,但这样用起来会很麻烦。

解决方案

​ 目标是将 locales 目录一起打包进 exe 文件中,查阅 pyinstaller 的官方文档,了解到执行之前的 pyinstaller -F src\\main.py 命令会在目录下生成一个 .spec 文件,pyinstaller 通过该文件的内容来构建应用程序。

the first thing PyInstaller does is to build a spec (specification) file myscript.spec. That file is stored in the –specpath directory, by default the current directory.

The spec file tells PyInstaller how to process your script. It encodes the script names and most of the options you give to the pyinstaller command. The spec file is actually executable Python code. PyInstaller builds the app by executing the contents of the spec file.

使用记事本打开,.spec 文件里面大致长这样(来自官方例子)

block_cipher = None
a = Analysis(['minimal.py'],
     pathex=['/Developer/PItests/minimal'],
     binaries=None,
     datas=None,
     hiddenimports=[],
     hookspath=None,
     runtime_hooks=None,
     excludes=None,
     cipher=block_cipher)
pyz = PYZ(a.pure, a.zipped_data,
     cipher=block_cipher)
exe = EXE(pyz,... )
coll = COLLECT(...)

其中,Analysis 里面有个 datas 参数,用于存放非二进制文件,也就是我们想让程序包含的静态文件。我们只要把 locales 目录填到这里面打包就会添加进去。当然不是填一个路径就好了,data 的格式如下:

–add-data

SRC 就是未打包前的文件路径,DEST 是打包后文件的路径。以我的项目为例,打包前 locales 在 src/locales,打包后我想讲里面的文件放到临时目录的根目录下就填 ./locales,临时目录是什么后面讲。于是在我的 .spec文件里 datas 处就写成 datas=[("src/locales","./locales")]。如果有多个路径就以这样形式 datas=[(src1, dest1), (src2, dest2), ...]就OK。

这样打包部分的配置就改完了,不要急,还要改下源代码。exe 文件在运行时会生成一个 临时目录,我们之前 datas 中的文件也会在该目录下。看看你的源码,如果调用资源用的是相对路径,那读取的是 exe 文件当前的目录,必然是找不到资源的。所以要把源码中相对路径改成临时目录的绝对路径。

sys 中的 _MEIPASS 属性存储了临时目录路径,直接获取即可。如果程序运行环境是打包后的,那么在 sys 中会添加一个 frozen 属性,通过能不能获取 frozen 属性可以判断当前环境是打包前还是打包后,具体详情请查阅 pyinstaller 官方文档(末尾有地址)。打包前就不需要获取临时目录路径了,直接用文件所在目录路径就行。

注意:打包后环境 file 属性不生效

import sys
import os

if getattr(sys, 'frozen', None):
    dir = sys._MEIPASS
else:
    dir = os.path.dirname(__file__)

获取路径 dir,可以使用 os.path.join() 来拼接路径,把源码中调用 datas 中资源地方的路径改成 os.path.join(dir, <打包后相对路径>)<!--打包后相对路径-->

如我的项目中原来的 './locales' 处就变成了 os.path.join(dir, 'locales')

最后一步,打包!不要再输之前的命令了,要使用改过之后的 .spec 文件进行打包,输入 pyinstaller -F &#x6587;&#x4EF6;&#x540D;.spec 就完成了。

参考文献

Original: https://www.cnblogs.com/WindChenCC/p/15851222.html
Author: WindChen
Title: Python:使用pyinstaller打包含有gettext locales语言环境的项目

原创文章受到原创版权保护。转载请注明出处:https://www.johngo689.com/815065/

转载文章受原作者版权保护。转载请注明原作者出处!

(0)

大家都在看

  • Django-11-最最最常用的数据库查询

    数据库的增删查改(CRUD),包括增加(Create)、查阅(Read)、更新(Update)以及(Delete),都来自ORM的核心 模型类.管理器对象。该对象是模型自带的对象方…

    Python 2023年8月4日
    054
  • 带薪玩一周游戏,还要涨工资

    带薪玩游戏,是多么开心的事情,我就找到了。 前段时间,公司接到一个模拟业务场景的项目,需要在图形界面上模拟业务场景,比如人跑动,拖拽物体等,从而获取不太业务场景的模拟数据。 由于商…

    Python 2023年9月20日
    060
  • np.random.permutation函数

    目录 一:函数介绍 二:实例 2.1 直接处理数组或列表数 2.2 间接处理:不改变原数据(对数组下标的处理) 2.3 实例:鸢尾花数据中对鸢尾花的随机打乱(可以直接用) 一:函数…

    Python 2023年8月24日
    0105
  • 目标检测算法部署网页web端3-页面美化与前端获值后端处理-Flask接口

    前面写了web端的页面,但是界面明显不太好看,为了方便优化页面,我们常常会使用现成的框架来封装好,比如使用layui 官网地址号:layui 下载安装包后 像这样放置即可 我们来对…

    Python 2023年8月12日
    068
  • Pygame教程系列二:MoviePy视频播放篇

    【前言】 在pygame 2.0.0版本之前,播放视频可以使用 pygame.movie.Movie(‘xxxx.mpg’)播放(只支持.mpg格式的视频),但是在pygame2….

    Python 2023年9月21日
    064
  • 用Python实现序列帧播放器

    用Python实现序列帧播放器 注意 以下所有代码 不可直接使用,若要使用请到百度网盘上下载源码!链接:https://pan.baidu.com/s/1P0x8ddbnn5veF…

    Python 2023年9月21日
    0100
  • 这几个Matplotlib绘图技巧,真的是太实用了

    今天呢,小编来为大家分享几个用 matplotlib模块绘制图表的小技巧,希望看了之后会对大家有不少的帮助!! 在图表中插入图片 如果我们想要在绘制的图表中插入图片,具体该怎么来实…

    Python 2023年8月31日
    084
  • opencv图像处理基础(python)

    numpy 访问图像 Numpy.array库是Python处理图像的基础。 在OpenCV中, 通道的顺序是B→G→R 在OpenCV中,最小的数据类型是无符号的8位数 可以使用…

    Python 2023年8月27日
    060
  • 点云作业python基础

    DataFrame是pandas包中的重要数据类型,相当于表格数据类型,常用的操作如下: 创建DataFrame import pandas as pd df = pd.DataF…

    Python 2023年8月20日
    061
  • python绘制各种摆线(包括心形线星形线等,超炫酷)

    本文有更加优雅的实现方式:Python高级动态绘图系统:复杂曲线的轨迹演示 文章目录 * – + 摆线 + 外摆线和心脏线 + 内摆线与星形线 摆线 最简单的旋轮线就是…

    Python 2023年9月3日
    093
  • torch.load()加载模型及其map_location参数

    函数格式为: torch.load(f, map_location=None, pickle_module=pickle, **pickle_load_args),一般我们使用的时…

    Python 2023年10月27日
    057
  • 数据分析与数据挖掘研究之一

    前言:之前做过一些数据分析与数据挖掘相关的工作,最近抽空将之前做的内容简单整理一下,方便查看,主要使用R语言和PERL脚本语言,使用TCGA和ICGC数据库中的临床数据,做类似的分…

    Python 2023年10月22日
    043
  • Part14:Pandas批量拆分与合并Excel文件

    Pandas批量拆分Excel与合并Excel 实例演示: 1.将一个大Excel等份拆成多个Excel 2.将多个小Excel合并成一个大Excel并标记来源 #&#x6…

    Python 2023年8月8日
    086
  • 图像恢复 SWinIR : 彻底理解论文和源代码 (注释详尽)

    文章目录 * – 1. SwinIR 论文 – 2. SWinIR 网络结构 – + 2.1 整体框架 + 2.2 浅层特征提取 + 2.3 深…

    Python 2023年9月15日
    0103
  • python矩阵乘法基础小结

    Python的numpy矩阵乘法相关:1.直接对array之间使用 表示进行点乘,维度较低的array_x1最高纬度(设为n维)的数字,必须与纬度较高array_x2对应维度上的数…

    Python 2023年8月26日
    081
  • Python Pandas 数据分析工具透视表(pivot table)

    数据透视表概念 数据透视表是Excel中常用的工具,本片文章的重点不是认识数据透视表,所以找了一片文章,供大家参考。>>>Excel学习笔记-数据透视表 透视表操…

    Python 2023年8月17日
    0101
亲爱的 Coder【最近整理,可免费获取】👉 最新必读书单  | 👏 面试题下载  | 🌎 免费的AI知识星球