From 0d0f0b4978e8598b7f5035334d4e48b78702a5d5 Mon Sep 17 00:00:00 2001 From: Oguz Kocer Date: Mon, 9 Dec 2024 15:09:41 -0500 Subject: [PATCH] Add attempt specific fields to AutoDiscoveryUniffiResult --- wp_api/src/api_error.rs | 4 +- wp_api/src/login/login_client.rs | 2 +- wp_api/src/login/url_discovery.rs | 74 ++++++++++++++----- wp_api/src/parsed_url.rs | 2 +- .../tests/test_login_immut.rs | 16 ++-- 5 files changed, 71 insertions(+), 27 deletions(-) diff --git a/wp_api/src/api_error.rs b/wp_api/src/api_error.rs index 16d552e2..2124ae8b 100644 --- a/wp_api/src/api_error.rs +++ b/wp_api/src/api_error.rs @@ -309,7 +309,7 @@ pub enum WpErrorCode { CustomError(String), } -#[derive(Debug, PartialEq, Eq, thiserror::Error, uniffi::Error)] +#[derive(Debug, Clone, PartialEq, Eq, thiserror::Error, uniffi::Error)] pub enum RequestExecutionError { #[error( "Request execution failed!\nStatus Code: '{:?}'.\nResponse: '{}'", @@ -322,7 +322,7 @@ pub enum RequestExecutionError { }, } -#[derive(Debug, PartialEq, Eq, thiserror::Error, uniffi::Error)] +#[derive(Debug, Clone, PartialEq, Eq, thiserror::Error, uniffi::Error)] pub enum MediaUploadRequestExecutionError { #[error( "Request execution failed!\nStatus Code: '{:?}'.\nResponse: '{}'", diff --git a/wp_api/src/login/login_client.rs b/wp_api/src/login/login_client.rs index 08979836..30049708 100644 --- a/wp_api/src/login/login_client.rs +++ b/wp_api/src/login/login_client.rs @@ -113,7 +113,7 @@ impl WpLoginClient { return Err(AutoDiscoveryAttemptFailure::ParseApiDetails { parsed_site_url, api_root_url, - error, + parsing_error_message: error.to_string(), }) } }; diff --git a/wp_api/src/login/url_discovery.rs b/wp_api/src/login/url_discovery.rs index 77d73253..f0116851 100644 --- a/wp_api/src/login/url_discovery.rs +++ b/wp_api/src/login/url_discovery.rs @@ -21,17 +21,28 @@ impl AutoDiscoveryAttempt { #[derive(Debug, uniffi::Record)] pub struct AutoDiscoveryUniffiResult { - pub attempts: HashMap>, + pub user_input_attempt: Arc, + pub successful_attempt: Option>, + pub auto_https_attempt: Option>, + pub auto_dot_php_extension_for_wp_admin_attempt: Option>, + pub is_successful: bool, } impl From for AutoDiscoveryUniffiResult { fn from(value: AutoDiscoveryResult) -> Self { + let get_attempt_result = |attempt_type| { + value + .get_attempt(&attempt_type) + .map(|a| Arc::new(a.clone())) + }; Self { - attempts: value - .attempts - .into_iter() - .map(|(k, v)| (k, Arc::new(v))) - .collect(), + user_input_attempt: Arc::new(value.user_input_attempt().clone()), + successful_attempt: value.find_successful().map(|a| Arc::new(a.clone())), + auto_https_attempt: get_attempt_result(AutoDiscoveryAttemptType::AutoHttps), + auto_dot_php_extension_for_wp_admin_attempt: get_attempt_result( + AutoDiscoveryAttemptType::AutoDotPhpExtensionForWpAdmin, + ), + is_successful: value.is_successful(), } } } @@ -42,15 +53,41 @@ pub struct AutoDiscoveryResult { } impl AutoDiscoveryResult { - pub fn find_successful(self) -> Option { + pub fn is_successful(&self) -> bool { self.attempts - .into_iter() - .find(|(attempt_type, result)| result.result.is_ok()) - .map(|(attempt_type, result)| result) + .iter() + .any(|(_, result)| result.is_successful()) + } + + pub fn find_successful(&self) -> Option<&AutoDiscoveryAttemptResult> { + // If the user attempt is successful, prefer it over other attempts + let user_input_attempt = self.user_input_attempt(); + if user_input_attempt.is_successful() { + return Some(user_input_attempt); + } + self.attempts.iter().find_map(|(_, result)| { + if result.is_successful() { + Some(result) + } else { + None + } + }) + } + + pub fn user_input_attempt(&self) -> &AutoDiscoveryAttemptResult { + self.get_attempt(&AutoDiscoveryAttemptType::UserInput) + .expect("User input url is always attempted") + } + + pub fn get_attempt( + &self, + attempt_type: &AutoDiscoveryAttemptType, + ) -> Option<&AutoDiscoveryAttemptResult> { + self.attempts.get(attempt_type) } } -#[derive(Debug, uniffi::Object)] +#[derive(Debug, Clone, uniffi::Object)] pub struct AutoDiscoveryAttemptResult { pub attempt_type: AutoDiscoveryAttemptType, pub attempt_site_url: String, @@ -128,14 +165,14 @@ impl AutoDiscoveryAttemptResult { } } -#[derive(Debug)] +#[derive(Debug, Clone)] pub struct AutoDiscoveryAttemptSuccess { pub parsed_site_url: ParsedUrl, pub api_root_url: ParsedUrl, pub api_details: WpApiDetails, } -#[derive(Debug)] +#[derive(Debug, Clone)] pub enum AutoDiscoveryAttemptFailure { ParseSiteUrl { error: ParseUrlError, @@ -156,7 +193,7 @@ pub enum AutoDiscoveryAttemptFailure { ParseApiDetails { parsed_site_url: ParsedUrl, api_root_url: ParsedUrl, - error: serde_json::Error, + parsing_error_message: String, }, } @@ -179,8 +216,11 @@ impl AutoDiscoveryAttemptFailure { AutoDiscoveryAttemptFailure::FetchApiRootUrl { error, .. } => error.to_string(), AutoDiscoveryAttemptFailure::ParseApiRootUrl { error, .. } => error.to_string(), AutoDiscoveryAttemptFailure::FetchApiDetails { error, .. } => error.to_string(), - AutoDiscoveryAttemptFailure::ParseApiDetails { error, .. } => { - format!("Failed to parse api details: {:#?}", error) + AutoDiscoveryAttemptFailure::ParseApiDetails { + parsing_error_message, + .. + } => { + format!("Failed to parse api details: {:#?}", parsing_error_message) } } } @@ -297,7 +337,7 @@ pub(crate) fn construct_attempts(input_site_url: String) -> Vec