Add a script to add git tags to the corresponding builds of a package

Basically the script will query koji for all the existing builds about
this package, try to figure out from which git commit they originated
and tag the commit with the corresponding NEVR.

Signed-off-by: Pierre-Yves Chibon <pingou@pingoured.fr>
This commit is contained in:
Pierre-Yves Chibon 2020-03-02 18:11:27 +01:00
parent f12b1a8f6e
commit f69210f2b3
3 changed files with 103 additions and 3 deletions

View file

@ -1,7 +1,7 @@
import argparse
import sys
from . import changelog, release
from . import changelog, release, tag_package
subcmd_modules_by_name = {}
@ -24,7 +24,7 @@ def get_cli_args(args):
subparsers = parser.add_subparsers(dest="subcommand", required=True)
for subcmd_module in (changelog, release):
for subcmd_module in (changelog, release, tag_package):
subcmd_name = subcmd_module.register_subcommand(subparsers)
if subcmd_name in subcmd_modules_by_name:

View file

@ -48,9 +48,10 @@ def parse_release_tag(tag: str) -> Tuple[Optional[int], Optional[str], Optional[
def koji_init(koji_url: str):
global _kojiclient
_kojiclient = koji.ClientSession(koji_url)
return _kojiclient
def get_package_builds(pkgname: str) -> List[dict]:
def get_package_builds(pkgname: str, extras: bool = False) -> List[dict]:
assert _kojiclient
pkgid = _kojiclient.getPackageID(pkgname)

View file

@ -0,0 +1,99 @@
#!/usr/bin/python3
import logging
import os
import subprocess
from .misc import get_package_builds, koji_init
_log = logging.getLogger(__name__)
escape_chars = {
"^": "%5E",
"%": "%25",
"~": "%7E",
}
def register_subcommand(subparsers):
subcmd_name = "tag-project"
tag_project_parser = subparsers.add_parser(
subcmd_name, help="Tag the git commits corresponding to a build in koji",
)
tag_project_parser.add_argument("worktree_path", help="Path to the dist-git worktree")
return subcmd_name
def run_command(command, cwd=None):
""" Run the specified command in a specific working directory if one
is specified.
"""
output = None
try:
output = subprocess.check_output(command, cwd=cwd, stderr=subprocess.PIPE)
except subprocess.CalledProcessError as e:
command_str = " ".join(command)
_log.error("Command `{}` return code: `{}`".format(command_str, e.returncode))
_log.error("stdout:\n-------\n{}".format(e.stdout))
_log.error("stderr:\n-------\n{}".format(e.stderr))
raise RuntimeError(
"Command `{}` failed to run, returned {}".format(command_str, e.returncode)
)
return output
def main(args):
""" Main method. """
kojiclient = koji_init(args.koji_url)
repopath = args.worktree_path
name = os.path.basename(repopath)
for build in get_package_builds(name):
if build.get("epoch"):
nevr = f"{build['name']}-{build['epoch']}:{build['version']}-{build['release']}"
else:
nevr = f"{build['name']}-{build['version']}-{build['release']}"
commit = None
if "source" in build and build["source"]:
com = build["source"].partition("#")[-1]
try:
int(com, 16)
commit = com
except ValueError:
# The hash isn't an hexadecimal number so, skipping it
pass
if commit is None:
tasks = kojiclient.getTaskChildren(build["task_id"])
task = [t for t in tasks if t["method"] == "buildSRPMFromSCM"][0]
task_req = kojiclient.getTaskRequest(task["id"])
if "fedoraproject.org" in task_req[0]:
com = task_req[0].partition("#")[-1]
# git commit hashes are 40 characters long, so we will
# assume if the part after the '#' in 40 characters long it
# is a commit hash and not a 40 characters long branch or
# tag name
if len(com) == 40:
try:
int(com, 16)
commit = com
except ValueError:
# The hash isn't an hexadecimal number so, skipping it
pass
if commit:
# Escape un-allowed characters
for char in escape_chars:
nevr = nevr.replace(char, escape_chars[char])
command = ["git", "tag", nevr, commit]
try:
run_command(command, cwd=repopath)
except RuntimeError as err:
print(err)
else:
print(f"tagged commit {commit} as {nevr}")