git.py 2.1 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980
  1. import os
  2. import tempfile
  3. import logging
  4. from dulwich import index
  5. from dulwich.client import get_transport_and_path
  6. from dulwich.repo import Repo
  7. logger = logging.getLogger(__name__)
  8. def clone_branch(repo_url, branch="master", folder=None):
  9. return clone(repo_url, 'refs/heads/' + branch, folder)
  10. def clone_tag(repo_url, tag, folder=None):
  11. return clone(repo_url, 'refs/tags/' + tag, folder)
  12. def checkout(rep, ref=None):
  13. is_commit = False
  14. if ref is None:
  15. ref = 'refs/heads/master'
  16. elif not ref.startswith('refs/'):
  17. is_commit = True
  18. elif ref.startswith('refs/tags'):
  19. ref = rep.ref(ref)
  20. is_commit = True
  21. if is_commit:
  22. rep['HEAD'] = rep.commit(ref)
  23. else:
  24. rep['HEAD'] = rep.refs[ref]
  25. indexfile = rep.index_path()
  26. tree = rep["HEAD"].tree
  27. index.build_index_from_tree(rep.path, indexfile, rep.object_store, tree)
  28. return rep.path
  29. def pull(origin, rep, ref=None):
  30. clone(origin, ref, None, rep)
  31. return rep, rep.path
  32. def clone(repo_url, ref=None, folder=None, rep=None):
  33. is_commit = False
  34. if ref is None:
  35. ref = 'refs/heads/master'
  36. elif not ref.startswith('refs/'):
  37. is_commit = True
  38. logger.debug("clone repo_url={0}, ref={1}".format(repo_url, ref))
  39. if not rep:
  40. if folder is None:
  41. folder = tempfile.mkdtemp()
  42. else:
  43. os.mkdir(folder)
  44. logger.debug("folder = {0}".format(folder))
  45. rep = Repo.init(folder)
  46. client, relative_path = get_transport_and_path(repo_url)
  47. logger.debug("client={0}".format(client))
  48. remote_refs = client.fetch(relative_path, rep)
  49. for k, v in remote_refs.iteritems():
  50. try:
  51. rep.refs.add_if_new(k, v)
  52. except:
  53. pass
  54. if ref.startswith('refs/tags'):
  55. ref = rep.ref(ref)
  56. is_commit = True
  57. if is_commit:
  58. rep['HEAD'] = rep.commit(ref)
  59. else:
  60. rep['HEAD'] = remote_refs[ref]
  61. indexfile = rep.index_path()
  62. tree = rep["HEAD"].tree
  63. index.build_index_from_tree(rep.path, indexfile, rep.object_store, tree)
  64. logger.debug("done")
  65. return rep, folder