diff --git a/Cargo.lock b/Cargo.lock index ec53801afb98..445cd11aacd4 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -26,18 +26,6 @@ dependencies = [ "const-random", ] -[[package]] -name = "ahash" -version = "0.8.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "77c3a9648d43b9cd48db467b3f87fdd6e146bcc88ab0180006cef2179fe11d01" -dependencies = [ - "cfg-if 1.0.0", - "once_cell", - "version_check", - "zerocopy", -] - [[package]] name = "aho-corasick" version = "1.1.2" @@ -62,12 +50,6 @@ dependencies = [ "alloc-no-stdlib", ] -[[package]] -name = "allocator-api2" -version = "0.2.16" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0942ffc6dcaadf03badf6e6a2d0228460359d5e34b57ccdc720b7382dfbd5ec5" - [[package]] name = "android-tzdata" version = "0.1.1" @@ -480,16 +462,6 @@ dependencies = [ "windows-targets 0.48.5", ] -[[package]] -name = "chumsky" -version = "0.9.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8eebd66744a15ded14960ab4ccdbfb51ad3b81f51f3f04a80adac98c985396c9" -dependencies = [ - "hashbrown 0.14.3", - "stacker", -] - [[package]] name = "ciborium" version = "0.2.1" @@ -738,7 +710,7 @@ version = "3.11.10" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0f260e2fc850179ef410018660006951c1b55b79e8087e87111a2c388994b9b5" dependencies = [ - "ahash 0.3.8", + "ahash", "cfg-if 0.1.10", "num_cpus", ] @@ -1223,10 +1195,6 @@ name = "hashbrown" version = "0.14.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "290f1a1d9242c78d09ce40a5e87e7554ee637af1351968159f4952f028f75604" -dependencies = [ - "ahash 0.8.7", - "allocator-api2", -] [[package]] name = "heck" @@ -2252,15 +2220,6 @@ dependencies = [ "unicode-ident", ] -[[package]] -name = "psm" -version = "0.1.21" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5787f7cda34e3033a72192c018bc5883100330f362ef279a8cbccfce8bb4e874" -dependencies = [ - "cc", -] - [[package]] name = "pubgrub" version = "0.2.1" @@ -2822,7 +2781,6 @@ dependencies = [ "pep508_rs", "puffin-normalize", "regex", - "rfc2047-decoder", "serde", "serde_json", "tempfile", @@ -3119,20 +3077,6 @@ dependencies = [ "rand", ] -[[package]] -name = "rfc2047-decoder" -version = "1.0.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9e372613f15fc5171f9052b0c1fbafca5b1e5b0ba86aa13c9c39fd91ca1f7955" -dependencies = [ - "base64 0.21.7", - "charset", - "chumsky", - "memchr", - "quoted_printable", - "thiserror", -] - [[package]] name = "ring" version = "0.17.7" @@ -3418,19 +3362,6 @@ version = "0.9.8" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6980e8d7511241f8acf4aebddbb1ff938df5eebe98691418c4468d0b72a96a67" -[[package]] -name = "stacker" -version = "0.1.15" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c886bd4480155fd3ef527d45e9ac8dd7118a898a46530b7b94c3e21866259fce" -dependencies = [ - "cc", - "cfg-if 1.0.0", - "libc", - "psm", - "winapi", -] - [[package]] name = "strsim" version = "0.10.0" @@ -4486,26 +4417,6 @@ dependencies = [ "linked-hash-map", ] -[[package]] -name = "zerocopy" -version = "0.7.32" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "74d4d3961e53fa4c9a25a8637fc2bfaf2595b3d3ae34875568a5cf64787716be" -dependencies = [ - "zerocopy-derive", -] - -[[package]] -name = "zerocopy-derive" -version = "0.7.32" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9ce1b18ccd8e73a9321186f97e46f9f04b778851177567b1975109d26a08d2a6" -dependencies = [ - "proc-macro2", - "quote", - "syn 2.0.48", -] - [[package]] name = "zip" version = "0.6.6" diff --git a/Cargo.toml b/Cargo.toml index 96a2f7982fa0..a92251e56976 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -67,7 +67,6 @@ regex = { version = "1.10.2" } reqwest = { version = "0.11.23", default-features = false, features = ["json", "gzip", "brotli", "stream", "rustls-tls"] } reqwest-middleware = { version = "0.2.4" } reqwest-retry = { version = "0.3.0" } -rfc2047-decoder = { version = "1.0.2" } rmp-serde = { version = "1.1.2" } rustc-hash = { version = "1.1.0" } seahash = { version = "4.1.0" } diff --git a/crates/pypi-types/Cargo.toml b/crates/pypi-types/Cargo.toml index c998935b4d0f..dce1bde26575 100644 --- a/crates/pypi-types/Cargo.toml +++ b/crates/pypi-types/Cargo.toml @@ -21,7 +21,6 @@ chrono = { workspace = true, features = ["serde"] } mailparse = { workspace = true } once_cell = { workspace = true } regex = { workspace = true } -rfc2047-decoder = { workspace = true } serde = { workspace = true } thiserror = { workspace = true } tracing = { workspace = true } diff --git a/crates/pypi-types/src/metadata.rs b/crates/pypi-types/src/metadata.rs index 775deaa90b64..c57b18335088 100644 --- a/crates/pypi-types/src/metadata.rs +++ b/crates/pypi-types/src/metadata.rs @@ -75,24 +75,16 @@ pub enum Error { impl Metadata21 { /// Parse distribution metadata from metadata bytes pub fn parse(content: &[u8]) -> Result { - // HACK: trick mailparse to parse as UTF-8 instead of ASCII - let mut mail = b"Content-Type: text/plain; charset=utf-8\n".to_vec(); - mail.extend_from_slice(content); - - let msg = mailparse::parse_mail(&mail)?; + let msg = mailparse::parse_mail(&content)?; let headers = msg.get_headers(); let get_first_value = |name| { headers.get_first_header(name).and_then(|header| { - match rfc2047_decoder::decode(header.get_value_raw()) { - Ok(value) => { - if value == "UNKNOWN" { - None - } else { - Some(value) - } - } - Err(_) => None, + let value = header.get_value(); + if value == "UNKNOWN" { + None + } else { + Some(value) } }) }; @@ -141,3 +133,45 @@ impl Metadata21 { }) } } + +impl FromStr for Metadata21 { + type Err = Error; + fn from_str(s: &str) -> Result { + Metadata21::parse(s.as_bytes()) + } +} + +#[cfg(test)] +mod tests { + use std::str::FromStr; + + use pep440_rs::Version; + use puffin_normalize::PackageName; + + use crate::Error; + + use super::Metadata21; + + #[test] + fn test_parse_from_str() { + let s = "Metadata-Version: 1.0"; + let meta: Result = s.parse(); + assert!(matches!(meta, Err(Error::FieldNotFound("Name")))); + + let s = "Metadata-Version: 1.0\nName: asdf"; + let meta = Metadata21::parse(s.as_bytes()); + assert!(matches!(meta, Err(Error::FieldNotFound("Version")))); + + let s = "Metadata-Version: 1.0\nName: asdf\nVersion: 1.0"; + let meta = Metadata21::parse(s.as_bytes()).unwrap(); + assert_eq!(meta.metadata_version, "1.0"); + assert_eq!(meta.name, PackageName::from_str("asdf").unwrap()); + assert_eq!(meta.version, Version::new([1, 0])); + + let s = "Metadata-Version: 1.0\nName: asdf\nVersion: 1.0\nAuthor: 中文\n\n一个 Python 包"; + let meta = Metadata21::parse(s.as_bytes()).unwrap(); + assert_eq!(meta.metadata_version, "2.0"); + assert_eq!(meta.name, PackageName::from_str("asdf").unwrap()); + assert_eq!(meta.version, Version::new([1, 0])); + } +} diff --git a/requirements.in b/requirements.in new file mode 100644 index 000000000000..7e66a17d49cb --- /dev/null +++ b/requirements.in @@ -0,0 +1 @@ +black