syncable_cli/analyzer/tool_management/installers/
common.rs1use crate::error::Result;
2use log::{debug, info, warn};
3use std::process::Command;
4
5#[derive(Debug, Clone)]
6pub enum InstallationStrategy {
7 PackageManager(String), DirectDownload { url: String, extract_to: String },
9 Script { command: String, args: Vec<String> },
10 Manual { instructions: String },
11}
12
13pub struct InstallationUtils;
15
16impl InstallationUtils {
17 pub fn execute_command(command: &str, args: &[&str]) -> Result<bool> {
19 debug!("Executing command: {} {}", command, args.join(" "));
20
21 let output = Command::new(command).args(args).output()?;
22
23 if output.status.success() {
24 info!(
25 "✅ Command executed successfully: {} {}",
26 command,
27 args.join(" ")
28 );
29 Ok(true)
30 } else {
31 let stderr = String::from_utf8_lossy(&output.stderr);
32 warn!(
33 "❌ Command failed: {} {} - {}",
34 command,
35 args.join(" "),
36 stderr
37 );
38 Ok(false)
39 }
40 }
41
42 pub fn is_command_available(command: &str) -> bool {
44 Command::new(command)
45 .arg("--version")
46 .output()
47 .map(|output| output.status.success())
48 .unwrap_or(false)
49 }
50
51 pub fn get_user_bin_dir() -> std::path::PathBuf {
53 if cfg!(windows) {
54 if let Ok(userprofile) = std::env::var("USERPROFILE") {
55 std::path::PathBuf::from(userprofile)
56 .join(".local")
57 .join("bin")
58 } else {
59 std::path::PathBuf::from(".").join("bin")
60 }
61 } else if let Ok(home) = std::env::var("HOME") {
62 std::path::PathBuf::from(home).join(".local").join("bin")
63 } else {
64 std::path::PathBuf::from(".").join("bin")
65 }
66 }
67
68 pub fn ensure_dir_exists(path: &std::path::Path) -> Result<()> {
70 if !path.exists() {
71 std::fs::create_dir_all(path)?;
72 info!("Created directory: {}", path.display());
73 }
74 Ok(())
75 }
76}