1
0
mirror of https://github.com/deadc0de6/dotdrop.git synced 2026-02-16 02:36:11 +00:00

merge defaultlink

This commit is contained in:
deadc0de6
2019-04-08 07:51:36 +02:00
22 changed files with 1295 additions and 84 deletions

View File

@@ -152,7 +152,6 @@ config:
dotpath: dotfiles dotpath: dotfiles
ignoreempty: false ignoreempty: false
keepdot: false keepdot: false
link_by_default: false
longkey: false longkey: false
showdiff: false showdiff: false
workdir: ~/.config/dotdrop workdir: ~/.config/dotdrop

View File

@@ -119,14 +119,14 @@ _dotdrop-import ()
'(--verbose)--verbose' \ '(--verbose)--verbose' \
'(-b)-b' \ '(-b)-b' \
'(--no-banner)--no-banner' \ '(--no-banner)--no-banner' \
'(-l)-l' \
'(--inv-link)--inv-link' \
'(-d)-d' \ '(-d)-d' \
'(--dry)--dry' \ '(--dry)--dry' \
'(-c=-)-c=-' \ '(-c=-)-c=-' \
'(--cfg=-)--cfg=-' \ '(--cfg=-)--cfg=-' \
'(-p=-)-p=-' \ '(-p=-)-p=-' \
'(--profile=-)--profile=-' \ '(--profile=-)--profile=-' \
'(-l=-)-l=-' \
'(--link=-)--link=-' \
else else
myargs=('<path>') myargs=('<path>')

View File

@@ -119,14 +119,14 @@ _dotdrop.sh-import ()
'(--verbose)--verbose' \ '(--verbose)--verbose' \
'(-b)-b' \ '(-b)-b' \
'(--no-banner)--no-banner' \ '(--no-banner)--no-banner' \
'(-l)-l' \
'(--inv-link)--inv-link' \
'(-d)-d' \ '(-d)-d' \
'(--dry)--dry' \ '(--dry)--dry' \
'(-c=-)-c=-' \ '(-c=-)-c=-' \
'(--cfg=-)--cfg=-' \ '(--cfg=-)--cfg=-' \
'(-p=-)-p=-' \ '(-p=-)-p=-' \
'(--profile=-)--profile=-' \ '(--profile=-)--profile=-' \
'(-l=-)-l=-' \
'(--link=-)--link=-' \
else else
myargs=('<path>') myargs=('<path>')

2
completion/dotdrop-completion.bash Normal file → Executable file
View File

@@ -50,7 +50,7 @@ _dotdrop_import()
cur="${COMP_WORDS[COMP_CWORD]}" cur="${COMP_WORDS[COMP_CWORD]}"
if [ $COMP_CWORD -ge 2 ]; then if [ $COMP_CWORD -ge 2 ]; then
COMPREPLY=( $( compgen -fW '-V --verbose -b --no-banner -l --inv-link -d --dry -c= --cfg= -p= --profile= ' -- $cur) ) COMPREPLY=( $( compgen -fW '-V --verbose -b --no-banner -d --dry -c= --cfg= -p= --profile= -l= --link= ' -- $cur) )
fi fi
} }

View File

@@ -50,7 +50,7 @@ _dotdropsh_import()
cur="${COMP_WORDS[COMP_CWORD]}" cur="${COMP_WORDS[COMP_CWORD]}"
if [ $COMP_CWORD -ge 2 ]; then if [ $COMP_CWORD -ge 2 ]; then
COMPREPLY=( $( compgen -fW '-V --verbose -b --no-banner -l --inv-link -d --dry -c= --cfg= -p= --profile= ' -- $cur) ) COMPREPLY=( $( compgen -fW '-V --verbose -b --no-banner -d --dry -c= --cfg= -p= --profile= -l= --link= ' -- $cur) )
fi fi
} }

View File

@@ -5,6 +5,7 @@ config:
banner: true banner: true
longkey: false longkey: false
keepdot: false keepdot: false
link_by_default: false link_import_default: nolink
link_dotfile_default: nolink
dotfiles: dotfiles:
profiles: profiles:

View File

@@ -31,7 +31,8 @@ class Cfg:
key_keepdot = 'keepdot' key_keepdot = 'keepdot'
key_ignoreempty = 'ignoreempty' key_ignoreempty = 'ignoreempty'
key_showdiff = 'showdiff' key_showdiff = 'showdiff'
key_deflink = 'link_by_default' key_imp_link = 'link_on_import'
key_dotfile_link = 'link_dotfile_default'
key_workdir = 'workdir' key_workdir = 'workdir'
key_import_vars = 'import_variables' key_import_vars = 'import_variables'
key_import_actions = 'import_actions' key_import_actions = 'import_actions'
@@ -69,17 +70,22 @@ class Cfg:
key_profiles_incl = 'include' key_profiles_incl = 'include'
key_profiles_imp = 'import' key_profiles_imp = 'import'
# link values
lnk_nolink = LinkTypes.NOLINK.name.lower()
lnk_link = LinkTypes.LINK.name.lower()
lnk_children = LinkTypes.LINK_CHILDREN.name.lower()
# settings defaults # settings defaults
default_dotpath = 'dotfiles' default_dotpath = 'dotfiles'
default_backup = True default_backup = True
default_create = True default_create = True
default_banner = True default_banner = True
default_link = LinkTypes.NOLINK
default_longkey = False default_longkey = False
default_keepdot = False default_keepdot = False
default_showdiff = False default_showdiff = False
default_ignoreempty = False default_ignoreempty = False
default_link_by_default = False default_link_imp = lnk_nolink
default_link = lnk_nolink
default_workdir = '~/.config/dotdrop' default_workdir = '~/.config/dotdrop'
def __init__(self, cfgpath, profile=None, debug=False): def __init__(self, cfgpath, profile=None, debug=False):
@@ -95,6 +101,7 @@ class Cfg:
# make sure to have an absolute path to config file # make sure to have an absolute path to config file
self.cfgpath = os.path.abspath(cfgpath) self.cfgpath = os.path.abspath(cfgpath)
self.debug = debug self.debug = debug
self._modified = False
# init the logger # init the logger
self.log = Logger() self.log = Logger()
@@ -185,11 +192,25 @@ class Cfg:
return False return False
return True return True
def _get_def_link(self):
"""get dotfile link entry when not specified"""
string = self.lnk_settings[self.key_dotfile_link].lower()
return self._string_to_linktype(string)
def _string_to_linktype(self, string):
"""translate string to linktype"""
if string == self.lnk_link.lower():
return LinkTypes.LINK
elif string == self.lnk_children.lower():
return LinkTypes.LINK_CHILDREN
return LinkTypes.NOLINK
def _parse(self, profile=None): def _parse(self, profile=None):
"""parse config file""" """parse config file"""
# parse the settings # parse the settings
self.lnk_settings = self.content[self.key_settings] self.lnk_settings = self.content[self.key_settings]
self._complete_settings() if not self._complete_settings():
return False
# parse the profiles # parse the profiles
self.lnk_profiles = self.content[self.key_profiles] self.lnk_profiles = self.content[self.key_profiles]
@@ -254,7 +275,9 @@ class Cfg:
if not self.content[self.key_dotfiles]: if not self.content[self.key_dotfiles]:
# ensures the dotfiles entry is a dict # ensures the dotfiles entry is a dict
self.content[self.key_dotfiles] = {} self.content[self.key_dotfiles] = {}
for k, v in self.content[self.key_dotfiles].items():
for k in self.content[self.key_dotfiles].keys():
v = self.content[self.key_dotfiles][k]
src = os.path.normpath(v[self.key_dotfiles_src]) src = os.path.normpath(v[self.key_dotfiles_src])
dst = os.path.normpath(v[self.key_dotfiles_dst]) dst = os.path.normpath(v[self.key_dotfiles_dst])
@@ -264,18 +287,23 @@ class Cfg:
msg = 'only one of `link` or `link_children` allowed per' msg = 'only one of `link` or `link_children` allowed per'
msg += ' dotfile, error on dotfile "{}".' msg += ' dotfile, error on dotfile "{}".'
self.log.err(msg.format(k)) self.log.err(msg.format(k))
return False
# Otherwise, get link type # fix it
link = LinkTypes.NOLINK v = self._fix_dotfile_link(k, v)
if self.key_dotfiles_link in v and v[self.key_dotfiles_link]: self.content[self.key_dotfiles][k] = v
link = LinkTypes.PARENTS
if self.key_dotfiles_link_children in v \
and v[self.key_dotfiles_link_children]:
link = LinkTypes.CHILDREN
# get link type
link = self._get_def_link()
if self.key_dotfiles_link in v:
link = self._string_to_linktype(v[self.key_dotfiles_link])
# get ignore empty
noempty = v[self.key_dotfiles_noempty] if \ noempty = v[self.key_dotfiles_noempty] if \
self.key_dotfiles_noempty \ self.key_dotfiles_noempty \
in v else self.lnk_settings[self.key_ignoreempty] in v else self.lnk_settings[self.key_ignoreempty]
# parse actions
itsactions = v[self.key_dotfiles_actions] if \ itsactions = v[self.key_dotfiles_actions] if \
self.key_dotfiles_actions in v else [] self.key_dotfiles_actions in v else []
actions = self._parse_actions(itsactions) actions = self._parse_actions(itsactions)
@@ -319,7 +347,7 @@ class Cfg:
# disable transformation when link is true # disable transformation when link is true
if link != LinkTypes.NOLINK and (trans_r or trans_w): if link != LinkTypes.NOLINK and (trans_r or trans_w):
msg = 'transformations disabled for \"{}\"'.format(dst) msg = 'transformations disabled for \"{}\"'.format(dst)
msg += ' because link is True' msg += ' because link|link_children is enabled'
self.log.warn(msg) self.log.warn(msg)
trans_r = None trans_r = None
trans_w = None trans_w = None
@@ -559,6 +587,7 @@ class Cfg:
def _complete_settings(self): def _complete_settings(self):
"""set settings defaults if not present""" """set settings defaults if not present"""
self._fix_deprecated()
if self.key_dotpath not in self.lnk_settings: if self.key_dotpath not in self.lnk_settings:
self.lnk_settings[self.key_dotpath] = self.default_dotpath self.lnk_settings[self.key_dotpath] = self.default_dotpath
if self.key_backup not in self.lnk_settings: if self.key_backup not in self.lnk_settings:
@@ -571,8 +600,6 @@ class Cfg:
self.lnk_settings[self.key_long] = self.default_longkey self.lnk_settings[self.key_long] = self.default_longkey
if self.key_keepdot not in self.lnk_settings: if self.key_keepdot not in self.lnk_settings:
self.lnk_settings[self.key_keepdot] = self.default_keepdot self.lnk_settings[self.key_keepdot] = self.default_keepdot
if self.key_deflink not in self.lnk_settings:
self.lnk_settings[self.key_deflink] = self.default_link_by_default
if self.key_workdir not in self.lnk_settings: if self.key_workdir not in self.lnk_settings:
self.lnk_settings[self.key_workdir] = self.default_workdir self.lnk_settings[self.key_workdir] = self.default_workdir
if self.key_showdiff not in self.lnk_settings: if self.key_showdiff not in self.lnk_settings:
@@ -580,6 +607,78 @@ class Cfg:
if self.key_ignoreempty not in self.lnk_settings: if self.key_ignoreempty not in self.lnk_settings:
self.lnk_settings[self.key_ignoreempty] = self.default_ignoreempty self.lnk_settings[self.key_ignoreempty] = self.default_ignoreempty
if self.key_dotfile_link not in self.lnk_settings:
self.lnk_settings[self.key_dotfile_link] = self.default_link
else:
key = self.lnk_settings[self.key_dotfile_link]
if key != self.lnk_link and \
key != self.lnk_children and \
key != self.lnk_nolink:
self.log.err('bad value for {}'.format(self.key_dotfile_link))
return False
if self.key_imp_link not in self.lnk_settings:
self.lnk_settings[self.key_imp_link] = self.default_link_imp
else:
key = self.lnk_settings[self.key_imp_link]
if key != self.lnk_link and \
key != self.lnk_children and \
key != self.lnk_nolink:
self.log.err('bad value for {}'.format(self.key_dotfile_link))
return False
return True
def _fix_deprecated(self):
"""fix deprecated entries"""
# link_by_default
key = 'link_by_default'
newkey = self.key_imp_link
if key in self.lnk_settings:
if self.lnk_settings[key]:
self.lnk_settings[newkey] = self.lnk_link
else:
self.lnk_settings[newkey] = self.lnk_nolink
del self.lnk_settings[key]
self._modified = True
def _fix_dotfile_link(self, key, entry):
"""fix deprecated link usage in dotfile entry"""
v = entry
if self.key_dotfiles_link not in v \
and self.key_dotfiles_link_children not in v:
# nothing defined
return v
new = self.lnk_nolink
if self.key_dotfiles_link in v \
and type(v[self.key_dotfiles_link]) is bool:
# patch link: <bool>
if v[self.key_dotfiles_link]:
new = self.lnk_link
else:
new = self.lnk_nolink
self._modified = True
if self.debug:
self.log.dbg('link updated for {} to {}'.format(key, new))
elif self.key_dotfiles_link_children in v \
and type(v[self.key_dotfiles_link_children]) is bool:
# patch link_children: <bool>
if v[self.key_dotfiles_link_children]:
new = self.lnk_children
else:
new = self.lnk_nolink
del v[self.key_dotfiles_link_children]
self._modified = True
if self.debug:
self.log.dbg('link updated for {} to {}'.format(key, new))
else:
# no change
new = v[self.key_dotfiles_link]
v[self.key_dotfiles_link] = new
return v
def _save(self, content, path): def _save(self, content, path):
"""writes the config to file""" """writes the config to file"""
ret = False ret = False
@@ -587,6 +686,8 @@ class Cfg:
ret = yaml.safe_dump(content, f, ret = yaml.safe_dump(content, f,
default_flow_style=False, default_flow_style=False,
indent=2) indent=2)
if ret:
self._modified = False
return ret return ret
def _norm_key_elem(self, elem): def _norm_key_elem(self, elem):
@@ -663,12 +764,12 @@ class Cfg:
return False, self._get_long_key(path, keys) return False, self._get_long_key(path, keys)
return False, self._get_short_key(path, keys) return False, self._get_short_key(path, keys)
def new(self, dotfile, profile, link=LinkTypes.NOLINK, debug=False): def new(self, src, dst, profile, link, debug=False):
"""import new dotfile """import new dotfile"""
dotfile key will change and can be empty"""
# keep it short # keep it short
home = os.path.expanduser('~') home = os.path.expanduser('~')
dotfile.dst = dotfile.dst.replace(home, '~', 1) dst = dst.replace(home, '~', 1)
dotfile = Dotfile('', dst, src)
# adding new profile if doesn't exist # adding new profile if doesn't exist
if profile not in self.lnk_profiles: if profile not in self.lnk_profiles:
@@ -714,10 +815,9 @@ class Cfg:
} }
# set the link flag # set the link flag
if link == LinkTypes.PARENTS: if link != self._get_def_link():
dots[dotfile.key][self.key_dotfiles_link] = True val = link.name.lower()
elif link == LinkTypes.CHILDREN: dots[dotfile.key][self.key_dotfiles_link] = val
dots[dotfile.key][self.key_dotfiles_link_children] = True
# link it to this profile in the yaml file # link it to this profile in the yaml file
pro = self.content[self.key_profiles][profile] pro = self.content[self.key_profiles][profile]
@@ -744,7 +844,13 @@ class Cfg:
def get_settings(self): def get_settings(self):
"""return all defined settings""" """return all defined settings"""
return self.lnk_settings.copy() settings = self.lnk_settings.copy()
# patch link entries
key = self.key_imp_link
settings[key] = self._string_to_linktype(settings[key])
key = self.key_dotfile_link
settings[key] = self._string_to_linktype(settings[key])
return settings
def get_variables(self, profile, debug=False): def get_variables(self, profile, debug=False):
"""return the variables for this profile""" """return the variables for this profile"""
@@ -852,6 +958,10 @@ class Cfg:
self.lnk_settings[self.key_workdir] = workdir self.lnk_settings[self.key_workdir] = workdir
return ret return ret
def is_modified(self):
"""need the db to be saved"""
return self._modified
def save(self): def save(self):
"""save the config to file""" """save the config to file"""
# temporary reset paths # temporary reset paths

View File

@@ -15,7 +15,6 @@ from dotdrop.templategen import Templategen
from dotdrop.installer import Installer from dotdrop.installer import Installer
from dotdrop.updater import Updater from dotdrop.updater import Updater
from dotdrop.comparator import Comparator from dotdrop.comparator import Comparator
from dotdrop.dotfile import Dotfile
from dotdrop.config import Cfg from dotdrop.config import Cfg
from dotdrop.utils import get_tmpdir, remove, strip_home, run from dotdrop.utils import get_tmpdir, remove, strip_home, run
from dotdrop.linktypes import LinkTypes from dotdrop.linktypes import LinkTypes
@@ -60,9 +59,10 @@ def cmd_install(o):
preactions.append(action) preactions.append(action)
if o.debug: if o.debug:
LOG.dbg('installing {}'.format(dotfile)) LOG.dbg('installing {}'.format(dotfile))
if hasattr(dotfile, 'link') and dotfile.link == LinkTypes.PARENTS: if hasattr(dotfile, 'link') and dotfile.link == LinkTypes.LINK:
r = inst.link(t, dotfile.src, dotfile.dst, actions=preactions) r = inst.link(t, dotfile.src, dotfile.dst, actions=preactions)
elif hasattr(dotfile, 'link') and dotfile.link == LinkTypes.CHILDREN: elif hasattr(dotfile, 'link') and \
dotfile.link == LinkTypes.LINK_CHILDREN:
r = inst.link_children(t, dotfile.src, dotfile.dst, r = inst.link_children(t, dotfile.src, dotfile.dst,
actions=preactions) actions=preactions)
else: else:
@@ -238,13 +238,16 @@ def cmd_importer(o):
strip = os.sep strip = os.sep
src = src.lstrip(strip) src = src.lstrip(strip)
# create a new dotfile # set the link attribute
dotfile = Dotfile('', dst, src) linktype = o.import_link
if linktype == LinkTypes.LINK_CHILDREN and \
linktype = LinkTypes(o.link) not os.path.isdir(path):
LOG.err('importing \"{}\" failed!'.format(path))
ret = False
continue
if o.debug: if o.debug:
LOG.dbg('new dotfile: {}'.format(dotfile)) LOG.dbg('new dotfile: src:{} dst:{}'.format(src, dst))
# prepare hierarchy for dotfile # prepare hierarchy for dotfile
srcf = os.path.join(o.dotpath, src) srcf = os.path.join(o.dotpath, src)
@@ -261,19 +264,14 @@ def cmd_importer(o):
cmd = ['cp', '-R', '-L', dst, srcf] cmd = ['cp', '-R', '-L', dst, srcf]
if o.dry: if o.dry:
LOG.dry('would run: {}'.format(' '.join(cmd))) LOG.dry('would run: {}'.format(' '.join(cmd)))
if linktype == LinkTypes.PARENTS:
LOG.dry('would symlink {} to {}'.format(srcf, dst))
else: else:
r, _ = run(cmd, raw=False, debug=o.debug, checkerr=True) r, _ = run(cmd, raw=False, debug=o.debug, checkerr=True)
if not r: if not r:
LOG.err('importing \"{}\" failed!'.format(path)) LOG.err('importing \"{}\" failed!'.format(path))
ret = False ret = False
continue continue
if linktype == LinkTypes.PARENTS: retconf, dotfile = o.conf.new(src, dst, o.profile,
remove(dst) linktype, debug=o.debug)
os.symlink(srcf, dst)
retconf, dotfile = o.conf.new(dotfile, o.profile,
link=linktype, debug=o.debug)
if retconf: if retconf:
LOG.sub('\"{}\" imported'.format(path)) LOG.sub('\"{}\" imported'.format(path))
cnt += 1 cnt += 1
@@ -455,6 +453,10 @@ def main():
LOG.err('interrupted') LOG.err('interrupted')
ret = False ret = False
if ret and o.conf.is_modified():
LOG.log('config file updated')
o.conf.save()
return ret return ret

View File

@@ -30,6 +30,9 @@ class Dotfile:
self.dst = dst self.dst = dst
self.src = src self.src = src
self.link = link self.link = link
# ensure link of right type
if type(link) != LinkTypes:
raise Exception('bad value for link: {}'.format(link))
self.actions = actions self.actions = actions
self.trans_r = trans_r self.trans_r = trans_r
self.trans_w = trans_w self.trans_w = trans_w

View File

@@ -3,5 +3,5 @@ from enum import IntEnum
class LinkTypes(IntEnum): class LinkTypes(IntEnum):
NOLINK = 0 NOLINK = 0
PARENTS = 1 LINK = 1
CHILDREN = 2 LINK_CHILDREN = 2

View File

@@ -6,6 +6,7 @@ stores all options to use across dotdrop
""" """
import os import os
import sys
import socket import socket
from docopt import docopt from docopt import docopt
@@ -33,6 +34,11 @@ HOMECFG = '~/.config/{}'.format(NAME)
ETCXDGCFG = '/etc/xdg/{}'.format(NAME) ETCXDGCFG = '/etc/xdg/{}'.format(NAME)
ETCCFG = '/etc/{}'.format(NAME) ETCCFG = '/etc/{}'.format(NAME)
OPT_LINK = {
LinkTypes.NOLINK.name.lower(): LinkTypes.NOLINK,
LinkTypes.LINK.name.lower(): LinkTypes.LINK,
LinkTypes.LINK_CHILDREN.name.lower(): LinkTypes.LINK_CHILDREN}
BANNER = """ _ _ _ BANNER = """ _ _ _
__| | ___ | |_ __| |_ __ ___ _ __ __| | ___ | |_ __| |_ __ ___ _ __
/ _` |/ _ \| __/ _` | '__/ _ \| '_ | / _` |/ _ \| __/ _` | '__/ _ \| '_ |
@@ -44,7 +50,7 @@ USAGE = """
Usage: Usage:
dotdrop install [-VbtfndD] [-c <path>] [-p <profile>] [<key>...] dotdrop install [-VbtfndD] [-c <path>] [-p <profile>] [<key>...]
dotdrop import [-Vbld] [-c <path>] [-p <profile>] <path>... dotdrop import [-Vbd] [-c <path>] [-p <profile>] [-l <link>] <path>...
dotdrop compare [-Vb] [-c <path>] [-p <profile>] dotdrop compare [-Vb] [-c <path>] [-p <profile>]
[-o <opts>] [-C <file>...] [-i <pattern>...] [-o <opts>] [-C <file>...] [-i <pattern>...]
dotdrop update [-VbfdkP] [-c <path>] [-p <profile>] dotdrop update [-VbfdkP] [-c <path>] [-p <profile>]
@@ -61,11 +67,11 @@ Options:
-C --file=<path> Path of dotfile to compare. -C --file=<path> Path of dotfile to compare.
-i --ignore=<pattern> Pattern to ignore. -i --ignore=<pattern> Pattern to ignore.
-o --dopts=<opts> Diff options [default: ]. -o --dopts=<opts> Diff options [default: ].
-l --link=<link> "link_on_import" (nolink|link|link_children).
-n --nodiff Do not diff when installing. -n --nodiff Do not diff when installing.
-t --temp Install to a temporary directory for review. -t --temp Install to a temporary directory for review.
-T --template Only template dotfiles. -T --template Only template dotfiles.
-D --showdiff Show a diff before overwriting. -D --showdiff Show a diff before overwriting.
-l --inv-link Invert the value of "link_by_default" when importing.
-P --show-patch Provide a one-liner to manually patch template. -P --show-patch Provide a one-liner to manually patch template.
-f --force Do not warn if exists. -f --force Do not warn if exists.
-k --key Treat <path> as a dotfile key. -k --key Treat <path> as a dotfile key.
@@ -74,7 +80,6 @@ Options:
-b --no-banner Do not display the banner. -b --no-banner Do not display the banner.
-v --version Show version. -v --version Show version.
-h --help Show this screen. -h --help Show this screen.
""".format(BANNER, PROFILE) """.format(BANNER, PROFILE)
@@ -179,6 +184,8 @@ class Options(AttrMonitor):
self.conf = Cfg(self.confpath, profile=profile, debug=self.debug) self.conf = Cfg(self.confpath, profile=profile, debug=self.debug)
# transform the configs in attribute # transform the configs in attribute
for k, v in self.conf.get_settings().items(): for k, v in self.conf.get_settings().items():
if self.debug:
self.log.dbg('setting: {}={}'.format(k, v))
setattr(self, k, v) setattr(self, k, v)
def _apply_args(self): def _apply_args(self):
@@ -195,16 +202,18 @@ class Options(AttrMonitor):
# adapt attributes based on arguments # adapt attributes based on arguments
self.dry = self.args['--dry'] self.dry = self.args['--dry']
self.safe = not self.args['--force'] self.safe = not self.args['--force']
self.link = LinkTypes.NOLINK
if self.link_by_default:
self.link = LinkTypes.PARENTS
if self.args['--inv-link']: # import link default value
# Only invert link type from NOLINK to PARENTS and vice-versa self.import_link = self.link_on_import
if self.link == LinkTypes.NOLINK: if self.args['--link']:
self.link = LinkTypes.PARENTS # overwrite default import link with cli switch
elif self.link == LinkTypes.PARENTS: link = self.args['--link']
self.link = LinkTypes.NOLINK if link not in OPT_LINK.keys():
self.log.err('bad option for --link: {}'.format(link))
sys.exit(USAGE)
self.import_link = OPT_LINK[link]
if self.debug:
self.log.dbg('link_import value: {}'.format(self.import_link))
# "listfiles" specifics # "listfiles" specifics
self.listfiles_templateonly = self.args['--template'] self.listfiles_templateonly = self.args['--template']

140
tests-ng/deprecated-link.sh Executable file
View File

@@ -0,0 +1,140 @@
#!/usr/bin/env bash
# author: deadc0de6 (https://github.com/deadc0de6)
# Copyright (c) 2017, deadc0de6
#
# test migration from link/link_children to single entry
# returns 1 in case of error
#
# exit on first error
set -e
# all this crap to get current path
rl="readlink -f"
if ! ${rl} "${0}" >/dev/null 2>&1; then
rl="realpath"
if ! hash ${rl}; then
echo "\"${rl}\" not found !" && exit 1
fi
fi
cur=$(dirname "$(${rl} "${0}")")
#hash dotdrop >/dev/null 2>&1
#[ "$?" != "0" ] && echo "install dotdrop to run tests" && exit 1
#echo "called with ${1}"
# dotdrop path can be pass as argument
ddpath="${cur}/../"
[ "${1}" != "" ] && ddpath="${1}"
[ ! -d ${ddpath} ] && echo "ddpath \"${ddpath}\" is not a directory" && exit 1
export PYTHONPATH="${ddpath}:${PYTHONPATH}"
bin="python3 -m dotdrop.dotdrop"
echo "dotdrop path: ${ddpath}"
echo "pythonpath: ${PYTHONPATH}"
# get the helpers
source ${cur}/helpers
echo -e "\e[96m\e[1m==> RUNNING $(basename $BASH_SOURCE) <==\e[0m"
################################################################
# this is the test
################################################################
# the dotfile source
tmps=`mktemp -d --suffix='-dotdrop-tests'`
mkdir -p ${tmps}/dotfiles
# the dotfile destination
tmpd=`mktemp -d --suffix='-dotdrop-tests'`
# create the config file
cfg="${tmps}/config.yaml"
cat > ${cfg} << _EOF
config:
backup: false
create: true
dotpath: dotfiles
link_by_default: true
dotfiles:
f_link:
dst: ${tmpd}/abc
src: abc
link: true
f_link1:
dst: ${tmpd}/abc
src: abc
link: true
f_nolink:
dst: ${tmpd}/abc
src: abc
link: false
f_nolink1:
dst: ${tmpd}/abc
src: abc
link: false
f_children:
dst: ${tmpd}/abc
src: abc
link_children: true
f_children2:
dst: ${tmpd}/abc
src: abc
link_children: true
f_children3:
dst: ${tmpd}/abc
src: abc
link_children: false
profiles:
p1:
dotfiles:
- f_link
- f_nolink
- f_nolink1
- f_children
- f_children2
- f_children3
_EOF
cat ${cfg}
# create the dotfiles
echo "test" > ${tmps}/dotfiles/abc
echo "test" > ${tmpd}/abc
# compare
cd ${ddpath} | ${bin} compare -c ${cfg} -p p1
# install
#cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
cat ${cfg}
# fail if find some of these entries
echo "========> test for bad entries"
set +e
grep 'link_children: true' ${cfg} >/dev/null && exit 1
grep 'link_children: false' ${cfg} >/dev/null && exit 1
grep 'link: true' ${cfg} >/dev/null && exit 1
grep 'link: false' ${cfg} >/dev/null && exit 1
grep 'link_by_default: true' ${cfg} >/dev/null && exit 1
grep 'link_by_default: false' ${cfg} >/dev/null && exit 1
set -e
# test values have been correctly updated
echo "========> test for updated entries"
dotfiles=`cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 | grep -v '^ '`
echo "${dotfiles}" | grep '^f_link ' | grep ', link: link)'
echo "${dotfiles}" | grep '^f_nolink ' | grep ', link: nolink)'
echo "${dotfiles}" | grep '^f_nolink1 ' | grep ', link: nolink)'
echo "${dotfiles}" | grep '^f_children ' | grep ', link: link_children)'
echo "${dotfiles}" | grep '^f_children2 ' | grep ', link: link_children)'
echo "${dotfiles}" | grep '^f_children3 ' | grep ', link: nolink)'
## CLEANING
rm -rf ${tmps} ${tmpd}
echo "OK"
exit 0

130
tests-ng/import-link-children.sh Executable file
View File

@@ -0,0 +1,130 @@
#!/usr/bin/env bash
# author: deadc0de6 (https://github.com/deadc0de6)
# Copyright (c) 2017, deadc0de6
#
# test importing link_children
# returns 1 in case of error
#
# exit on first error
set -e
# all this crap to get current path
rl="readlink -f"
if ! ${rl} "${0}" >/dev/null 2>&1; then
rl="realpath"
if ! hash ${rl}; then
echo "\"${rl}\" not found !" && exit 1
fi
fi
cur=$(dirname "$(${rl} "${0}")")
#hash dotdrop >/dev/null 2>&1
#[ "$?" != "0" ] && echo "install dotdrop to run tests" && exit 1
#echo "called with ${1}"
# dotdrop path can be pass as argument
ddpath="${cur}/../"
[ "${1}" != "" ] && ddpath="${1}"
[ ! -d ${ddpath} ] && echo "ddpath \"${ddpath}\" is not a directory" && exit 1
export PYTHONPATH="${ddpath}:${PYTHONPATH}"
bin="python3 -m dotdrop.dotdrop"
echo "dotdrop path: ${ddpath}"
echo "pythonpath: ${PYTHONPATH}"
# get the helpers
source ${cur}/helpers
echo -e "\e[96m\e[1m==> RUNNING $(basename $BASH_SOURCE) <==\e[0m"
################################################################
# this is the test
################################################################
# the dotfile source
tmps=`mktemp -d --suffix='-dotdrop-tests'`
mkdir -p ${tmps}/dotfiles
# the dotfile destination
tmpd=`mktemp -d --suffix='-dotdrop-tests'`
# dotpath
dotpath="${tmps}/dotfiles"
mkdir -p ${dotpath}
# create the dotfile to import
dt="${tmpd}/directory"
mkdir -p ${dt}
# subdir
dtsub1="${dt}/sub1"
mkdir -p ${dtsub1}
dtsub2="${dt}/sub2"
mkdir -p ${dtsub2}
dtsub3="${dtsub1}/subsub1"
mkdir -p ${dtsub3}
# files
f1="${dt}/file"
subf1="${dtsub1}/file"
subf2="${dtsub2}/file"
subf3="${dtsub3}/file"
touch ${f1} ${subf1} ${subf2} ${subf3}
# create the config file
cfg="${tmps}/config.yaml"
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
dotfiles:
profiles:
_EOF
# import
cd ${ddpath} | ${bin} import -c ${cfg} -p p1 -V --link=link_children ${dt}
# check is set to link_children
line=$(cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V | grep "d_`basename ${dt}`")
echo ${line} | grep 'link: link_children'
# checks file exists in dotpath
[ ! -e ${dotpath}/${dt} ] && echo "dotfile not imported" && exit 1
[ ! -e ${dotpath}/${dtsub1} ] && echo "sub1 not found in dotpath" && exit 1
[ ! -e ${dotpath}/${dtsub2} ] && echo "sub2 not found in dotpath" && exit 1
[ ! -e ${dotpath}/${dtsub3} ] && echo "sub3 not found in dotpath" && exit 1
[ ! -e ${dotpath}/${f1} ] && echo "f1 not found in dotpath" && exit 1
[ ! -e ${dotpath}/${subf1} ] && echo "subf1 not found in dotpath" && exit 1
[ ! -e ${dotpath}/${subf2} ] && echo "subf2 not found in dotpath" && exit 1
[ ! -e ${dotpath}/${subf3} ] && echo "subf3 not found in dotpath" && exit 1
# checks file exists in fs
[ ! -e ${dt} ] && echo "dotfile not imported" && exit 1
[ ! -e ${dtsub1} ] && echo "sub1 not found in fs" && exit 1
[ ! -e ${dtsub2} ] && echo "sub2 not found in fs" && exit 1
[ ! -e ${dtsub3} ] && echo "sub3 not found in fs" && exit 1
[ ! -e ${f1} ] && echo "f1 not found in fs" && exit 1
[ ! -e ${subf1} ] && echo "subf1 not found in fs" && exit 1
[ ! -e ${subf2} ] && echo "subf2 not found in fs" && exit 1
[ ! -e ${subf3} ] && echo "subf3 not found in fs" && exit 1
# install
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
# checks file have correct type in fs
[ ! -h ${f1} ] && echo "f1 is not a symlink" && exit 1
[ -h ${subf1} ] && echo "subf1 is not a regular file" && exit 1
[ -h ${subf2} ] && echo "subf2 is not a regular file" && exit 1
[ -h ${subf3} ] && echo "subf3 is not a regular file" && exit 1
[ ! -h ${dtsub1} ] && echo "dtsub1 is not a symlink" && exit 1
[ ! -h ${dtsub2} ] && echo "dtsub2 is not a symlink" && exit 1
[ -h ${dtsub3} ] && echo "dtsub3 is not a regular directory" && exit 1
## CLEANING
rm -rf ${tmps} ${tmpd}
echo "OK"
exit 0

156
tests-ng/inst-link-default.sh Executable file
View File

@@ -0,0 +1,156 @@
#!/usr/bin/env bash
# author: deadc0de6 (https://github.com/deadc0de6)
# Copyright (c) 2017, deadc0de6
#
# test link_dotfile_default
# returns 1 in case of error
#
# exit on first error
set -e
# all this crap to get current path
rl="readlink -f"
if ! ${rl} "${0}" >/dev/null 2>&1; then
rl="realpath"
if ! hash ${rl}; then
echo "\"${rl}\" not found !" && exit 1
fi
fi
cur=$(dirname "$(${rl} "${0}")")
#hash dotdrop >/dev/null 2>&1
#[ "$?" != "0" ] && echo "install dotdrop to run tests" && exit 1
#echo "called with ${1}"
# dotdrop path can be pass as argument
ddpath="${cur}/../"
[ "${1}" != "" ] && ddpath="${1}"
[ ! -d ${ddpath} ] && echo "ddpath \"${ddpath}\" is not a directory" && exit 1
export PYTHONPATH="${ddpath}:${PYTHONPATH}"
bin="python3 -m dotdrop.dotdrop"
echo "dotdrop path: ${ddpath}"
echo "pythonpath: ${PYTHONPATH}"
# get the helpers
source ${cur}/helpers
echo -e "\e[96m\e[1m==> RUNNING $(basename $BASH_SOURCE) <==\e[0m"
################################################################
# this is the test
################################################################
# the dotfile source
tmps=`mktemp -d --suffix='-dotdrop-tests'`
mkdir -p ${tmps}/dotfiles
# the dotfile destination
tmpd=`mktemp -d --suffix='-dotdrop-tests'`
#echo "dotfile destination: ${tmpd}"
# create the dotfile
mkdir -p ${tmps}/dotfiles/abc
echo "test link_dotfile_default 1" > ${tmps}/dotfiles/abc/file1
echo "test link_dotfile_default 2" > ${tmps}/dotfiles/abc/file2
# create a shell script
# create the config file
cfg="${tmps}/config.yaml"
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_dotfile_default: nolink
dotfiles:
d_abc:
dst: ${tmpd}/abc
src: abc
profiles:
p1:
dotfiles:
- d_abc
_EOF
#cat ${cfg}
# install
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
#cat ${cfg}
# ensure exists and is not link
[ ! -d ${tmpd}/abc ] && echo "not a directory" && exit 1
[ -h ${tmpd}/abc ] && echo "not a regular file" && exit 1
[ ! -e ${tmpd}/abc/file1 ] && echo "not exist" && exit 1
[ -h ${tmpd}/abc/file1 ] && echo "not a regular file" && exit 1
[ ! -e ${tmpd}/abc/file2 ] && echo "not exist" && exit 1
[ -h ${tmpd}/abc/file2 ] && echo "not a regular file" && exit 1
rm -rf ${tmpd}/abc
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_dotfile_default: link
dotfiles:
d_abc:
dst: ${tmpd}/abc
src: abc
profiles:
p1:
dotfiles:
- d_abc
_EOF
# install
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
#cat ${cfg}
# ensure exists and parent is a link
[ ! -e ${tmpd}/abc ] && echo "not exist" && exit 1
[ ! -h ${tmpd}/abc ] && echo "not a symlink" && exit 1
[ ! -e ${tmpd}/abc/file1 ] && echo "not exist" && exit 1
[ -h ${tmpd}/abc/file1 ] && echo "not a regular file" && exit 1
[ ! -e ${tmpd}/abc/file2 ] && echo "not exist" && exit 1
[ -h ${tmpd}/abc/file2 ] && echo "not a regular file" && exit 1
rm -rf ${tmpd}/abc
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_dotfile_default: link_children
dotfiles:
d_abc:
dst: ${tmpd}/abc
src: abc
profiles:
p1:
dotfiles:
- d_abc
_EOF
# install
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
#cat ${cfg}
# ensure exists and children are links
[ ! -e ${tmpd}/abc ] && echo "not exist" && exit 1
[ -h ${tmpd}/abc ] && echo "not a regular file" && exit 1
[ ! -e ${tmpd}/abc/file1 ] && echo "not exist" && exit 1
[ ! -h ${tmpd}/abc/file1 ] && echo "not a symlink" && exit 1
[ ! -e ${tmpd}/abc/file2 ] && echo "not exist" && exit 1
[ ! -h ${tmpd}/abc/file2 ] && echo "not a symlink" && exit 1
rm -rf ${tmpd}/abc
## CLEANING
rm -rf ${tmps} ${tmpd} ${scr}
echo "OK"
exit 0

View File

@@ -104,9 +104,11 @@ cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
#cat ${tmpd}/abc #cat ${tmpd}/abc
grep '^this should exist' ${tmpd}/abc >/dev/null grep '^this should exist' ${tmpd}/abc >/dev/null
grep -v '^this should not exist' ${tmpd}/abc >/dev/null
grep '^this should exist too' ${tmpd}/abc >/dev/null grep '^this should exist too' ${tmpd}/abc >/dev/null
grep -v '^this should not exist either' ${tmpd}/abc >/dev/null set +e
grep '^this should not exist' ${tmpd}/abc >/dev/null && exit 1
grep '^this should not exist either' ${tmpd}/abc >/dev/null && exit 1
set -e
#cat ${tmpd}/abc #cat ${tmpd}/abc

107
tests-ng/link-import-default.sh Executable file
View File

@@ -0,0 +1,107 @@
#!/usr/bin/env bash
# author: deadc0de6 (https://github.com/deadc0de6)
# Copyright (c) 2019, deadc0de6
#
# test the use of the keyword "link_on_import"
# returns 1 in case of error
#
# exit on first error
set -e
# all this crap to get current path
rl="readlink -f"
if ! ${rl} "${0}" >/dev/null 2>&1; then
rl="realpath"
if ! hash ${rl}; then
echo "\"${rl}\" not found !" && exit 1
fi
fi
cur=$(dirname "$(${rl} "${0}")")
#hash dotdrop >/dev/null 2>&1
#[ "$?" != "0" ] && echo "install dotdrop to run tests" && exit 1
#echo "called with ${1}"
# dotdrop path can be pass as argument
ddpath="${cur}/../"
[ "${1}" != "" ] && ddpath="${1}"
[ ! -d ${ddpath} ] && echo "ddpath \"${ddpath}\" is not a directory" && exit 1
export PYTHONPATH="${ddpath}:${PYTHONPATH}"
bin="python3 -m dotdrop.dotdrop"
echo "dotdrop path: ${ddpath}"
echo "pythonpath: ${PYTHONPATH}"
# get the helpers
source ${cur}/helpers
echo -e "\e[96m\e[1m==> RUNNING $(basename $BASH_SOURCE) <==\e[0m"
################################################################
# this is the test
################################################################
# the dotfile source
tmps=`mktemp -d --suffix='-dotdrop-tests'`
mkdir -p ${tmps}/dotfiles
# the dotfile destination
tmpd=`mktemp -d --suffix='-dotdrop-tests'`
# create the config file
cfg="${tmps}/config.yaml"
# create the source
echo "abc" > ${tmpd}/abc
# import with nolink by default
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_on_import: nolink
dotfiles:
profiles:
_EOF
# import
cd ${ddpath} | ${bin} import -c ${cfg} -p p1 -V ${tmpd}/abc
# checks
inside="${tmps}/dotfiles/${tmpd}/abc"
[ ! -e ${inside} ] && exit 1
set +e
cat ${cfg} | grep 'link:' && exit 1
set -e
# import with parent by default
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_on_import: link
dotfiles:
profiles:
_EOF
# import
cd ${ddpath} | ${bin} import -c ${cfg} -p p1 -V ${tmpd}/abc
# checks
inside="${tmps}/dotfiles/${tmpd}/abc"
[ ! -e ${inside} ] && exit 1
cat ${cfg}
cat ${cfg} | grep 'link: link' >/dev/null
## CLEANING
rm -rf ${tmps} ${tmpd}
echo "OK"
exit 0

479
tests-ng/link-value-tests.sh Executable file
View File

@@ -0,0 +1,479 @@
#!/usr/bin/env bash
# author: deadc0de6 (https://github.com/deadc0de6)
# Copyright (c) 2019, deadc0de6
#
# test the behavior when playing with link_dotfile_default
# and link_on_import on import
# returns 1 in case of error
#
# exit on first error
set -e
# all this crap to get current path
rl="readlink -f"
if ! ${rl} "${0}" >/dev/null 2>&1; then
rl="realpath"
if ! hash ${rl}; then
echo "\"${rl}\" not found !" && exit 1
fi
fi
cur=$(dirname "$(${rl} "${0}")")
#hash dotdrop >/dev/null 2>&1
#[ "$?" != "0" ] && echo "install dotdrop to run tests" && exit 1
#echo "called with ${1}"
# dotdrop path can be pass as argument
ddpath="${cur}/../"
[ "${1}" != "" ] && ddpath="${1}"
[ ! -d ${ddpath} ] && echo "ddpath \"${ddpath}\" is not a directory" && exit 1
export PYTHONPATH="${ddpath}:${PYTHONPATH}"
bin="python3 -m dotdrop.dotdrop"
echo "dotdrop path: ${ddpath}"
echo "pythonpath: ${PYTHONPATH}"
# get the helpers
source ${cur}/helpers
echo -e "\e[96m\e[1m==> RUNNING $(basename $BASH_SOURCE) <==\e[0m"
################################################################
# this is the test
################################################################
# the dotfile source
tmps=`mktemp -d --suffix='-dotdrop-tests'`
mkdir -p ${tmps}/dotfiles
# the dotfile destination
tmpd=`mktemp -d --suffix='-dotdrop-tests'`
# create the config file
cfg="${tmps}/config.yaml"
# ----------------------------------------------------------
echo -e "\n======> import with all default"
# create the source
rm -rf ${tmpd}/qwert
echo "test" > ${tmpd}/qwert
# clean
rm -rf ${tmps}/dotfiles
mkdir -p ${tmps}/dotfiles
# config file
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
dotfiles:
profiles:
_EOF
# import
df="${tmpd}/qwert"
cd ${ddpath} | ${bin} import -c ${cfg} -p p1 ${df} -V
# checks
cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V
line=$(cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V | grep "f_`basename ${df}`")
echo ${line} | grep 'link: nolink'
# try to install
rm -rf ${tmpd}/qwert
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
[ ! -e ${df} ] && echo "does not exist" && exit 1
[ -h ${df} ] && echo "is symlink" && exit 1
# ----------------------------------------------------------
echo -e "\n======> import with link_on_import=nolink and link_dotfile_default=nolink"
# create the source
rm -rf ${tmpd}/qwert
echo "test" > ${tmpd}/qwert
# clean
rm -rf ${tmps}/dotfiles
mkdir -p ${tmps}/dotfiles
# config file
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_on_import: nolink
link_dotfile_default: nolink
dotfiles:
profiles:
_EOF
# import
df="${tmpd}/qwert"
cd ${ddpath} | ${bin} import -c ${cfg} -p p1 ${df} -V
# checks
cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V
line=$(cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V | grep "f_`basename ${df}`")
echo ${line} | grep 'link: nolink'
# try to install
rm -rf ${tmpd}/qwert
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
[ ! -e ${df} ] && echo "does not exist" && exit 1
[ -h ${df} ] && echo "is symlink" && exit 1
# ----------------------------------------------------------
echo -e "\n======> import with link_on_import=nolink and link_dotfile_default=nolink and --link=nolink"
# create the source
rm -rf ${tmpd}/qwert
echo "test" > ${tmpd}/qwert
# clean
rm -rf ${tmps}/dotfiles
mkdir -p ${tmps}/dotfiles
# config file
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_on_import: nolink
link_dotfile_default: nolink
dotfiles:
profiles:
_EOF
# import
df="${tmpd}/qwert"
cd ${ddpath} | ${bin} import -c ${cfg} -p p1 ${df} -V --link=nolink
# checks
cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V
line=$(cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V | grep "f_`basename ${df}`")
echo ${line} | grep 'link: nolink'
# try to install
rm -rf ${tmpd}/qwert
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
[ ! -e ${df} ] && echo "does not exist" && exit 1
[ -h ${df} ] && echo "is symlink" && exit 1
# ----------------------------------------------------------
echo -e "\n======> import with link_on_import=nolink and link_dotfile_default=nolink and --link=link"
# create the source
rm -rf ${tmpd}/qwert
echo "test" > ${tmpd}/qwert
# clean
rm -rf ${tmps}/dotfiles
mkdir -p ${tmps}/dotfiles
# config file
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_on_import: nolink
link_dotfile_default: nolink
dotfiles:
profiles:
_EOF
# import
df="${tmpd}/qwert"
cd ${ddpath} | ${bin} import -c ${cfg} -p p1 ${df} -V --link=link
# checks
cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V
line=$(cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V | grep "f_`basename ${df}`")
echo ${line} | grep 'link: link'
# try to install
rm -rf ${tmpd}/qwert
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
[ ! -e ${df} ] && echo "does not exist" && exit 1
[ ! -h ${df} ] && echo "not symlink" && exit 1
# ----------------------------------------------------------
echo -e "\n======> import with link_on_import=link and link_dotfile_default=nolink"
# create the source
rm -rf ${tmpd}/qwert
echo "test" > ${tmpd}/qwert
# clean
rm -rf ${tmps}/dotfiles
mkdir -p ${tmps}/dotfiles
# config file
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_on_import: link
link_dotfile_default: nolink
dotfiles:
profiles:
_EOF
# import
df="${tmpd}/qwert"
cd ${ddpath} | ${bin} import -c ${cfg} -p p1 ${df} -V
# checks
cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V
line=$(cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V | grep "f_`basename ${df}`")
echo ${line} | grep 'link: link'
# try to install
rm -rf ${tmpd}/qwert
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
[ ! -e ${df} ] && echo "does not exist" && exit 1
[ ! -h ${df} ] && echo "not symlink" && exit 1
# ----------------------------------------------------------
echo -e "\n======> import with link_on_import=link and link_dotfile_default=nolink and --link=nolink"
# create the source
rm -rf ${tmpd}/qwert
echo "test" > ${tmpd}/qwert
# clean
rm -rf ${tmps}/dotfiles
mkdir -p ${tmps}/dotfiles
# config file
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_on_import: link
link_dotfile_default: nolink
dotfiles:
profiles:
_EOF
# import
df="${tmpd}/qwert"
cd ${ddpath} | ${bin} import -c ${cfg} -p p1 ${df} -V --link=nolink
# checks
cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V
line=$(cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V | grep "f_`basename ${df}`")
echo ${line} | grep 'link: nolink'
# try to install
rm -rf ${tmpd}/qwert
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
[ ! -e ${df} ] && echo "does not exist" && exit 1
[ -h ${df} ] && echo "is symlink" && exit 1
# ----------------------------------------------------------
echo -e "\n======> import with link_on_import=nolink and link_dotfile_default=link"
# create the source
rm -rf ${tmpd}/qwert
echo "test" > ${tmpd}/qwert
# clean
rm -rf ${tmps}/dotfiles
mkdir -p ${tmps}/dotfiles
# config file
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_on_import: nolink
link_dotfile_default: link
dotfiles:
profiles:
_EOF
# import
df="${tmpd}/qwert"
cd ${ddpath} | ${bin} import -c ${cfg} -p p1 ${df} -V --link=nolink
# checks
cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V
line=$(cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V | grep "f_`basename ${df}`")
echo ${line} | grep 'link: nolink'
# try to install
rm -rf ${tmpd}/qwert
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
[ ! -e ${df} ] && echo "does not exist" && exit 1
[ -h ${df} ] && echo "is symlink" && exit 1
# ----------------------------------------------------------
echo -e "\n======> import with link_on_import=link and link_dotfile_default=nolink and --link=nolink"
# create the source
rm -rf ${tmpd}/qwert
echo "test" > ${tmpd}/qwert
# clean
rm -rf ${tmps}/dotfiles
mkdir -p ${tmps}/dotfiles
# config file
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_on_import: link
link_dotfile_default: nolink
dotfiles:
profiles:
_EOF
# import
df="${tmpd}/qwert"
cd ${ddpath} | ${bin} import -c ${cfg} -p p1 ${df} -V --link=nolink
# checks
cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V
line=$(cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V | grep "f_`basename ${df}`")
echo ${line} | grep 'link: nolink'
# try to install
rm -rf ${tmpd}/qwert
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
[ ! -e ${df} ] && echo "does not exist" && exit 1
[ -h ${df} ] && echo "is symlink" && exit 1
# ----------------------------------------------------------
echo -e "\n======> import with all default and --link=link"
# create the source
rm -rf ${tmpd}/qwert
echo "test" > ${tmpd}/qwert
# clean
rm -rf ${tmps}/dotfiles
mkdir -p ${tmps}/dotfiles
# config file
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
dotfiles:
profiles:
_EOF
# import
df="${tmpd}/qwert"
cd ${ddpath} | ${bin} import -c ${cfg} --link=link -p p1 ${df} -V
# checks
cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V
line=$(cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V | grep "f_`basename ${df}`")
echo ${line} | grep 'link: link'
# try to install
rm -rf ${tmpd}/qwert
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
[ ! -e ${df} ] && echo "does not exist" && exit 1
[ ! -h ${df} ] && echo "not a symlink" && exit 1
# ----------------------------------------------------------
echo -e "\n======> import with all default and --link=link_children"
# create the source
rm -rf ${tmpd}/qwert
echo "test" > ${tmpd}/qwert
# clean
rm -rf ${tmps}/dotfiles
mkdir -p ${tmps}/dotfiles
# config file
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
dotfiles:
profiles:
_EOF
# import
df="${tmpd}/qwert"
set +e
cd ${ddpath} | ${bin} import -c ${cfg} --link=link_children -p p1 ${df} -V
[ "$?" = "0" ] && echo "link_children with file should fail" && exit 1
set -e
# ----------------------------------------------------------
echo -e "\n======> import with all default and --link=link_children"
# create the source
rm -rf ${tmpd}/qwert
mkdir -p ${tmpd}/qwert
echo "test" > ${tmpd}/qwert/file
mkdir -p ${tmpd}/qwert/directory
echo "test" > ${tmpd}/qwert/directory/file
# clean
rm -rf ${tmps}/dotfiles
mkdir -p ${tmps}/dotfiles
# config file
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
dotfiles:
profiles:
_EOF
# import
df="${tmpd}/qwert"
cd ${ddpath} | ${bin} import -c ${cfg} --link=link_children -p p1 ${df} -V
# checks
cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V
line=$(cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V | grep "d_`basename ${df}`")
echo ${line} | grep 'link: link_children'
# try to install
rm -rf ${tmpd}/qwert
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
[ ! -e ${df} ] && echo "does not exist" && exit 1
[ -h ${df} ] && echo "is a symlink" && exit 1
[ ! -h ${df}/file ] && echo "file is not a symlink" && exit 1
[ ! -h ${df}/directory ] && echo "directory is not a symlink" && exit 1
[ -h ${df}/directory/file ] && echo "directory/file is a symlink" && exit 1
echo -e "\n======> import with link_on_import=link_children and link_dotfile_default=nolink"
# create the source
rm -rf ${tmpd}/qwert
mkdir -p ${tmpd}/qwert
echo "test" > ${tmpd}/qwert/file
mkdir -p ${tmpd}/qwert/directory
echo "test" > ${tmpd}/qwert/directory/file
# clean
rm -rf ${tmps}/dotfiles
mkdir -p ${tmps}/dotfiles
# config file
cat > ${cfg} << _EOF
config:
backup: true
create: true
dotpath: dotfiles
link_on_import: link_children
link_dotfile_default: nolink
dotfiles:
profiles:
_EOF
# import
df="${tmpd}/qwert"
cd ${ddpath} | ${bin} import -c ${cfg} -p p1 ${df} -V
# checks
cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V
line=$(cd ${ddpath} | ${bin} listfiles -c ${cfg} -p p1 -V | grep "d_`basename ${df}`")
echo ${line} | grep 'link: link_children'
# try to install
rm -rf ${tmpd}/qwert
cd ${ddpath} | ${bin} install -f -c ${cfg} -p p1 -V
[ ! -e ${df} ] && echo "does not exist" && exit 1
[ -h ${df} ] && echo "is a symlink" && exit 1
[ ! -h ${df}/file ] && echo "file is not a symlink" && exit 1
[ ! -h ${df}/directory ] && echo "directory is not a symlink" && exit 1
[ -h ${df}/directory/file ] && echo "directory/file is a symlink" && exit 1
## CLEANING
rm -rf ${tmps} ${tmpd}
echo "OK"
exit 0

View File

@@ -27,6 +27,7 @@ set -e
# comment this to get debug info # comment this to get debug info
export DOTDROP_FORCE_NODEBUG= export DOTDROP_FORCE_NODEBUG=
export DOTDROP_NOBANNER=
# execute tests with coverage # execute tests with coverage
PYTHONPATH=dotdrop ${nosebin} -s --with-coverage --cover-package=dotdrop PYTHONPATH=dotdrop ${nosebin} -s --with-coverage --cover-package=dotdrop

View File

@@ -89,7 +89,7 @@ def _fake_args():
args['--force'] = False args['--force'] = False
args['--nodiff'] = False args['--nodiff'] = False
args['--showdiff'] = True args['--showdiff'] = True
args['--inv-link'] = False args['--link'] = 'nolink'
args['--template'] = False args['--template'] = False
args['--temp'] = False args['--temp'] = False
args['<key>'] = [] args['<key>'] = []
@@ -118,14 +118,13 @@ def load_options(confpath, profile):
args['--cfg'] = confpath args['--cfg'] = confpath
args['--profile'] = profile args['--profile'] = profile
# and get the options # and get the options
# TODO need to patch options
o = Options(args=args) o = Options(args=args)
o.profile = profile o.profile = profile
o.dry = False o.dry = False
o.profile = profile o.profile = profile
o.safe = True o.safe = True
o.install_diff = True o.install_diff = True
o.link = LinkTypes.NOLINK.value o.import_link = LinkTypes.NOLINK
o.install_showdiff = True o.install_showdiff = True
o.debug = True o.debug = True
if ENV_NODEBUG in os.environ: if ENV_NODEBUG in os.environ:

View File

@@ -6,11 +6,15 @@ basic unittest for the config parser
import unittest import unittest
from unittest.mock import patch
import os import os
import yaml import yaml
from dotdrop.config import Cfg from dotdrop.config import Cfg
from tests.helpers import get_tempdir, clean, create_fake_config from dotdrop.options import Options
from dotdrop.linktypes import LinkTypes
from tests.helpers import get_tempdir, clean, \
create_fake_config, _fake_args
class TestConfig(unittest.TestCase): class TestConfig(unittest.TestCase):
@@ -45,6 +49,84 @@ class TestConfig(unittest.TestCase):
self.assertTrue(conf._is_valid()) self.assertTrue(conf._is_valid())
self.assertTrue(conf.dump() != '') self.assertTrue(conf.dump() != '')
def test_def_link(self):
self._test_link_import('nolink', LinkTypes.LINK, 'link')
self._test_link_import('nolink', LinkTypes.NOLINK, 'nolink')
self._test_link_import('nolink',
LinkTypes.LINK_CHILDREN,
'link_children')
self._test_link_import('link', LinkTypes.LINK, 'link')
self._test_link_import('link', LinkTypes.NOLINK, 'nolink')
self._test_link_import('link',
LinkTypes.LINK_CHILDREN,
'link_children')
self._test_link_import('link_children', LinkTypes.LINK, 'link')
self._test_link_import('link_children', LinkTypes.NOLINK, 'nolink')
self._test_link_import('link_children', LinkTypes.LINK_CHILDREN,
'link_children')
self._test_link_import_fail('whatever')
@patch('dotdrop.config.open', create=True)
@patch('dotdrop.config.os.path.exists', create=True)
def _test_link_import(self, cfgstring, expected,
cliargs, mock_exists, mock_open):
data = '''
config:
backup: true
create: true
dotpath: dotfiles
banner: true
longkey: false
keepdot: false
link_on_import: {}
link_dotfile_default: nolink
dotfiles:
profiles:
'''.format(cfgstring)
mock_open.side_effect = [
unittest.mock.mock_open(read_data=data).return_value
]
mock_exists.return_value = True
args = _fake_args()
args['--profile'] = 'p1'
args['--cfg'] = 'mocked'
args['--link'] = cliargs
o = Options(args=args)
self.assertTrue(o.import_link == expected)
@patch('dotdrop.config.open', create=True)
@patch('dotdrop.config.os.path.exists', create=True)
def _test_link_import_fail(self, value, mock_exists, mock_open):
data = '''
config:
backup: true
create: true
dotpath: dotfiles
banner: true
longkey: false
keepdot: false
link_on_import: {}
link_dotfile_default: nolink
dotfiles:
profiles:
'''.format(value)
mock_open.side_effect = [
unittest.mock.mock_open(read_data=data).return_value
]
mock_exists.return_value = True
args = _fake_args()
args['--profile'] = 'p1'
args['--cfg'] = 'mocked'
with self.assertRaisesRegex(ValueError, 'config is not valid'):
o = Options(args=args)
print(o.import_link)
def test_include(self): def test_include(self):
tmp = get_tempdir() tmp = get_tempdir()
self.assertTrue(os.path.exists(tmp)) self.assertTrue(os.path.exists(tmp))

View File

@@ -112,11 +112,11 @@ class TestImport(unittest.TestCase):
o.import_path = dfiles o.import_path = dfiles
cmd_importer(o) cmd_importer(o)
# import symlink # import symlink
o.link = LinkTypes.PARENTS o.import_link = LinkTypes.LINK
sfiles = [dotfile6, dotfile7] sfiles = [dotfile6, dotfile7]
o.import_path = sfiles o.import_path = sfiles
cmd_importer(o) cmd_importer(o)
o.link = LinkTypes.NOLINK o.import_link = LinkTypes.NOLINK
# reload the config # reload the config
o = load_options(confpath, profile) o = load_options(confpath, profile)
@@ -191,12 +191,6 @@ class TestImport(unittest.TestCase):
sub4) sub4)
self.assertTrue(os.path.exists(s4)) self.assertTrue(os.path.exists(s4))
# test symlink on filesystem
self.assertTrue(os.path.islink(dotfile6))
self.assertTrue(os.path.realpath(dotfile6) == indt6)
self.assertTrue(os.path.islink(dotfile7))
self.assertTrue(os.path.realpath(dotfile7) == indt7)
cmd_list_profiles(o) cmd_list_profiles(o)
cmd_list_files(o) cmd_list_files(o)

View File

@@ -17,8 +17,8 @@ from dotdrop.installer import Installer
from dotdrop.action import Action from dotdrop.action import Action
from dotdrop.dotdrop import cmd_install from dotdrop.dotdrop import cmd_install
from dotdrop.options import BACKUP_SUFFIX from dotdrop.options import BACKUP_SUFFIX
from dotdrop.linktypes import LinkTypes
from dotdrop.utils import header from dotdrop.utils import header
from dotdrop.linktypes import LinkTypes
class TestInstall(unittest.TestCase): class TestInstall(unittest.TestCase):
@@ -57,12 +57,7 @@ exec bspwm
f.write(' {}:\n'.format(d.key)) f.write(' {}:\n'.format(d.key))
f.write(' dst: {}\n'.format(d.dst)) f.write(' dst: {}\n'.format(d.dst))
f.write(' src: {}\n'.format(d.src)) f.write(' src: {}\n'.format(d.src))
if d.link == LinkTypes.CHILDREN: f.write(' link: {}\n'.format(d.link.name.lower()))
f.write(' link_children: {}\n'
.format(str(d.link == LinkTypes.CHILDREN).lower()))
else:
f.write(' link: {}\n'
.format(str(d.link == LinkTypes.PARENTS).lower()))
if len(d.actions) > 0: if len(d.actions) > 0:
f.write(' actions:\n') f.write(' actions:\n')
for action in d.actions: for action in d.actions:
@@ -122,7 +117,8 @@ exec bspwm
f5, c5 = create_random_file(tmp) f5, c5 = create_random_file(tmp)
dst5 = os.path.join(dst, get_string(6)) dst5 = os.path.join(dst, get_string(6))
self.addCleanup(clean, dst5) self.addCleanup(clean, dst5)
d5 = Dotfile(get_string(6), dst5, os.path.basename(f5), link=True) d5 = Dotfile(get_string(6), dst5,
os.path.basename(f5), link=LinkTypes.LINK)
# create the dotfile directories in dotdrop # create the dotfile directories in dotdrop
dir1 = create_dir(os.path.join(tmp, get_string(6))) dir1 = create_dir(os.path.join(tmp, get_string(6)))
@@ -148,7 +144,8 @@ exec bspwm
sub4, _ = create_random_file(dir2) sub4, _ = create_random_file(dir2)
self.assertTrue(os.path.exists(sub4)) self.assertTrue(os.path.exists(sub4))
# make up the dotfile # make up the dotfile
d7 = Dotfile(get_string(6), dst7, os.path.basename(dir2), link=True) d7 = Dotfile(get_string(6), dst7,
os.path.basename(dir2), link=LinkTypes.LINK)
# to test actions # to test actions
value = get_string(12) value = get_string(12)