如何解決Python包依賴(lài)問(wèn)題

以簡(jiǎn)潔高效(指編程較為高效, 而不是運(yùn)行速度)出名的Python, 在包依賴(lài)問(wèn)題上有時(shí)候讓人撓頭.

一些新手復(fù)制了Github上的項(xiàng)目準(zhǔn)備運(yùn)行, 很多時(shí)候會(huì)在包依賴(lài)這一步上卡個(gè)半天.(這里推薦新手最好在基于Linux的系統(tǒng)或者M(jìn)ac上, 一些包[比如Scrapy的Win32相關(guān)依賴(lài)]可能無(wú)法直接通過(guò)包管理工具安裝, 會(huì)讓新手從入門(mén)到放棄). 其他涉及到項(xiàng)目需要到其他機(jī)器部署時(shí), 也會(huì)遇到包依賴(lài)問(wèn)題.

# 這可能是部署過(guò)程中最常見(jiàn)的錯(cuò)誤
ModuleNotFoundError: No Module named 'XXX'

通過(guò)pip輸出依賴(lài)

pip freeze > requirements.txt

這個(gè)命令可能是很多同學(xué)用來(lái)輸出依賴(lài)的命令, 但它輸出的是當(dāng)前環(huán)境下(
筆者默認(rèn)你使用的是Python的虛擬環(huán)境)的所有包, 也就是輸出當(dāng)前你安裝的全部非Python標(biāo)準(zhǔn)庫(kù)包)
筆者在自己終端上試了一下, 輸出的文件如下: (這里暴露了我沒(méi)有按項(xiàng)目建虛擬環(huán)境的爛習(xí)慣(逃)

# 省略N個(gè)庫(kù)
....
Django==1.11.8
django-mongonaut==0.2.21
docopt==0.6.2
Flask==0.10.1
Flask-Bootstrap==3.0.3.1
Flask-Login==0.3.1
Flask-Mail==0.9.0
Flask-Migrate==1.1.0
Flask-Moment==0.2.1
Flask-PageDown==0.1.4
Flask-Script==0.6.6
Flask-SQLAlchemy==1.0
Flask-WTF==0.9.4
ForgeryPy==0.1
html5lib==1.0b3
hyperlink==17.3.1
idna==2.6
incremental==17.5.0
itsdangerous==0.23
Jinja2==2.7.1
lxml==4.1.1
Mako==0.9.1
Markdown==2.3.1
MarkupSafe==0.18
mongoengine==0.9.0
numpy==1.14.0
pandas==0.22.0
parsel==1.3.1
pdfkit==0.6.1
pipreqs==0.4.9
pyasn1==0.4.2
pyasn1-modules==0.2.1
pycparser==2.18
PyDispatcher==2.0.5
pymongo==2.8
PyMySQL==0.7.9
pyOpenSSL==17.5.0
python-dateutil==2.6.1
pytz==2017.3
queuelib==1.4.2
requests==2.18.4
requests-file==1.4.3
scrape==0.9.12
Scrapy==1.5.0
...
# 省略N+1個(gè)庫(kù)

對(duì)于按項(xiàng)目建環(huán)境的同學(xué), 這種輸出方式是沒(méi)有多大問(wèn)題的
只要部署的時(shí)候在終端鍵入pip install -r requirements.txt就可以安裝好依賴(lài)了, 但是對(duì)于沒(méi)有嚴(yán)格區(qū)分項(xiàng)目環(huán)境的同學(xué), 一次性安裝了其他的包, 并不是一個(gè)好的解決方案.

通過(guò)pipreqs庫(kù)輸出依賴(lài)

如這個(gè)庫(kù)的名稱(chēng)所示, 就是為了方便管理依賴(lài)而生.
與pip直接導(dǎo)出全部不同, pipreqs只導(dǎo)出指定項(xiàng)目下Python文件import的庫(kù)
用法如下

# 安裝
pip install pipreqs
# 切換到項(xiàng)目目錄
# 輸出requirements.txt到項(xiàng)目根目錄下
pipreqs --use-local ./

這里我切換到一個(gè)Django項(xiàng)目目錄下, 打開(kāi)requirements.txt, 內(nèi)容是:

pandas==0.22.0
django_debug_toolbar.egg==info
mongoengine==0.9.0
Django==1.11.8

瞬間清爽不少.

通過(guò)Pipenv管理依賴(lài)

Pipenv, 匯集了Pip,Pipfile和Virtualenv的功能贡耽,是一個(gè)強(qiáng)大的命令行工具价认。

這里展示最簡(jiǎn)單的用法

  1. pip install pipenv安裝好庫(kù).
  2. 切換到項(xiàng)目根目錄
  3. 終端鍵入Pipenv install

如果你尚未建立requirements.txt那么將會(huì)得到一個(gè)空白的Pipfile文本文件, 此時(shí)我們?cè)诿钚兄惺褂?code>pipenv install 包名, 會(huì)在Pipefile寫(xiě)入對(duì)應(yīng)包信息, 之后用戶(hù)要安裝依賴(lài)時(shí), 使用pipenv install即可.
如果你已經(jīng)建立, 終端上會(huì)輸出以下信息:

requirements.txt found, instead of Pipfile! Converting…
Warning: Your Pipfile now contains pinned versions, if your requirements.txt did. 
We recommend updating your Pipfile to specify the "*" version, instead.
...

上面的輸出意思是: 找到了requirements.txt, 但不是Pipfile, 正在轉(zhuǎn)換...
Pipefile現(xiàn)在將包含固定版本信息, 如果你的requirements.txt中已包含.
我們推薦升級(jí)你的Pipefile到指定版本...

輸出Pipenv文件, 得到以下內(nèi)容:

[[source]]
url = "https://pypi.org/simple"
verify_ssl = true
name = "pypi"

[packages]
mongoengine = "==0.9.0"
"django-debug-toolbar.egg" = "==info"
django = "==1.11.8"
pandas = "==0.22.0"

[dev-packages]

[requires]
python_version = "3.6"

可以清楚的看到整個(gè)文件結(jié)構(gòu), 第一個(gè)是[source]是安裝庫(kù)所在源, 第二個(gè)是依賴(lài)庫(kù)的信息, 第三個(gè)是當(dāng)你開(kāi)發(fā)環(huán)境所需要的包, 最后一個(gè)是Python版本.
當(dāng)你需要區(qū)分開(kāi)發(fā)環(huán)境和正式版本發(fā)布環(huán)境時(shí), 可以使用以下命令:

pipenv install --dev 包名

如果正式版本發(fā)布時(shí), 鍵入Pipenv install, 將不會(huì)安裝dev標(biāo)記的包
除非其他開(kāi)發(fā)人員鍵入Pipenv install -dev, 才會(huì)安裝所有包.


微信公眾號(hào):程序員的碎碎念

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市读拆,隨后出現(xiàn)的幾起案子靴庆,更是在濱河造成了極大的恐慌,老刑警劉巖东帅,帶你破解...
    沈念sama閱讀 217,734評(píng)論 6 505
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異巩踏,居然都是意外死亡秃诵,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,931評(píng)論 3 394
  • 文/潘曉璐 我一進(jìn)店門(mén)塞琼,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)菠净,“玉大人,你說(shuō)我怎么就攤上這事屈梁∴土罚” “怎么了?”我有些...
    開(kāi)封第一講書(shū)人閱讀 164,133評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵在讶,是天一觀的道長(zhǎng)煞抬。 經(jīng)常有香客問(wèn)我,道長(zhǎng)构哺,這世上最難降的妖魔是什么革答? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,532評(píng)論 1 293
  • 正文 為了忘掉前任,我火速辦了婚禮曙强,結(jié)果婚禮上残拐,老公的妹妹穿的比我還像新娘。我一直安慰自己碟嘴,他們只是感情好溪食,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,585評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布。 她就那樣靜靜地躺著娜扇,像睡著了一般错沃。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上雀瓢,一...
    開(kāi)封第一講書(shū)人閱讀 51,462評(píng)論 1 302
  • 那天枢析,我揣著相機(jī)與錄音,去河邊找鬼刃麸。 笑死醒叁,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的泊业。 我是一名探鬼主播把沼,決...
    沈念sama閱讀 40,262評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼吁伺!你這毒婦竟也來(lái)了智政?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書(shū)人閱讀 39,153評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤箱蝠,失蹤者是張志新(化名)和其女友劉穎,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體宦搬,經(jīng)...
    沈念sama閱讀 45,587評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡牙瓢,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,792評(píng)論 3 336
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了间校。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片矾克。...
    茶點(diǎn)故事閱讀 39,919評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖憔足,靈堂內(nèi)的尸體忽然破棺而出胁附,到底是詐尸還是另有隱情,我是刑警寧澤滓彰,帶...
    沈念sama閱讀 35,635評(píng)論 5 345
  • 正文 年R本政府宣布控妻,位于F島的核電站,受9級(jí)特大地震影響揭绑,放射性物質(zhì)發(fā)生泄漏弓候。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,237評(píng)論 3 329
  • 文/蒙蒙 一他匪、第九天 我趴在偏房一處隱蔽的房頂上張望菇存。 院中可真熱鬧,春花似錦邦蜜、人聲如沸依鸥。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 31,855評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)贱迟。三九已至,卻和暖如春井辆,著一層夾襖步出監(jiān)牢的瞬間关筒,已是汗流浹背。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 32,983評(píng)論 1 269
  • 我被黑心中介騙來(lái)泰國(guó)打工杯缺, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留蒸播,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 48,048評(píng)論 3 370
  • 正文 我出身青樓萍肆,卻偏偏與公主長(zhǎng)得像袍榆,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子塘揣,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,864評(píng)論 2 354

推薦閱讀更多精彩內(nèi)容