UV - Python Package Manager

What is UV?

UV is a next-generation Python toolchain written in Rust. It unifies package management, virtual environments, and Python version control into a single, high-performance binary — no activation steps, no Python preinstalled.

Why UV Exists

Python development traditionally requires multiple tools — pip, venv, and pyenv — leading to slow installs, multiple CLIs, and the “bootstrap problem” (needing Python installed first). Even Poetry, which improved dependency resolution, still relies on external Python managers and mutates the shell via activated environments, causing inconsistent command behavior.

UV rethinks the workflow. It replaces multiple tools with one binary, supports the official PEP-518 pyproject.toml standard, and runs code with uv run — activating virtual environments internally per process without affecting your terminal. It also includes a Python version manager, SAT-based dependency resolution, and lockfile reproducibility.

The result: a tool that is 10–20× faster than pip or Poetry, works the same across macOS, Linux, and Windows, and removes most friction from Python development workflows.

Feature Comparison

Category Aspect pyenv + pip + venv Poetry + pyenv UV
Dependency Management Dependency resolution algorithm Sequential / greedy (may install conflicts) ✅ SAT solver (correct, reproducible) ✅ SAT solver (optimized, parallel)
Reproducibility with lock files requirements.txt: none
pip freeze: partial, no hashes
✅ Yes (poetry.lock) ✅ Yes (uv.lock)
Performance (install ~50 packages) 1× baseline (30–45s) ~1.3× faster (25–35s) ✅ 10–15× faster (2–3s, optimized in Rust)
Environment Management Virtual environment activation Manual activation required; mutates shell poetry run auto-activates uv run auto-activates internally (no shell mutation)
Tool integration 3 separate tools 2 tools (still needs pyenv) ✅ Single tool
Python Version Management Install / switch Python versions Via pyenv (mutates shell environment) Via pyenv (mutates shell environment) ✅ Built-in (no shell mutation)
Bootstrap requirement Needs Python preinstalled Needs Python preinstalled ✅ None (self-contained binary)

Typical Workflows Compared

Note: Poetry + pyenv covers most of the same workflow steps as UV, but UV is significantly faster, isolates environments without shell mutation, and includes a built-in Python version manager.

pyenv + pip + venv Poetry + pyenv UV
pyenv install 3.12
pyenv local 3.12
python -m venv .venv
source .venv/bin/activate
pip install -r requirements.txt
(wait 30–60s)
pyenv install 3.12
pyenv local 3.12
poetry install
(wait 20–40s)
uv python install 3.12
uv sync
(wait 2–3s)
python script.py poetry run python script.py uv run python script.py
deactivate (no deactivate needed) (no deactivate needed)

Using UV

Install UV

# macOS / Linux
curl -LsSf https://astral.sh/uv/install.sh | sh

# Windows (PowerShell)
powershell -c "irm https://astral.sh/uv/install.ps1 | iex"

# Verify
uv --version

Start a Project

# Create and enter project
mkdir my-project && cd my-project

# Initialize pyproject.toml and environment
uv init

# Or if pyproject.toml already exists:
uv sync

Minimal pyproject.toml example:

[project]
name = "my-project"
version = "0.1.0"
requires-python = ">=3.11"

dependencies = [
    "requests>=2.31.0",
]

Managing Dependencies

Add / remove packages updates pyproject.toml automatically:

[project]
dependencies = [
    "requests>=2.31.0",
]

[tool.uv.dev-dependencies]
pytest = "*"
# Add main dependency
uv add requests

# Add dev dependency
uv add --dev pytest

# Remove dependency
uv remove requests

Dependency Groups (Optional)

Defined in pyproject.toml:

[dependency-groups]
dev = ["pytest", "mypy", "ruff"]
docs = ["mkdocs", "mkdocs-material"]
# Install groups
uv sync --group dev
uv sync --group docs

Python Versions

Stored in pyproject.toml:

[tool.uv.python]
3.12 = "*"
3.11 = "*"
# Install / switch Python
uv python install 3.12
uv python install 3.11

# List installed versions
uv python list

Running Scripts & Tools

Commands are defined or come from installed packages; uv run reads from pyproject.toml or the environment:

[project.scripts]
my-tool = "my_package.main:cli"
# Run Python script or module
uv run python main.py
uv run python -m module_name

# Run installed tools
uv run pytest
uv run mypy src/
uv run ruff check src/
uv run ruff format src/

# Run a custom script
uv run my-tool

Notes

No activation needed — uv run handles isolated environments internally, so your terminal environment remains unchanged.

0 comments :

This work is licensed under BSD Zero Clause License | nacho4d ®