hooks: add internal check for external hook API
Add an internal check to make sure we always follow the API we've
documented for external authors. Since the internal call is a bit
ad-hoc, it can be easy to miss a call site.
Change-Id: Ie8cd298d1fc34f10f3c5eb353512a3e881f42252
Reviewed-on: https://gerrit-review.googlesource.com/c/git-repo/+/481721
Reviewed-by: Nasser Grainawi <nasser.grainawi@oss.qualcomm.com>
Reviewed-by: Gavin Mak <gavinmak@google.com>
Tested-by: Mike Frysinger <vapier@google.com>
Commit-Queue: Mike Frysinger <vapier@google.com>
diff --git a/hooks.py b/hooks.py
index 82bf7e3..f940e3f 100644
--- a/hooks.py
+++ b/hooks.py
@@ -22,6 +22,12 @@
from git_refs import HEAD
+# The API we've documented to hook authors. Keep in sync with repo-hooks.md.
+_API_ARGS = {
+ "pre-upload": {"project_list", "worktree_list"},
+}
+
+
class RepoHook:
"""A RepoHook contains information about a script to run as a hook.
@@ -56,6 +62,7 @@
hooks_project,
repo_topdir,
manifest_url,
+ bug_url=None,
bypass_hooks=False,
allow_all_hooks=False,
ignore_hooks=False,
@@ -75,6 +82,7 @@
run with CWD as this directory.
If you have a manifest, this is manifest.topdir.
manifest_url: The URL to the manifest git repo.
+ bug_url: The URL to report issues.
bypass_hooks: If True, then 'Do not run the hook'.
allow_all_hooks: If True, then 'Run the hook without prompting'.
ignore_hooks: If True, then 'Do not abort action if hooks fail'.
@@ -85,6 +93,7 @@
self._hooks_project = hooks_project
self._repo_topdir = repo_topdir
self._manifest_url = manifest_url
+ self._bug_url = bug_url
self._bypass_hooks = bypass_hooks
self._allow_all_hooks = allow_all_hooks
self._ignore_hooks = ignore_hooks
@@ -414,6 +423,20 @@
ignore the result through the option combinations as listed in
AddHookOptionGroup().
"""
+ # Make sure our own callers use the documented API.
+ exp_kwargs = _API_ARGS.get(self._hook_type, set())
+ got_kwargs = set(kwargs.keys())
+ if exp_kwargs != got_kwargs:
+ print(
+ "repo internal error: "
+ f"hook '{self._hook_type}' called incorrectly\n"
+ f" got: {sorted(got_kwargs)}\n"
+ f" expected: {sorted(exp_kwargs)}\n"
+ f"Please file a bug: {self._bug_url}",
+ file=sys.stderr,
+ )
+ return False
+
# Do not do anything in case bypass_hooks is set, or
# no-op if there is no hooks project or if hook is disabled.
if (
@@ -472,6 +495,7 @@
"manifest_url": manifest.manifestProject.GetRemote(
"origin"
).url,
+ "bug_url": manifest.contactinfo.bugurl,
}
)
return cls(*args, **kwargs)