打包你的Python程式~PyInstaller基礎篇


Mar 10, 2020

介紹

  • 開發完的python工具,想發送給親朋好友使用,順便得到一些好棒棒的讚賞,這時候,你需要pyinstaller ,它可以幫你打包相關的python scriptlibrary,編譯出一個執行檔,提供使用者直接操作使用。
    • 罷特!仍有需要注意的地方,可參考底下的 小結1-跨平台問題

準備

  • 強烈建議使用python virtualenv來建構你的開發環境,系統乾淨之外,在執行pyinstaller打包時,可以避免打包不必要的library進來,減少執行檔的大小。

安裝

  • pip install pyinstaller
    • 個人推薦3.4版

基礎指令

  • 安裝完後,咱們先來看看他有哪些功能,開啟terminal 輸入pyinstaller --help ,簡單來說,就是pyinstaller + [功能指令] + [你的python script]

usage: pyinstaller [-h] [-v] [-D] [-F] [--specpath DIR] [-n NAME]                          
                   [--add-data <SRC;DEST or SRC:DEST>]                                     
                   [--add-binary <SRC;DEST or SRC:DEST>] [-p DIR]                          
                   [--hidden-import MODULENAME]                                            
                   [--additional-hooks-dir HOOKSPATH]                                      
                   [--runtime-hook RUNTIME_HOOKS] [--exclude-module EXCLUDES]              
                   [--key KEY] [-d [{all,imports,bootloader,noarchive}]] [-s]              
                   [--noupx] [-c] [-w]                                                     
                   [-i <FILE.ico or FILE.exe,ID or FILE.icns>]                             
                   [--version-file FILE] [-m <FILE or XML>] [-r RESOURCE]                  
                   [--uac-admin] [--uac-uiaccess] [--win-private-assemblies]               
                   [--win-no-prefer-redirects]                                             
                   [--osx-bundle-identifier BUNDLE_IDENTIFIER]                             
                   [--runtime-tmpdir PATH] [--bootloader-ignore-signals]                   
                   [--distpath DIR] [--workpath WORKPATH] [-y]                             
                   [--upx-dir UPX_DIR] [-a] [--clean] [--log-level LEVEL]                  
                   scriptname [scriptname ...]  

...省略 ...

What to generate:
  -D, --onedir          Create a one-folder bundle containing an executable
                        (default)
  -F, --onefile         Create a one-file bundled executable.
  --specpath DIR        Folder to store the generated spec file (default:
                        current directory)
  -n NAME, --name NAME  Name to assign to the bundled app and spec file
                        (default: first script's basename)
  • 功能落落長,沒關係,我們先學會下面的基本指令,建立我們的自信心 :100:
縮寫指令 完整指令 說明
-D --onedir default:將所有的東西打包到一個資料夾中
-F --onefile 將所有的東西打包到一個檔案中,ex: windows的exe檔
--specpath 輸出spec檔案到指定的資料夾
-n Name --name Name 打包的檔名

準備

  • 為了測試pyinstaller厲害的地方,咱們來安裝個GUI工具來測試 pip install PySide2,讓我們打包的程式,點兩下有個UI可以跑出來 :+1:
  • 開啟一個main.py貼上以下的程式碼:
import sys, os
from PySide2.QtWidgets import QApplication, QLabel
from PySide2.QtCore    import Qt

if __name__ == "__main__":

    # 下面指令是告訴QT,我要設計一個600(w)x100(h)大小的Label widget,上面顯示著`OKLA`
    app = QApplication(sys.argv)
    label = QLabel('OKLA')
    label.setFixedSize(300, 100)
    label.setAlignment(Qt.AlignHCenter|Qt.AlignVCenter)
    label.show()

    sys.exit(app.exec_())
  • python main.py執行看看,會跑出如下的UI畫面

Test1: 快速打包(產出執行檔+相依的檔案)

  • 開啟terminal到資料夾下,並輸入以下指令pyinstaller main.py
    • 開始編譯
      -
  • 出現successfully編譯成功啦!

  • 檢查資料夾,會多出資料夾builddist,以及main.spec

檔案 說明
build資料夾 編譯執行檔過程的產物,先不須理會
dist 資料夾 :accept: 編譯的結果,也就是我們要的執行檔
main.spec 其實是根據使用者針對pyinstaller有使用到的功能,整理成spec檔,進階的方式也可以進去裡面修改,會在下一次介紹。

  • 開啟dist/main資料夾,你會發現到一個main執行檔

Test2: 完整打包(打包出一個檔案)

  • 為了避免編譯出錯,我們先將剛剛的distbuild資料夾砍掉,在輸入以下指令,並將他命名為justRunMe

    • pyinstaller -F -n justRunMe main.py, 打包比較久,先吃塊蛋糕:cake:
  • 編譯完後,打開dist資料夾,剛剛的程式都被打包成一個檔案,並命名為justRunMe,點兩下...見證奇蹟的Magic出現了

小結

  • pyinstaller對於python開發者是個方便打包的軟體,這幾個指令足夠應付一般的使用。
  • 不過,在windows及Linux(Ubuntu18.04)有個小地方要注意:

1. 跨平台的問題:

Windows:

  • 打包的東西能夠順利的拷貝到其他的Windows平台上執行,完全沒問題。

Linux(於Ubuntu18.04測試):

  • 如果你打包的系統是python3.6,但運行於python3.5或以下版本的電腦,系統將無法順利運行,原因如下,簡單來說 GLIBC可以往後兼容,但不能往前,所以使用上要注意

2. 編譯後的檔案大小

  • 這篇提到,不同的python版本,編譯出來的檔案大小也會不同。
  • 根據我的測試,不同的pyInstaller版本,打包的結果也會有所不同,推測應該是掃描相依lib時有所不同

  • 我實際測試的結果:
    • pyInstaller 3.4 => 打包後60幾mb
    • pyInstaller>=3.5 => 打包後120幾mb :

Reference

#Python #pyinstaller






你可能感興趣的文章

ASP.NET Core  Web API 入門教學 - 資料庫連線設定 Database First,Scaffold-DbContext Build Failed解決方式

ASP.NET Core Web API 入門教學 - 資料庫連線設定 Database First,Scaffold-DbContext Build Failed解決方式

如何以 NSubstitute 處理 Expression & IQueryable

如何以 NSubstitute 處理 Expression & IQueryable

Secure Apache Using Certbot with Let's Encrypt on Ubuntu 20.04

Secure Apache Using Certbot with Let's Encrypt on Ubuntu 20.04






留言討論




kanter0831 Sep 24, 2020

您好,請教一下
我在Windows平台下能打包成Linux的執行檔嗎???

0618017 Jun 07, 2021

開虛擬機去打包?