Align `pyproject.toml` dependency constraints with versions resolved by `uv`.
Project description
uv-align
uv-align is a Rust command-line tool that keeps your Python dependency constraints in sync between pyproject.toml and uv.lock.
When you run uv lock --upgrade, uv resolves and updates uv.lock with the latest compatible versions, but leaves the version constraints in pyproject.toml untouched.
This means your declared constraints can drift from what uv actually resolved - uv-align bridges that gap.
It reads the resolved versions from uv.lock and updates the version numbers in pyproject.toml accordingly, preserving your existing operators (>=, ==, etc.), upper bounds, environment markers, and formatting.
It does not require a virtual environment as it does not install packages, and never modifies uv.lock directly (uv is responsible for that).
Links:
Table of Contents
Installation
As a tool (recommended)
Install uv-align as a global tool:
uv tool install uv-align
If you'd like to run it without installing:
uvx uv-align
As a dev dependency
To pin uv-align to a specific project, add it to your development dependencies in pyproject.toml:
uv add uv-align --optional dev
As a pre-built binary
Pre-built binaries for Linux, macOS, and Windows are available on the GitHub Releases page.
Quick Guide
uv-align -h # Show help message
uv-align --check # Check for out-of-sync dependencies between `pyproject.toml` and `uv.lock`
uv-align -y # Update any out-of-sync version constraints in `pyproject.toml`
uv-align -yu # Upgrade dependencies and update version constraints in `pyproject.toml`
Example output:
Usage
Align `pyproject.toml` dependency constraints with versions resolved by `uv`
Usage: uv-align [OPTIONS] [PATH]
Arguments:
[PATH] Path to folder containing `pyproject.toml` and `uv.lock` files [default: .]
Options:
--check Show a diff of dependency updates without applying them
-y, --yes Automatically apply all changes without prompting
-u, --upgrade Upgrade dependencies in `uv.lock` with `uv lock --upgrade`
-v, --verbose Show detailed information about dependency updates
-h, --help Print help
How It Works
uv-align is a file transformer - in its default mode it reads two files and writes one, with no network access or environment inspection.
The optional --upgrade flag adds a uv invocation that does require network access to fetch updated package metadata.
Step 1 - Parse pyproject.toml
All dependency entries are read from three locations:
[project.dependencies]- main dependencies[project.optional-dependencies]- extras groups (e.g.dev,docs)[dependency-groups]- PEP 735 groups supported by uv
Each entry is parsed as a PEP 508 string.
The package name, version operator (>=, ==, ~=, etc.), lower-bound version, and any suffix constraints (e.g. ,<1.0) are extracted separately.
Git/URL dependencies (e.g. package @ git+https://...) are included in the parsed output but have no version to compare, so they are naturally skipped during the diff step.
Extras (e.g. package[extra]) and environment markers (e.g. ; python_version >= '3.11') are stripped as they are not relevant to version bumping.
Package names are normalised per PEP 503 (lowercase, runs of [-_.] collapsed to -) to ensure consistent matching.
Step 2 - Parse uv.lock
Every [[package]] entry in the lockfile is read to build a list of resolved package names and versions.
Package names are normalised in the same way as step 1, so that my_package and my-package match correctly.
Packages without a version field (git/URL sources) are skipped naturally by the parser.
Step 3 - Compute the diff
Each dependency from pyproject.toml that has a resolved version is looked up in the lockfile by its normalised name.
If the resolved version differs from the declared version, a change is recorded.
Version strings are compared after normalising trailing .0 components, so 0.25.0 and 0.25 are treated as equal and no spurious change is emitted.
Step 4 - Report or apply
In --check mode, the diff is printed and the tool exits with code 1 if any changes are needed (suitable for CI), or code 0 if everything is already in sync.
Otherwise, the user is prompted to confirm before changes are applied (or -y skips the prompt).
Changes are written back to pyproject.toml using toml_edit - a format-preserving TOML library that modifies only the version numbers, leaving all comments, whitespace, and key ordering intact.
The original operator and any suffix constraints are preserved verbatim.
Step 5 - Upgrade mode (-u)
With --upgrade, uv lock --upgrade runs first to fetch and resolve the latest compatible versions, updating uv.lock accordingly.
Steps 1–4 then run as normal to align pyproject.toml with the newly resolved versions.
The number of updated, added, and removed packages reported by uv is printed as a summary, with full package details available via --verbose.
License
This project is licensed under the MIT License - see the LICENSE file for details.
Project details
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distributions
Built Distributions
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file uv_align-0.1.3-py3-none-win_amd64.whl.
File metadata
- Download URL: uv_align-0.1.3-py3-none-win_amd64.whl
- Upload date:
- Size: 567.0 kB
- Tags: Python 3, Windows x86-64
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
228bf84d3d5742468794c30a73958719edfb5f3e6734a955e29a96147bb23c86
|
|
| MD5 |
c0223583c9de6d99cb5f4780ef16d0ce
|
|
| BLAKE2b-256 |
2df72f6cc8e9e07ffa6b61ef93a9d4a049f79b2a55af7769aff0abddb1399355
|
Provenance
The following attestation bundles were made for uv_align-0.1.3-py3-none-win_amd64.whl:
Publisher:
publish.yml on javidahmed64592/uv-align
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
uv_align-0.1.3-py3-none-win_amd64.whl -
Subject digest:
228bf84d3d5742468794c30a73958719edfb5f3e6734a955e29a96147bb23c86 - Sigstore transparency entry: 2042873437
- Sigstore integration time:
-
Permalink:
javidahmed64592/uv-align@3437123d338abd0078a55ae70063233b0c7ec456 -
Branch / Tag:
refs/tags/v0.1.3 - Owner: https://github.com/javidahmed64592
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@3437123d338abd0078a55ae70063233b0c7ec456 -
Trigger Event:
push
-
Statement type:
File details
Details for the file uv_align-0.1.3-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.
File metadata
- Download URL: uv_align-0.1.3-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
- Upload date:
- Size: 764.0 kB
- Tags: Python 3, manylinux: glibc 2.17+ x86-64
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
014052779541483998c9ab83a16a81d73aa863707fd5fbe7ac84f8a25e9a6602
|
|
| MD5 |
24404997363d63e2f1feaf2fe76dc67d
|
|
| BLAKE2b-256 |
4bfac392f0062248662d9b554bf65df73c94f5163f9e1f67cf22871b35ec6d87
|
Provenance
The following attestation bundles were made for uv_align-0.1.3-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl:
Publisher:
publish.yml on javidahmed64592/uv-align
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
uv_align-0.1.3-py3-none-manylinux_2_17_x86_64.manylinux2014_x86_64.whl -
Subject digest:
014052779541483998c9ab83a16a81d73aa863707fd5fbe7ac84f8a25e9a6602 - Sigstore transparency entry: 2042872778
- Sigstore integration time:
-
Permalink:
javidahmed64592/uv-align@3437123d338abd0078a55ae70063233b0c7ec456 -
Branch / Tag:
refs/tags/v0.1.3 - Owner: https://github.com/javidahmed64592
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@3437123d338abd0078a55ae70063233b0c7ec456 -
Trigger Event:
push
-
Statement type:
File details
Details for the file uv_align-0.1.3-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl.
File metadata
- Download URL: uv_align-0.1.3-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
- Upload date:
- Size: 746.7 kB
- Tags: Python 3, manylinux: glibc 2.17+ ARM64
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
8036465cddbc6e03f7f1c49216861586fc9f38a921887d88bdb56a6eb37bae16
|
|
| MD5 |
0473ac95b98171d5ad72092b5e1b7085
|
|
| BLAKE2b-256 |
64433c35d719548e76b1b41e75628dd89689a0dea555433765dd68a3ffbad432
|
Provenance
The following attestation bundles were made for uv_align-0.1.3-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl:
Publisher:
publish.yml on javidahmed64592/uv-align
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
uv_align-0.1.3-py3-none-manylinux_2_17_aarch64.manylinux2014_aarch64.whl -
Subject digest:
8036465cddbc6e03f7f1c49216861586fc9f38a921887d88bdb56a6eb37bae16 - Sigstore transparency entry: 2042871923
- Sigstore integration time:
-
Permalink:
javidahmed64592/uv-align@3437123d338abd0078a55ae70063233b0c7ec456 -
Branch / Tag:
refs/tags/v0.1.3 - Owner: https://github.com/javidahmed64592
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@3437123d338abd0078a55ae70063233b0c7ec456 -
Trigger Event:
push
-
Statement type:
File details
Details for the file uv_align-0.1.3-py3-none-macosx_11_0_arm64.whl.
File metadata
- Download URL: uv_align-0.1.3-py3-none-macosx_11_0_arm64.whl
- Upload date:
- Size: 698.7 kB
- Tags: Python 3, macOS 11.0+ ARM64
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
862722d99936b80a3647d957e18e854aeb337cba4decaa4e6aa8793258f22f97
|
|
| MD5 |
1a56cf4955324445d3caf5d127355701
|
|
| BLAKE2b-256 |
7e5db21dbc469650724d1bc1d9e6d988565ca0337ccef7ba927b40df0b1d9ee7
|
Provenance
The following attestation bundles were made for uv_align-0.1.3-py3-none-macosx_11_0_arm64.whl:
Publisher:
publish.yml on javidahmed64592/uv-align
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
uv_align-0.1.3-py3-none-macosx_11_0_arm64.whl -
Subject digest:
862722d99936b80a3647d957e18e854aeb337cba4decaa4e6aa8793258f22f97 - Sigstore transparency entry: 2042873893
- Sigstore integration time:
-
Permalink:
javidahmed64592/uv-align@3437123d338abd0078a55ae70063233b0c7ec456 -
Branch / Tag:
refs/tags/v0.1.3 - Owner: https://github.com/javidahmed64592
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@3437123d338abd0078a55ae70063233b0c7ec456 -
Trigger Event:
push
-
Statement type:
File details
Details for the file uv_align-0.1.3-py3-none-macosx_10_12_x86_64.whl.
File metadata
- Download URL: uv_align-0.1.3-py3-none-macosx_10_12_x86_64.whl
- Upload date:
- Size: 715.4 kB
- Tags: Python 3, macOS 10.12+ x86-64
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
6a3ad3f49b3e665bb90e90dcc194e1d4bae9345aa9a6121fcd5e4e6662cf0534
|
|
| MD5 |
a114c0e63a66c6a99c2d01b11546784a
|
|
| BLAKE2b-256 |
90e4336143a6b80cdc89769bd23246c7310b5748345b7369582e7ab5c1cf9228
|
Provenance
The following attestation bundles were made for uv_align-0.1.3-py3-none-macosx_10_12_x86_64.whl:
Publisher:
publish.yml on javidahmed64592/uv-align
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
uv_align-0.1.3-py3-none-macosx_10_12_x86_64.whl -
Subject digest:
6a3ad3f49b3e665bb90e90dcc194e1d4bae9345aa9a6121fcd5e4e6662cf0534 - Sigstore transparency entry: 2042874163
- Sigstore integration time:
-
Permalink:
javidahmed64592/uv-align@3437123d338abd0078a55ae70063233b0c7ec456 -
Branch / Tag:
refs/tags/v0.1.3 - Owner: https://github.com/javidahmed64592
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@3437123d338abd0078a55ae70063233b0c7ec456 -
Trigger Event:
push
-
Statement type: