secra_plugins 0.1.32

生产级插件系统 - 插件的生命周期
Documentation
//! 插件初始化相关操作

use crate::config::PluginConfig;
use crate::error::{PluginManagerError, PluginManagerResult};
use crate::status::PluginStatus;
use crate::manager::types::{PluginInstance, PluginMap};
use crate::manager::validation::sanitize_plugin_name;
use tokio::time::{timeout, Duration};
use tracing::{debug, error, info, trace, warn};

/// 初始化所有插件
///
/// 批量初始化所有处于 `Loaded` 状态的插件。初始化顺序会优先处理主插件,
/// 然后处理子插件,确保依赖关系的正确初始化。
///
/// # 参数
/// * `plugins` - 插件实例的共享映射表,使用 `Arc<RwLock<>>` 保证线程安全
/// * `timeout_secs` - 每个插件初始化的超时时间(秒)
///
/// # 返回值
/// * `PluginManagerResult<()>` - 成功时返回 `Ok(())`
///
/// # 行为
/// * 只初始化状态为 `Loaded` 的插件
/// * 按照主插件优先、子插件其次的顺序初始化
/// * 如果某个插件初始化失败,会将其状态设置为 `Error`,但继续初始化其他插件
/// * 初始化超时也会将插件状态设置为 `Error`
///
/// # 状态转换
/// * `Loaded` -> `Initialized`: 初始化成功
/// * `Loaded` -> `Error`: 初始化失败或超时
///
/// # 示例
/// ```no_run
/// use std::sync::Arc;
/// use tokio::sync::RwLock;
/// use std::collections::HashMap;
/// 
/// # async fn example() {
/// let plugins = Arc::new(RwLock::new(HashMap::new()));
/// initialize_all_plugins(plugins, 30).await?;
/// # }
/// ```
pub async fn initialize_all_plugins(
    plugins: PluginMap,
    timeout_secs: u64,
) -> PluginManagerResult<()> {
    trace!("开始批量初始化插件,超时时间: {}s", timeout_secs);
    info!("开始初始化插件...");

    let init_order = {
        trace!("获取读锁,查找需要初始化的插件");
        let plugins = plugins.read().await;
        let mut init_order = Vec::new();
        let mut child_order = Vec::new();

        for (id, plugin_instance) in plugins.iter() {
            if plugin_instance.status == PluginStatus::Loaded {
                if plugin_instance.metadata.is_sub_plugin {
                    trace!("发现需要初始化的子插件: {}", id);
                    child_order.push(id.to_string());
                } else {
                    trace!("发现需要初始化的主插件: {}", id);
                    init_order.push(id.to_string());
                }
            }
        }

        let child_count = child_order.len();
        init_order.extend(child_order);
        debug!("需要初始化的插件: {} 个主插件, {} 个子插件", 
               init_order.len() - child_count, child_count);
        init_order
    };

    let mut success_count = 0;
    let mut failure_count = 0;
    
    for plugin_id in init_order {
        trace!("初始化插件: {}", plugin_id);
        let mut plugins = plugins.write().await;

        if let Some(plugin_instance) = plugins.get_mut(&plugin_id) {
            if plugin_instance.status == PluginStatus::Loaded {
                let mut config = PluginConfig::default();
                config.enabled = true;
                debug!("创建默认配置,调用插件 initialize 方法: {}", plugin_id);

                let init_result = timeout(
                    Duration::from_secs(timeout_secs),
                    plugin_instance.plugin.initialize(config)
                ).await;

                match init_result {
                    Ok(Ok(_)) => {
                        if plugin_instance.status.validate_transition(&PluginStatus::Initialized).is_ok() {
                            plugin_instance.status = PluginStatus::Initialized;
                            info!("插件初始化成功: {}", plugin_id);
                            success_count += 1;
                        } else {
                            plugin_instance.status = PluginStatus::Error("状态转换无效".to_string());
                            error!("插件 {} 状态转换无效", plugin_id);
                            failure_count += 1;
                        }
                    }
                    Ok(Err(e)) => {
                        plugin_instance.status = PluginStatus::Error(e.to_string());
                        error!("插件初始化失败 {}: {}", plugin_id, e);
                        failure_count += 1;
                    }
                    Err(_) => {
                        plugin_instance.status = PluginStatus::Error("初始化超时".to_string());
                        error!("插件初始化超时: {} (超时时间: {}s)", plugin_id, timeout_secs);
                        failure_count += 1;
                    }
                }
            } else {
                trace!("插件 {} 状态不是 Loaded,跳过: {:?}", plugin_id, plugin_instance.status);
            }
        }
    }

    info!("插件初始化完成 - 成功: {}, 失败: {}, 总计: {}", 
          success_count, failure_count, success_count + failure_count);
    trace!("批量初始化插件流程完成");
    Ok(())
}

/// 初始化单个插件
///
/// 初始化指定的插件。插件必须处于 `Loaded` 状态才能初始化。
/// 初始化过程会调用插件的 `initialize()` 方法,并设置默认配置。
///
/// # 参数
/// * `plugins` - 插件实例的共享映射表,使用 `Arc<RwLock<>>` 保证线程安全
/// * `plugin_id` - 要初始化的插件ID
/// * `timeout_secs` - 初始化的超时时间(秒)
///
/// # 返回值
/// * `PluginManagerResult<()>` - 成功时返回 `Ok(())`
///
/// # 错误
/// * `PluginManagerError::NotFound` - 如果指定的插件不存在
/// * `PluginManagerError::StateError` - 如果插件状态不正确或状态转换无效
/// * `PluginManagerError::ExecutionError` - 如果初始化失败或超时
///
/// # 状态转换
/// * `Loaded` -> `Initialized`: 初始化成功
/// * `Loaded` -> `Error`: 初始化失败或超时
///
/// # 配置
/// 初始化时会使用默认配置,并设置 `enabled = true`。
///
/// # 示例
/// ```no_run
/// use std::sync::Arc;
/// use tokio::sync::RwLock;
/// use std::collections::HashMap;
/// 
/// # async fn example() {
/// let plugins = Arc::new(RwLock::new(HashMap::new()));
/// initialize_plugin(plugins, "my-plugin", 30).await?;
/// # }
/// ```
pub async fn initialize_plugin(
    plugins: PluginMap,
    plugin_id: &str,
    timeout_secs: u64,
) -> PluginManagerResult<()> {
    trace!("开始初始化单个插件: {} (超时: {}s)", plugin_id, timeout_secs);
    
    let sanitized_plugin_id = sanitize_plugin_name(plugin_id)?;
    debug!("插件ID清理: {} -> {}", plugin_id, sanitized_plugin_id);

    let mut plugins = plugins.write().await;

    if let Some(plugin_instance) = plugins.get_mut(&sanitized_plugin_id) {
        debug!("找到插件实例: {} (状态: {:?})", 
               plugin_instance.metadata.name, plugin_instance.status);
        
        if plugin_instance.status == PluginStatus::Loaded {
            let mut config = PluginConfig::default();
            config.enabled = true;
            trace!("创建默认配置,调用插件 initialize 方法");

            let init_result = timeout(
                Duration::from_secs(timeout_secs),
                plugin_instance.plugin.initialize(config)
            ).await;

            match init_result {
                Ok(Ok(_)) => {
                    if plugin_instance.status.validate_transition(&PluginStatus::Initialized).is_ok() {
                        plugin_instance.status = PluginStatus::Initialized;
                        info!("插件初始化成功: {}", sanitized_plugin_id);
                        trace!("插件状态已更新为 Initialized");
                    } else {
                        plugin_instance.status = PluginStatus::Error("状态转换无效".to_string());
                        error!("插件 {} 状态转换无效", sanitized_plugin_id);
                        return Err(PluginManagerError::StateError("状态转换无效".to_string()));
                    }
                }
                Ok(Err(e)) => {
                    plugin_instance.status = PluginStatus::Error(e.to_string());
                    error!("插件初始化失败 {}: {}", sanitized_plugin_id, e);
                    return Err(PluginManagerError::ExecutionError(
                        format!("插件初始化失败: {}", e)
                    ));
                }
                Err(_) => {
                    plugin_instance.status = PluginStatus::Error("初始化超时".to_string());
                    error!("插件初始化超时: {} (超时时间: {}s)", sanitized_plugin_id, timeout_secs);
                    return Err(PluginManagerError::ExecutionError(
                        format!("插件初始化超时(超时时间: {}秒)", timeout_secs)
                    ));
                }
            }
        } else {
            warn!("插件 {} 状态不正确,无法初始化: {:?}", sanitized_plugin_id, plugin_instance.status);
            return Err(PluginManagerError::StateError(
                format!("插件状态不正确,无法初始化: {:?}", plugin_instance.status)
            ));
        }
    } else {
        error!("插件不存在: {}", plugin_id);
        return Err(PluginManagerError::not_found(plugin_id));
    }

    trace!("插件初始化流程完成");
    Ok(())
}