pep etiketine sahip kayıtlar gösteriliyor. Tüm kayıtları göster
pep etiketine sahip kayıtlar gösteriliyor. Tüm kayıtları göster

uv ve pyproject.toml ile Kapsamlı Python Proje Yönetimi Rehberi



Giriş

Bu kılavuzda ilk partın amacı, Python Geliştirme Önerileri (PEP) standartlarının geçmişten günümüze değişiminden bahsederek pyproject.toml dosyası ile Python proje yönetimi için kapsamlı bir rehber sağlamaktır. Tarihsel bağlamın bu şekilde gözden geçirilmesi, mevcut uygulamaları anlamak için önemlidir. İlk partı Reinforced Learning tarafından hazırlanmış olan faydalı bulduğum dökümanı Türkçeye çevirip bazı ekleme, çıkarma ve özetlemeler yaparak oluşturdum. Sayfasına çok teşekkür ederim.
İkinci part ise en sık kullandığım uv komutlarını içeren bir kullanım kılavuzu / cheat sheet içerir.

2.bölüme bölüme atlamak için tıklayın.


Bu yazıda PEP'ler tarafından sağlanan değişikliklerin sorunları nasıl çözdüğünü uv'yi kullanarak açıklayacağız.

Python proje yönetimi ve paketleme genellikle araçlara dayandığından (bağımlılıklarınızı yüklemek, projenizi derlemek vb.), bahsettiğimiz kavramları göstermek için bir araç kullanmanın harika bir fikir olduğunu düşündüm. Genel olarak araçlar standardın ötesine geçer, örneğin bu yazıda seçilen araç uv, standartta olmayan ancak uv gibi birçok aracın sunduğu bir özellik olan "düzenlenebilir bağımlılıklar" olarak adlandırılan şeye izin verir.

Standartta yer alan, standardın ötesinde olan ve bir araç tarafından sağlanan ve aracın desteklemediği yeni standartlar arasındaki bu ayrımı akılda tutmak önemlidir.

Pip birçok ihtiyaç için tek başına yeterli olabilir fakat düzenli ve kapsamlı bir yönetime gelince her şeyib manuel yapılması gerekiyor. uv "Rust dilinde yazılmış son derece hızlı bir Python paket ve proje yöneticisi". Ele alacağımız komutlar init, add, lock, sync, run ve tool. Bu komutlar, keşfedeceğimiz tüm kavramları göstermeme izin verecek.

Uygulama Projesi Oluşturma

uv init komutu, neredeyse tüm uv komutları gibi kendi kendini açıklayıcıdır, bir projeyi başlatmak için kullanılır.

Boş bir projeden başladığımız için, bu şu dosyaları oluşturacaktır: .gitignore, .python-version, hello.py, pyproject.toml ve README.md.

Resmi belgelere göre .python-version "projenin varsayılan Python sürümünü içerir" ve uv'ye projenin sanal ortamını oluştururken hangi Python sürümünü kullanacağını söyler.

Bu dosyalar arasında en önemlisi dosya pyproject.toml dosyasıdır.

pyproject.toml


pyproject.toml dosyası, proje meta verilerini, bağımlılıkları ve derleme gereksinimlerini bildirimsel bir şekilde belirtmek için kullanılan standartlaştırılmış bir yapılandırma dosyasıdır. Bu dosyayı derleme araçları dışındaki araçları ve bunların nasıl yapılandırıldığını eklemek için de kullanabilirsiniz.

Not: Projeniz için bir pyproject.toml dosyasına sahip olmak gerekli değildir ve derleme sistemlerini ve meta verileri belirtmenin başka yolları da vardır, ancak pyproject.toml, özellikle PEP 518 ve PEP 517'den sonra proje meta verileri söz konusu olduğunda Python projesi için standartlaştırılmış yapılandırma dosyası haline gelmiştir.

pyproject.toml'den önce, Python geliştiricileri paketlerini oluşturmak, kurmak ve dağıtmak için setup.py adlı çalıştırılabilir bir Python dosyası kullanıyordu. Ve bir Python projesi oluşturmanın ana iki yolu, standart kütüphanenin bir parçası olan distutils ve standart kütüphanenin bir parçası olmayan setuptools idi.

setuptools, distutils aracılığıyla standart kütüphane ile sağlananlardan daha fazla özellik sunan bir kütüphane olarak ortaya çıktı, ancak aynı zamanda birçok sorunla birlikte geldi. Distutils standart kütüphanenin bir parçası olduğu için, geliştiriciler projelerini oluşturmak için herhangi bir bağımlılığa (Python'un kendisi hariç) ihtiyaç duymuyorlardı. Ancak distutils oldukça basitti ve minimal ihtiyaçları olan projeler için yeterli olsa da, setuptools'un sağladığı daha fazla işlevsellik gerektiren karmaşık projeleri tatmin etmiyordu. Bu yüzden popülerliği arttı ve geliştiriciler setuptools'u tercih etti ve karşılaştığımız ilk sorunu görüyor musunuz? Şimdi projeyi derlemek veya kurmak için setuptools olan bir derleme bağımlılığımız var.

setup.py'nin distutils ile sınırlı kullanımların ötesine geçememesine neden olan şey, çalıştırılması için kod gerektirmesidir. Ve standart kütüphane tarafından desteklenmeyen ihtiyaçlarınız olduğu sürece, sorunlarla karşılaşacaksınız. Öte yandan, pyproject.toml, programın yazıldığı koddan bağımsız olarak herhangi bir aracın, herhangi bir derleme sisteminin okuyabileceği, ayrıştırabileceği ve yorumlayabileceği statik bir dosyadır. Bir pyproject.toml dosyasının içinde ne olduğunu keşfetmek için hiçbir şeye ihtiyacınız yoktur ve onu bu kadar harika yapan da budur. 

PEP 518 pyproject.toml için neden TOML formatı, isimlendirme, anlamsal bir sürüm anahtarının reddedilmesi gibi bazı kararlara değinmektedir.

Bir pyproject.toml dosyası ne içerir?

Bir pyproject.toml üç tablodan oluşabilir, [project], [build-system], ve [tool]. Bunların olması zorunlu değildir, ancak genellikle bir pyproject.toml en azından [project] tablosunu içerir. Örneğin basit "uv init" komutu bizim için bunu oluşturdu. init komutunun proje paketlemesi için gereken [build-system] tablosunu da otomatik olarak ekleyen seçenekler sunduğunu göreceğiz. tool]tablosuna gelince, diğer komutlar "uv add --dev" gibi veya test/diğer araçlarınız için yapılandırmalar belirlerken bu tablo üzerinde hareket eder.

PEP 518 ayrıca [tool] tablosunun arkasındaki amacı da belirtir. Üçüncü taraf araçların yapılandırılması için ayrılmıştır. Her aracın kendi alt tablosu tool.$İSİM olmalıdır. Örnek: [tool.uv] veya [tool.pydoc].

[project] Tablosu
PEP 621, [project] tablosu aracılığıyla bir projenin temel meta verilerinin nasıl beyan edileceğini belirtir.

Sadece iki zorunlu anahtar vardır, projenin adı olan "name" ve PEP 440'da belirtildiği gibi projenin sürümü olan "version". name statik olarak sağlanmalıdır, version ise dinamik olarak sağlanabilir, her iki durumda da gerekli bir anahtardır.
Bu PEP tarafından belirtilen isteğe bağlı anahtarlar şunlardır: 
  • description (açıklama), 
  • readme (beni oku açıklaması), 
  • requires-python (gerekli sürüm), 
  • license (lisans), 
  • authors/maintainers (geliştiriciler), 
  • keywords (anahtar sözcüler), 
  • entry-points, (uygulamanın çalıştıracağı kod), 
  • dependencies (gerekli bağımlılık paketleri)
  • optional-dependencies (örneğin --dev / geliştiriciler için tercihe bağlı paketler) 
  • dependency-groups (örneğin torch'un cpu veya gpu/cuda sürümü gibi bağımlılık grupları)

[tool] Tablosu
Örneğin pytest gibi bir test aracı kullanıyorsak alakalı yapılandırmaları bu dosyaya ekleyebiliriz. (Dahil edilecek dizin, görmezden gelinecek uyarılar.. gibi)

[build-system] Tablosu
Bir build-system (yapı sistemi), projenin nasıl paketleneceğini ve kurulacağını belirler. Projeler, pyproject.toml dosyasının [build-system] tablosunda bir derleme sistemi bildirip yapılandırabilir. Derleme meta verileri, bir derleme sisteminin derleme işlemi sırasında kullanacağı tüm bilgilerdir. Yapılandırma dosyaları, derleme seçenekleri, hangi dosyaların dahil edilip hangilerinin dahil edilmeyeceğine ilişkin talimatlar vb. olabilir. 
Not: Bu tablo eğer uygulamayı paketleyip pip ile yüklenebilir halde paketlemek istemiyorsak gerekli değildir.

uv init Parametreleri

--package
    Python paketi olarak oluşturulacak projeyi ayarlar. Proje için bir `[build-system]` tanımlar. Dağıtılabilir bir paket için uygundur. Bu, `--lib` kullanıldığında da varsayılan davranıştır.
 
--no-package
    Projeyi bir Python paketi olarak oluşturulacak şekilde ayarlamama. Proje için bir `[build-system]` içermez. Bu, `--app` kullanıldığında da varsayılan davranıştır.
-------
--app
    Bir uygulama için proje oluşturma. Bu, `--lib` istenmezse varsayılan davranıştır. Bu proje türü web sunucuları, komut dosyaları ve komut satırı arayüzleri içindir.

--lib
    Bir kütüphane için proje oluşturun. Kütüphane, bir Python paketi olarak oluşturulup dağıtılması amaçlanan bir projedir.


Örnek bir pyproject.toml dosyası (--app --no-package modu için)
[project]
name = "sg-project-template"
version = "0.1.0"
description = "Bu sglbl.com için hazırlanmış bir toml örneğidir."
readme = "README.md"
requires-python = ">=3.10"

dependencies = [
    "fastapi>=0.115.6",
]

[dependency-groups]
dev = [
    "jupyter>=1.1.1",
    "pytest>=8.3.3",
]

# filter dependencies warnings and future warnings
[tool.pytest.ini_options]
pythonpath = "."
filterwarnings = ["ignore::DeprecationWarning", "ignore::FutureWarning"]

Python Modül/Paket Terminolojisi


Module (Modül): "Python'da kodun yeniden kullanılabilirliğinin temel birimi". Ya bir .py dosyasıdır ve bu durumda saf modül olarak adlandırılır (merhaba dünya yazdıran bir işlev tanımlamak kadar basit bir şey bile olabilir) ya da düşük seviyeli bir dilde yazılmış bir şeydir (genellikle C çünkü CPython Python'un en yaygın uygulamasıdır) ve bu durumda bir uzantı modülü olarak adlandırılır.

Package (Paket): insanlar genellikle paket terimini hem "içe aktarma paketi" hem de "dağıtım paketi" hakkında konuşmak için kullanırlar.
Bir import package "içe aktarma paketi", python kodunuza aktarabileceğiniz bir şeydir. Modülleri veya özyinelemeli olarak diğer içe aktarma paketlerini içerir. Python'un modül isim alanını noktalı modül isimleriyle yapılandırmanın bir yoludur.
Bir distribution package "dağıtım paketi" yükleyebileceğiniz bir şeydir. Python içe aktarma paketlerini, modülleri ve diğer kaynak dosyalarını, sürüm numaraları ve bağımlılıklar gibi meta verilerle birlikte içeren sürümlü bir arşiv dosyasıdır. Genellikle pip install ile yüklediğiniz veya uv add'in yüklediği şeydir.
İnsanların her ikisi için de aynı "paket" terimini kullanmasına neden olan bir ilişki olduğu açıktır. Genellikle "pip install numpy" ile yüklersiniz ve sonra Python modüllerinizde "import numpy as np" kodunuza eklersiniz.

Not: Fakat import package'ler ve distribution package'ler her zaman aynı ada sahip değildir, Pillow dağıtım paketi (pip install pillow) PIL içe aktarma paketini (from PIL import Image) sağlar.

uv.lock Kilit Dosyası
Kilit dosyaları, bir ortamda yüklü olan paketlerin ve bağımlılıklarının tam olarak çözümlenmiş sürümlerini kaydeden dosyalardır. uv, uv.lock adlı platformlar arası (evrensel) kilit dosyası oluştururken Poetry gibi başka proje yönetimi uygulaması, poetry.lock adlı platformdan bağımsız bir kilit dosyası oluşturur ve pip-tools tarafından oluşturulan gibi sabitlenmiş sürümleri ve karmaları içeren bir requirements.txt dosyası da bir kilit dosyası olarak kabul edilebilir.

🚀uv pip-tools, pipx, poetry, pyenv, venv, virtualenv ve daha fazlasının yerini alan (en az 10 kat daha hızlı) tek bir araç olduğu için diğerlerinin detaylarına girmiyorum.

Reinforced Knowledge github sayfasını takip etmek için tıklayınız.


uv Kullanım/Komut Kılavuzu


UV'yi sisteme yükleyin
curl -LsSf https://astral.sh/uv/install.sh | sh
Bir Proje Oluşturma [--app (paketlenmeyecek uygulama) modu için]
# dizin adını proje olarak alır
uv init
# veya projenizi adlandırın ve proje dizinini açın
uv init myproject && cd myproject
# Not: Komutlar .git/ dizinini ve pyproject.toml dosyasını başlatır
.venv adıyla bir virtual environment (sanal proje ortamı) oluşturun
# Varsayılan ad: .venv
uv venv
# İsimlendirme ile: önerilmez
uv venv .venv2
# Ekstradan şunu çalıştırmanız gerekir: export UV_PROJECT_ENVIRONMENT=.venv2

# VEYA BELİRLİ BIR PYTHON SÜRÜMÜYLE DE OLUŞTURABİLİRSİNİZ.

# 1. Başka bir python sürümünü yükleyin:
uv python install 3.12.3
# 2. Sürümü proje kök dizinindeki bir dosyaya da sabitleyebilirsiniz.
uv python pin 3.12.3 # Varsayılan: pyproject.toml'yi karşılayan daha en yüksek sürüm
# 3. Bu sürümle .venv oluşturun
uv venv --python 3.12.3 
Projeye özgü python'ın bulunduğu sanal ortamı (virtual environment) etkinleştirme
source .venv/bin/activate
Dependency (Bağımlılık) paketi yükleyip toml'a ekleme
uv add pandas
# geliştirme bağımlılık grubuna ekleyin.
uv add --dev pytest jupyter  
uv add --group dev pytest jupyter
# toml yerine sadece aktif virtual environment'e ekleme
uv pip install numpy
# son sürüme güncelleme
uv pip install numpy --upgrade
PyPI - Python Paket İndeksi Listesinde olmayan bir paketi ekleme
# Örnek: Torch'un cpu sürümünü yükleme
uv add torch --index https://download.pytorch.org/whl/cpu --index-strategy unsafe-best-match
# pyproject.toml adresinden --no-deps ile yükleyin [Çakışan bağımlılıkları yüklemek için]
uv pip install -r pyproject.toml --index-strategy unsafe-best-match --no-deps

Bağımlılıkları kaldırın
uv remove loguru
uv remove --dev jupyter
Gereksinimleri pyproject.toml'daki tabloya bakıp yükleyin.
uv sync
uv sync --dev
# veya
uv pip install -r pyproject.toml
Yüklü paketleri listeleme
uv pip list
# Bağımlılık ağacı şeklinde görmek için
uv tree
pyproject.toml gereksinimlerini requirements.txt dosyasına kaydetme
uv pip compile pyproject.toml -o requirements.txt
requirements.txt gereksinimlerini pyproject.toml dosyasına kaydetme
uv add -r requirements.txt
# Dosya pypi'dan olmayan ekstra url içeriyorsa
uv add -r requirements.txt --index https://download.pytorch.org/whl/cpu --index-strategy unsafe-best-match
Proje ortamında bir python dosyası çalıştırma (pyproject.toml'a göre)
uv run main.py
Araçları projenizin içine yüklemeden çalıştırma (uvx)
# Örneğin pytest'i çalıştırmak için
uvx pytest
# veya uv tool komutu ile
uv tool run pytest

Paylaş:

Ara