mirror of
https://github.com/astral-sh/uv.git
synced 2025-10-28 18:54:10 +00:00
Read package metadata from pyproject.toml when statically defined (#2676)
## Summary Now that we're resolving metadata more aggressively for local sources, it's worth doing this. We now pull metadata from the `pyproject.toml` directly if it's statically-defined. Closes https://github.com/astral-sh/uv/issues/2629.
This commit is contained in:
parent
248d6f89ef
commit
365c292525
9 changed files with 302 additions and 34 deletions
|
|
@ -955,10 +955,10 @@ impl<'a, T: BuildContext> SourceDistCachedBuilder<'a, T> {
|
|||
) -> Result<Option<Metadata23>, Error> {
|
||||
debug!("Preparing metadata for: {source}");
|
||||
|
||||
// Attempt to read static metadata from the source distribution.
|
||||
// Attempt to read static metadata from the `PKG-INFO` file.
|
||||
match read_pkg_info(source_root).await {
|
||||
Ok(metadata) => {
|
||||
debug!("Found static metadata for: {source}");
|
||||
debug!("Found static `PKG-INFO` for: {source}");
|
||||
|
||||
// Validate the metadata.
|
||||
if let Some(name) = source.name() {
|
||||
|
|
@ -973,7 +973,30 @@ impl<'a, T: BuildContext> SourceDistCachedBuilder<'a, T> {
|
|||
return Ok(Some(metadata));
|
||||
}
|
||||
Err(err @ (Error::MissingPkgInfo | Error::DynamicPkgInfo(_))) => {
|
||||
debug!("No static metadata available for: {source} ({err:?})");
|
||||
debug!("No static `PKG-INFO` available for: {source} ({err:?})");
|
||||
}
|
||||
Err(err) => return Err(err),
|
||||
}
|
||||
|
||||
// Attempt to read static metadata from the `pyproject.toml`.
|
||||
match read_pyproject_toml(source_root).await {
|
||||
Ok(metadata) => {
|
||||
debug!("Found static `pyproject.toml` for: {source}");
|
||||
|
||||
// Validate the metadata.
|
||||
if let Some(name) = source.name() {
|
||||
if metadata.name != *name {
|
||||
return Err(Error::NameMismatch {
|
||||
metadata: metadata.name,
|
||||
given: name.clone(),
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
return Ok(Some(metadata));
|
||||
}
|
||||
Err(err @ (Error::MissingPyprojectToml | Error::DynamicPyprojectToml(_))) => {
|
||||
debug!("No static `pyproject.toml` available for: {source} ({err:?})");
|
||||
}
|
||||
Err(err) => return Err(err),
|
||||
}
|
||||
|
|
@ -1105,6 +1128,25 @@ pub(crate) async fn read_pkg_info(source_tree: &Path) -> Result<Metadata23, Erro
|
|||
Ok(metadata)
|
||||
}
|
||||
|
||||
/// Read the [`Metadata23`] from a source distribution's `pyproject.tom` file, if it defines static
|
||||
/// metadata consistent with PEP 621.
|
||||
pub(crate) async fn read_pyproject_toml(source_tree: &Path) -> Result<Metadata23, Error> {
|
||||
// Read the `pyproject.toml` file.
|
||||
let content = match fs::read_to_string(source_tree.join("pyproject.toml")).await {
|
||||
Ok(content) => content,
|
||||
Err(err) if err.kind() == std::io::ErrorKind::NotFound => {
|
||||
return Err(Error::MissingPyprojectToml);
|
||||
}
|
||||
Err(err) => return Err(Error::CacheRead(err)),
|
||||
};
|
||||
|
||||
// Parse the metadata.
|
||||
let metadata =
|
||||
Metadata23::parse_pyproject_toml(&content).map_err(Error::DynamicPyprojectToml)?;
|
||||
|
||||
Ok(metadata)
|
||||
}
|
||||
|
||||
/// Read an existing HTTP-cached [`Manifest`], if it exists.
|
||||
pub(crate) fn read_http_manifest(cache_entry: &CacheEntry) -> Result<Option<Manifest>, Error> {
|
||||
match fs_err::File::open(cache_entry.path()) {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue