use anyhow::{Context, Result, bail};
use crate::workflow::file_ops::{handle_file_operations, symlink_claude_local_md};
use crate::{config, git};
pub fn run(all: bool) -> Result<()> {
let repo_root =
git::get_main_worktree_root().context("Could not find the main git worktree")?;
let cwd = std::env::current_dir().context("Failed to get current directory")?;
let cwd_rel_dir = config::find_project_config(&cwd)?
.map(|loc| loc.rel_dir)
.unwrap_or_default();
let main_config_start = if cwd_rel_dir.as_os_str().is_empty() {
repo_root.clone()
} else {
repo_root.join(&cwd_rel_dir)
};
let (config, config_location) =
config::Config::load_with_location_from(&main_config_start, None)?;
let rel_dir = config_location
.as_ref()
.map(|loc| loc.rel_dir.clone())
.unwrap_or_default();
let file_ops_source = if rel_dir.as_os_str().is_empty() {
repo_root.clone()
} else {
repo_root.join(&rel_dir)
};
let targets = if all {
let worktrees = git::list_worktrees().context("Failed to list worktrees")?;
let mut paths = Vec::new();
for (path, _branch) in worktrees {
if path == repo_root {
continue;
}
let target = if rel_dir.as_os_str().is_empty() {
path
} else {
path.join(&rel_dir)
};
paths.push(target);
}
if paths.is_empty() {
bail!("No worktrees found (besides main)");
}
paths
} else {
let worktree_root =
git::get_repo_root().context("Failed to determine current worktree root")?;
if worktree_root == repo_root {
bail!(
"Current directory is the main worktree. \
Run this from inside a worktree, or use --all."
);
}
let target = if rel_dir.as_os_str().is_empty() {
worktree_root
} else {
worktree_root.join(&rel_dir)
};
vec![target]
};
for target in &targets {
handle_file_operations(&file_ops_source, target, &config.files)
.with_context(|| format!("Failed to sync files to {}", target.display()))?;
symlink_claude_local_md(&repo_root, target)
.with_context(|| format!("Failed to sync CLAUDE.local.md to {}", target.display()))?;
let name = target
.file_name()
.map(|n| n.to_string_lossy().to_string())
.unwrap_or_else(|| target.display().to_string());
println!("✓ Synced files to '{}'", name);
}
Ok(())
}