import os
import utils
import logging
+import git
from patch import PatchTestPatch
logger = logging.getLogger('patchtest')
# prefixes used for temporal branches/stashes
prefix = 'patchtest'
+
def __init__(self, patch, repodir, commit=None, branch=None):
self._repodir = repodir
+ self._repo = git.Repo.init(repodir)
self._patch = PatchTestPatch(patch)
- self._current_branch = self._get_current_branch()
+ self._current_branch = self._repo.active_branch.name
# targeted branch defined on the patch may be invalid, so make sure there
# is a corresponding remote branch
valid_patch_branch = None
- if self._patch.branch in self.upstream_branches():
+ if self._patch.branch in self._repo.branches:
valid_patch_branch = self._patch.branch
# Target Branch
self._workingbranch = "%s_%s" % (PatchTestRepo.prefix, os.getpid())
- # create working branch
- self._exec({'cmd': ['git', 'checkout', '-b', self._workingbranch, self._commit]})
+ # create working branch. Use the '-B' flag so that we just
+ # check out the existing one if it's there
+ self._repo.git.execute(['git', 'checkout', '-B', self._workingbranch, self._commit])
self._patchmerged = False
# Check if patch can be merged using git-am
self._patchcanbemerged = True
try:
- self._exec({'cmd': ['git', 'am', '--keep-cr'], 'input': self._patch.contents})
- except utils.CmdException as ce:
- self._exec({'cmd': ['git', 'am', '--abort']})
+ # Make sure to get the absolute path of the file
+ self._repo.git.execute(['git', 'apply', '--check', os.path.abspath(self._patch.path)], with_exceptions=True)
+ except git.exc.GitCommandError as ce:
self._patchcanbemerged = False
- finally:
- # if patch was applied, remove it
- if self._patchcanbemerged:
- self._exec({'cmd':['git', 'reset', '--hard', self._commit]})
# for debugging purposes, print all repo parameters
logger.debug("Parameters")
def canbemerged(self):
return self._patchcanbemerged
- def _exec(self, cmds):
- _cmds = []
- if isinstance(cmds, dict):
- _cmds.append(cmds)
- elif isinstance(cmds, list):
- _cmds = cmds
- else:
- raise utils.CmdException({'cmd':str(cmds)})
-
- results = []
- cmdfailure = False
- try:
- results = utils.exec_cmds(_cmds, self._repodir)
- except utils.CmdException as ce:
- cmdfailure = True
- raise ce
- finally:
- if cmdfailure:
- for cmd in _cmds:
- logger.debug("CMD: %s" % ' '.join(cmd['cmd']))
- else:
- for result in results:
- cmd, rc, stdout, stderr = ' '.join(result['cmd']), result['returncode'], result['stdout'], result['stderr']
- logger.debug("CMD: %s RCODE: %s STDOUT: %s STDERR: %s" % (cmd, rc, stdout, stderr))
-
- return results
-
- def _get_current_branch(self, commit='HEAD'):
- cmd = {'cmd':['git', 'rev-parse', '--abbrev-ref', commit]}
- cb = self._exec(cmd)[0]['stdout']
- if cb == commit:
- logger.warning('You may be detached so patchtest will checkout to master after execution')
- cb = 'master'
- return cb
-
def _get_commitid(self, commit):
if not commit:
return None
try:
- cmd = {'cmd':['git', 'rev-parse', '--short', commit]}
- return self._exec(cmd)[0]['stdout']
- except utils.CmdException as ce:
- # try getting the commit under any remotes
- cmd = {'cmd':['git', 'remote']}
- remotes = self._exec(cmd)[0]['stdout']
- for remote in remotes.splitlines():
- cmd = {'cmd':['git', 'rev-parse', '--short', '%s/%s' % (remote, commit)]}
- try:
- return self._exec(cmd)[0]['stdout']
- except utils.CmdException:
- pass
+ return self._repo.rev_parse(commit).hexsha
+ except Exception as e:
+ print(f"Couldn't find commit {commit} in repo")
return None
- def upstream_branches(self):
- cmd = {'cmd':['git', 'branch', '--remotes']}
- remote_branches = self._exec(cmd)[0]['stdout']
-
- # just get the names, without the remote name
- branches = set(branch.split('/')[-1] for branch in remote_branches.splitlines())
- return branches
-
def merge(self):
if self._patchcanbemerged:
- self._exec({'cmd': ['git', 'am', '--keep-cr'],
- 'input': self._patch.contents,
- 'updateenv': {'PTRESOURCE':self._patch.path}})
+ self._repo.git.execute(['git', 'am', '--keep-cr', os.path.abspath(self._patch.path)])
self._patchmerged = True
def clean(self):
- self._exec({'cmd':['git', 'checkout', '%s' % self._current_branch]})
- self._exec({'cmd':['git', 'branch', '-D', self._workingbranch]})
+ self._repo.git.execute(['git', 'checkout', self._current_branch])
+ self._repo.git.execute(['git', 'branch', '-D', self._workingbranch])
self._patchmerged = False