Як створити розподіл джерела без використання файла setup.py?


10

З наступною структурою пакету

.
├── my_package
   └── __init__.py
├── setup.cfg
└── setup.py

Зміст setup.py

from setuptools import setup
setup()

Зміст setup.cfg

[metadata]
name = my_package
version = 0.1

[options]
packages = find:

Я можу створити колесо або розподіл джерела для my_packageподібного

pip wheel --no-deps -w dist .
# generates file ./dist/my_package-0.1-py3-none-any.whl
python setup.py sdist
# generates file ./dist/my_package-0.1.tar.gz

Але, на думку керівника setuptools , декларативна конфігурація збірки є ідеальною, а використання імперативної збірки буде кодовим запахом. Тож ми замінюємо setup.pyна pyproject.toml:

.
├── my_package
   └── __init__.py
├── setup.cfg
└── pyproject.toml

Зміст pyproject.toml

[build-system]
build-backend = "setuptools.build_meta"
requires = ["setuptools", "wheel"]

І ви все одно можете побудувати колесо так само, як і раніше, це працює. Але sdist не працює:

python: can't open file 'setup.py': [Errno 2] No such file or directory

Тож як ви насправді повинні створити файл .tar.gz за допомогою setuptools ? Який користувацький інструмент для створення sdist? Я не хочу змінювати бекенд збірки. Схоже, що інші інструменти упаковки пишуть власні точки введення збірки, але я подумав, що весь сенс у визначенні декларативної системи збирання в метаданих був таким, що вам не доведеться брати до рук систему збирання, вивчаючи, як кожен різний інструмент упаковки очікує, що буде викликано або потрібно буде перейти до інтерпретатора та викликати API Python вручну. Але PEP для системних вимог до збірки вже понад 2 роки. Я пропускаю тут щось очевидне?

Як побудувати розподіл джерела без використання setup.pyфайлу?

Відповіді:


10

Це дещо суперечлива тема, і на даний момент відповідь полягає в тому, що не існує жодного єдиного інструменту, з яким всі згодні - це "правильний спосіб" побудувати дистрибутивні джерела, а також те, що було б цим інструментом. Ви можете побачити довгу нитку про це в дискурсі Python Packaging .

Я НЕ наважуюся дати занадто багато порад упаковки в міцних форматах , тому що пісок завжди змінюється, але за станом на листопад 2019 року, setup.py sdistє НЕ рекомендується, але це дійсно має всі недоліки , які PEP 517 і PEP 518 були призначені для виправлення - а саме , що у вас є щоб створити середовище збирання самостійно (і знати про всі залежності побудови), і воно працює лише з setuptools / distutils та їх еквівалентами.

Це не "офіційна" рекомендація, а поточна найкраща заміна для setup.py sdistі setup.py bdist_wheelвикликає версію командного рядка pep517. Заміна на sdist:

python -m pep517.build --source .

Ви можете одночасно створити колесо та розподіл джерела так:

python -m pep517.build --source --binary .

Ось так я створюю свої пакети, сумісні з PEP 517.

Це вимагає, щоб у вашому проекті були і клавіші must must pyproject.toml, і pyproject.tomlповинні бути , але він буде працювати для будь-якого проекту із сумісним PEP 517 (включаючи ).build-system.requiresbuild-system.build-backendflit

Інші інструменти :

Чому б не використовувати flitабо poetryабо hatch? Ці інструменти доступні для тих, хто хоче ними користуватися, але вони не є відповіддю на це питання . Це питання задає питання про побудову проектів, setuptoolsякі використовують декларативний setup.cfgформат. Ні, flitні poetryвиступають як загальні PEP 517 будують передні частини, і тому вони працюють лише як команди збірки для проектів, використовуючи відповідні межі.

Я недостатньо знайомий з тим, hatchщоб сказати, чи може він керувати проектами за допомогою інших програм, ніж setuptools, але (знову ж таки, з листопада 2019 року), це не Frontend PEP 517, і він не працюватиме, якщо у вас немає a setup.py(це призведе до помилки "не вдається відкрити файл setup.py", і він ігнорує ваш pyproject.tomlфайл).


Навіщо зосереджуватися на тому, pep517.buildщо мається на увазі лише як експеримент, тимчасова милиця, коли є продуктивні інструменти, такі як фліт, поезія, хетч і, мабуть, навіть більше?
sinoroc

1
Тому що це був вдалий експеримент в моїй оцінці (я та багато інших людей з PyPA використовую його), оскільки він має правильну семантику для роботи, і тому, що це єдиний загальноприйнятий PEP 517, який я знаю. flit і поезія вертикально інтегровані в тому, що вони очікують, що ви будете використовувати їхню програму. Здається, люк робить багато інших речей. pep517.buildце простий інструмент, побудований саме для цієї мети.
Павло

Ну правильно, хороший пункт. Я зосереджувався на складанні бек-ендів. І я насправді думав, що pep517.buildце один із них. Але зовсім не це, насправді це фальшива збірка. Також люк не готовий до PEP517, як я бачу зараз.
sinoroc

1
Я оновив свою відповідь, щоб вирішити ваше питання.
Павло

Так, ідеально. Я видаляю свою відповідь.
sinoroc

-1

Що стосується упаковки Python, то немає нічого "очевидного". Дійсно, наразі, принаймні, якщо ви використовуєте distutils / setuptools, необхідно створити (майже) порожній setup.pyфайл, навіть якщо ви використовуєте повністю декларативний setup.cfg:

#!/usr/bin/env python
from setuptools import setup
setup()

Я також рекомендую chmod +x setup.py.

У цьому випадку ви просто пишете "точку входу" до системи збирання, і setup()це лише main()функція для неї, але тепер усі аргументи, які традиційно передавались, setup()можна прочитати setup.cfgзамість них.

Тепер ви можете використовувати, setup.py sdistякщо ви хочете зробити вихідний тарбол:

./setup.py sdist

Ви також можете спробувати одну з альтернативних систем побудови, яку ввімкнено через pyproject.toml, наприклад, Flit .


Не впевнений, чому це знижується; це в основному правильно, навіть якщо є інші рішення.
Ігуананавт

2
Назва питання "Як побудувати розподіл джерела без використання файла setup.py?" Ця відповідь, здається, просто демонструє "ось як відтворити той самий файл setup.py, який ви тільки що видалили", що не корисно.
качконіс

Так, але це грунтувалося на нерозумінні, що написання декларації setup.cfgозначає, що більше setup.pyне потрібно використовувати setuptools, що не відповідає дійсності. Тільки тому, що назва питання вводить в оману, не означає, що відповідь є. Вони написали в тілі запитання "Так як же насправді побудувати файл .tar.gz за допомогою setuptools ?" на що це відповідає правильно.
Ігуананавт

1
Це насправді так. Setuptools не вимагає setup.py файл , якщо ви використовуєте PEP 517.
Paul

"якщо ви використовуєте PEP 517" За винятком більшості людей. Він все ще є тимчасовим і ледь навіть не згадується в упаковці.python.org . Це не те, що ви мали б, якщо не знаєте, як шукати його. Якщо ви просто хочете, щоб установочні версії працювали так, як це було завжди, це правильно.
Ігуананавт
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.