mirror of
https://github.com/astral-sh/uv.git
synced 2025-09-29 21:44:51 +00:00
Expand scope of archive timestamping (#1960)
## Summary Instead of looking at _either_ `pyproject.toml` or `setup.py`, we should just be conservative and take the most-recent timestamp out of `pyproject.toml`, `setup.py`, and `setup.cfg`. That will help prevent staleness issues like those described in https://github.com/astral-sh/uv/issues/1913#issuecomment-1961544084.
This commit is contained in:
parent
8d706b0f2a
commit
f449bd41fb
1 changed files with 28 additions and 12 deletions
|
@ -1,3 +1,4 @@
|
||||||
|
use std::cmp::max;
|
||||||
use std::fmt::{Display, Formatter};
|
use std::fmt::{Display, Formatter};
|
||||||
use std::io;
|
use std::io;
|
||||||
use std::io::Write;
|
use std::io::Write;
|
||||||
|
@ -638,33 +639,48 @@ impl ArchiveTimestamp {
|
||||||
/// Return the modification timestamp for an archive, which could be a file (like a wheel or a zip
|
/// Return the modification timestamp for an archive, which could be a file (like a wheel or a zip
|
||||||
/// archive) or a directory containing a Python package.
|
/// archive) or a directory containing a Python package.
|
||||||
///
|
///
|
||||||
/// If the path is to a directory with no entrypoint (i.e., no `pyproject.toml` or `setup.py`),
|
/// If the path is to a directory with no entrypoint (i.e., no `pyproject.toml`, `setup.py`, or
|
||||||
/// returns `None`.
|
/// `setup.cfg`), returns `None`.
|
||||||
pub fn from_path(path: impl AsRef<Path>) -> Result<Option<Self>, io::Error> {
|
pub fn from_path(path: impl AsRef<Path>) -> Result<Option<Self>, io::Error> {
|
||||||
let metadata = fs_err::metadata(path.as_ref())?;
|
let metadata = fs_err::metadata(path.as_ref())?;
|
||||||
if metadata.is_file() {
|
if metadata.is_file() {
|
||||||
Ok(Some(Self::Exact(Timestamp::from_metadata(&metadata))))
|
Ok(Some(Self::Exact(Timestamp::from_metadata(&metadata))))
|
||||||
} else {
|
} else {
|
||||||
// TODO(charlie): Take the maximum of `pyproject.toml`, `setup.py`, and `setup.cfg`.
|
// Compute the modification timestamp for the `pyproject.toml`, `setup.py`, and
|
||||||
if let Some(metadata) = path
|
// `setup.cfg` files, if they exist.
|
||||||
|
let pyproject_toml = path
|
||||||
.as_ref()
|
.as_ref()
|
||||||
.join("pyproject.toml")
|
.join("pyproject.toml")
|
||||||
.metadata()
|
.metadata()
|
||||||
.ok()
|
.ok()
|
||||||
.filter(std::fs::Metadata::is_file)
|
.filter(std::fs::Metadata::is_file)
|
||||||
{
|
.as_ref()
|
||||||
Ok(Some(Self::Approximate(Timestamp::from_metadata(&metadata))))
|
.map(Timestamp::from_metadata);
|
||||||
} else if let Some(metadata) = path
|
|
||||||
|
let setup_py = path
|
||||||
.as_ref()
|
.as_ref()
|
||||||
.join("setup.py")
|
.join("setup.py")
|
||||||
.metadata()
|
.metadata()
|
||||||
.ok()
|
.ok()
|
||||||
.filter(std::fs::Metadata::is_file)
|
.filter(std::fs::Metadata::is_file)
|
||||||
{
|
.as_ref()
|
||||||
Ok(Some(Self::Approximate(Timestamp::from_metadata(&metadata))))
|
.map(Timestamp::from_metadata);
|
||||||
} else {
|
|
||||||
Ok(None)
|
let setup_cfg = path
|
||||||
}
|
.as_ref()
|
||||||
|
.join("setup.cfg")
|
||||||
|
.metadata()
|
||||||
|
.ok()
|
||||||
|
.filter(std::fs::Metadata::is_file)
|
||||||
|
.as_ref()
|
||||||
|
.map(Timestamp::from_metadata);
|
||||||
|
|
||||||
|
// Take the most recent timestamp of the three files.
|
||||||
|
let Some(timestamp) = max(pyproject_toml, max(setup_py, setup_cfg)) else {
|
||||||
|
return Ok(None);
|
||||||
|
};
|
||||||
|
|
||||||
|
Ok(Some(Self::Approximate(timestamp)))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue