Skip to content

Commit 26b1a7f

Browse files
committed
fixed #122: made shared group resolution work on windows
1 parent 859caac commit 26b1a7f

3 files changed

Lines changed: 20 additions & 15 deletions

File tree

src/dotfiles.rs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -469,12 +469,13 @@ pub fn get_nonexistent_groups(
469469

470470
// searches for a link in a path and if the symlink points to a valid dotfile
471471
// it returns the group dotfile
472-
pub fn get_group_from_target_path(target_path: &Path) -> Option<Dotfile> {
473-
let mut file_path = PathBuf::from(target_path).canonicalize().ok()?;
472+
pub fn get_dotfile_from_path(target_path: &Path) -> Option<Dotfile> {
473+
let mut file_path = PathBuf::from(target_path);
474474
if !file_path.exists() {
475475
return None;
476476
}
477477

478+
478479
if let Ok(dotfile) = dotfiles::Dotfile::try_from(file_path.clone()) {
479480
return Some(dotfile);
480481
}

src/fileops.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -567,7 +567,7 @@ pub fn groupis_cmd(ctx: &Context, files: &[String]) -> Result<(), ExitCode> {
567567
continue;
568568
}
569569

570-
let Some(group) = dotfiles::get_group_from_target_path(file_path) else {
570+
let Some(group) = dotfiles::get_dotfile_from_path(file_path) else {
571571
eprintln!("{}", t!("errors.not_a_tuckr_dotfile", file = file).red());
572572
continue;
573573
};

src/symlinks.rs

Lines changed: 16 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -398,9 +398,15 @@ impl<'a> SymlinkHandler<'a> {
398398
return;
399399
};
400400

401-
let mut removed_groups = HashSet::new();
401+
let mut removed_files = HashSet::new();
402402
let mut added_files = HashSet::new();
403403

404+
// Context: if a directory is a symlink of a group and then another group tries to symlink to that same directory
405+
// we would end up adding a symlink inside another symlink, borking the user's dotfiles.
406+
// So the solution is to detect that the directory should be shared by multiple groups or even multiple dotfiles profiles,
407+
// If that happens we should remove all the groups that will share those directories, create the shared directories
408+
// and then add everything back in
409+
404410
while let Some(idx) = dotfiles::get_highest_priority_target_idx(&groups) {
405411
let group = &groups[idx];
406412
let group = Dotfile::try_from(self.dotfiles_dir.join("Configs").join(group)).unwrap();
@@ -410,8 +416,8 @@ impl<'a> SymlinkHandler<'a> {
410416

411417
// if there's a symlink in this path, we take its group and put it in the "to be removed" bucket
412418
// it will later be readded so that the groups are all contained in the same parent directory
413-
if let Some(group) = dotfiles::get_group_from_target_path(&f_target) {
414-
removed_groups.insert(group);
419+
if let Some(dotfile) = dotfiles::get_dotfile_from_path(&f_target) {
420+
removed_files.insert(dotfile);
415421
}
416422
added_files.insert(f);
417423
}
@@ -429,18 +435,18 @@ impl<'a> SymlinkHandler<'a> {
429435

430436
// NOTE/TODO?: this will only work if the dotfiles are in the same profile context
431437
// maybe we should instead move the files into a temporary and then move them back
432-
for group in &removed_groups {
433-
self.remove(dry_run, &group.group_name);
438+
for file in &removed_files {
439+
self.remove(dry_run, &file.group_name);
434440

435-
let target_path = group.to_target_path().unwrap();
436-
fs::create_dir_all(if group.path.is_file() {
441+
let target_path = file.to_target_path().unwrap();
442+
fs::create_dir_all(if file.path.is_file() {
437443
target_path.parent().unwrap()
438444
} else {
439445
&target_path
440446
})
441-
.unwrap();
447+
.unwrap();
442448

443-
let group_iter = Dotfile::try_from(group.group_path.clone())
449+
let group_iter = Dotfile::try_from(file.group_path.clone())
444450
.unwrap()
445451
.try_iter()
446452
.unwrap();
@@ -468,9 +474,7 @@ impl<'a> SymlinkHandler<'a> {
468474
symlink_file(dry_run, file.path);
469475
}
470476

471-
// we do this because otherwise the next time this function is called
472-
// the dotfile won't be in the symlink status cache
473-
// TODO: find a better way??
477+
// we have to update the cache to reflect the new state
474478
self.symlinked
475479
.insert(group.into(), group_only_added_files.into_iter().collect());
476480
self.not_symlinked.remove(group);

0 commit comments

Comments
 (0)