def get_temp_project(origin=None, repo_path=BARE_REPO_PATH): if origin: prefix_path = get_repo_root() temp_repo_path = tempfile.mkdtemp(suffix=".git", prefix="test_", dir=prefix_path) project_name = temp_repo_path[len(prefix_path) + 1:][:-4] project = CodeDoubanProject.add(project_name, TEMP_PROJECT_OWNER, TEMP_PROJECT_DESCRIPTION, fork_from=origin.id, create_trac=False) return project prefix_path = get_repo_root() temp_repo_path = tempfile.mkdtemp(suffix=".git", prefix="test_", dir=prefix_path) project_name = temp_repo_path[len(prefix_path) + 1:][:-4] project = CodeDoubanProject.add(project_name, TEMP_PROJECT_OWNER, TEMP_PROJECT_DESCRIPTION) shutil.rmtree(temp_repo_path) repo = Jagare(repo_path) repo.clone(temp_repo_path, bare=True) return project
def test_merge_commits(self): repo = Jagare(self.path) BR = 'br_test_merge' path = self.get_temp_path() # repo has work-tree repo.clone(path, branch=BARE_REPO_OTHER_BRANCH) repo = Jagare(os.path.join(path, '.git')) ret = repo.create_branch(BR, BARE_REPO_OTHER_BRANCH) assert ret commit_something(path, branch=BR) repo.update_head(BARE_REPO_OTHER_BRANCH) merge_index = repo.merge_commits(repo.head.target.hex, BR) assert merge_index['has_conflicts'] is False
def test_merge_head(self): repo = Jagare(self.path) BR = 'br_test_merge' path = self.get_temp_path() # repo has work-tree repo.clone(path, branch=BARE_REPO_OTHER_BRANCH) repo = Jagare(os.path.join(path, '.git')) ret = repo.create_branch(BR, BARE_REPO_OTHER_BRANCH) assert ret commit_something(path, branch=BR) repo.update_head(BARE_REPO_OTHER_BRANCH) merge_result = repo.merge_head(BR) assert merge_result['is_fastforward']
def test_merge_commits(self): repo = Jagare(self.path) BR = 'br_test_merge' path = self.get_temp_path() # repo has work-tree repo.clone(path, branch=BARE_REPO_OTHER_BRANCH) repo = Jagare(os.path.join(path, '.git')) ret = repo.create_branch(BR, BARE_REPO_OTHER_BRANCH) assert ret commit_something(path, branch=BR) repo.update_head(BARE_REPO_OTHER_BRANCH) merge_index = repo.merge_commits(repo.head.target.hex, BR) assert merge_index['has_conflicts'] == False
def test_delete(self): repo = Jagare(self.path) path = self.get_temp_path() clone_repo = repo.clone(path, bare=True) clone_repo.delete_branch('chinese') branches = clone_repo.branches assert 'chinese' in repo.branches assert 'chinese' not in branches assert 'master' in branches
def test_mirror(self): repo = Jagare(self.path) path = self.get_temp_path() clone_repo = repo.clone(path, mirror=True) pygit2_repo = Repository(path) assert is_repository(path) is True assert pygit2_repo.is_empty is False assert pygit2_repo.is_bare is True assert clone_repo.empty is False assert clone_repo.bare is True
def test_simple(self): repo = Jagare(self.path) path = self.get_temp_path() clone_repo = repo.clone(path) pygit2_repo = Repository(path) assert is_repository(path) is True assert pygit2_repo.is_empty is False assert pygit2_repo.is_bare is False assert clone_repo.empty is False assert clone_repo.bare is False
def _merge(self, no_ff): repo = Jagare(self.path) BR = 'br_test_merge' path = self.get_temp_path() # repo has work-tree repo.clone(path, branch=BARE_REPO_OTHER_BRANCH) repo = Jagare(os.path.join(path, '.git')) ret = repo.create_branch(BR, BARE_REPO_OTHER_BRANCH) assert ret sha1 = repo.sha(BARE_REPO_OTHER_BRANCH) commit_something(path, branch=BR) repo.update_head(BARE_REPO_OTHER_BRANCH) ret = repo.merge(BR, no_ff=no_ff) sha2 = repo.sha(BARE_REPO_OTHER_BRANCH) assert sha1 != sha2 assert repo.sha(sha1) == sha1
def clone(name, clone_from): target_path = os.path.join(config.REPOS_PATH, name) target_path = endwith_git(target_path) clone_path = os.path.join(config.REPOS_PATH, clone_from) clone_path = endwith_git(clone_path) repository_exist = is_repository(target_path) if repository_exist: raise JagareError("repository already exists", 409) clone_repository_exist = is_repository(clone_path) if not clone_repository_exist: raise JagareError("clone repository does not exist", 400) jagare = Jagare(clone_path) jagare.clone(target_path, bare=True) return make_message_response("clone success")
def clone_to(self, path, to_path, is_bare, branch, is_mirror, env): try: repo = Jagare(path) to_repo = repo.clone(path=to_path, bare=is_bare, branch=branch, mirror=is_mirror, env=env) return Repository(path=to_repo.path, is_empty=to_repo.empty, is_bare=to_repo.bare, workdir=to_repo.repository.workdir, head=to_repo.head and to_repo.head.name) except Exception as e: raise ServiceUnavailable(repr(e))
def test_merge_flow(self): repo = Jagare(self.path) BR = 'br_test_merge' sha1 = repo.sha(BARE_REPO_OTHER_BRANCH) from_repo_path = self.get_temp_path() from_repo = repo.clone(from_repo_path, branch=BARE_REPO_OTHER_BRANCH, bare=True) ret = from_repo.create_branch(BR, BARE_REPO_OTHER_BRANCH) assert ret commit_something(from_repo_path, branch=BR) tmpdir = self.get_temp_path() # different repo sha = repo.merge_flow('lh', '*****@*****.**', 'test_header', 'test_body', tmpdir, from_repo_path, BR, BARE_REPO_OTHER_BRANCH, remote_name='hub/xxxproject', no_ff=True) assert sha sha2 = repo.sha(BARE_REPO_OTHER_BRANCH) assert sha1 != sha2 assert repo.sha(sha1) == sha1 # same repo tmpdir2 = self.get_temp_path() from_sha1 = from_repo.sha(BARE_REPO_OTHER_BRANCH) assert from_sha1 == sha1 sha = from_repo.merge_flow('lh', '*****@*****.**', 'test_header', 'test_body', tmpdir2, from_repo_path, BR, BARE_REPO_OTHER_BRANCH, no_ff=True) assert sha from_sha2 = from_repo.sha(BARE_REPO_OTHER_BRANCH) assert from_sha1 != from_sha2 assert from_repo.sha(from_sha1) == from_sha1
def cloneRepo(payload): """ clone to local """ project_id = payload.get('project_id', None) pro = ProjectModel() project_info = pro.getInfoByProjectId(project_id) error = None if project_info: try: Jagare.clone(project_info['gitaddress'], project_info['localaddress'], callbacks=Jagare.auth(project_info['gituser'], conf.auth.pubkey, conf.auth.privkey, '')) res_string = 'ready' except Exception as e: res_string = 'clone_error' error = str(e) else: res_string = 'no_project' error = 'not found this project' pro.updateProjectState(project_id, res_string, error) return 'success'
def test_can_merge(self): repo = Jagare(self.path) BR = 'br_test_merge' from_repo_path = self.get_temp_path() from_repo = repo.clone(from_repo_path, branch=BARE_REPO_OTHER_BRANCH, bare=True) ret = from_repo.create_branch(BR, BARE_REPO_OTHER_BRANCH) assert ret commit_something(from_repo_path, branch=BR) tmpdir = self.get_temp_path() ret = repo.can_merge(tmpdir, from_repo_path, BR, BARE_REPO_OTHER_BRANCH, remote_name='hub/xxxproject') assert ret is True
class Repo(object): provided_features = [] def __init__(self, path): self.type = "repo" self.path = path self.repo = Jagare(self.path) def provide(self, name): '''检查是否提供某功能,即是否提供某接口''' return name in self.provided_features @property def is_empty(self): return self.repo.empty @property def default_branch(self): branch = None head = self.repo.head if head: branch = head.name.rpartition('/')[-1] return branch def update_default_branch(self, name): branches = self.repo.branches if name not in branches: return None self.repo.update_head(name) def clone(self, path, bare=None, branch=None, mirror=None, env=None): self.repo.clone(path, bare=bare, branch=branch, mirror=mirror, env=env) def archive(self, name): content = self.repo.archive(name) outbuffer = StringIO() zipfile = gzip.GzipFile(mode='wb', compresslevel=6, fileobj=outbuffer) zipfile.writelines(content) zipfile.close() out = outbuffer.getvalue() return out def get_submodule(self, ref, path): path = path.strip() gitmodules = self.repo.show("%s:%s" % (ref, '.gitmodules')) if not gitmodules: return None submodules_lines = gitmodules["data"].split('\n') modules_str = '\n'.join([line.strip() for line in submodules_lines]) config = ConfigParser.RawConfigParser() config.readfp(StringIO(modules_str)) for section in config.sections(): if config.has_option(section, 'path') and config.get( section, 'path') == path: url = config.get(section, 'url') return Submodule(url, path) return None def get_file(self, ref, path): blob = self.repo.show("%s:%s" % (ref, path)) if not blob: return None if blob['type'] != 'blob': return None # TODO: validate blob return Blob(self, blob) def get_file_by_lines(self, ref, path): blob = self.get_file(ref, path) # TODO: blob.size < xxx if not blob or blob.binary: return None if not blob.data: return [] src = blob.data return src.splitlines() def get_file_n_lines(self, ref, path): lines = self.get_file_by_lines(ref, path) if lines: return len(lines) return 0 def get_commits(self, *w, **kw): commits = self.repo.rev_list(*w, **kw) # TODO: validate commits return [Commit(self, commit) for commit in commits] def get_raw_diff(self, ref, from_ref=None, **kw): ''' get Jagare formated diff dict ''' return self.repo.diff(ref, from_ref=from_ref, **kw) def get_diff(self, ref=None, from_ref=None, linecomments=[], raw_diff=None, **kw): ''' get ngit wrapped diff object ''' _raw_diff = None if raw_diff: _raw_diff = raw_diff elif ref: _raw_diff = self.get_raw_diff(ref, from_ref=from_ref, **kw) if _raw_diff: return Diff(self, _raw_diff, linecomments) else: return None def get_diff_length(self, ref, from_ref=None, **kw): _raw_diff = self.get_raw_diff(ref, from_ref=from_ref, **kw) return len(_raw_diff['patches']) if _raw_diff else 0 def get_last_commit(self, ref, path=None): if not path: return self.get_commit(ref) commit = self.repo.rev_list(ref, path=path, max_count=1) if not commit: return None commit = commit[0] commit = Commit(self, commit) return commit def get_commit(self, ref): sha = self.repo.resolve_commit(ref) if not sha: return None commit = self.repo.show(sha) if not commit: return None # TODO: validate commit return Commit(self, commit) def delete_branch(self, name): self.repo.delete_branch(name) def get_path_by_ref(self, ref): ''' get blob or tree ''' path = self.repo.show(ref) if not path: return None if path['type'] == 'tree': path = Tree(self, path['entries']) elif path['type'] == 'blob': path = Blob(self, path) else: path = None return path def get_path(self, ref, path): _item = self.repo.show("%s:%s" % (ref, path)) if not _item: return None if _item['type'] == 'tree': item = Tree(self, _item['entries']) elif _item['type'] == 'blob': item = Blob(self, _item) else: item = None return item
class Repo(object): provided_features = [] def __init__(self, path): self.type = "repo" self.path = path self.repo = Jagare(self.path) def provide(self, name): '''检查是否提供某功能,即是否提供某接口''' return name in self.provided_features @property def is_empty(self): return self.repo.empty @property def default_branch(self): branch = None head = self.repo.head if head: branch = head.name.rpartition('/')[-1] return branch def update_default_branch(self, name): branches = self.repo.branches if name not in branches: return None self.repo.update_head(name) def clone(self, path, bare=None, branch=None, mirror=None, env=None): self.repo.clone(path, bare=bare, branch=branch, mirror=mirror, env=env) def archive(self, name): content = self.repo.archive(name) outbuffer = StringIO() zipfile = gzip.GzipFile(mode='wb', compresslevel=6, fileobj=outbuffer) zipfile.writelines(content) zipfile.close() out = outbuffer.getvalue() return out def get_submodule(self, ref, path): path = path.strip() gitmodules = self.repo.show("%s:%s" % (ref, '.gitmodules')) if not gitmodules: return None submodules_lines = gitmodules["data"].split('\n') modules_str = '\n'.join([line.strip() for line in submodules_lines]) config = ConfigParser.RawConfigParser() config.readfp(StringIO(modules_str)) for section in config.sections(): if config.has_option(section, 'path') and config.get(section, 'path')==path: url = config.get(section, 'url') return Submodule(url, path) return None def get_file(self, ref, path): blob = self.repo.show("%s:%s" % (ref, path)) if not blob: return None if blob['type'] != 'blob': return None # TODO: validate blob return Blob(self, blob) def get_file_by_lines(self, ref, path): blob = self.get_file(ref, path) # TODO: blob.size < xxx if not blob or blob.binary: return None if not blob.data: return [] src = blob.data return src.splitlines() def get_file_n_lines(self, ref, path): lines = self.get_file_by_lines(ref, path) if lines: return len(lines) return 0 def get_commits(self, *w, **kw): commits = self.repo.rev_list(*w, **kw) # TODO: validate commits return [Commit(self, commit) for commit in commits] def get_raw_diff(self, ref, from_ref=None, **kw): ''' get Jagare formated diff dict ''' return self.repo.diff(ref, from_ref=from_ref, **kw) def get_diff(self, ref=None, from_ref=None, linecomments=[], raw_diff=None, **kw): ''' get ngit wrapped diff object ''' _raw_diff = None if raw_diff: _raw_diff = raw_diff elif ref: _raw_diff = self.get_raw_diff(ref, from_ref=from_ref, **kw) if _raw_diff: return Diff(self, _raw_diff, linecomments) else: return None def get_diff_length(self, ref, from_ref=None, **kw): _raw_diff = self.get_raw_diff(ref, from_ref=from_ref, **kw) return len(_raw_diff['patches']) if _raw_diff else 0 def get_last_commit(self, ref, path=None): if not path: return self.get_commit(ref) commit = self.repo.rev_list(ref, path=path, max_count=1) if not commit: return None commit = commit[0] commit = Commit(self, commit) return commit def get_commit(self, ref): sha = self.repo.resolve_commit(ref) if not sha: return None commit = self.repo.show(sha) if not commit: return None # TODO: validate commit return Commit(self, commit) def delete_branch(self, name): self.repo.delete_branch(name) def get_path_by_ref(self, ref): ''' get blob or tree ''' path = self.repo.show(ref) if not path: return None if path['type'] == 'tree': path = Tree(self, path['entries']) elif path['type'] == 'blob': path = Blob(self, path) else: path = None return path def get_path(self, ref, path): _item = self.repo.show("%s:%s" % (ref, path)) if not _item: return None if _item['type'] == 'tree': item = Tree(self, _item['entries']) elif _item['type'] == 'blob': item = Blob(self, _item) else: item = None return item
class Repo(object): provided_features = [] def __init__(self, path): self.type = "repo" self.path = path self.repo = Jagare(self.path) def provide(self, name): '''检查是否提供某功能,即是否提供某接口''' return name in self.provided_features @property def empty(self): return self.is_empty @property def is_empty(self): return self.repo.empty @property def default_branch(self): branch = '' head = self.repo.head if head: branch = head.name[REFS_HEADS_PREFIX_LENGTH:] return branch def update_default_branch(self, name): branches = self.repo.branches if name not in branches: return None self.repo.update_head(name) def clone(self, path, bare=None, branch=None, mirror=None, env=None, shared=None): self.repo.clone(path, bare=bare, branch=branch, mirror=mirror, env=env) # shared=shared) why? def archive(self, name, ref='master', ext='tar.gz'): content = self.repo.archive(name, ref=ref) if ext == 'tar': return content outbuffer = StringIO() zipfile = gzip.GzipFile(mode='wb', compresslevel=6, fileobj=outbuffer) zipfile.write(content) zipfile.close() out = outbuffer.getvalue() return out def get_submodule(self, ref, path): path = path.strip() gitmodules = self.repo.show("%s:%s" % (ref, '.gitmodules')) if not gitmodules: return None submodules_lines = gitmodules["data"].split('\n') modules_str = '\n'.join([line.strip() for line in submodules_lines]) config = ConfigParser.RawConfigParser() config.readfp(StringIO(modules_str)) for section in config.sections(): if config.has_option(section, 'path') and config.get( section, 'path') == path: url = config.get(section, 'url') return Submodule(url, path) return None def get_file(self, ref, path): blob = self.repo.show("%s:%s" % (ref, path)) if not blob: return None if blob['type'] != 'blob': return None # TODO: validate blob return Blob(self, blob) def get_file_by_lines(self, ref, path): blob = self.get_file(ref, path) # TODO: blob.size < xxx if not blob or blob.binary: return None if not blob.data: return [] src = blob.data return src.splitlines() def get_file_n_lines(self, ref, path): lines = self.get_file_by_lines(ref, path) if lines: return len(lines) return 0 def get_commits(self, to_ref, from_ref=None, path=None, skip=0, max_count=0, author=None, query=None, first_parent=None, since=0, no_merges=None): commits = self.repo.rev_list(to_ref=to_ref, from_ref=from_ref, path=path, skip=skip, max_count=max_count, author=author, query=query, first_parent=first_parent, since=since, no_merges=no_merges) return [Commit(self, commit) for commit in commits] def get_raw_diff(self, ref, from_ref=None, paths=None, **kw): ''' get Jagare formated diff dict ''' try: diff = self.repo.diff(ref, from_ref=from_ref, paths=paths, **kw) except KeyError: return None return diff def get_diff(self, ref=None, from_ref=None, linecomments=[], raw_diff=None, paths=None, **kw): ''' get ngit wrapped diff object ''' _raw_diff = None if raw_diff: _raw_diff = raw_diff elif ref: _raw_diff = self.get_raw_diff(ref, from_ref=from_ref, paths=paths, **kw) if _raw_diff: return Diff(self, _raw_diff, linecomments) else: return None def get_diff_length(self, ref, from_ref=None, **kw): _raw_diff = self.get_raw_diff(ref, from_ref=from_ref, **kw) return len(_raw_diff['patches']) if _raw_diff else 0 def get_last_commit(self, ref, path=None, no_merges=False): if not path: return self.get_commit(ref) commit = self.repo.rev_list(ref, path=path, max_count=1, no_merges=no_merges) if not commit: return None commit = commit[0] commit = Commit(self, commit) return commit def get_previours_commit(self, ref, path): """previours commit that touch the specified path""" commits = self.repo.rev_list(ref, path=path, max_count=2, no_merges=True) for commit in commits: if commit['sha'] != self.repo.sha(ref): return Commit(self, commit) return None def get_commit(self, ref): sha = self.repo.resolve_commit(ref) if not sha: return None commit = self.repo.show(sha) if not commit: return None # TODO: validate commit return Commit(self, commit) def delete_branch(self, name): self.repo.delete_branch(name) def get_path_by_ref(self, ref): ''' get blob or tree ''' path = self.repo.show(ref) if not path: return None if path['type'] == 'tree': path = Tree(self, path['entries']) elif path['type'] == 'blob': path = Blob(self, path) else: path = None return path def get_path(self, ref, path): _item = self.repo.show("%s:%s" % (ref, path)) if not _item: return None if _item['type'] == 'tree': item = Tree(self, _item['entries']) elif _item['type'] == 'blob': item = Blob(self, _item) else: item = None return item def get_last_update_timestamp(self): commit = self.get_last_commit('HEAD') if not commit: return 0 return int(commit.author_timestamp)