mirror of
https://github.com/astral-sh/uv.git
synced 2025-07-07 21:35:00 +00:00
Use filename trait for WheelWire
conversion (#3651)
## Summary The main motivation here is that the `.filename()` method that we implement on `Url` will do URL decoding for the last segment, which we were missing here. The errors are a bit awkward, because in `crates/uv-resolver/src/lock.rs`, we wrap in `failed to extract filename from URL: {url}`, so in theory we want the underlying errors to _omit_ the URL? But sometimes they use `#[error(transparent)]`?
This commit is contained in:
parent
657eebd50b
commit
f3965fef5e
4 changed files with 19 additions and 15 deletions
|
@ -14,8 +14,11 @@ pub enum Error {
|
|||
#[error(transparent)]
|
||||
WheelFilename(#[from] distribution_filename::WheelFilenameError),
|
||||
|
||||
#[error("Unable to extract filename from URL: {0}")]
|
||||
UrlFilename(Url),
|
||||
#[error("Unable to extract file path from URL: {0}")]
|
||||
MissingFilePath(Url),
|
||||
|
||||
#[error("Could not extract path segments from URL: {0}")]
|
||||
MissingPathSegments(Url),
|
||||
|
||||
#[error("Distribution not found at: {0}")]
|
||||
NotFound(Url),
|
||||
|
|
|
@ -709,13 +709,15 @@ impl RemoteSource for File {
|
|||
impl RemoteSource for Url {
|
||||
fn filename(&self) -> Result<Cow<'_, str>, Error> {
|
||||
// Identify the last segment of the URL as the filename.
|
||||
let filename = self
|
||||
let path_segments = self
|
||||
.path_segments()
|
||||
.and_then(Iterator::last)
|
||||
.ok_or_else(|| Error::UrlFilename(self.clone()))?;
|
||||
.ok_or_else(|| Error::MissingPathSegments(self.clone()))?;
|
||||
|
||||
// This is guaranteed by the contract of `Url::path_segments`.
|
||||
let last = path_segments.last().expect("path segments is non-empty");
|
||||
|
||||
// Decode the filename, which may be percent-encoded.
|
||||
let filename = urlencoding::decode(filename)?;
|
||||
let filename = urlencoding::decode(last)?;
|
||||
|
||||
Ok(filename)
|
||||
}
|
||||
|
|
|
@ -336,7 +336,7 @@ impl<'a> Planner<'a> {
|
|||
// Store the canonicalized path, which also serves to validate that it exists.
|
||||
let path = match url
|
||||
.to_file_path()
|
||||
.map_err(|()| Error::UrlFilename(url.to_url()))?
|
||||
.map_err(|()| Error::MissingFilePath(url.to_url()))?
|
||||
.canonicalize()
|
||||
{
|
||||
Ok(path) => path,
|
||||
|
|
|
@ -1087,15 +1087,14 @@ impl TryFrom<WheelWire> for Wheel {
|
|||
type Error = String;
|
||||
|
||||
fn try_from(wire: WheelWire) -> Result<Wheel, String> {
|
||||
let path_segments = wire
|
||||
.url
|
||||
.path_segments()
|
||||
.ok_or_else(|| format!("could not extract path from URL `{}`", wire.url))?;
|
||||
// This is guaranteed by the contract of Url::path_segments.
|
||||
let last = path_segments.last().expect("path segments is non-empty");
|
||||
let filename = last
|
||||
// Extract the filename segment from the URL.
|
||||
let filename = wire.url.filename().map_err(|err| err.to_string())?;
|
||||
|
||||
// Parse the filename as a wheel filename.
|
||||
let filename = filename
|
||||
.parse::<WheelFilename>()
|
||||
.map_err(|err| format!("failed to parse `{last}` as wheel filename: {err}"))?;
|
||||
.map_err(|err| format!("failed to parse `{filename}` as wheel filename: {err}"))?;
|
||||
|
||||
Ok(Wheel {
|
||||
url: wire.url,
|
||||
hash: wire.hash,
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue