關於PyInstaller
將程序運行需要的包和解釋器打包起來。
官方文檔:https://pyinstaller.readthedocs.io/en/stable/requirements.html
打包到一個文件夾
pyinstaller main.py
打包成一個可執行文件
運行時會創建一個臨時文件夾,將需要的包複製到臨時文件夾中,因此稍慢一些,正常結束時會自動刪除,異常結束可能不會刪除臨時文件夾。
pyinstaller --onefile main.py # pyinstaller -F main.py
pyinstaller --onefile --windowed main.py # 窗口應用
隱藏源代碼
打包的應用不包含任何源代碼,不過編譯成pyc文件,可以被反編譯暴露代碼邏輯。
如果想更徹底的隱藏源代碼,使用CPython編譯,再用pyinstaller打包。
pyinstaller還可以對python字節碼進行加密,不過也可以被輕易得到祕鑰解密得到字節碼。
如何使用
執行pyinstaller main.py
,在當前目錄自動建立兩個目錄build
和dist
,還生成了一個main.spec
文件。其中build
放了build日誌和duild過程中需要的文件,dist
中放了打包的包和生成的可執行文件。main.spec
後面會仔細講。
UPX
UPX壓縮可執行文件和庫,使得更小。運行時動態解壓。
加密python字節碼
需要先安裝PyCrypto模塊,使用參數--key={16char}
多版本
在虛擬環境下pyinstaller
支持不同的python版本.
在不同虛擬機下pyinstaller
以支持不同的OS.
sepc文件
可用pyi-makespec main.py
命令生成spec文件,暫時不進行打包。
其中最長需要修改的就是datas
這個部分,可以將代碼中用到的文件一起打包,例如datas=[('./data/1.img', './data/'), ('./model/detect.weights', '.')]
,格式是(相對於spec的路徑,相對於可執行exe的路徑)。不過好像打包之後手動複製過去也行。
Maximum recursion depth exceeded:
遞歸層數過深,可以通過在main.spec文件中添加以下兩行代碼解決
# -*- mode: python -*- import sys sys.setrecursionlimit(5000) #5000可根據情況修改
Cannot find existing PyQt5 plugin directories:
找不到PyQt5,這種情況可能你是用conda安裝的PyQt5,重新用pip安裝一下可以解決這個問題。
You may load I/O plugins with the skimage.io.use_plugin
command. A list of all available plugins can be found using skimage.io.plugins()
:
將main.spec中的相關地方修改成以下形式:
from PyInstaller.utils.hooks import collect_data_files, collect_submodules datas = collect_data_files("skimage.io._plugins") hiddenimports = collect_submodules('skimage.io._plugins')
實際打包過程中由於代碼中使用的包不同可能還會碰到其它的問題,就需要自己去摸索了。
參考