Как заставить "python -m venv" напрямую устанавливать последнюю версию pip
Как часть шага компиляции для новой версии Python, я выбираю и запускаю get-pip.py
, чтобы установить последнюю версию pip рядом с исполняемым файлом python:
$ /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)
У меня 25 таких версий под /opt/python
, хотя я в основном использую пять последних версий каждой версии major.minor, которая не является EOL. Для настройки заказа я использовал для запуска virtualenv
или мой virtualenvutils
с -p /opt/python/X.Y.Z/bin/python
возможность получить виртуальную среду с определенной версией.
В 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, так как это имело PendingDeprecationWarning
по крайней мере, с 2014 года (как видно из результатов этого вопроса)
При расследовании замены 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
версия! Если вы используете его, вы получите:
Вы используете версию 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
лишенный virtualenv, а затем добавить 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
pip 18.0 из /opt/python/3.7.0/lib/python3.7/site-packages/pip (python 3.7)
Что вызывает /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
создает virtualenv с последними pip
версия без возврата к сценариям, псевдонимам или с использованием нескольких команд? Имея последние pip
установлен под /opt/python/3.7.0
явно недостаточно.
Есть два колеса в комплекте:
/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
проблема с версией
6 ответов
Хитрость заключается не в том, чтобы установить связанную версию pip (которая почти всегда будет устаревшей), а в том, чтобы использовать ее для установки самой последней версии из Интернета.
Стандартная библиотека venv
предлагает --without-pip
флаг, который может здесь помочь. После создания виртуальной среды без pip вы можете "запустить" колесо surepip напрямую благодаря импортеру zip Python. Это быстрее и менее опасно, чем установка 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] = pathlib.Path(ensurepip.__path__[0]).glob('_bundled/pip*.whl'); 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
flags для достижения того же на Python 2.7.
Python 3.9's venv
может получить --upgrade-deps
возможность автоматизировать это, см. https://bugs.python.org/issue34556 для получения дополнительной информации об этом.
Я использую upgrade-ensurepip
обновить те pip
а также setuptools
файлы колеса, которые являются частью ensurepip
пакет. Это не так элегантно, как возможность обновления ensurepip
с помощью pip
, но все же предпочтительнее делать это вручную.
Это ожидаемое поведение. python -m venv
звонки python -m ensurepip
установить pip
и этот ответ показывает, что ensurepip
установит только в комплекте версию даже с --upgrade
вариант. Официального варианта обновления в комплекте нет. pip
а также setuptools
,
Ну, у меня также нет хорошей идеи, чтобы решить эту проблему, так как это просто спроектированное поведение. Я хотел бы дать два предложения:
использование
pipenv
, Это действительно хорошо! И в будущем он станет официальным менеджером пакетов следующего поколения (хотя существует большая проблема, связанная со структурой текущего Pypi. Короче говоря, менеджер пакетов может определять зависимости только при загрузке всего пакета. Это создает огромные трудности для построение графика зависимостей.).Реализуйте свой обычай
EnvBuilder
На самом деле есть официальный пример по этому поводу. И в примере, он также используетget-pip.py
установить последнюю версиюpip
,
Вот версия сценария @ wim для powershell (7):
ПРИМЕЧАНИЕ. Это жестко запрограммировано в моем каталоге, но я исправлю это, когда выйду с работы:
Function Install-VEnv() {
$py="python"
if (!((Test-Path ./.venv) -and (Get-Item ./.venv).getType().Name -match 'DirectoryInfo')) {
echo "creating venv..."
# TODO fix prompt to not be hardcoded
python -m venv .venv --prompt=tensorflow_models --without-pip
if (!$?) {
Write-Error "ERROR: Problem creating venv"
return 1
} else {
$whl=$(python -c "import pathlib, ensurepip; [whl] = pathlib.Path(ensurepip.__path__[0]).glob('_bundled/pip*.whl'); print(whl)")
echo "boostrapping pip using $whl"
.venv/Scripts/python $whl/pip install --upgrade pip setuptools wheel
. .venv/Scripts/Activate.ps1
}
} else {
. .venv/Scripts/Activate.ps1
}
}
Не стесняйтесь поправлять меня. Все мои знания о PowerShell были получены от призраков...
К вашему сведению, добавлен Python 3.9
--upgrade-deps
варианты обновления pip + setuptools до последней версии на PyPI.
python -m venv .venv --upgrade-deps
Если вы используете virtualenvwrapper, вы можете добавить команду обновленияpostmkvirtualenv
сценарий. Он находится в~/.virtualenvs
папка по умолчанию.
Каждый раз, когда вы создаете новую виртуальную среду, pip будет обновляться. Я знаю, что это не идеальное решение, но оно работает.
# vim ~/.virtualenvs/postmkvirtualenv
pip install --upgrade pip