From 4143ac0194ec1af0c8fed7aa6eae375137892d4b Mon Sep 17 00:00:00 2001 From: FabianLars Date: Fri, 11 Jul 2025 23:19:24 +0200 Subject: [PATCH] partially revert feature flags. code cleanup & fixes --- Cargo.lock | 38 ++++++++++++++--- plugins/websocket/Cargo.toml | 6 +-- plugins/websocket/src/lib.rs | 82 +++++++++++++++--------------------- 3 files changed, 67 insertions(+), 59 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 09bce844..9d136107 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -3797,6 +3797,19 @@ dependencies = [ "zeroize", ] +[[package]] +name = "rustls-native-certs" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fcaf18a4f2be7326cd874a5fa579fae794320a0f388d365dca7e480e55f83f8a" +dependencies = [ + "openssl-probe", + "rustls-pemfile", + "rustls-pki-types", + "schannel", + "security-framework", +] + [[package]] name = "rustls-pemfile" version = "2.1.2" @@ -4367,7 +4380,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "936cac0ab331b14cb3921c62156d913e4c15b74fb6ec0f3146bd4ef6e4fb3c12" dependencies = [ "atoi", - "base64 0.22.0", + "base64 0.22.1", "bitflags 2.4.1", "byteorder", "bytes", @@ -4410,7 +4423,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9734dbce698c67ecf67c442f768a5e90a49b2a4d61a9f1d59f73874bd4cf0710" dependencies = [ "atoi", - "base64 0.22.0", + "base64 0.22.1", "bitflags 2.4.1", "byteorder", "crc", @@ -5297,6 +5310,17 @@ dependencies = [ "tokio", ] +[[package]] +name = "tokio-rustls" +version = "0.26.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0c7bc40d0e5a97695bb96e27995cd3a08538541b0a846f65bba7a359f36700d4" +dependencies = [ + "rustls", + "rustls-pki-types", + "tokio", +] + [[package]] name = "tokio-stream" version = "0.1.14" @@ -5316,10 +5340,13 @@ checksum = "489a59b6730eda1b0171fcfda8b121f4bee2b35cba8645ca35c5f7ba3eb736c1" dependencies = [ "futures-util", "log", - "native-tls", + "rustls", + "rustls-native-certs", + "rustls-pki-types", "tokio", - "tokio-native-tls", + "tokio-rustls", "tungstenite", + "webpki-roots", ] [[package]] @@ -5486,8 +5513,9 @@ dependencies = [ "http 1.0.0", "httparse", "log", - "native-tls", "rand 0.9.1", + "rustls", + "rustls-pki-types", "sha1", "thiserror 2.0.9", "utf-8", diff --git a/plugins/websocket/Cargo.toml b/plugins/websocket/Cargo.toml index e16e1c43..7fa8c9ff 100644 --- a/plugins/websocket/Cargo.toml +++ b/plugins/websocket/Cargo.toml @@ -19,14 +19,10 @@ http = "1" rand = "0.8" futures-util = "0.3" tokio = { version = "1", features = ["net", "sync"] } -tokio-tungstenite = "0.27" +tokio-tungstenite = { version = "0.27", features = ["rustls-tls-webpki-roots"] } hyper = { version = "1", features = ["client"] } hyper-util = { version = "0.1", features = ["tokio", "http1"] } base64 = "0.22" [features] -default = ["rustls-tls"] -native-tls = ["tokio-tungstenite/native-tls"] -native-tls-vendored = ["native-tls", "tokio-tungstenite/native-tls-vendored"] -rustls-tls = ["tokio-tungstenite/rustls-tls-webpki-roots"] rustls-tls-native-roots = ["tokio-tungstenite/rustls-tls-native-roots"] \ No newline at end of file diff --git a/plugins/websocket/src/lib.rs b/plugins/websocket/src/lib.rs index 120b1b4b..edbc953d 100644 --- a/plugins/websocket/src/lib.rs +++ b/plugins/websocket/src/lib.rs @@ -14,7 +14,7 @@ use tauri::{ }; use tokio::{net::TcpStream, sync::Mutex}; use tokio_tungstenite::{ - client_async_tls_with_config, connect_async_with_config, + client_async_tls_with_config, connect_async_tls_with_config, tungstenite::{ client::IntoClientRequest, error::UrlError, @@ -26,6 +26,7 @@ use tokio_tungstenite::{ use std::collections::HashMap; use std::str::FromStr; +use std::sync::Mutex as StdMutex; type Id = u32; type WebSocket = WebSocketStream>; @@ -44,13 +45,15 @@ enum Error { #[error(transparent)] InvalidHeaderName(#[from] tokio_tungstenite::tungstenite::http::header::InvalidHeaderName), #[error(transparent)] - ProxyConnectionError(#[from] hyper::Error), + ProxyConnection(#[from] hyper::Error), #[error("proxy returned status code: {0}")] - ProxyStatusError(u16), + ProxyStatus(u16), #[error(transparent)] - ProxyIoError(std::io::Error), + ProxyIo(#[from] std::io::Error), #[error(transparent)] - ProxyHttpError(http::Error), + ProxyHttp(#[from] http::Error), + #[error(transparent)] + ProxyJoinHandle(#[from] tokio::task::JoinError), } impl Serialize for Error { @@ -65,8 +68,8 @@ impl Serialize for Error { #[derive(Default)] struct ConnectionManager(Mutex>); -struct TlsConnector(Mutex>); -struct ProxyConfigurationInternal(Mutex>); +struct TlsConnector(StdMutex>); +struct ProxyConfigurationInternal(StdMutex>); #[derive(Clone)] pub struct ProxyAuth { @@ -178,31 +181,20 @@ async fn connect( } } - #[cfg(any(feature = "rustls-tls", feature = "native-tls"))] - let tls_connector = match window.try_state::() { - Some(tls_connector) => tls_connector.0.lock().await.clone(), - None => None, - }; - #[cfg(not(any(feature = "rustls-tls", feature = "native-tls")))] - let tls_connector = None; + let tls_connector = window + .try_state::() + .and_then(|c| c.0.lock().unwrap().clone()); - let proxy_config = match window.try_state::() { - Some(proxy_config) => proxy_config.0.lock().await.clone(), - None => None, - }; + let proxy_config = window + .try_state::() + .and_then(|c| c.0.lock().unwrap().clone()); let ws_stream = if let Some(proxy_config) = proxy_config { connect_using_proxy(request, config, proxy_config, tls_connector).await? } else { - #[cfg(any(feature = "rustls-tls", feature = "native-tls"))] - let (ws_stream, _) = - connect_async_tls_with_config(request, config.map(Into::into), false, tls_connector) - .await?; - #[cfg(not(any(feature = "rustls-tls", feature = "native-tls")))] - let (ws_stream, _) = - connect_async_with_config(request, config.map(Into::into), false).await?; - - ws_stream + connect_async_tls_with_config(request, config.map(Into::into), false, tls_connector) + .await? + .0 }; tauri::async_runtime::spawn(async move { @@ -237,7 +229,7 @@ async fn connect( }))) .unwrap() } - Ok(Message::Frame(_)) => serde_json::Value::Null, // This value can't be recieved. + Ok(Message::Frame(_)) => serde_json::Value::Null, // This value can't be received. Err(e) => serde_json::to_value(Error::from(e)).unwrap(), }; let js = format_callback(callback_function, &response) @@ -274,8 +266,7 @@ async fn connect_using_proxy( "{}:{}", proxy_config.proxy_url, proxy_config.proxy_port )) - .await - .map_err(|original| Error::ProxyIoError(original))?; + .await?; let io = TokioIo::new(tcp); let (mut request_sender, proxy_connection) = @@ -289,21 +280,14 @@ async fn connect_using_proxy( req_builder = req_builder.header("Proxy-Authorization", format!("Basic {}", auth.encode())); } - let req = req_builder - .body("".to_string()) - .map_err(|orig| Error::ProxyHttpError(orig))?; + // TODO: This looks super fishy + let req = req_builder.body("".to_string())?; let res = request_sender.send_request(req).await?; - if res.status().as_u16() < 200 || res.status().as_u16() >= 300 { - return Err(Error::ProxyStatusError(res.status().as_u16())); + if !res.status().is_success() { + return Err(Error::ProxyStatus(res.status().as_u16())); } - // expect is fine since it would only rely panics from within the tokio task (or a cancellation which does not happen) - let proxy_connection = proxy_connection_task - .await - .expect("Panic in tokio task during websocket proxy initialization")?; - - let proxy_tcp_wrapper = proxy_connection.io; - let proxied_tcp_socket = proxy_tcp_wrapper.into_inner(); + let proxied_tcp_socket = proxy_connection_task.await??.io.into_inner(); let (ws_stream, _) = client_async_tls_with_config( request, proxied_tcp_socket, @@ -373,8 +357,8 @@ impl Builder { .invoke_handler(tauri::generate_handler![connect, send]) .setup(|app| { app.manage(ConnectionManager::default()); - app.manage(TlsConnector(Mutex::new(self.tls_connector))); - app.manage(ProxyConfigurationInternal(Mutex::new( + app.manage(TlsConnector(StdMutex::new(self.tls_connector))); + app.manage(ProxyConfigurationInternal(StdMutex::new( self.proxy_configuration, ))); @@ -387,9 +371,9 @@ impl Builder { pub async fn reconfigure_proxy(app: &AppHandle, proxy_config: Option) { if let Some(state) = app.try_state::() { if let Some(proxy_config) = proxy_config { - state.0.lock().await.replace(proxy_config); + state.0.lock().unwrap().replace(proxy_config); } else { - state.0.lock().await.take(); + state.0.lock().unwrap().take(); } } } @@ -397,22 +381,22 @@ pub async fn reconfigure_proxy(app: &AppHandle, proxy_config: Option) { if let Some(state) = app.try_state::() { if let Some(tls_connector) = tls_connector { - state.0.lock().await.replace(tls_connector); + state.0.lock().unwrap().replace(tls_connector); } else { - state.0.lock().await.take(); + state.0.lock().unwrap().take(); } } } // Copied from tokio-tungstenite internal function (tokio-tungstenite/src/lib.rs) with the same name // Get a domain from an URL. +#[allow(clippy::result_large_err)] #[inline] fn domain( request: &tokio_tungstenite::tungstenite::handshake::client::Request, ) -> tokio_tungstenite::tungstenite::Result { match request.uri().host() { // rustls expects IPv6 addresses without the surrounding [] brackets - #[cfg(feature = "__rustls-tls")] Some(d) if d.starts_with('[') && d.ends_with(']') => Ok(d[1..d.len() - 1].to_string()), Some(d) => Ok(d.to_string()), None => Err(tokio_tungstenite::tungstenite::Error::Url(