diff --git a/Cargo.lock b/Cargo.lock index 6f54bb938..17c27c18a 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1043,35 +1043,6 @@ version = "0.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8d7439c3735f405729d52c3fbbe4de140eaf938a1fe47d227c27f8254d4302a5" -[[package]] -name = "dbus" -version = "0.9.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1bb21987b9fb1613058ba3843121dd18b163b254d8a6e797e144cbac14d96d1b" -dependencies = [ - "libc", - "libdbus-sys", - "winapi", -] - -[[package]] -name = "dbus-secret-service" -version = "4.0.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b42a16374481d92aed73ae45b1f120207d8e71d24fb89f357fadbd8f946fd84b" -dependencies = [ - "aes", - "block-padding", - "cbc", - "dbus", - "futures-util", - "hkdf", - "num", - "once_cell", - "rand", - "sha2", -] - [[package]] name = "deadpool" version = "0.10.0" @@ -2235,19 +2206,6 @@ dependencies = [ "windows-sys 0.52.0", ] -[[package]] -name = "keyring" -version = "4.0.0-rc.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bb06f73ca0ea1cbd3858e54404585e33dccb860cb4fc8a66ad5e75a5736f3f19" -dependencies = [ - "byteorder", - "dbus-secret-service", - "log", - "security-framework", - "windows-sys 0.59.0", -] - [[package]] name = "kurbo" version = "0.8.3" @@ -2278,15 +2236,6 @@ version = "0.2.174" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1171693293099992e19cddea4e8b849964e9846f4acee11b3948bcc337be8776" -[[package]] -name = "libdbus-sys" -version = "0.2.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "06085512b750d640299b79be4bad3d2fa90a9c00b1fd9e1b46364f66f0485c72" -dependencies = [ - "pkg-config", -] - [[package]] name = "libmimalloc-sys" version = "0.1.43" @@ -5123,7 +5072,6 @@ dependencies = [ "futures", "http", "insta", - "keyring", "percent-encoding", "reqwest", "reqwest-middleware", @@ -5136,6 +5084,7 @@ dependencies = [ "tokio", "tracing", "url", + "uv-keyring", "uv-once-map", "uv-redacted", "uv-small-str", diff --git a/Cargo.toml b/Cargo.toml index be72883c3..348400e4a 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -42,6 +42,7 @@ uv-git-types = { path = "crates/uv-git-types" } uv-globfilter = { path = "crates/uv-globfilter" } uv-install-wheel = { path = "crates/uv-install-wheel", default-features = false } uv-installer = { path = "crates/uv-installer" } +uv-keyring = { path = "crates/uv-keyring" } uv-macros = { path = "crates/uv-macros" } uv-metadata = { path = "crates/uv-metadata" } uv-normalize = { path = "crates/uv-normalize" } @@ -124,7 +125,6 @@ indoc = { version = "2.0.5" } itertools = { version = "0.14.0" } jiff = { version = "0.2.0", features = ["serde"] } junction = { version = "1.2.0" } -keyring = { version = "4.0.0-rc.1", features = ["encrypted"] } mailparse = { version = "0.16.0" } md-5 = { version = "0.10.6" } memchr = { version = "2.7.4" } diff --git a/crates/uv-auth/Cargo.toml b/crates/uv-auth/Cargo.toml index 1e93a4aec..e9402a06b 100644 --- a/crates/uv-auth/Cargo.toml +++ b/crates/uv-auth/Cargo.toml @@ -10,6 +10,7 @@ doctest = false workspace = true [dependencies] +uv-keyring = { workspace = true } uv-once-map = { workspace = true } uv-redacted = { workspace = true } uv-small-str = { workspace = true } @@ -21,7 +22,6 @@ async-trait = { workspace = true } base64 = { workspace = true } futures = { workspace = true } http = { workspace = true } -keyring = { workspace = true } percent-encoding = { workspace = true } reqwest = { workspace = true } reqwest-middleware = { workspace = true } diff --git a/crates/uv-auth/src/keyring.rs b/crates/uv-auth/src/keyring.rs index 779ab2823..d3b76f277 100644 --- a/crates/uv-auth/src/keyring.rs +++ b/crates/uv-auth/src/keyring.rs @@ -53,7 +53,7 @@ impl KeyringProvider { /// Store credentials for the given [`Url`] to the keyring if the /// keyring provider backend is `Native`. #[instrument(skip_all, fields(url = % url.to_string(), username))] - pub fn store_if_native(&self, url: &DisplaySafeUrl, credentials: &Credentials) { + pub async fn store_if_native(&self, url: &DisplaySafeUrl, credentials: &Credentials) { let Some(username) = credentials.username() else { trace!("Unable to store credentials in keyring for {url} due to missing username"); return; @@ -67,7 +67,7 @@ impl KeyringProvider { KeyringProviderBackend::Native => { // Only store credentials if not already stored during this uv invocation. if !STORED_KEYRING_URLS.contains(url) { - self.store_native(url.as_str(), username, password); + self.store_native(url.as_str(), username, password).await; STORED_KEYRING_URLS.insert(url.clone()); } } @@ -82,9 +82,9 @@ impl KeyringProvider { /// Store credentials to the system keyring for the given `service_name`/`username` /// pair. #[instrument(skip(self))] - fn store_native(&self, service: &str, username: &str, password: &str) { + async fn store_native(&self, service: &str, username: &str, password: &str) { let prefixed_service = format!("{UV_SERVICE_PREFIX}{service}"); - let entry = match keyring::Entry::new(&prefixed_service, username) { + let entry = match uv_keyring::Entry::new(&prefixed_service, username) { Ok(entry) => entry, Err(err) => { warn_user_once!( @@ -93,7 +93,7 @@ impl KeyringProvider { return; } }; - match entry.set_password(password) { + match entry.set_password(password).await { Ok(()) => { debug!("Storing credentials for {service} in system keyring"); } @@ -129,7 +129,7 @@ impl KeyringProvider { // trace!("Checking keyring for URL {url}"); let mut credentials = match self.backend { - KeyringProviderBackend::Native => self.fetch_native(url.as_str(), username), + KeyringProviderBackend::Native => self.fetch_native(url.as_str(), username).await, KeyringProviderBackend::Subprocess => { self.fetch_subprocess(url.as_str(), username).await } @@ -147,7 +147,7 @@ impl KeyringProvider { }; trace!("Checking keyring for host {host}"); credentials = match self.backend { - KeyringProviderBackend::Native => self.fetch_native(&host, username), + KeyringProviderBackend::Native => self.fetch_native(&host, username).await, KeyringProviderBackend::Subprocess => self.fetch_subprocess(&host, username).await, #[cfg(test)] KeyringProviderBackend::Dummy(ref store) => { @@ -252,13 +252,17 @@ impl KeyringProvider { } #[instrument(skip(self))] - fn fetch_native(&self, service: &str, username: Option<&str>) -> Option<(String, String)> { + async fn fetch_native( + &self, + service: &str, + username: Option<&str>, + ) -> Option<(String, String)> { let prefixed_service = format!("{UV_SERVICE_PREFIX}{service}"); let username = username?; - if let Ok(entry) = keyring::Entry::new(&prefixed_service, username) { - match entry.get_password() { + if let Ok(entry) = uv_keyring::Entry::new(&prefixed_service, username) { + match entry.get_password().await { Ok(password) => return Some((username.to_string(), password)), - Err(keyring::Error::NoEntry) => { + Err(uv_keyring::Error::NoEntry) => { debug!("No entry found in system keyring for {service}"); } Err(err) => { diff --git a/crates/uv-auth/src/middleware.rs b/crates/uv-auth/src/middleware.rs index 8cb4b7e76..0fd43c122 100644 --- a/crates/uv-auth/src/middleware.rs +++ b/crates/uv-auth/src/middleware.rs @@ -399,7 +399,7 @@ impl AuthMiddleware { .is_ok_and(|response| response.error_for_status_ref().is_ok()) { if let (Some(index_url), Some(keyring)) = (index_url, &self.keyring) { - keyring.store_if_native(index_url, &credentials); + keyring.store_if_native(index_url, &credentials).await; } trace!("Updating cached credentials for {url} to {credentials:?}"); self.cache().insert(&url, credentials);