xbp 10.7.0

XBP is a zero-config build pack that can also interact with proxies, kafka, sockets, synthetic monitors.
Documentation
use colored::Colorize;
use tokio::process::Command;

pub async fn pm2_start_wrapper(args: Vec<String>, debug: bool) -> Result<(), String> {
    if args.is_empty() {
        println!("{}", "Usage: xbp start <command> [pm2-options]".yellow());
        println!();
        println!("{}", "Examples:".bright_blue());
        println!("  xbp start \"npm start\" --name my-app");
        println!("  xbp start \"./binary --port 3050\" --name my-service");
        println!("  xbp start \"cargo run\" --name rust-app --watch");
        println!();
        println!("{}", "Common PM2 options:".bright_blue());
        println!("  {} - Process name", "--name".cyan());
        println!("  {} - Watch for file changes", "--watch".cyan());
        println!(
            "  {} - Max memory before restart",
            "--max-memory-restart".cyan()
        );
        println!("  {} - Number of instances", "--instances".cyan());
        println!("  {} - Cron pattern for restart", "--cron-restart".cyan());
        return Ok(());
    }

    let mut cmd = Command::new("pm2");
    cmd.arg("start");

    for arg in args {
        cmd.arg(arg);
    }

    if debug {
        tracing::debug!("Executing: pm2 start {:?}", cmd);
    }

    let output = cmd
        .output()
        .await
        .map_err(|e| format!("Failed to execute pm2 start: {}", e))?;

    if !output.status.success() {
        let stderr = String::from_utf8_lossy(&output.stderr);
        return Err(format!("PM2 start failed: {}", stderr));
    }

    let stdout = String::from_utf8_lossy(&output.stdout);
    print!("{}", stdout);

    Ok(())
}