Bagaimana cara membangun distribusi sumber tanpa menggunakan file setup.py?

10

Dengan struktur paket berikut

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

Isi dari setup.py

from setuptools import setup
setup()

Isi dari setup.cfg

[metadata]
name = my_package
version = 0.1

[options]
packages = find:

Saya dapat membuat roda atau sumber distribusi untuk my_packageseperti ini

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

Tetapi menurut pengelola setuptools , konfigurasi build deklaratif adalah ideal dan menggunakan build imperatif akan menjadi kode bau. Jadi kami ganti setup.pydengan pyproject.toml:

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

Isi dari pyproject.toml

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

Dan Anda masih bisa membangun roda dengan cara yang sama seperti sebelumnya, itu berhasil. Tapi sdist tidak berfungsi:

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

Jadi bagaimana Anda seharusnya membangun file .tar.gz menggunakan setuptools ? Apa alat yang dihadapi pengguna untuk membuat sdist? Saya tidak ingin mengubah backend build. Sepertinya alat pengemasan lainnya semuanya menulis titik masuk build mereka sendiri, tetapi saya pikir inti dari mendefinisikan sistem build deklaratif dalam metadata adalah agar Anda tidak perlu terlibat langsung dengan sistem build, mempelajari bagaimana masing-masing alat pengemasan yang berbeda diharapkan dipanggil atau harus masuk ke juru bahasa dan memanggil API Python secara manual. Tetapi PEP untuk persyaratan sistem bangunan sudah berusia lebih dari 2 tahun sekarang. Apakah saya melewatkan sesuatu yang jelas di sini?

Bagaimana cara membangun distribusi sumber tanpa menggunakan setup.pyfile?

platipus
sumber

Jawaban:

10

Ini adalah topik yang agak kontroversial, dan jawaban untuk saat ini adalah bahwa tidak ada satu alat pun yang disetujui semua orang adalah "cara yang tepat" untuk membangun distribusi sumber, tidak juga seperti apa alat itu. Anda dapat melihat utas panjang tentang hal itu pada wacana Kemasan Python .

Aku ragu-ragu untuk memberikan terlalu banyak saran kemasan dalam format tahan lama karena pasir selalu bergeser, tetapi sebagai dari November 2019, setup.py sdistadalah tidak usang, tetapi tidak memiliki semua kelemahan yang PEP 517 dan PEP 518 dimaksudkan untuk memperbaiki - yaitu bahwa Anda memiliki untuk membuat lingkungan build sendiri (dan tahu tentang semua dependensi build), dan itu hanya berfungsi dengan setuptools / distutils dan padanannya.

Ini bukan rekomendasi "resmi", tetapi pengganti terbaik saat ini untuk setup.py sdistdan setup.py bdist_wheelmenjalankan versi baris perintah dari pep517. Pengganti untuk sdistadalah:

python -m pep517.build --source .

Anda dapat membangun roda dan distribusi sumber pada saat yang sama seperti:

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

Ini adalah bagaimana saya membangun paket kompatibel PEP 517 saya.

Ini mensyaratkan bahwa proyek Anda memiliki pyproject.toml, dan pyproject.tomlharus memiliki build-system.requiresdan build-system.build-backendkunci, tetapi itu akan bekerja untuk proyek apa pun dengan backend kompatibel PEP 517 (termasuk flit).

Alat lainnya :

Mengapa tidak menggunakan flitatau poetryatau hatch? Semua alat itu tersedia bagi mereka yang ingin menggunakannya, tetapi itu bukan jawaban untuk pertanyaan ini . Pertanyaan ini menanyakan tentang proyek yang dibangun dengan setuptoolsmenggunakan setup.cfgformat deklaratif . Baik flitmaupun poetrybertindak sebagai PEP 517 generik membangun front-end, dan sehingga mereka hanya bekerja sebagai membangun perintah untuk proyek menggunakan backend masing-masing.

Saya cukup tidak akrab dengan hatchmengatakan apakah atau tidak dapat mengelola proyek dengan backends lain dari setuptools, tapi (lagi, seperti dari November 2019), itu bukan suatu PEP 517 frontend, dan itu tidak akan bekerja jika Anda tidak memiliki a setup.py(itu akan meningkatkan kesalahan "tidak dapat membuka file setup.py", dan itu akan mengabaikan pyproject.tomlfile Anda ).

Paul
sumber
Mengapa fokus pada pep517.buildyang hanya dimaksudkan sebagai percobaan, penopang sementara ketika ada alat produktif seperti flit, puisi, palka, dan mungkin bahkan lebih?
sinoroc
1
Karena itu adalah percobaan yang berhasil dalam perkiraan saya (saya dan banyak orang PyPA lainnya menggunakannya), karena memiliki semantik yang tepat untuk pekerjaan itu, dan karena itu adalah satu-satunya tujuan umum PEP 517 membangun front-end yang saya tahu. flit dan puisi terintegrasi secara vertikal karena mereka mengharapkan Anda menggunakan backend mereka. palka tampaknya melakukan banyak hal lain. pep517.buildadalah alat sederhana yang dibuat untuk tujuan ini.
Paul
Ah benar, poin bagus. Saya fokus pada build back-end. Dan saya benar-benar berpikir pep517.buildsalah satunya. Tapi tidak sama sekali, itu sebenarnya front-end build. Juga menetas tidak siap PEP517 seperti yang saya lihat sekarang.
sinoroc
1
Saya telah memperbarui jawaban saya untuk menjawab pertanyaan Anda.
Paul
Ya, sempurna. Saya menghapus jawaban saya.
sinoroc
-1

Tidak ada yang "jelas" ketika datang ke kemasan Python. Memang, untuk saat ini, setidaknya jika Anda menggunakan distutils / setuptools perlu untuk membuat setup.pyfile kosong (hampir) , bahkan jika Anda menggunakan deklaratif sepenuhnya setup.cfg:

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

Saya juga merekomendasikan chmod +x setup.py.

Dalam hal ini Anda hanya menulis "titik masuk" ke sistem build sendiri, dan setup()hanya main()fungsi untuk itu - tetapi sekarang semua argumen yang secara tradisional diteruskan setup()dapat dibaca dari setup.cfggantinya.

Sekarang Anda masih bisa menggunakan setup.py sdistjika Anda ingin membuat tarball sumber:

./setup.py sdist

Anda juga dapat mencoba salah satu sistem build alternatif yang diaktifkan via pyproject.toml, seperti Flit .

Iguananaut
sumber
Tidak yakin mengapa ini sedang diturunkan; itu pada dasarnya benar bahkan jika ada solusi lain.
Iguananaut
2
Judul pertanyaannya adalah "Bagaimana cara membangun distribusi sumber tanpa menggunakan file setup.py?" Jawaban ini tampaknya hanya menunjukkan "inilah cara membuat ulang file setup.py yang sama dengan yang baru saja Anda hapus", yang tidak berguna.
platypus
Ya, tapi itu didasarkan pada kesalahpahaman bahwa menulis deklaratif setup.cfgberarti bahwa setup.pytidak perlu lagi menggunakan setuptools, yang tidak benar. Hanya karena judul pertanyaan itu menyesatkan, bukan berarti jawabannya. Mereka menulis di badan pertanyaan, "Jadi bagaimana Anda seharusnya membangun file .tar.gz menggunakan setuptools ?" yang ini menjawab dengan benar.
Iguananaut
1
Sebenarnya itu benar. setuptools tidak memerlukan file setup.py jika Anda menggunakan PEP 517.
Paul
"Jika Anda menggunakan PEP 517" Kecuali kebanyakan orang tidak. Ini masih sementara, dan bahkan tidak disebutkan dalam packaging.python.org . Itu bukan sesuatu yang akan Anda miliki kecuali Anda tahu untuk mencarinya. Jika Anda hanya ingin setuptools berfungsi seperti biasa, ini benar.
Iguananaut