use std::path::PathBuf;
pub fn execute(project_root: &std::path::Path, force: bool) -> anyhow::Result<()> {
let binary_path = find_binary_path()?;
println!("Forge uninstall");
println!("===============");
println!();
println!("Binary: {}", binary_path.display());
if binary_path.exists() {
std::fs::remove_file(&binary_path)?;
println!(" Removed.");
} else {
println!(" Not found (already removed?).");
}
let forge_dir = project_root.join(".forge");
if forge_dir.exists() {
if force {
std::fs::remove_dir_all(&forge_dir)?;
println!();
println!("Project data: {}", forge_dir.display());
println!(" Removed.");
} else {
println!();
println!("Project data: {}", forge_dir.display());
println!(" Kept. Use --force to also remove .forge/ project data.");
}
}
if let Ok(home) = std::env::var("HOME") {
let global_dir = PathBuf::from(&home).join(".forge");
if global_dir.exists() {
if force {
std::fs::remove_dir_all(&global_dir)?;
println!();
println!("Global config: {}", global_dir.display());
println!(" Removed.");
} else {
println!();
println!("Global config: {}", global_dir.display());
println!(" Kept. Use --force to also remove ~/.forge/ global config.");
}
}
}
println!();
println!("Forge has been uninstalled.");
Ok(())
}
fn find_binary_path() -> anyhow::Result<PathBuf> {
if let Ok(exe) = std::env::current_exe() {
let resolved = exe.canonicalize().unwrap_or(exe);
return Ok(resolved);
}
if let Ok(output) = std::process::Command::new("which").arg("forge").output()
&& output.status.success()
{
let path = String::from_utf8_lossy(&output.stdout).trim().to_string();
if !path.is_empty() {
return Ok(PathBuf::from(path));
}
}
anyhow::bail!("Could not determine forge binary location. Remove it manually.")
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn test_find_binary_path_returns_something() {
let result = find_binary_path();
assert!(result.is_ok(), "Should find the test binary path");
}
#[test]
fn test_uninstall_removes_forge_dir() {
let tmp = tempfile::tempdir().unwrap();
let forge_dir = tmp.path().join(".forge");
std::fs::create_dir_all(&forge_dir).unwrap();
std::fs::write(forge_dir.join("state.json"), "{}").unwrap();
let fake_bin = tmp.path().join("forge-test-bin");
std::fs::write(&fake_bin, "fake").unwrap();
assert!(forge_dir.exists());
std::fs::remove_dir_all(&forge_dir).unwrap();
assert!(!forge_dir.exists());
}
}