From a2a9e1fb91709a1336c125f93c42a9d6635a4144 Mon Sep 17 00:00:00 2001 From: dein0s Date: Wed, 22 Mar 2017 13:22:10 +0300 Subject: [PATCH] Add force option to clean plugin --- plugins/clean.py | 20 +++++++++++++------- test/tests/clean-outside-force.bash | 18 ++++++++++++++++++ test/tests/defaults.bash | 27 ++++++++++++++++++++++++++- 3 files changed, 57 insertions(+), 8 deletions(-) create mode 100644 test/tests/clean-outside-force.bash diff --git a/plugins/clean.py b/plugins/clean.py index dbd11af..7e6cba1 100644 --- a/plugins/clean.py +++ b/plugins/clean.py @@ -17,18 +17,22 @@ class Clean(dotbot.Plugin): def _process_clean(self, targets): success = True + defaults = self._context.defaults().get(self._directive, {}) + force = defaults.get('force', False) for target in targets: - success &= self._clean(target) + if isinstance(targets, dict): + force = targets[target].get('force', force) + success &= self._clean(target, force) if success: self._log.info('All targets have been cleaned') else: self._log.error('Some targets were not successfully cleaned') return success - def _clean(self, target): + def _clean(self, target, force): ''' - Cleans all the broken symbolic links in target that point to - a subdirectory of the base directory. + Cleans all the broken symbolic links in target if they point to + a subdirectory of the base directory or if forced to clean. ''' if not os.path.isdir(os.path.expanduser(target)): self._log.debug('Ignoring nonexistent directory %s' % target) @@ -36,10 +40,12 @@ class Clean(dotbot.Plugin): for item in os.listdir(os.path.expanduser(target)): path = os.path.join(os.path.expanduser(target), item) if not os.path.exists(path) and os.path.islink(path): - if self._in_directory(path, self._context.base_directory()): - self._log.lowinfo('Removing invalid link %s -> %s' % - (path, os.path.join(os.path.dirname(path), os.readlink(path)))) + points_at = os.path.join(os.path.dirname(path), os.readlink(path)) + if self._in_directory(path, self._context.base_directory()) or force: + self._log.lowinfo('Removing invalid link %s -> %s' % (path, points_at)) os.remove(path) + else: + self._log.lowinfo('Link %s -> %s not removed.' % (path, points_at)) return True def _in_directory(self, path, directory): diff --git a/test/tests/clean-outside-force.bash b/test/tests/clean-outside-force.bash new file mode 100644 index 0000000..16a740d --- /dev/null +++ b/test/tests/clean-outside-force.bash @@ -0,0 +1,18 @@ +test_description='clean forced to remove files linking outside dotfiles directory' +. '../test-lib.bash' + +test_expect_success 'setup' ' +ln -s /nowhere ~/.g +' + +test_expect_success 'run' ' +run_dotbot < ${DOTFILES}/f && echo "grape" > ~/f && -ln -s ~/f ~/.f +ln -s ~/f ~/.f && +ln -s /nowhere ~/.g ' test_expect_failure 'run-fail' ' @@ -32,3 +33,27 @@ EOF test_expect_success 'test' ' grep "apple" ~/.f ' + +test_expect_success 'run-fail' ' +run_dotbot <