diff --git a/rpmautospec.py b/rpmautospec.py new file mode 100755 index 0000000..ee03eb7 --- /dev/null +++ b/rpmautospec.py @@ -0,0 +1,6 @@ +#!/usr/bin/env python + +from rpmautospec.cli import main + + +main() diff --git a/rpmautospec/__init__.py b/rpmautospec/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/generate_changelog.py b/rpmautospec/changelog.py similarity index 86% rename from generate_changelog.py rename to rpmautospec/changelog.py index 4930572..ccdac70 100644 --- a/generate_changelog.py +++ b/rpmautospec/changelog.py @@ -13,6 +13,18 @@ import pygit2 _log = logging.getLogger(__name__) +def register_subcommand(subparsers): + subcmd_name = "generate-changelog" + + gen_changelog_parser = subparsers.add_parser( + subcmd_name, help="Generate changelog entries from git commit logs", + ) + + gen_changelog_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. @@ -31,8 +43,10 @@ def run_command(command, cwd=None): def main(args): """ Main method. """ - repo_obj = pygit2.Repository(args[0]) - name = os.path.basename(args[0]) + repopath = args.worktree_path + + repo_obj = pygit2.Repository(repopath) + name = os.path.basename(repopath) branch = repo_obj.lookup_branch(repo_obj.head.shorthand) commit = branch.peel(pygit2.Commit) @@ -53,7 +67,7 @@ def main(args): repo_obj.checkout_tree( commit, strategy=pygit2.GIT_CHECKOUT_FORCE | pygit2.GIT_CHECKOUT_RECREATE_MISSING, ) - if os.path.exists(os.path.join(args[0], f"{name}.spec")): + if os.path.exists(os.path.join(repopath, f"{name}.spec")): try: output = run_command( [ @@ -63,7 +77,7 @@ def main(args): "--specfile", f"{name}.spec", ], - cwd=args[0], + cwd=repopath, ) except Exception: continue @@ -108,7 +122,3 @@ def main(args): ) print("- %s" % message) print() - - -if __name__ == "__main__": - main(sys.argv[1:]) diff --git a/rpmautospec/cli.py b/rpmautospec/cli.py new file mode 100644 index 0000000..df907cd --- /dev/null +++ b/rpmautospec/cli.py @@ -0,0 +1,43 @@ +import argparse +import sys + +from . import changelog, release + + +subcmd_modules_by_name = {} + + +def get_cli_args(args): + global subcmd_modules_by_name + + parser = argparse.ArgumentParser(prog="rpmautospec") + + # global arguments + + parser.add_argument( + "--koji-url", + help="The base URL of the Koji hub", + default="https://koji.fedoraproject.org/kojihub", + ) + + # parsers for sub-commands + + subparsers = parser.add_subparsers(dest="subcommand", required=True) + + for subcmd_module in (changelog, release): + subcmd_name = subcmd_module.register_subcommand(subparsers) + + if subcmd_name in subcmd_modules_by_name: + raise RuntimeError(f"Sub-command specified more than once: {subcmd_name}.") + + subcmd_modules_by_name[subcmd_name] = subcmd_module + + return parser.parse_args(args) + + +def main(): + args = get_cli_args(sys.argv[1:]) + + if args.subcommand: + subcmd_module = subcmd_modules_by_name[args.subcommand] + subcmd_module.main(args) diff --git a/next_build.py b/rpmautospec/release.py similarity index 91% rename from next_build.py rename to rpmautospec/release.py index b074a64..00d308d 100644 --- a/next_build.py +++ b/rpmautospec/release.py @@ -20,29 +20,27 @@ _disttag_re = re.compile(r"^\.?(?P[^\d\.]+)(?P\d+)") _evr_re = re.compile(r"^(?:(?P\d+):)?(?P[^-:]+)(?:-(?P[^-:]+))?$") -def get_cli_arguments(args): - """ Set the CLI argument parser and return the argument parsed. - """ - parser = argparse.ArgumentParser(description="Script to determine the next NVR of a build") - parser.add_argument( - "--koji-url", - help="The base URL of the Koji hub", - default="https://koji.fedoraproject.org/kojihub", +def register_subcommand(subparsers): + subcmd_name = "calculate-release" + + calc_release_parser = subparsers.add_parser( + subcmd_name, help="Calculate the next release tag for a package build", ) - parser.add_argument( + + calc_release_parser.add_argument( "--algorithm", "--algo", - help="The algorithm with which to determine the next release", + help="The algorithm with which to calculate the next release", choices=["sequential_builds", "holistic_heuristic"], default="sequential_builds", ) - parser.add_argument("package", help="The name of the package of interest") - parser.add_argument("dist", help="The dist-tag of interest") - parser.add_argument( + calc_release_parser.add_argument("package", help="The name of the package of interest") + calc_release_parser.add_argument("dist", help="The dist-tag of interest") + calc_release_parser.add_argument( "evr", help="The [epoch:]version[-release] of the package", nargs="?", type=parse_evr, ) - return parser.parse_args(args) + return subcmd_name def parse_evr(evr_str): @@ -255,7 +253,6 @@ def main_holistic_heuristic_algo(args, client, pkgid): def main(args): """ Main method. """ - args = get_cli_arguments(args) client = koji.ClientSession(args.koji_url) pkgid = client.getPackageID(args.package) @@ -267,7 +264,3 @@ def main(args): main_sequential_builds_algo(args, client, pkgid) elif args.algorithm == "holistic_heuristic": main_holistic_heuristic_algo(args, client, pkgid) - - -if __name__ == "__main__": - sys.exit(main(sys.argv[1:])) diff --git a/setup.cfg b/setup.cfg index ed40883..0a6b351 100644 --- a/setup.cfg +++ b/setup.cfg @@ -5,5 +5,5 @@ exclude = .git,.tox,dist,*egg,build,tools #ignore = # Configure flake8-import-order -application-import-names = generate_changelog,next_build +application-import-names = rpmautospec import-order-style = google diff --git a/tests/test_next_build.py b/tests/test_calc_release.py similarity index 82% rename from tests/test_next_build.py rename to tests/test_calc_release.py index f63f61f..1b66210 100644 --- a/tests/test_next_build.py +++ b/tests/test_calc_release.py @@ -4,7 +4,7 @@ from unittest import mock import pytest -import next_build +from rpmautospec import release __here__ = os.path.dirname(__file__) @@ -42,13 +42,19 @@ class TestNextBuild: ) as f: koji_list_builds_output = json.load(f) - with mock.patch("next_build.koji") as mock_koji: + with mock.patch("rpmautospec.release.koji") as mock_koji: mock_client = mock.MagicMock() mock_koji.ClientSession.return_value = mock_client mock_client.getPackageID.return_value = 1234 mock_client.listBuilds.return_value = koji_list_builds_output - next_build.main((test_data["package"], test_data["dist"])) + main_args = mock.Mock() + main_args.algorithm = "sequential_builds" + main_args.package = test_data["package"] + main_args.dist = test_data["dist"] + main_args.evr = None + + release.main(main_args) mock_client.getPackageID.assert_called_once() mock_client.listBuilds.assert_called_once()