[英]How to get "python -m venv" to directly install latest pip version
作為新 python 版本編譯步驟的一部分,我獲取並運行get-pip.py
,以便在 python 可執行文件旁邊安裝最新的 pip:
$ /opt/python/3.7.0/bin/python --version
Python 3.7.0
$ /opt/python/3.7.0/bin/pip --version
pip 18.0 from /opt/python/3.7.0/lib/python3.7/site-packages/pip (python 3.7)
我在/opt/python
下有 25 個這樣的版本,盡管我主要使用不是 EOL 的每個 Major.minor 版本的五個最新版本。 為了設置環境,我曾經使用-p /opt/python/XYZ/bin/python
選項運行virtualenv
或我的virtualenvutils
以獲得具有特定版本的虛擬環境。
在 Python 3.7 中,這會給出 imp 模塊棄用警告:
$ virtualenv -p /opt/python/3.7.0/bin/python /tmp/py37virtualenv
Running virtualenv with interpreter /opt/python/3.7.0/bin/python
Using base prefix '/opt/python/3.7.0'
/opt/util/virtualenvutils/lib/python3.6/site-packages/virtualenv.py:1041: DeprecationWarning: the imp module is deprecated in favour of importlib; see the module's documentation for alternative uses
import imp
New python executable in /tmp/py37virtualenv/bin/python
Installing setuptools, pip, wheel...done.
我幾乎不希望這會在 virtualenv 中得到解決,因為至少從 2014 年開始就有PendingDeprecationWarning
(從這個問題的輸出中可以看出)
在調查替換virtualenv
與python -m venv
在virtualenvutils
,我首先創建一個新的venv
用手基於虛擬環境:
$ /opt/python/3.7.0/bin/python -m venv /tmp/py37venv
$ /tmp/py37venv/bin/pip --version
pip 10.0.1 from /tmp/py37venv/lib/python3.7/site-packages/pip (python 3.7)
那有一個舊的pip
版本! 如果你使用它,你會得到:
您使用的是 pip 版本 10.0.1,但是版本 18.0 可用。
您應該考慮通過“pip install --upgrade pip”命令升級
在使用virtualenv
創建的虛擬環境中,您會立即獲得最新版本:
$ /tmp/py37virtualenv/bin/pip --version
pip 18.0 from /tmp/py37virtualenv/lib/python3.7/site-packages/pip (python 3.7)
我可以運行創建后步驟:
/tmp/py37venv/bin/pip install -U --disable-pip-version-check pip
這將需要額外的時間。 如果pip
有一些安全更新,這意味着運行非安全版本以獲得安全版本,這是一個理想的攻擊點。
從virtualenvutils
執行多個步驟來創建pip
-less virtualenv 然后使用get-pip.py
添加pip
get-pip.py
。 從命令行這不是那么簡單:
$ /opt/python/3.7.0/bin/python -m venv --without-pip /tmp/py37venvnopip
$ /tmp/py37venvnopip/bin/python -c "from urllib.request import urlopen; response = urlopen('https://bootstrap.pypa.io/get-pip'); open('/tmp/tmp_get_pip.py', 'w').write(response.read())"
$ /opt/python/3.7.0/bin/python /tmp/tmp_get_pip.py
......
$ /opt/python/3.7.0/bin/pip --version
來自 /opt/python/3.7.0/lib/python3.7/site-packages/pip (python 3.7) 的 pip 18.0
是什么導致/opt/python/3.7.0/bin/python -m venv
采用舊的pip
版本? 3.7.0 發布時那個版本可用嗎?
如何以某種方式更新我在/opt/python/3.7.0
下的安裝,以便使用/opt/python/3.7.0/bin/python -m venv
創建一個具有最新pip
版本的 virtualenv,而無需恢復到腳本、別名或使用多個命令? 在/opt/python/3.7.0
下安裝最新的pip
顯然是不夠的。
有兩個捆綁的輪子:
/opt/python/3.7.0/lib/python3.7/ensurepip/_bundled/setuptools-39.0.1-py2.py3-none-any.whl
/opt/python/3.7.0/lib/python3.7/ensurepip/_bundled/pip-10.0.1-py2.py3-none-any.whl
我懷疑我需要更新這些。 有沒有比手動更新更好的方法? /some/python -m venv
一些選項會很好。
(並且運行/some/python -m ensurepip --upgrade
不起作用)
運行已棄用的/opt/python/3.7.0/bin/pyvenv
具有相同的舊pip
版本問題。
訣竅不是安裝pip 的捆綁版本(它幾乎總是過時的),而是使用它來安裝來自 Internet 的最新版本。
標准庫venv
提供了一個--without-pip
標志,可以在這里提供幫助。 創建沒有 pip 的虛擬環境后,您可以直接“執行”ensurepip 的輪子,這要歸功於 Python 的 zip 導入器。 這比安裝 pip 然后立即使用相同的 pip 安裝卸載自身並升級更快,也更簡單。
代碼勝於雄辯,所以這里是我描述的過程的示例 bash 函數:
# in ~/.bashrc or wherever
function ve() {
local py="python3"
if [ ! -d ./.venv ]; then
echo "creating venv..."
if ! $py -m venv .venv --prompt=$(basename $PWD) --without-pip; then
echo "ERROR: Problem creating venv" >&2
return 1
else
local whl=$($py -c "import pathlib, ensurepip; whl = list(pathlib.Path(ensurepip.__path__[0]).glob('_bundled/pip*.whl'))[0]; print(whl)")
echo "boostrapping pip using $whl"
.venv/bin/python $whl/pip install --upgrade pip setuptools wheel
source .venv/bin/activate
fi
else
source .venv/bin/activate
fi
}
如果您更喜歡舊項目virtualenv
,它還提供--no-pip
、 --no-setuptools
和--no-wheel
標志以在 Python 2.7 上實現相同的目標。
Python 3.9 的venv
可能會獲得一個venv
--upgrade-deps
選項來自動執行此操作,有關更多信息,請參閱https://bugs.python.org/issue34556 。
我使用upgrade-ensurepip
來更新作為ensurepip
包一部分的那些pip
和setuptools
輪文件。 它不像能夠通過pip
升級ensurepip
那樣優雅,但它仍然比手動升級ensurepip
可取。
這是預期的行為。 python -m venv
調用python -m ensurepip
來安裝pip
並且這個答案表明即使使用--upgrade
選項, ensurepip
也只會安裝捆綁版本。 沒有任何官方選項來更新捆綁的pip
和setuptools
。
好吧,我也沒有解決這個問題的好主意,因為它只是設計的行為。 我想給出兩個建議:
使用pipenv
。 真的很好! 並且未來會是下一代官方的包管理器(雖然目前Pypi的結構有很大的問題。總之,包管理器只能通過下載整個包來決定依賴。這給了一個巨大的難度構建依賴關系圖。)。
實現您的自定義EnvBuilder
,實際上有一個關於此的官方示例。 在示例中,它還使用get-pip.py
來安裝最新的pip
。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.