Allow multiple source entries for each package in tool.uv.sources (#7745)

## Summary

This PR enables users to provide multiple source entries in
`tool.uv.sources`, e.g.:

```toml
[tool.uv.sources]
httpx = [
  { git = "https://github.com/encode/httpx", tag = "0.27.2", marker = "sys_platform == 'darwin'" },
  { git = "https://github.com/encode/httpx", tag = "0.24.1", marker = "sys_platform == 'linux'" },
]
```

The implementation is relatively straightforward: when we lower the
requirement, we now return an iterator rather than a single requirement.
In other words, the above is transformed into two requirements:

```txt
httpx @ git+https://github.com/encode/httpx@0.27.2 ; sys_platform == 'darwin'
httpx @ git+https://github.com/encode/httpx@0.24.1 ; sys_platform == 'linux'
```

We verify (at deserialization time) that the markers are
non-overlapping.

Closes https://github.com/astral-sh/uv/issues/3397.
This commit is contained in:
Charlie Marsh 2024-09-30 17:16:44 -04:00 committed by GitHub
parent 71d5661bd8
commit f67347e72c
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
17 changed files with 1063 additions and 206 deletions

View file

@ -14,7 +14,7 @@ use uv_normalize::{GroupName, PackageName, DEV_DEPENDENCIES};
use uv_warnings::{warn_user, warn_user_once};
use crate::pyproject::{
Project, PyProjectToml, PyprojectTomlError, Source, ToolUvSources, ToolUvWorkspace,
Project, PyProjectToml, PyprojectTomlError, Source, Sources, ToolUvSources, ToolUvWorkspace,
};
#[derive(thiserror::Error, Debug)]
@ -78,7 +78,7 @@ pub struct Workspace {
/// The sources table from the workspace `pyproject.toml`.
///
/// This table is overridden by the project sources.
sources: BTreeMap<PackageName, Source>,
sources: BTreeMap<PackageName, Sources>,
/// The `pyproject.toml` of the workspace root.
pyproject_toml: PyProjectToml,
}
@ -517,7 +517,7 @@ impl Workspace {
}
/// The sources table from the workspace `pyproject.toml`.
pub fn sources(&self) -> &BTreeMap<PackageName, Source> {
pub fn sources(&self) -> &BTreeMap<PackageName, Sources> {
&self.sources
}
@ -531,7 +531,7 @@ impl Workspace {
.as_ref()
.and_then(|uv| uv.sources.as_ref())
.map(ToolUvSources::inner)
.map(|sources| sources.values())
.map(|sources| sources.values().flat_map(Sources::iter))
})
})
.flatten()
@ -1755,9 +1755,11 @@ mod tests {
}
},
"sources": {
"bird-feeder": {
"workspace": true
}
"bird-feeder": [
{
"workspace": true
}
]
},
"pyproject_toml": {
"project": {
@ -1773,9 +1775,11 @@ mod tests {
"tool": {
"uv": {
"sources": {
"bird-feeder": {
"workspace": true
}
"bird-feeder": [
{
"workspace": true
}
]
},
"workspace": {
"members": [