Как стать автором
Обновить

Комментарии 40

Ни слова про packages и команду build...

старался выделить самое основное, что поможет начать работать с poetry
в самом начале написано, что цель статьи - немного познакомить с основными командами, а также в сравнении с pip указано, что не все моменты/преимущества выделены
информации пришлось поместить много, поэтому не всё добавил

poetry справедливее сравнивать не с голым pip, а с pip-tools — там можно и requirements.txt сохранить, и получить такой же чёткий контроль всех версий пакетов.


Выбор между poetry и pip-tools уже не так очевиден.

В какой-то момент добавил к использованию pip пакет pip-tools, и в принципе проблема с тем, что непонятно откуда какие зависимости приходят ушла, теперь все нужные для проекта зависимости описываю в requirements.in, а requirements.txt генерится и содержит в принципе ту же метадату о взаимосвязях зависимостей. Есть ли в poetry еще плюсы? Может установка быстрее или что-нибудь еще?

Для меня, скажем, основной плюс в том, что это all-in-one solution. На чистой машине выкачиваю репозиторий проекта, по toml файлу автоматом создаётся virtual environment и устанавливаются зависимости. Вместо python набираю poetry run python -- запускается версия Питона в виртуальном окружении. Можно настроить так, чтобы окружение создавалось в папке проекта, тогда если проект больше не нужен, папка удаляется -- и всё с концами. Ещё у меня была проблема с тем, что какой-то из более стандартных менеджеров зависимостей на каких-то проектах зависал навечно при попытке определить скачиваемые пакеты, вот и пришлось искать альтернативы.

+удобно использовать несколько версий Python
poetry env use <пусть до python.exe нужной версии>

особенно, когда хотите перейти от более старой версии к более новой, но боитесь что-то сломать, самое-то

Это неплохо конечно, но у меня для этого докер есть, любой новый сервис сразу заворачивается в контейнер типовой конфигурации, где уже и pip-tools сидит. А там я уже могу как угодно не только версиями питона вращать, но и версиями системных пакетов.

докеры - хороший вариант, когда работаете над большими/долго живущими проектами
а если, допустим, человек хочет дома создать какой-то пет-проект или надо быстро опробовать какую-то фишку (которая не факт, что пригодится), то не совсем удобно тянуть за собой докер, когда можно выполнить poetry new test_project и начинать работать
но это дело привычки, если рука набита или есть заготовки, чтобы создать докер за минуту, то почему бы и нет

А расскажите как вы разрабатываете в docker?

Ну как, описываю Dockerfile, с помощью docker-compose пробрасываю нужные порты/волюмы/переменные окружения/дебажную команду запуска, цепляю удаленный интерпретатор из собранного образа в pycharm и сижу довольный.

А если нужно погонять что-то, что требует использования gui погонять.

Ну например игру на pygame запилить. Как тут с докером обойтись?

pyproject.toml - это часть стандарта PEP 517 и PEP 518. Насколько я понимаю, pip-tools использует свой собственный подход не основанный на PEP.

Ооо, зашел на сайт Poetry, почитал и понял, что эта штука по сути куда шире и роскошнее, чем описано в статье. Pip -- это просто package installer, а Poetry -- средство управления проектом на python (здесь и управление зависимостями, и изоляция, и публикация, и этот волшебный poetry run). До этого я также не вникал и думал, что это просто какая-то замена pip, потому что читал статьи типа этой. Спасибо в общем за ваш комментарий!

Стандартный workflow для pip-tools:


pip-compile --output-file=requirements.txt requirements.in
git add requirements.*
git commit -v

Получаем обычный requirements.txt, такой же, каким он был и 10 лет назад, просто в каждой строчке жёстко прописана версия пакета, в т.ч. все зависимости (которые в requirements.in не требуется указывать). Никакой магии. Потом ставим:


.venv/bin/pip install -r requirements.txt

PEP-517/518 это, конечно, хорошо, но вариант с pip-tools выглядит проще, при этом получаем то же самый результат.

У poetry есть то же самое: poetry export -o requirements.txt. Я это использую в Docker-образах, чтобы не тащить туда лишние зависимости.

Чем это лучше или хуже pip-tools, я не знаю. Мне удобно.

Есть более правильный способ

poetry build

А в Dockerfile

ENV WHEEL "socks5_tune-$VERSION-py3-none-any.whl"

COPY dist/$WHEEL /app/

RUN pip install --no-cache-dir /app/$WHEEL

И в итоге сборка будет не воспроизводимой, потому что файл создавали на каком-то конкретном хосте, а не в явно заданном окружении в Dockerfile

Почему не воспроизводимой? Собирайте на CI в той же версии image. Или используйте docker multi-stage build.

Подскажите, что делать, если нужны два списка пакетов, например для тестирования и для продакшена?

при установке пакетов можно использовать

# установить зависимость в общий список
poetry add pygame
# установить зависимость в качестве dev пакета
poetry add pygame --dev

либо вручную вписать в toml файл для продакшена в блок [tool.poetry.dependencies]

[tool.poetry.dependencies]
pygame = "^2.1.0"

для dev

[tool.poetry.dev-dependencies]
Pympler = "^0.9"

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

# установить все зависимости (в т.ч. dev)
poetry install
# игнорировать dev зависимости
poetry install --no-dev

Недавно наткнулся на вот такой баг:

https://github.com/python-poetry/poetry/issues/3139

Если сначала установить зависимости для одного окружения, а потом поверх установить зависимости для другого, poetry сначала удалит все пакеты первого окружения, и затем накатит второе. Как я понял, это было сделано для упрощения решения проблем с конфликтами версий установленных пакетов, поскольку так не нужно учитывать наличие уже установленных, но несовместимых друг с другом версий пакетов.

Но при этом он удаляет все пакеты старого окружения, в т.ч. и транзитивные зависимости. И если такой зависимостью случайно окажется virtualenv, он его удалит, и затем перестанет работать, т.к. сам от него зависит.

Да и если говорить о других зависимостях, сейчас это работает странно - poetry может считать, что зависимость установлена, хотя сам же ее и удалил при очистке окружения, и в итоге установка падает на пустом месте с кучей ошибок

То бишь cargo для питона? А как сами пакеты ставятся при наличии проекта и toml? Откуда пакеты берутся и в каком формате (eggs, wheels)? Появился новый Poetry registry с пакетами?

Стандартный источник pypi.org. Можно указывать свои кастомные.
Насчет формата не скажу, про предполагаю, что стандарт сейчас wheels.

Я так и не понял, что оно даст мне, если я перестану использовать pip и начну poetry. Что-то станет ещё более гибким, ок. А проблему оно какую решает?

Нормальный фриз зависимостей пакетов которые вы используете через poetry.lock что бы воспроизвести точно такое же окружение на 2 машине.
С обычным пипом частенько было когда на 2 машине устанавливались другие, обновленные подзависимости у пакетов и получались проблемы.

Это не "фриз", это "lock". Да, из всех языков, только pip жил без лока и его, местами, не хватает.

Собственно, pip-tools всё это и делает. В requirements.in пишем пакеты, которые нам нужны, а pip-tools создаёт requirements.txt, где вписаны абсолютно все пакеты, со всеми зависимостями и для каждого задана точная версия. Тот же самый лок.

А можно ли при помощи poetry скачать (не устанавливая) все нужные файлы зависимостей, чтобы их можно было перенести на сервер без интернета и там развернуть? (и умеет ли poetry инсталлировать скачанное заранее в оффлайн-режиме?)

https://pip.pypa.io/en/stable/cli/pip_wheel/

На сервере-сервере сборщике:
pip wheel --wheel-dir /tmp/wheels -r requirements.txt

На офлайн-сервере, после копирования wheels через флешку:
pip install ./wheels/*

Ну и сам детерминированный
requirements.txt можно получить с помощью poetry.

По мне так poetry нисколько не прекрасен, тормознутная поделка, которая с помощью непонятной магии пытается вам втюхать venv + pip в своей обертке. Совершено не подходит для проектов на conda, от слова совсем. По мне так pip на любом проекте хватает с лихвой и нет ему достойной альтернативы, пока.

conda вещь в себе, то что в ней pip работает это скорее недосмотр а не фича, нормально с ним конда работать не умеет.

По сути - питон в окнах и питон в линуксе это две совершенно разные среды которые делают одинаково больно, но по разному.

Главная особенность poetry не упомянута. Проект обещает наиболее корректное разрешение версий зависимостей, без внезапных неудач посреди установки сотни зависимостей, потому что где-то противоречия возникли.

Интересно каким образом он обещает это сделать, если на уровне API pypi и аналогичные ему репозитории не умеют отдавать метаданные пакета без его скачивания?

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

https://github.com/pypa/warehouse/issues/8254

В итоге появился план вытаскивать из загружаемых .whl файлов список зависимостей и хранить его в отдельном файле, чтобы улучшить резолвинг зависимостей:

https://github.com/pypa/warehouse/pull/9972

И правки до сих пор не смержили. Плюс это повлияет только на новые версии пакетов, обсуждение способа парсинге зависимостей уже залитых пактов все ещё идёт.

А без них, что pip, что poetry находятся в одинаковой ситуации - чтобы скачать зависимости пакета, нужно сначала скачать пакет, распарсить его метаданные, потом скачать его зависимости, зависимости его зависимостей и т.п.

Более того, проблема решаема только для .whl, потому что он собирается для определенной версии Python и ОС. А вот если выгружать в pypi исходники пакета в .tar.gz, метаданные из него вынуть не выйдет, потому что зависимости могут быть указаны в setup.py, т.е. определяться динамически в момент запуска сборки.

Что такого революционного предлагает poetry, кроме requirements.lock файла? Так это файл ему точно так же придется подготавливать, скачивая пакеты из pypi

Спасибо за замечание, я не был в курсе таких проблем в pypi.


Я с pipenv в ситуацию кривых разрешений версий попадаю часто, и это вынуждает разрешать версии в ручную, выясняя, какие пакеты в каком порядке ставить. Poetry меня обнадеживает.


Процитирую poetry readme, как дополнение к исходному комментарию:


Dependency resolution
The dependency resolution is erratic and will fail even if there is a solution. Let's take an example:

pipenv install oslo.utils==1.4.0
will fail with this error:

Could not find a version that matches pbr!=0.7,!=2.1.0,<1.0,>=0.6,>=2.0.0
while Poetry will get you the right set of packages:

poetry add oslo.utils=1.4.0
results in :

  - Installing pytz (2018.3)
  - Installing netifaces (0.10.6)
  - Installing netaddr (0.7.19)
  - Installing oslo.i18n (2.1.0)
  - Installing iso8601 (0.1.12)
  - Installing six (1.11.0)
  - Installing babel (2.5.3)
  - Installing pbr (0.11.1)
  - Installing oslo.utils (1.4.0)
This is possible thanks to the efficient dependency resolver at the heart of Poetry.

Here is a breakdown of what exactly happens here:

oslo.utils (1.4.0) depends on:

pbr (>=0.6,!=0.7,<1.0)
Babel (>=1.3)
six (>=1.9.0)
iso8601 (>=0.1.9)
oslo.i18n (>=1.3.0)
netaddr (>=0.7.12)
netifaces (>=0.10.4)
What interests us is pbr (>=0.6,!=0.7,<1.0).

At this point, poetry will choose pbr==0.11.1 which is the latest version that matches the constraint.

Next it will try to select oslo.i18n==3.20.0 which is the latest version that matches oslo.i18n (>=1.3.0).

However this version requires pbr (!=2.1.0,>=2.0.0) which is incompatible with pbr==0.11.1, so poetry will try to find a version of oslo.i18n that satisfies pbr (>=0.6,!=0.7,<1.0).

By analyzing the releases of oslo.i18n, it will find oslo.i18n==2.1.0 which requires pbr (>=0.11,<2.0). At this point the rest of the resolution is straightforward since there is no more conflict.

Добавлю, что последние версии Poetry забагованы.
https://github.com/python-poetry/poetry/issues/4523 - это пофикшено в последней версии 1.1.10
https://github.com/python-poetry/poetry/issues/4163 - а это так пока и не пофикшено, хотя сильно ломает Poetry в Windows (по моему опыту, на всех проектах).
Так что приходится сидеть пока на чуть более старой версии. Вот такие дела.

Ну и про тормоза уже упоминали, да.

Но мы продолжаем пользоваться poetry ради version locking, т.к. альтернатив мало. Тот же pipenv ещё более тормозной.

В JS-мире npm и yarn уже давно нормально работают.

Установки пакетов в указанную директорию не появилось? Очень полезно для multi-stage.

из коробки - используется venv
```
export POETRY_VIRTUALENVS_PATH=.venv
export POETRY_VIRTUALENVS_IN_PROJECT=1
poetry install

```

Установить poetry на windows можно либо при помощи pip:

$ pip install poetry

Successfully installed SecretStorage-3.3.3 cachecontrol-0.12.11
cffi-1.15.1 cleo-2.0.1 crashtest-0.4.1 cryptography-39.0.2
distlib-0.3.6 dulwich-0.21.3 filelock-3.9.0 html5lib-1.1
importlib-metadata-6.0.0 installer-0.6.0 jaraco.classes-3.2.3
jeepney-0.8.0 jsonschema-4.17.3 keyring-23.13.1 lockfile-0.12.2
more-itertools-9.1.0 msgpack-1.0.5 pkginfo-1.9.6 platformdirs-2.6.2
poetry-1.4.0 poetry-core-1.5.1 poetry-plugin-export-1.3.0
pycparser-2.21 pyrsistent-0.19.3 rapidfuzz-2.13.7 zipp-3.15.0
requests-toolbelt-0.10.1 shellingham-1.5.0.post1 tomlkit-0.11.6
trove-classifiers-2023.3.9 virtualenv-20.21.0 webencodings-0.5.1

Вот спасибо

Зарегистрируйтесь на Хабре , чтобы оставить комментарий

Публикации