Merge branch 'fix-checkupdates-one-MR-per-app' into 'master'

checkupdates: --merge_request commits to branch named after appid

See merge request fdroid/fdroidserver!1550
This commit is contained in:
Hans-Christoph Steiner 2024-10-30 19:03:14 +00:00
commit 83a3227235
2 changed files with 70 additions and 11 deletions

View File

@ -684,7 +684,15 @@ def get_last_build_from_app(app: metadata.App) -> metadata.Build:
return metadata.Build() return metadata.Build()
def push_commits(remote_name='origin', verbose=False): def get_git_repo_and_main_branch():
git_repo = git.Repo.init('.')
main_branch = 'main'
if main_branch not in git_repo.heads:
main_branch = 'master'
return git_repo, main_branch
def push_commits(remote_name='origin', branch_name='checkupdates', verbose=False):
"""Make git branch then push commits as merge request. """Make git branch then push commits as merge request.
This uses the appid as the standard branch name so that there is This uses the appid as the standard branch name so that there is
@ -701,17 +709,16 @@ def push_commits(remote_name='origin', verbose=False):
* https://docs.gitlab.com/ee/user/project/push_options.html * https://docs.gitlab.com/ee/user/project/push_options.html
""" """
git_repo = git.Repo.init('.') git_repo, default = get_git_repo_and_main_branch()
files = set() files = set()
upstream_main = 'main' if 'main' in git_repo.remotes.upstream.refs else 'master' upstream_main = default if default in git_repo.remotes.upstream.refs else 'main'
local_main = 'main' if 'main' in git_repo.refs else 'master' local_main = default if default in git_repo.refs else 'main'
for commit in git_repo.iter_commits(f'upstream/{upstream_main}...{local_main}'): for commit in git_repo.iter_commits(f'upstream/{upstream_main}...{local_main}'):
files.update(commit.stats.files.keys()) files.update(commit.stats.files.keys())
branch_name = 'checkupdates'
files = list(files) files = list(files)
if len(files) == 1: if len(files) == 1:
m = re.match(r'metadata/([^\s]+)\.yml', files[0]) m = re.match(r'metadata/(\S+)\.yml', files[0])
if m: if m:
branch_name = m.group(1) # appid branch_name = m.group(1) # appid
if not files: if not files:
@ -767,13 +774,10 @@ def push_commits(remote_name='origin', verbose=False):
logging.debug(remote.url + ': ' + pushinfo.summary) logging.debug(remote.url + ': ' + pushinfo.summary)
def prune_empty_appid_branches(git_repo=None): def prune_empty_appid_branches(git_repo=None, main_branch='main'):
"""Remove empty branches from checkupdates-bot git remote.""" """Remove empty branches from checkupdates-bot git remote."""
if git_repo is None: if git_repo is None:
git_repo = git.Repo.init('.') git_repo, main_branch = get_git_repo_and_main_branch()
main_branch = 'main'
if main_branch not in git_repo.remotes.upstream.refs:
main_branch = 'master'
upstream_main = 'upstream/' + main_branch upstream_main = 'upstream/' + main_branch
remote = git_repo.remotes.origin remote = git_repo.remotes.origin
@ -856,6 +860,12 @@ def main():
logging.info(msg) logging.info(msg)
try: try:
if options.merge_request:
logging.info(f'Creating merge request branch for {appid}')
git_repo, main_branch = get_git_repo_and_main_branch()
git_repo.create_head(appid, f"upstream/{main_branch}", force=True)
git_repo.git.checkout(appid)
checkupdates_app(app, options.auto, options.commit or options.merge_request) checkupdates_app(app, options.auto, options.commit or options.merge_request)
processed.append(appid) processed.append(appid)
except Exception as e: except Exception as e:

View File

@ -463,6 +463,55 @@ class CheckupdatesTest(unittest.TestCase):
fdroidserver.checkupdates.main() fdroidserver.checkupdates.main()
sys_exit.assert_not_called() sys_exit.assert_not_called()
def test_get_git_repo_and_main_branch(self):
os.chdir(self.testdir.name)
git_repo = git.Repo.init()
open('foo', 'w').close()
git_repo.git.add(all=True)
git_repo.index.commit("all files")
repo, branch = fdroidserver.checkupdates.get_git_repo_and_main_branch()
self.assertTrue(branch in ('main', 'master'))
self.assertTrue(branch in repo.heads)
@mock.patch('sys.exit')
@mock.patch('fdroidserver.common.read_app_args')
@mock.patch('fdroidserver.checkupdates.checkupdates_app')
def test_merge_requests_branch(self, checkupdates_app, read_app_args, sys_exit):
def _sys_exit(return_code=0):
assert return_code == 0
def _checkupdates_app(app, auto, commit): # pylint: disable=unused-argument
os.mkdir('metadata')
Path(f'metadata/{app["packageName"]}.yml').write_text('AutoName: Example')
git_repo.git.add(all=True)
git_repo.index.commit("Example")
def _read_app_args(apps=[]):
appid = apps[0]
return {appid: {'packageName': appid}}
appid = 'com.example'
read_app_args.side_effect = _read_app_args
checkupdates_app.side_effect = _checkupdates_app
sys_exit.side_effect = _sys_exit
# set up clean git repo
os.chdir(self.testdir.name)
git_repo = git.Repo.init()
open('foo', 'w').close()
git_repo.git.add(all=True)
git_repo.index.commit("all files")
# --merge-request assumes remotes called 'origin' and 'upstream'
git_repo.create_remote('origin', os.getcwd()).fetch()
git_repo.create_remote('upstream', os.getcwd()).fetch()
assert appid not in git_repo.heads
with mock.patch('sys.argv', ['fdroid checkupdates', '--merge-request', appid]):
fdroidserver.checkupdates.main()
sys_exit.assert_called_once()
assert appid in git_repo.heads
if __name__ == "__main__": if __name__ == "__main__":
import argparse import argparse