mirror of
https://github.com/astral-sh/uv.git
synced 2025-08-04 19:08:04 +00:00
Allow conflicting extras in explicit index assignments (#9160)
## Summary This PR enables something like the "final boss" of PyTorch setups -- explicit support for CPU vs. GPU-enabled variants via extras: ```toml [project] name = "project" version = "0.1.0" requires-python = ">=3.13.0" dependencies = [] [project.optional-dependencies] cpu = [ "torch==2.5.1+cpu", ] gpu = [ "torch==2.5.1", ] [tool.uv.sources] torch = [ { index = "torch-cpu", extra = "cpu" }, { index = "torch-gpu", extra = "gpu" }, ] [[tool.uv.index]] name = "torch-cpu" url = "https://download.pytorch.org/whl/cpu" explicit = true [[tool.uv.index]] name = "torch-gpu" url = "https://download.pytorch.org/whl/cu124" explicit = true [tool.uv] conflicts = [ [ { extra = "cpu" }, { extra = "gpu" }, ], ] ``` It builds atop the conflicting extras work to allow sources to be marked as specific to a dedicated extra being enabled or disabled. As part of this work, sources now have an `extra` field. If a source has an `extra`, it means that the source is only applied to the requirement when defined within that optional group. For example, `{ index = "torch-cpu", extra = "cpu" }` above only applies to `"torch==2.5.1+cpu"`. The `extra` field does _not_ mean that the source is "enabled" when the extra is activated. For example, this wouldn't work: ```toml [project] name = "project" version = "0.1.0" requires-python = ">=3.13.0" dependencies = ["torch"] [tool.uv.sources] torch = [ { index = "torch-cpu", extra = "cpu" }, { index = "torch-gpu", extra = "gpu" }, ] [[tool.uv.index]] name = "torch-cpu" url = "https://download.pytorch.org/whl/cpu" explicit = true [[tool.uv.index]] name = "torch-gpu" url = "https://download.pytorch.org/whl/cu124" explicit = true ``` In this case, the sources would effectively be ignored. Extras are really confusing... but I think this is correct? We don't want enabling or disabling extras to affect resolution information that's _outside_ of the relevant optional group.
This commit is contained in:
parent
a88a3e5eba
commit
e4fc875afa
19 changed files with 1607 additions and 227 deletions
|
@ -335,18 +335,17 @@ dependencies = ["torch"]
|
|||
|
||||
[tool.uv.sources]
|
||||
torch = [
|
||||
{ index = "torch-cu118", marker = "sys_platform == 'darwin'"},
|
||||
{ index = "torch-cu124", marker = "sys_platform != 'darwin'"},
|
||||
{ index = "torch-cpu", marker = "platform_system == 'Darwin'"},
|
||||
{ index = "torch-gpu", marker = "platform_system == 'Linux'"},
|
||||
]
|
||||
|
||||
[[tool.uv.index]]
|
||||
name = "torch-cu118"
|
||||
url = "https://download.pytorch.org/whl/cu118"
|
||||
name = "torch-cpu"
|
||||
url = "https://download.pytorch.org/whl/cpu"
|
||||
|
||||
[[tool.uv.index]]
|
||||
name = "torch-cu124"
|
||||
name = "torch-gpu"
|
||||
url = "https://download.pytorch.org/whl/cu124"
|
||||
|
||||
```
|
||||
|
||||
## Optional dependencies
|
||||
|
@ -394,6 +393,36 @@ $ uv add httpx --optional network
|
|||
If you have optional dependencies that conflict with one another, resolution will fail
|
||||
unless you explicitly [declare them as conflicting](./projects.md#optional-dependencies).
|
||||
|
||||
Sources can also be declared as applying only to a specific optional dependency. For example, to
|
||||
pull `torch` from different PyTorch indexes based on an optional `cpu` or `gpu` extra:
|
||||
|
||||
```toml title="pyproject.toml"
|
||||
[project]
|
||||
dependencies = []
|
||||
|
||||
[project.optional-dependencies]
|
||||
cpu = [
|
||||
"torch",
|
||||
]
|
||||
gpu = [
|
||||
"torch",
|
||||
]
|
||||
|
||||
[tool.uv.sources]
|
||||
torch = [
|
||||
{ index = "torch-cpu", extra = "cpu" },
|
||||
{ index = "torch-gpu", extra = "gpu" },
|
||||
]
|
||||
|
||||
[[tool.uv.index]]
|
||||
name = "torch-cpu"
|
||||
url = "https://download.pytorch.org/whl/cpu"
|
||||
|
||||
[[tool.uv.index]]
|
||||
name = "torch-gpu"
|
||||
url = "https://download.pytorch.org/whl/cu124"
|
||||
```
|
||||
|
||||
## Development dependencies
|
||||
|
||||
Unlike optional dependencies, development dependencies are local-only and will _not_ be included in
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue