cromwell_symlink.py 2.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576
  1. import argparse
  2. import logging
  3. import os
  4. import sys
  5. from .. import io
  6. LOG = logging.getLogger()
  7. def symlink(actual, symbolic=None, force=True):
  8. """Symlink into cwd, relatively.
  9. symbolic name is basename(actual) if not provided.
  10. If not force, raise when already exists and does not match.
  11. But ignore symlink to self.
  12. """
  13. # COPIED VERBATIM FROM ./dazzler.py
  14. symbolic = os.path.basename(actual) if not symbolic else symbolic
  15. if os.path.abspath(actual) == os.path.abspath(symbolic):
  16. LOG.warning('Cannot symlink {!r} as {!r}, itself.'.format(actual, symbolic))
  17. return
  18. rel = os.path.relpath(actual)
  19. if force:
  20. LOG.info('ln -sf {} {}'.format(rel, symbolic))
  21. if os.path.lexists(symbolic):
  22. if os.readlink(symbolic) == rel:
  23. return
  24. else:
  25. os.unlink(symbolic)
  26. else:
  27. LOG.info('ln -s {} {}'.format(rel, symbolic))
  28. if os.path.lexists(symbolic):
  29. if os.readlink(symbolic) != rel:
  30. msg = '{!r} already exists as {!r}, not {!r}'.format(
  31. symbolic, os.readlink(symbolic), rel)
  32. raise Exception(msg)
  33. else:
  34. LOG.info('{!r} already points to {!r}'.format(symbolic, rel))
  35. return
  36. os.symlink(rel, symbolic)
  37. def run(input_fns):
  38. for fn in input_fns:
  39. symlink(fn)
  40. class HelpF(argparse.RawTextHelpFormatter, argparse.ArgumentDefaultsHelpFormatter):
  41. pass
  42. def parse_args(argv):
  43. description = 'Symlink into current directory. This helps keep command-lines short later.'
  44. epilog = ''
  45. parser = argparse.ArgumentParser(
  46. description=description,
  47. epilog=epilog,
  48. formatter_class=HelpF,
  49. )
  50. parser.add_argument(
  51. 'input_fns', nargs='*',
  52. help='These will be symlinked according to their basenames.')
  53. args = parser.parse_args(argv[1:])
  54. return args
  55. def main(argv=sys.argv):
  56. args = parse_args(argv)
  57. logging.basicConfig(level=logging.INFO)
  58. run(**vars(args))
  59. if __name__ == '__main__': # pragma: no cover
  60. main()