Bundle a locked uv environment into a self-contained, offline-installable directory. The output includes pinned requirements, third-party wheels, locally built wheels, and a portable Python interpreter.
- Exports locked requirements from your
uvlock file. - Downloads third-party wheels into
pack/wheels/. - Builds local workspace packages into
pack/vendor/. - Downloads a python-build-standalone archive into
pack/python/(unless you skip thepythonstep). - Writes
unpack.shandunpack.ps1to unpack the resulting venv offline.
Install uv-pack as a dev-dependency.
uv add --dev uv-packOnce installed, run using:
uv run uv-pack --helpYou can also use uv-pack as a tool.
# specify the python version! uv tool run --python 3.12 uv-pack --help # or using uvx (equivalent) uvx --python 3.12 uv-pack --helpuv-pack [STEPS...]Options:
STEPS: subset of pipeline steps (default:clean export download build python)-s, --skip: skip a pipeline step (can be supplied multiple times)-o, --output-directory: path to output directory (default:./pack)-v, --verbose: show more detailed pack progress logging--uv-build: extra args passed touv build--uv-export: extra args passed touv export--pip-download: extra args passed topip download
Pipeline steps:
clean: remove the output directoryexport: writerequirements.txtfiles for third-party and local packagesdownload: download third-party wheels and sourcesbuild: build local wheels and compile the combined requirements filepython: download a python-build-standalone archive for the current Python version and platform
# run the entire pipeline (default) with verbose outputs uv-pack --verbose # only clean and export the requirements uv-pack clean exportpack/ requirements.txt wheels/ requirements.txt vendor/ requirements.txt python/ # (omitted when the python step is skipped) unpack.sh unpack.ps1 .gitignore README.md POSIX (sh/bash/zsh):
./pack/unpack.shPowerShell:
.\pack\unpack.ps1All scripts also accept VENV_DIR, PYTHON_DIR and BASE_PY environment variables. Use BASE_PY when you skipped the python step during packing to provide a system python interpreter. VENV_DIR (default = .venv) and PYTHON_DIR (default = .python) can be used to customize the target python and venv directory. Set VENV_DIR="" to skip creating a virtual environment and install directly into BASE_PY.
UV_PYTHON_INSTALL_MIRROR can override the GitHub API endpoint to retrieve the Python releases, default is: https://api.github.com/repos/astral-sh/python-build-standalone/releases/latest.
GITHUB_TOKEN can be used to authenticate requests to the GitHub API to prevent possible rate-limiting.
- The pack process must happen in the
pyproject.tomloruv.tomldirectory, typically the repository root, becauseuvexports relative paths to the project root. - The build platform is expected to equal the usage platform; it is currently not possible to pack an environment for a different platform.
- The project Python version is ignored when running
uv-packas a tool (uv tool runoruvx) and should be specified usinguv tool run --python 3.11 uv-packoruvx --python 3.11 uv-pack, see uv#uv5951 and uv#8206. - The download process can be slow because
pip downloadis used as there is no native (parallel) uv download option available for wheels, see uv#3163.
Use --uv-export to forward arguments, for example:
uv-pack --uv-export "--package $MY_PACKAGE"to export only a specific workspace packageuv-pack --uv-export "--locked --dev"to include dev-deps and ensure an up-to-date lock fileuv-pack --uv-export "--all-extras"to include all extra dependencies
The same is true for --uv-build and --pip-download arguments.
The index urls set in pyproject.toml and uv.toml are not configured by default for the wheel download (pip download), you can specify them as:
uv-pack --pip-download "--index-url $MY_INDEX --extra-index-url $MY_EXTRA_INDEX"
Skip the python step: uv-pack --skip python. When unpacking, set BASE_PY to a system Python path.
Set BASE_PY to the target interpreter and VENV_DIR="" when unpacking. For example:
BASE_PY=/usr/bin/python3 VENV_DIR="" sh ./pack/unpack.shSkip the clean step: uv-pack --skip clean. Note that this automatically re-uses downloaded wheels and the downloaded Python interpreter.
Run only uv-pack build.
Move the pack to the final location and, depending on the shell used, call unpack.sh or unpack.ps1. Don't move the virtual environment or pack folder after unpacking (hardcoded paths).