From ddde547c081741f7d70c66789eeac79f66412d41 Mon Sep 17 00:00:00 2001 From: quexeky Date: Tue, 9 Sep 2025 09:58:59 +1000 Subject: [PATCH] chore: Remove unwraps from fetch_object and server_proto Signed-off-by: quexeky --- src-tauri/src/lib.rs | 9 ++-- src-tauri/src/remote/auth.rs | 10 ++-- src-tauri/src/remote/cache.rs | 2 +- src-tauri/src/remote/commands.rs | 11 ++--- src-tauri/src/remote/fetch_object.rs | 13 +++--- src-tauri/src/remote/server_proto.rs | 69 ++++++++++++++++++++-------- src-tauri/src/remote/utils.rs | 5 +- src-tauri/src/utils/app_emit.rs | 11 +++++ src-tauri/src/utils/mod.rs | 3 +- 9 files changed, 85 insertions(+), 48 deletions(-) create mode 100644 src-tauri/src/utils/app_emit.rs diff --git a/src-tauri/src/lib.rs b/src-tauri/src/lib.rs index a19d5db..dc48735 100644 --- a/src-tauri/src/lib.rs +++ b/src-tauri/src/lib.rs @@ -21,6 +21,7 @@ use crate::process::commands::open_process_logs; use crate::process::process_handlers::UMU_LAUNCHER_EXECUTABLE; use crate::remote::commands::auth_initiate_code; use crate::remote::fetch_object::fetch_object_wrapper; +use crate::remote::server_proto::handle_server_proto_wrapper; use crate::{database::db::DatabaseImpls, games::downloads::commands::resume_download}; use bitcode::{Decode, Encode}; use client::commands::fetch_state; @@ -61,7 +62,7 @@ use remote::commands::{ auth_initiate, fetch_drop_object, gen_drop_url, manual_recieve_handshake, retry_connect, sign_out, use_remote, }; -use remote::server_proto::{handle_server_proto, handle_server_proto_offline}; +use remote::server_proto::handle_server_proto_offline_wrapper; use serde::{Deserialize, Serialize}; use std::fs::File; use std::io::Write; @@ -164,7 +165,7 @@ async fn setup(handle: AppHandle) -> AppState<'static> { log4rs::init_config(config).expect("Failed to initialise log4rs"); let games = HashMap::new(); - let download_manager = Arc::new(DownloadManagerBuilder::build(handle.clone())); + let download_manager = Arc::new(DownloadManagerBuilder::build(handle.clone())); let process_manager = Arc::new(Mutex::new(ProcessManager::new(handle.clone()))); let compat_info = create_new_compat_info(); @@ -473,8 +474,8 @@ pub fn run() { offline!( state, - handle_server_proto, - handle_server_proto_offline, + handle_server_proto_wrapper, + handle_server_proto_offline_wrapper, request, responder ) diff --git a/src-tauri/src/remote/auth.rs b/src-tauri/src/remote/auth.rs index 58c9936..8963029 100644 --- a/src-tauri/src/remote/auth.rs +++ b/src-tauri/src/remote/auth.rs @@ -9,7 +9,7 @@ use tauri::{AppHandle, Emitter, Manager}; use url::Url; use crate::{ - database::{ + app_emit, database::{ db::{borrow_db_checked, borrow_db_mut_checked}, models::data::DatabaseAuth, }, error::{drop_server_error::DropServerError, remote_access_error::RemoteAccessError}, remote::{requests::make_authenticated_get, utils::{DROP_CLIENT_ASYNC, DROP_CLIENT_SYNC}}, AppState, AppStatus, User @@ -83,7 +83,7 @@ pub async fn fetch_user() -> Result { async fn recieve_handshake_logic(app: &AppHandle, path: String) -> Result<(), RemoteAccessError> { let path_chunks: Vec<&str> = path.split('/').collect(); if path_chunks.len() != 3 { - app.emit("auth/failed", ()).unwrap(); + app_emit!(app, "auth/failed", ()); return Err(RemoteAccessError::HandshakeFailed( "failed to parse token".to_string(), )); @@ -141,12 +141,12 @@ async fn recieve_handshake_logic(app: &AppHandle, path: String) -> Result<(), Re pub async fn recieve_handshake(app: AppHandle, path: String) { // Tell the app we're processing - app.emit("auth/processing", ()).unwrap(); + app_emit!(app, "auth/processing", ()); let handshake_result = recieve_handshake_logic(&app, path).await; if let Err(e) = handshake_result { warn!("error with authentication: {e}"); - app.emit("auth/failed", e.to_string()).unwrap(); + app_emit!(app, "auth/failed", e.to_string()); return; } @@ -161,7 +161,7 @@ pub async fn recieve_handshake(app: AppHandle, path: String) { drop(state_lock); - app.emit("auth/finished", ()).unwrap(); + app_emit!(app, "auth/finished", ()); } pub fn auth_initiate_logic(mode: String) -> Result { diff --git a/src-tauri/src/remote/cache.rs b/src-tauri/src/remote/cache.rs index 2bd0115..cb648c3 100644 --- a/src-tauri/src/remote/cache.rs +++ b/src-tauri/src/remote/cache.rs @@ -10,7 +10,7 @@ use crate::{ error::{cache_error::CacheError, remote_access_error::RemoteAccessError}, }; use bitcode::{Decode, DecodeOwned, Encode}; -use http::{header::{ToStrError, CONTENT_TYPE}, response::Builder as ResponseBuilder, Response}; +use http::{header::{CONTENT_TYPE}, response::Builder as ResponseBuilder, Response}; #[macro_export] macro_rules! offline { diff --git a/src-tauri/src/remote/commands.rs b/src-tauri/src/remote/commands.rs index 3f20493..4346aca 100644 --- a/src-tauri/src/remote/commands.rs +++ b/src-tauri/src/remote/commands.rs @@ -8,14 +8,11 @@ use tauri::{AppHandle, Emitter, Manager}; use url::Url; use crate::{ - AppState, AppStatus, - database::db::{borrow_db_checked, borrow_db_mut_checked}, - error::remote_access_error::RemoteAccessError, - remote::{ + app_emit, database::db::{borrow_db_checked, borrow_db_mut_checked}, error::remote_access_error::RemoteAccessError, remote::{ auth::generate_authorization_header, requests::generate_url, utils::{DROP_CLIENT_SYNC, DROP_CLIENT_WS_CLIENT}, - }, + }, AppState, AppStatus }; use super::{ @@ -83,7 +80,7 @@ pub fn sign_out(app: AppHandle) { } // Emit event for frontend - app.emit("auth/signedout", ()).unwrap(); + app_emit!(app, "auth/signedout", ()); } #[tauri::command] @@ -167,7 +164,7 @@ pub fn auth_initiate_code(app: AppHandle) -> Result { let result = load().await; if let Err(err) = result { warn!("{err}"); - app.emit("auth/failed", err.to_string()).unwrap(); + app_emit!(app, "auth/failed", err.to_string()); } }); diff --git a/src-tauri/src/remote/fetch_object.rs b/src-tauri/src/remote/fetch_object.rs index 4aa47cf..e3eaa3f 100644 --- a/src-tauri/src/remote/fetch_object.rs +++ b/src-tauri/src/remote/fetch_object.rs @@ -13,8 +13,8 @@ pub async fn fetch_object_wrapper(request: http::Request>, responder: Ur match fetch_object(request).await { Ok(r) => responder.respond(r), Err(e) => { - warn!("Cache error: {}", e); - responder.respond(Response::new(Vec::new())); + warn!("Cache error: {e}"); + responder.respond(Response::builder().status(500).body(Vec::new()).expect("Failed to build error response")); } }; } @@ -36,7 +36,7 @@ pub async fn fetch_object(request: http::Request>) -> Result { let resp_builder = ResponseBuilder::new().header( CONTENT_TYPE, @@ -48,8 +48,7 @@ pub async fn fetch_object(request: http::Request>) -> Result Vec::from(data), Err(e) => { warn!( - "Could not get data from cache object {} with error {}", - object_id, e + "Could not get data from cache object {object_id} with error {e}", ); Vec::new() } @@ -60,11 +59,11 @@ pub async fn fetch_object(request: http::Request>) -> Result { debug!("Object fetch failed with error {}. Attempting to download from cache", e); - return match cache_result { + match cache_result { Ok(cache_result) => Ok(cache_result.into()), Err(e) => { warn!("{e}"); diff --git a/src-tauri/src/remote/server_proto.rs b/src-tauri/src/remote/server_proto.rs index ed07c9b..c9c65e4 100644 --- a/src-tauri/src/remote/server_proto.rs +++ b/src-tauri/src/remote/server_proto.rs @@ -1,57 +1,88 @@ use std::str::FromStr; use http::{uri::PathAndQuery, Request, Response, StatusCode, Uri}; +use log::warn; use tauri::UriSchemeResponder; use crate::{database::db::borrow_db_checked, remote::utils::DROP_CLIENT_SYNC}; -pub async fn handle_server_proto_offline(_request: Request>, responder: UriSchemeResponder) { - let four_oh_four = Response::builder() - .status(StatusCode::NOT_FOUND) - .body(Vec::new()) - .unwrap(); - responder.respond(four_oh_four); +pub async fn handle_server_proto_offline_wrapper(request: Request>, responder: UriSchemeResponder) { + responder.respond(match handle_server_proto_offline(request).await { + Ok(res) => res, + Err(e) => unreachable!() + }); } -pub async fn handle_server_proto(request: Request>, responder: UriSchemeResponder) { +pub async fn handle_server_proto_offline(_request: Request>) -> Result>, StatusCode>{ + Ok(Response::builder() + .status(StatusCode::NOT_FOUND) + .body(Vec::new()) + .expect("Failed to build error response for proto offline")) + +} + +pub async fn handle_server_proto_wrapper(request: Request>, responder: UriSchemeResponder) { + match handle_server_proto(request).await { + Ok(r) => responder.respond(r), + Err(e) => { + warn!("Cache error: {e}"); + responder.respond(Response::builder().status(e).body(Vec::new()).expect("Failed to build error response")); + } + } +} + +async fn handle_server_proto(request: Request>) -> Result>, StatusCode> { let db_handle = borrow_db_checked(); let web_token = match &db_handle.auth.as_ref().unwrap().web_token { Some(e) => e, - None => return, + None => return Err(StatusCode::BAD_REQUEST), }; - let remote_uri = db_handle.base_url.parse::().unwrap(); + let remote_uri = db_handle.base_url.parse::().expect("Failed to parse base url"); let path = request.uri().path(); let mut new_uri = request.uri().clone().into_parts(); new_uri.path_and_query = - Some(PathAndQuery::from_str(&format!("{path}?noWrapper=true")).unwrap()); + Some(PathAndQuery::from_str(&format!("{path}?noWrapper=true")).expect("Failed to parse request path in proto")); new_uri.authority = remote_uri.authority().cloned(); new_uri.scheme = remote_uri.scheme().cloned(); - let new_uri = Uri::from_parts(new_uri).unwrap(); + let new_uri = Uri::from_parts(new_uri).expect(&format!("Failed to build new uri from parts")); let whitelist_prefix = ["/store", "/api", "/_", "/fonts"]; if whitelist_prefix.iter().all(|f| !path.starts_with(f)) { - webbrowser::open(&new_uri.to_string()).unwrap(); - return; + return match webbrowser::open(&new_uri.to_string()) { + Ok(_) => Ok(Response::new(Vec::new())), + Err(e) => { + warn!("Could not open web browser to link {new_uri} with error {e}"); + Ok(Response::new(Vec::new())) + } + } } let client = DROP_CLIENT_SYNC.clone(); - let response = client + let response = match client .request(request.method().clone(), new_uri.to_string()) .header("Authorization", format!("Bearer {web_token}")) .headers(request.headers().clone()) - .send() - .unwrap(); + .send() { + Ok(response) => response, + Err(e) => { + warn!("Could not send response. Got {e} when sending"); + return Err(e.status().unwrap_or(StatusCode::BAD_REQUEST)) + }, + }; let response_status = response.status(); - let response_body = response.bytes().unwrap(); + let response_body = match response.bytes() { + Ok(bytes) => bytes, + Err(e) => return Err(e.status().unwrap_or(StatusCode::INTERNAL_SERVER_ERROR)), + }; let http_response = Response::builder() .status(response_status) .body(response_body.to_vec()) - .unwrap(); + .expect("Failed to build server proto response"); - responder.respond(http_response); + Ok(http_response) } diff --git a/src-tauri/src/remote/utils.rs b/src-tauri/src/remote/utils.rs index 7ecac5e..4ea8814 100644 --- a/src-tauri/src/remote/utils.rs +++ b/src-tauri/src/remote/utils.rs @@ -11,10 +11,7 @@ use serde::Deserialize; use url::Url; use crate::{ - AppState, AppStatus, - database::db::{DATA_ROOT_DIR, borrow_db_mut_checked}, - error::remote_access_error::RemoteAccessError, - state_lock, + database::db::{borrow_db_mut_checked, DATA_ROOT_DIR}, error::remote_access_error::RemoteAccessError, state_lock, AppState, AppStatus }; #[derive(Deserialize)] diff --git a/src-tauri/src/utils/app_emit.rs b/src-tauri/src/utils/app_emit.rs new file mode 100644 index 0000000..c7e4161 --- /dev/null +++ b/src-tauri/src/utils/app_emit.rs @@ -0,0 +1,11 @@ +#[macro_export] +macro_rules! app_emit { + ($app:expr, $event:expr, $p:expr) => { + match $app.emit($event, $p) { + Ok(_) => (), + Err(e) => { + log::error!("Failed to emit event {} with error {}", $event, e); + } + }; + }; +} \ No newline at end of file diff --git a/src-tauri/src/utils/mod.rs b/src-tauri/src/utils/mod.rs index c2983d7..80e975b 100644 --- a/src-tauri/src/utils/mod.rs +++ b/src-tauri/src/utils/mod.rs @@ -1 +1,2 @@ -pub mod state_lock; \ No newline at end of file +mod app_emit; +mod state_lock;