淺談Python專案開發&管理

老胡的儲物櫃發表於2021-08-26

本文主要探討的是個人在Python專案開發&管理這塊的一些經驗之談,經過在團隊實踐後主要內容總結如下:

  • 基礎環境管理

  • 編碼標準&規範化

  • 遠端開發

  • 專案腳手架

???? 環境管理

使用AnacondaPipenv共同管理Python專案環境

環境管理這塊是個很普遍的問題,其面臨的問題如下:

  • 如何對不同專案,任意Python版本的環境進行管控

  • 如何對不同專案,內外網Python依賴庫進行管控(有些包是公司內部開發,那麼對於專案來說就需要同時管控內外網下的第三方包)

對於上面提到的問題,實際上解決問題的方向都是一致的,那就是引入虛擬環境,使得每個專案都有一個專屬環境就可以了。

如果你的公司在生產環境中使用Python有一定的年頭,如3~5年,可能有一些老的專案還在用Python3.5甚至Python2.7,那麼基本都會面臨不同專案不同Python版本的問題。

此時,面對的問題就是第一點提到的不同專案需要的Python環境不同的問題。對於這種情況,可以直接在電腦下載各個版本的Python環境,隨後到任意專案下就選用任意版本的Python環境即可,舉個例子:

  • 專案 P_01 依賴Python3.6:分配Python3.6環境

  • 專案 P_02 依賴Python3.7:分配Python3.7環境

對於各個不同版本Python環境的管理,個人推薦使用Anaconda[1]

# Mac Linux Win全平臺支援
# 以Linux為例
wget https://mirrors.tuna.tsinghua.edu.cn/anaconda/archive/Anaconda3-2021.05-Linux-x86_64.sh
chmod a+x ./Anaconda3-2021.05-Linux-x86_64.sh
./Anaconda3-2021.05-Linux-x86_64.sh

安裝完成後,即可建立不同的Python環境:

# 其他版本的建立類似
conda create -n python36 python=3.6
# 列出Python環境
conda env list

那麼對於專案 P_01,只需要在專案根目錄下進行剛才建立的虛擬環境即可source activate python36,進入相關環境後直接在環境內安裝相關依賴包即可。

也就是說,環境 python36 是專為專案 P_01 服務的,其他專案只需要再建立一個環境即可。接下來說說為什麼引入Pipenv

  • 支援對環境和第三方依賴進行管理

  • 很好地管控不同環境下的第三方庫,如專案的一部分依賴來自官方,一部分來自公司內部(不能公開)

以我個人舉例,構建一個Python專案的基礎步驟就是:

mkdir py_demo && cd py_demo
# 如果專案依賴3.6
pipenv install --python ~/anaconda3/envs/python36/bin/python3.6 --skip-lock
# 如果專案依賴3.7
pipenv install --python ~/anaconda3/envs/python37/bin/python3.7 --skip-lock

是不是很方便?這一番介紹下來如果你對AnacondaPipenv的功能邊界還是有疑惑的話,可以看看下方我畫的一張圖(個人理解,歡迎討論):

淺談Python專案開發&管理
pipenv

???? 編碼標準

對於編碼標準,我推薦跟著社群的PEP8走,之前我就已經翻譯過一篇如何用 PEP 8 編寫優雅的 Python 程式碼[2],所以編碼標準這塊就麻煩諸位移步看下哈。

淺談Python專案開發&管理
Guido 推薦規範

???? 規範化

所謂標準,如果純靠人自覺來遵守,實際上就比較理想主義,實際操作下來,我在團隊中在規範化這塊寫了個ci工具,核心就是使用了以下工具來自動標準規範化:

  • black:程式碼格式化

  • pylint:程式碼檢查

  • isort:導包規劃化

  • flake8(mccabe):程式碼複雜度檢查

接下來我將以VS Code為例,說一下怎麼配置,先進行基礎的準備工作:

pip install black pylint flake8

開啟VS Code後請先在設定中配置好 python  外掛關於 black&isort  的執行路徑:淺談Python專案開發&管理淺談Python專案開發&管理

將路徑配置好之後,然後在專案根目錄新增 setup.cfg

[isort]
multi_line_output=3
include_trailing_comma=True
force_grid_wrap=0
use_parentheses=True
line_length=88
known_first_party=src
lines_between_types=1
default_p=THIRDPARTY
ps=FUTURE,STDLIB,THIRDPARTY,FIRSTPARTY,LOCALFOLDER
[flake8]
ignore = D203
max-line-length = 88
exclude = .git,__pycache__,old,build,dist
max-complexity = 10

注意這裡,我們做了flake8關於複雜度的配置,實際上就相當於在根目錄執行:

flake8 --config=./setup.cfg --exit-zero --max-complexity 10 src

最後再針對專案進行以下設定:

  • 相關配置檔案的路徑

  • 自動儲存即自動格式化的

編輯.vscode/settings.json配置檔案即可:

{
    "python.linting.pylintEnabled": true,
    "python.sortImports.args": [
        "--settings-path=${workspaceFolder}/setup.cfg"
    ],
    "editor.codeActionsOnSave": {
        "source.organizeImports": true
    },
    "python.formatting.provider": "black",
    "python.envFile": "${workspaceFolder}/.env",
    "python.linting.enabled": true
}

說完了標準化,接下來整起來程式碼分析工具Pylint ,它分析程式碼中的錯誤,查詢不符合程式碼風格標準和有潛在問題的程式碼。

Pylint  本身的校驗還算是比較嚴格,所以需要新增一些配置限制一些沒必要的錯誤提示,可以在專案根目錄下建立檔案 .pylintrc :

[FORMAT]
max-line-length=120
[MESSAGES CONTROL]
disable=C0103,C0330,W0221,R0913,R0914,R0903,R0902,R0801

然後在專案根目錄下執行:

pylint --rcfile=./.pylintrc --exit-zero src

隨後就可以看到輸出的優化建議以及評分:

淺談Python專案開發&管理
score

???? 遠端開發

對於遠端開發,我主要調研以下兩個方向:

  • 在伺服器搭建遠端開發環境,基於code-server[3]

  • 本地編碼,利用遠端伺服器執行,Pycharm可行,VS Code應該也行

最終我選用了第一個方案,主要其雲開發的優勢非常吸引人:

  • 何時何地能聯網就能編碼

  • 基於 Code Server 和 VS Code 一樣的手感,香

其實Code Server的安裝非常簡單,直接執行以下命令(先安裝 Docker):

mkdir ~/code_data && cd ~/code_data
docker run -it --user root -p 0.0.0.0:8080:8080 -v "$PWD:/home/coder/project" -e PASSWORD="your password" -d codercom/code-server

淺談Python專案開發&管理我基於官方映象還增加了以下個性化配置,這塊大家可以根據自己的喜好來配置:

  • 支援 oh my zsh

  • 使用國內源

  • 支援 anaconda&pipenv 專案管理

  • 預設搭建了 Python 開發環境

    • pipenv 管理專案

    • black&isort&pylint 進行標準化

專案腳手架

基於公司業務形成開發標準,再基於開發標準抽象出業務模組,有了通用的業務模組實際上我們就可以構建自己的專案腳手架,我在自己團隊中針對業務方向抽象了三個方向的開發程式碼模板:

  • API 服務模板:針對介面服務的通用模板,開發者直接在對應檔案寫邏輯即可,預設配好了服務發現、日誌、配置熱更、資料庫操作、狀態碼管理等常規模組

  • 軟實時服務模板:消費資料團隊提供的主題,根據輸入資料秒級響應結果,比如實時消費登入資料判斷是否登入異常,配置了常見模組如消費模組、資料庫操作模組、熱更配置開發者直接在指定函式寫呼叫業務即可

  • 離線服務模板:針對特徵提取,基於各大雲商,封裝各種 ETL 常用模組,一切目的是為了提升開發效率

有了一些通用的模板,實際上就可以基於模板形成自己的腳手架,舉個例子大家可能就比較清楚了,比如某個開發者想要開發一個離線特徵提取服務,假設我們腳手架名字叫做oc_demo,那麼他只需在終端執行oc_demo,然後跟著腳手架走:

# 設定作者名
export PROJECT_AUTHOR=howie6879
# 利用離線腳手架建立專案
oc_demo my_project

此時,腳手架就會工作,下拉通用模板,並做一些個性化改動,輸出如下:

Cloning into 'my_project'...
remote: Enumerating objects: 1004, done.
remote: Counting objects: 100% (72/72), done.
remote: Compressing objects: 100% (59/59), done.
remote: Total 1004 (delta 27), reused 44 (delta 13), pack-reused 932
Receiving objects: 100% (1004/1004), 3.81 MiB | 2.32 MiB/s, done.
Resolving deltas: 100% (568/568), done.
######################################################
離線計算專案構建完成^_^
專案名稱:my_project
作者:howie6879
建議Python版本:Python3.6
專案環境管理:Pipenv
開始:
    cd my_project
    pipenv install --python PYTHON36_PATH
######################################################

此時進入目錄,作為開發者只需要在邏輯檔案那裡新建ETL即可,再也不用:

  • 每個成員建立不同風格的模組,維護起來麻煩

  • 不用重複性地造或者說複製他人寫好的通用模組

  • 每個專案風格相同,上手快

???? 說明

Python專案管理這塊,上面提到核心內容的都是我2018年基於社群的一些預設推薦方式梳理的(遠端開發除外),可能是我用著一直覺得沒啥問題,所以現在團隊用的還是這套,如果大家有什麼更好的建議,歡迎交流,如果覺得不錯,點個好看分享下吧哈哈。

參考資料

[1]

Anaconda: https://mirrors.tuna.tsinghua.edu.cn/anaconda/archive/

[2]

如何用 PEP 8 編寫優雅的 Python 程式碼: https://www.howie6879.cn/p/%E5%A6%82%E4%BD%95%E7%94%A8pep-8%E7%BC%96%E5%86%99%E4%BC%98%E9%9B%85%E7%9A%84python%E4%BB%A3%E7%A0%81/

[3]

code-server: https://github.com/cdr/code-server

相關文章