Як я можу використовувати файл вимог pip для видалення та встановлення пакунків?


90

У мене є файл вимог pip, який змінюється під час розробки.

Можна pipзмусити видалити пакети, які не відображаються у файлі вимог, а також встановити ті, що з’являються? Чи існує стандартний метод?

Це дозволило б файлу вимог pip бути канонічним списком пакетів - підхід "якщо і тільки якщо".

Оновлення : я запропонував це як нову функцію на https://github.com/pypa/pip/issues/716


3
Ви ДІЙСНО хочете, щоб pip видалив довільні пакети лише тому, що ваша програма їх не вимагає? Звучить трохи небезпечно ...
Скотт Хантер,

11
@ScottHunter Якщо ви знаходитесь у virtualenv без пакетів веб-сайтів, розумно захотіти це зробити.
Michael Mior

1
@ScottHunter Так, якщо використовується контрольоване (віртуальне) середовище, де я хочу визначити, що там є - і в цьому немає нічого іншого, що може спричинити проблеми, наприклад, несподівані залежності.
wodow

@MichaelMior Якщо це відповідь, додайте як відповідь, і я прийму її!
wodow

@wodow Готово. Єдиною причиною, по якій я не розмістив відповідь, є те, що, мабуть, існує більш корисне рішення, яке може допомогти вам досягти бажаного.
Michael Mior

Відповіді:


16

Коротка відповідь - ні, цього не можна зробити за допомогою pip.


32
як каже Стівен нижче:pip uninstall -r requirements.txt
Омміт

31
@Ommit Це не видаляє пакети, які не відображаються у файлі вимог. Він видаляє всі пакунки, які з’являються у файлі.
Майкл Міор

3
@Micheal Mior, ах, я не приділив достатньо уваги оригінальному питанню. Моє ліжко.
Ommit

4
Додайте -yкоманду @Ommit, щоб не натискати Y та вводити багато разів. Вчіться на моїх помилках.
Грег Хілстон,

1
Просто додати: pip uninstall -r requirements.txtбуде видалити лише версії у вашому requirements.txt. boto3==1.10.0Наприклад, якщо ви видалите програму , pip freezeвідобразиться, boto3==1.0.1чи раніше ви її встановлювали (або будь-яку стару версію).
Jordan Mackie

125

Це повинно видалити все, що не є в requirements.txt:

pip freeze | grep -v -f requirements.txt - | grep -v '^#' | xargs pip uninstall -y

Хоча це не буде працювати належним чином з пакетами, встановленими за допомогою -e, тобто зі сховища git або подібного. Щоб пропустити їх, просто відфільтруйте пакунки, починаючи з -eпрапора:

pip freeze | grep -v -f requirements.txt - | grep -v '^#' | grep -v '^-e ' | xargs pip uninstall -y

Тоді, очевидно:

pip install -r requirements.txt

Оновлення за 2016 рік: Ви, мабуть, насправді не хочете насправді використовувати вищевказаний підхід. Перевірте, pip-toolsіpip-sync які досягнення того, що ви, мабуть, прагнете зробити, є набагато надійнішим.

https://github.com/nvie/pip-tools

Оновлення за травень 2016 року:

Тепер ви також можете використовувати pip uninstall -r requirements.txt, однак це досягає в основному протилежного - він видаляє все вrequirements.txt

Оновлення за травень 2019 року:

Перевірте pipenv . У світі управління пакунками багато чого сталося, що робить подібні питання дещо застарілими. Насправді я все ще досить радісно використовую інструменти pip.


5
Це було б чудово. Мені здається хорошим способом змусити розробників бути явними щодо своїх залежностей, порушуючи все, якщо вони встановлюють щось на одному хості вручну, не оновлюючи свої вимоги .txt. Мені було б цікаво побачити, який тип зворотного зв’язку викликає запит на додавання, який створює цю функціональність.
Stephen Fuhry

Це правильна відповідь! Я поклав це в мій project.configфайл для Django на Elastic Beanstalk: 05_pip_clean: command: "pip freeze | grep -v -f requirements.txt - | grep -v '^#' | xargs pip uninstall -y". Тепер я можу відкочувати піп-пакети без відновлення мого середовища, просто використовуючи коментарі в requirements.txt. Це економить мені справжні простої. Дякую!
e.thompsy

чи коли-небудь виводиться піп-заморожування, починаючи з #? Іншими словами, чи потрібен другий grep?
xor

1
Не впевнений, що pip freezeкоментує, але коли-небудь вони можуть додати його до API, і якщо вони це роблять, це буде дійсним. Якщо вони цього не роблять, то вищезазначене не застосовується. Тире дозволяє використовувати stdin з попередньої команди, у цьому випадку тире повідомляє grep, щоб порівняти вміст requirements.txt з результатом pip freeze(результат pip freezeу цьому контексті є синонімом stdin)
Стівен Фурі

1
Я настійно рекомендую pip-інструменти. +1
ron rothman

16

Це не особливість pip, ні. Якщо ви дійсно хочете такого, ви можете написати сценарій для порівняння результату роботи pip freezeз вашимrequirements.txt , але це, швидше за все, буде більше клопоту, ніж це варте.

Використовуючи virtualenv, простіше і надійніше просто створити чисте середовище та (пере) встановити з requirements.txt, наприклад:

deactivate
rm -rf venv/
virtualenv venv/
source venv/bin/activate
pip install -r requirements.txt

6
Може бути корисним просто видалити пакети, яких немає у файлі вимог, якщо деякі пакети (PIL, lxml тощо) потребують тривалої компіляції - особливо якщо це відбувається на реальному сервері, який використовує віртуальне середовище.
Мелінат

@melinath Якщо їх немає у вашому файлі вимог і вони вже встановлені, то компіляція ніколи не повинна повторюватися.
Майкл Міор

1
@MichaelMior - якщо ви не скажете, скажімо, витерти весь virtualenv, як підказує ця відповідь.
мелінат

1
@melinath Але якщо ви стерли virtualenv і пакет не потрібен (і не у вашому requirements.txt), чому він колись буде встановлений знову?
Michael Mior

3
@MichaelMior Я спробую чіткіше вказати свій оригінальний коментар. Здається, ви, можливо, неправильно зрозуміли те, що я висловлював. Уявіть собі простий файл вимог, який містить PIL та lxml. Але тоді ви вирішите, що вам більше не потрібен lxml, і видалите його з файлу вимог. Якщо ви зробите, як пропонується у цій відповіді, і видалите virtualenv, вам доведеться переінсталювати (і перекомпілювати) PIL. Було б ефективніше мати можливість просто видалити lxml (тобто всі пакети, що не містяться у файлі вимог.)
melinath

11

Тепер ви можете передати -r requirements.txtаргумент pip uninstall.

pip uninstall -r requirements.txt -y

Принаймні станом на pip8.1.2, pip help uninstallпоказано:

...
Uninstall Options:
  -r, --requirement <file>    Uninstall all the packages listed in the given requirements file.  This option can be
                              used multiple times.
...

3
Це не видаляє пакети, які не відображаються у файлі. Вона видаляє пакети , які дійсно з'являються в файлі.
Michael Mior

4

Це давнє запитання (але хороше), і з моменту його задачі все істотно змінилося.

В pip-syncодній відповіді є випадкове посилання , але воно заслуговує на свою відповідь, оскільки саме воно вирішує проблему ОП.

pip-sync приймає requirements.txtфайл як вхідний файл і "підробляє" ваше поточне середовище Python, щоб воно точно відповідало тому , що в ньому знаходиться requirements.txt. Сюди входить видалення будь-яких пакунків, які є у вашому середовищі, але відсутні requirements.txt .

Приклад: Припустимо , що ми хочемо , щоб наш окр містити (тільки) 3 бібліотеки: libA, libBі libC, як так:

> cat requirements.txt
libA==1.0
libB==1.1
libC==1.2

Але наша env наразі містить libCі libD:

> pip freeze
libC==1.2
libD==1.3

Запуск pip-sync призведе до цього, що було нашим бажаним кінцевим станом:

> pip-sync requirements.txt
> pip freeze
libA==1.0
libB==1.1
libC==1.2

будьте обережні, якщо у вас є глобально встановлені інструменти pip, вони не видалятимуться у вашому активованому virtualenv ... все ще дивно, але в іншому випадку найпростіший інструмент управління вимогами я знаю.
benzkji

3

Пропозиція Стівена - приємна ідея, але, на жаль, вона не працює, якщо ви додаєте до свого файлу лише прямі вимоги, що для мене звучить чистіше.

Усі залежності будуть видалені, в тому числі навіть distribute, що само розбиваються pip.

Підтримка чистого файлу вимог під час відстеження версій віртуального середовища

Ось як я намагаюся відстежувати версії мого віртуального середовища. Я намагаюся підтримувати мінімум requirements.txt, включаючи лише прямі вимоги, і навіть не згадуючи обмеження версії, де я не впевнений.

Але крім того, я зберігаю і включаю в відстеження версій (скажімо git), фактичний стан мого virtualenv у venv.pipфайлі.

Ось зразок робочого процесу:


налаштування робочої області virtualenv із відстеженням версій:

mkdir /tmp/pip_uninstalling
cd /tmp/pip_uninstalling
virtualenv venv
. venv/bin/activate

ініціалізувати систему відстеження версій:

git init
echo venv > .gitignore
pip freeze > venv.pip
git add .gitignore venv.pip
git commit -m "Python project with venv"

встановити пакет із залежностями, включити його у файл вимог:

echo flask > requirements.txt
pip install -r requirements.txt
pip freeze > venv.pip

Тепер починайте створювати свій додаток, а потім виконайте комітування та запустіть нову гілку:

vim myapp.py
git commit -am "Simple flask application"
git checkout -b "experiments"

встановити додатковий пакет:

echo flask-script >> requirements.txt
pip install -r requirements.txt
pip freeze > venv.pip

... пограйте з нею, а потім поверніться до попередньої версії

vim manage.py
git commit -am "Playing with flask-script"
git checkout master

Тепер видаліть сторонні пакети:

pip freeze | grep -v -f venv.pip | xargs pip uninstall -y

Я припускаю, що процес можна автоматизувати за допомогою git хуків, але не будемо відходити від теми.

Звичайно, тоді має сенс використовувати якусь систему кешування пакунків або локальне сховище, як pip2pi



0

Хоча це безпосередньо не відповідає на питання, кращою альтернативою requirements.txtзараз є використання Pipfile. Це функціонує подібно до Ruby Gemfile. В даний час вам потрібно скористатися цим pipenvінструментом, але, сподіваємось, це врешті-решт буде включено в pip. Це забезпечує pipenv cleanкоманду, яка робить те, що ви хочете.

(Зверніть увагу, що ви можете імпортувати існуючий за requirements.txtдопомогою pipenv install -r requirements.txt. Після цього ви повинні мати a Pipfileі requirements.txtможна видалити.)


-3

Зараз це можливо за допомогою:

pip uninstall -r requirements.txt

2
Це не видаляє пакети, які не відображаються у файлі вимог. Вона видаляє всі пакети , які дійсно з'являються в файлі.
Майкл Міор
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.