now correctly detects hard links
simplified check_mode simplified other file attribute handling in link mode made conditionals clearer Signed-off-by: Brian Coca <briancoca+dev@gmail.com>
This commit is contained in:
parent
a32f1cac8d
commit
0121b96b1a
1 changed files with 26 additions and 33 deletions
55
files/file
55
files/file
|
@ -132,15 +132,6 @@ EXAMPLES = '''
|
||||||
- file: src=/file/to/link/to dest=/path/to/symlink owner=foo group=foo state=link
|
- file: src=/file/to/link/to dest=/path/to/symlink owner=foo group=foo state=link
|
||||||
'''
|
'''
|
||||||
|
|
||||||
def dolink(src, path, state, module):
|
|
||||||
try:
|
|
||||||
if state == 'hard':
|
|
||||||
os.link(src,path)
|
|
||||||
else:
|
|
||||||
os.symlink(src, path)
|
|
||||||
except OSError, e:
|
|
||||||
module.fail_json(path=path, msg='Error while linking: %s' % str(e))
|
|
||||||
|
|
||||||
def main():
|
def main():
|
||||||
|
|
||||||
# FIXME: pass this around, should not use global
|
# FIXME: pass this around, should not use global
|
||||||
|
@ -203,7 +194,10 @@ def main():
|
||||||
prev_state = 'link'
|
prev_state = 'link'
|
||||||
elif os.path.isdir(path):
|
elif os.path.isdir(path):
|
||||||
prev_state = 'directory'
|
prev_state = 'directory'
|
||||||
|
elif os.stat(path).st_nlink > 1:
|
||||||
|
prev_state = 'hard'
|
||||||
else:
|
else:
|
||||||
|
# could be many other tings, but defaulting to file
|
||||||
prev_state = 'file'
|
prev_state = 'file'
|
||||||
|
|
||||||
if prev_state != 'absent' and state == 'absent':
|
if prev_state != 'absent' and state == 'absent':
|
||||||
|
@ -229,9 +223,7 @@ def main():
|
||||||
module.exit_json(path=path, changed=True)
|
module.exit_json(path=path, changed=True)
|
||||||
|
|
||||||
if prev_state != 'absent' and prev_state != state:
|
if prev_state != 'absent' and prev_state != state:
|
||||||
if force and prev_state == 'file' and state == 'link':
|
if not (force and prev_state == 'file' and state == 'link'):
|
||||||
pass
|
|
||||||
else:
|
|
||||||
module.fail_json(path=path, msg='refusing to convert between %s and %s for %s' % (prev_state, state, src))
|
module.fail_json(path=path, msg='refusing to convert between %s and %s for %s' % (prev_state, state, src))
|
||||||
|
|
||||||
if prev_state == 'absent' and state == 'absent':
|
if prev_state == 'absent' and state == 'absent':
|
||||||
|
@ -279,42 +271,43 @@ def main():
|
||||||
module.fail_json(path=path, src=src, msg='src file does not exist')
|
module.fail_json(path=path, src=src, msg='src file does not exist')
|
||||||
|
|
||||||
if prev_state == 'absent':
|
if prev_state == 'absent':
|
||||||
if module.check_mode:
|
|
||||||
module.exit_json(changed=True)
|
|
||||||
dolink(src, path, state, module)
|
|
||||||
changed = True
|
changed = True
|
||||||
elif prev_state == 'link':
|
elif prev_state == 'link':
|
||||||
old_src = os.readlink(path)
|
old_src = os.readlink(path)
|
||||||
if not os.path.isabs(old_src):
|
if not os.path.isabs(old_src):
|
||||||
old_src = os.path.join(os.path.dirname(path), old_src)
|
old_src = os.path.join(os.path.dirname(path), old_src)
|
||||||
if old_src != src:
|
if old_src != src:
|
||||||
if module.check_mode:
|
changed = True
|
||||||
module.exit_json(changed=True)
|
elif prev_state == 'hard':
|
||||||
os.unlink(path)
|
if not (state == 'hard' and os.stat(path).st_ino == os.stat(src).st_ino):
|
||||||
dolink(src, path, state, module)
|
if not force:
|
||||||
|
module.fail_json(dest=path, src=src, msg='Cannot link, different hard link exists at destination')
|
||||||
changed = True
|
changed = True
|
||||||
elif prev_state == 'file':
|
elif prev_state == 'file':
|
||||||
if not force:
|
if not force:
|
||||||
module.fail_json(dest=path, src=src, msg='Cannot link, file exists at destination')
|
module.fail_json(dest=path, src=src, msg='Cannot link, file exists at destination')
|
||||||
else:
|
|
||||||
if module.check_mode:
|
|
||||||
module.exit_json(changed=True)
|
|
||||||
os.unlink(path)
|
|
||||||
dolink(src, path, state, module)
|
|
||||||
changed = True
|
changed = True
|
||||||
else:
|
else:
|
||||||
module.fail_json(dest=path, src=src, msg='unexpected position reached')
|
module.fail_json(dest=path, src=src, msg='unexpected position reached')
|
||||||
|
|
||||||
# set modes owners and context as needed
|
if changed and not module.check_mode:
|
||||||
|
if prev_state != 'absent':
|
||||||
file_args = module.load_file_common_arguments(module.params)
|
try:
|
||||||
changed = module.set_context_if_different(path, file_args['secontext'], changed)
|
os.unlink(path)
|
||||||
changed = module.set_owner_if_different(path, file_args['owner'], changed)
|
except OSError, e:
|
||||||
changed = module.set_group_if_different(path, file_args['group'], changed)
|
module.fail_json(path=path, msg='Error while removing existing target: %s' % str(e))
|
||||||
changed = module.set_mode_if_different(path, file_args['mode'], changed)
|
try:
|
||||||
|
if state == 'hard':
|
||||||
|
os.link(src,path)
|
||||||
|
else:
|
||||||
|
os.symlink(src, path)
|
||||||
|
except OSError, e:
|
||||||
|
module.fail_json(path=path, msg='Error while linking: %s' % str(e))
|
||||||
|
|
||||||
|
changed = module.set_file_attributes_if_different(file_args, changed)
|
||||||
module.exit_json(dest=path, src=src, changed=changed)
|
module.exit_json(dest=path, src=src, changed=changed)
|
||||||
|
|
||||||
|
else:
|
||||||
module.fail_json(path=path, msg='unexpected position reached')
|
module.fail_json(path=path, msg='unexpected position reached')
|
||||||
|
|
||||||
# this is magic, see lib/ansible/module_common.py
|
# this is magic, see lib/ansible/module_common.py
|
||||||
|
|
Loading…
Reference in a new issue