From b20b30baadd8137f12085c292838457cab048b9a Mon Sep 17 00:00:00 2001 From: Sline Date: Tue, 7 Oct 2025 07:31:35 +0800 Subject: [PATCH] refactor(config): move verify_config_initialization with backoff retry (#4952) --- src-tauri/src/config/config.rs | 71 ++++++++++++++++++++++++++- src-tauri/src/utils/resolve/mod.rs | 77 +----------------------------- 2 files changed, 71 insertions(+), 77 deletions(-) diff --git a/src-tauri/src/config/config.rs b/src-tauri/src/config/config.rs index 9b065b88..6aaa17d8 100644 --- a/src-tauri/src/config/config.rs +++ b/src-tauri/src/config/config.rs @@ -6,9 +6,11 @@ use crate::{ utils::{dirs, help, logging::Type}, }; use anyhow::{Result, anyhow}; +use backoff::{Error as BackoffError, ExponentialBackoff}; use std::path::PathBuf; +use std::time::Duration; use tokio::sync::OnceCell; -use tokio::time::{Duration, sleep}; +use tokio::time::sleep; pub const RUNTIME_CONFIG: &str = "clash-verge.yaml"; pub const CHECK_CONFIG: &str = "clash-verge-check.yaml"; @@ -163,6 +165,73 @@ impl Config { Ok(()) } + + pub async fn verify_config_initialization() { + logging!( + info, + Type::Setup, + true, + "Verifying config initialization..." + ); + + let backoff_strategy = ExponentialBackoff { + initial_interval: std::time::Duration::from_millis(100), + max_interval: std::time::Duration::from_secs(2), + max_elapsed_time: Some(std::time::Duration::from_secs(10)), + multiplier: 2.0, + ..Default::default() + }; + + let operation = || async { + if Config::runtime().await.latest_ref().config.is_some() { + logging!( + info, + Type::Setup, + true, + "Config initialization verified successfully" + ); + return Ok::<(), BackoffError>(()); + } + + logging!( + warn, + Type::Setup, + true, + "Runtime config not found, attempting to regenerate..." + ); + + match Config::generate().await { + Ok(_) => { + logging!(info, Type::Setup, true, "Config successfully regenerated"); + Ok(()) + } + Err(e) => { + logging!(warn, Type::Setup, true, "Failed to generate config: {}", e); + Err(BackoffError::transient(e)) + } + } + }; + + match backoff::future::retry(backoff_strategy, operation).await { + Ok(_) => { + logging!( + info, + Type::Setup, + true, + "Config initialization verified with backoff retry" + ); + } + Err(e) => { + logging!( + error, + Type::Setup, + true, + "Failed to verify config initialization after retries: {}", + e + ); + } + } + } } #[derive(Debug)] diff --git a/src-tauri/src/utils/resolve/mod.rs b/src-tauri/src/utils/resolve/mod.rs index 60f73cd4..f0fca765 100644 --- a/src-tauri/src/utils/resolve/mod.rs +++ b/src-tauri/src/utils/resolve/mod.rs @@ -66,7 +66,7 @@ pub fn resolve_setup_async() { init_verge_config().await; // 添加配置验证,确保运行时配置已正确生成 - verify_config_initialization().await; + Config::verify_config_initialization().await; init_core_manager().await; @@ -195,81 +195,6 @@ pub(super) async fn init_auto_lightweight_mode() { logging_error!(Type::Setup, true, auto_lightweight_mode_init().await); } -/// 验证配置初始化是否成功 -async fn verify_config_initialization() { - logging!( - info, - Type::Setup, - true, - "Verifying config initialization..." - ); - - // 检查运行时配置是否已正确生成 - if Config::runtime().await.latest_ref().config.is_some() { - logging!( - info, - Type::Setup, - true, - "Config initialization verified successfully" - ); - return; - } - - logging!( - warn, - Type::Setup, - true, - "Runtime config not found, regenerating..." - ); - - // 尝试重新生成配置,最多3次 - for attempt in 1..=3 { - logging!( - info, - Type::Setup, - true, - "Attempt {}/3 to regenerate config...", - attempt - ); - - match Config::generate().await { - Ok(_) => { - logging!( - info, - Type::Setup, - true, - "Config successfully regenerated on attempt {}", - attempt - ); - return; - } - Err(e) => { - logging!( - warn, - Type::Setup, - true, - "Failed to generate config on attempt {}: {}", - attempt, - e - ); - - if attempt == 3 { - logging!( - error, - Type::Setup, - true, - "Failed to generate config after 3 attempts" - ); - return; - } - - // 等待一段时间再重试 - tokio::time::sleep(tokio::time::Duration::from_millis(100 * attempt as u64)).await; - } - } - } -} - pub async fn init_work_config() { logging!( info,