From: Patrick Steinhardt <ps@pks.im>
To: Adrian Ratiu <adrian.ratiu@collabora.com>
Cc: git@vger.kernel.org, Emily Shaffer <emilyshaffer@google.com>,
Junio C Hamano <gitster@pobox.com>,
"brian m . carlson" <sandals@crustytoothpaste.net>
Subject: Re: [PATCH 10/10] hook: show disabled hooks in "git hook list"
Date: Wed, 11 Mar 2026 11:24:42 +0100 [thread overview]
Message-ID: <abFC6pEEmicjG6a9@pks.im> (raw)
In-Reply-To: <20260309005416.2760030-11-adrian.ratiu@collabora.com>
On Mon, Mar 09, 2026 at 02:54:16AM +0200, Adrian Ratiu wrote:
> diff --git a/builtin/hook.c b/builtin/hook.c
> index c806640361..ff446948fa 100644
> --- a/builtin/hook.c
> +++ b/builtin/hook.c
> @@ -72,16 +72,20 @@ static int list(int argc, const char **argv, const char *prefix,
> case HOOK_TRADITIONAL:
> printf("%s%c", _("hook from hookdir"), line_terminator);
> break;
> - case HOOK_CONFIGURED:
> - if (show_scope)
> - printf("%s (%s)%c",
> - h->u.configured.friendly_name,
> - config_scope_name(h->u.configured.scope),
> + case HOOK_CONFIGURED: {
> + const char *name = h->u.configured.friendly_name;
> + const char *scope = show_scope ?
> + config_scope_name(h->u.configured.scope) : NULL;
> + if (scope)
> + printf("%s (%s%s)%c", name, scope,
> + h->u.configured.disabled ? ", disabled" : "",
> line_terminator);
> + else if (h->u.configured.disabled)
> + printf("%s (disabled)%c", name, line_terminator);
> else
> - printf("%s%c", h->u.configured.friendly_name,
> - line_terminator);
> + printf("%s%c", name, line_terminator);
> break;
> + }
> default:
> BUG("unknown hook kind");
> }
Hm. This starts to feel less and less like an interface that can easily
be parsed by a machine, even with "-z". I guess this partly comes from
our insistence to reinvent the wheel in Git instead of just using
something like JSON :/
> diff --git a/hook.c b/hook.c
> index 2c03baeaac..4f4f060156 100644
> --- a/hook.c
> +++ b/hook.c
> @@ -119,6 +119,7 @@ static void list_hooks_add_default(struct repository *r, const char *hookname,
> struct hook_config_cache_entry {
> char *command;
> enum config_scope scope;
> + int disabled;
> };
>
> /*
Is there any reason this is an `int` and not a `bool`?
> @@ -217,8 +218,10 @@ static int hook_config_lookup_all(const char *key, const char *value,
> * every item's string is the hook's friendly-name and its util pointer is
> * a hook_config_cache_entry. All strings are owned by the map.
> *
> - * Disabled hooks and hooks missing a command are already filtered out at
> - * parse time, so callers can iterate the list directly.
> + * Disabled hooks are kept in the cache with entry->disabled set, so that
> + * "git hook list" can display them. Hooks missing a command are filtered
> + * out at build time; if a disabled hook has no command it is silently
What exactly does "build time" refer to? To me this reads like invoking
make :)
> + * skipped rather than triggering a fatal error.
> */
> void hook_cache_clear(struct hook_config_cache *cache)
> {
> @@ -268,21 +271,26 @@ static void build_hook_config_map(struct repository *r,
> struct hook_config_cache_entry *entry;
> char *command;
>
> - /* filter out disabled hooks */
> - if (unsorted_string_list_lookup(&cb_data.disabled_hooks,
> - hname))
> - continue;
> + int is_disabled =
> + !!unsorted_string_list_lookup(
> + &cb_data.disabled_hooks, hname);
>
> command = strmap_get(&cb_data.commands, hname);
> - if (!command)
> - die(_("'hook.%s.command' must be configured or "
> - "'hook.%s.event' must be removed;"
> - " aborting."), hname, hname);
> + if (!command) {
> + if (is_disabled)
> + warning(_("disabled hook '%s' has no "
> + "command configured"), hname);
> + else
> + die(_("'hook.%s.command' must be configured or "
> + "'hook.%s.event' must be removed;"
> + " aborting."), hname, hname);
> + }
>
> /* util stores a cache entry; owned by the cache. */
> CALLOC_ARRAY(entry, 1);
> - entry->command = xstrdup(command);
> + entry->command = command ? xstrdup(command) : NULL;
You can use `xstrdup_or_null()` here.
> entry->scope = scope;
> + entry->disabled = is_disabled;
> string_list_append(hooks, hname)->util = entry;
> }
>
> @@ -401,7 +411,16 @@ struct string_list *list_hooks(struct repository *r, const char *hookname,
> int hook_exists(struct repository *r, const char *name)
> {
> struct string_list *hooks = list_hooks(r, name, NULL);
> - int exists = hooks->nr > 0;
> + int exists = 0;
> +
> + for (size_t i = 0; i < hooks->nr; i++) {
> + struct hook *h = hooks->items[i].util;
> + if (h->kind == HOOK_TRADITIONAL ||
> + !h->u.configured.disabled) {
Is the first condition required? I would expect that `disabled` would
always be false for traditional hooks.
> + exists = 1;
> + break;
> + }
> + }
> string_list_clear_func(hooks, hook_free);
> free(hooks);
> return exists;
> diff --git a/hook.h b/hook.h
> index 0d711ed21a..0432df963f 100644
> --- a/hook.h
> +++ b/hook.h
> @@ -31,6 +31,7 @@ struct hook {
> const char *friendly_name;
> const char *command;
> enum config_scope scope;
> + int disabled;
> } configured;
> } u;
>
Same question here regarding the type of the struct member.
Patrick
next prev parent reply other threads:[~2026-03-11 10:24 UTC|newest]
Thread overview: 71+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-03-09 0:54 [PATCH 00/10] config-hook cleanups and two small 'git hook list' features Adrian Ratiu
2026-03-09 0:54 ` [PATCH 01/10] hook: move unsorted_string_list_remove() to string-list.[ch] Adrian Ratiu
2026-03-10 19:56 ` SZEDER Gábor
2026-03-11 11:08 ` Adrian Ratiu
2026-03-09 0:54 ` [PATCH 02/10] hook: fix minor style issues Adrian Ratiu
2026-03-09 2:12 ` Eric Sunshine
2026-03-09 0:54 ` [PATCH 03/10] hook: rename cb_data_free/alloc -> hook_data_free/alloc Adrian Ratiu
2026-03-11 10:24 ` Patrick Steinhardt
2026-03-11 11:09 ` Adrian Ratiu
2026-03-09 0:54 ` [PATCH 04/10] hook: detect & emit two more bugs Adrian Ratiu
2026-03-09 0:54 ` [PATCH 05/10] hook: replace hook_list_clear() -> string_list_clear_func() Adrian Ratiu
2026-03-09 2:18 ` Eric Sunshine
2026-03-10 14:20 ` Adrian Ratiu
2026-03-09 0:54 ` [PATCH 06/10] hook: make consistent use of friendly-name in docs Adrian Ratiu
2026-03-09 0:54 ` [PATCH 07/10] t1800: add test to verify hook execution ordering Adrian Ratiu
2026-03-09 0:54 ` [PATCH 08/10] hook: refactor hook_config_cache from strmap to named struct Adrian Ratiu
2026-03-09 21:59 ` Junio C Hamano
2026-03-10 14:19 ` Adrian Ratiu
2026-03-09 0:54 ` [PATCH 09/10] hook: show config scope in git hook list Adrian Ratiu
2026-03-09 21:59 ` Junio C Hamano
2026-03-10 14:45 ` Adrian Ratiu
2026-03-11 10:24 ` Patrick Steinhardt
2026-03-11 11:47 ` Adrian Ratiu
2026-03-09 0:54 ` [PATCH 10/10] hook: show disabled hooks in "git hook list" Adrian Ratiu
2026-03-11 10:24 ` Patrick Steinhardt [this message]
2026-03-11 12:24 ` Adrian Ratiu
2026-03-11 13:53 ` Patrick Steinhardt
2026-03-09 20:14 ` [PATCH 00/10] config-hook cleanups and two small 'git hook list' features Junio C Hamano
2026-03-10 14:37 ` Adrian Ratiu
2026-03-09 20:27 ` Junio C Hamano
2026-03-20 11:52 ` [PATCH v2 " Adrian Ratiu
2026-03-20 11:52 ` [PATCH v2 01/10] hook: move unsorted_string_list_remove() to string-list.[ch] Adrian Ratiu
2026-03-20 11:52 ` [PATCH v2 02/10] hook: fix minor style issues Adrian Ratiu
2026-03-24 8:37 ` Patrick Steinhardt
2026-03-24 19:19 ` Adrian Ratiu
2026-03-20 11:52 ` [PATCH v2 03/10] hook: rename cb_data_free/alloc -> hook_data_free/alloc Adrian Ratiu
2026-03-20 11:52 ` [PATCH v2 04/10] hook: detect & emit two more bugs Adrian Ratiu
2026-03-20 11:52 ` [PATCH v2 05/10] hook: replace hook_list_clear() -> string_list_clear_func() Adrian Ratiu
2026-03-24 8:37 ` Patrick Steinhardt
2026-03-24 22:33 ` Adrian Ratiu
2026-03-25 5:26 ` Patrick Steinhardt
2026-03-20 11:52 ` [PATCH v2 06/10] hook: make consistent use of friendly-name in docs Adrian Ratiu
2026-03-20 11:52 ` [PATCH v2 07/10] t1800: add test to verify hook execution ordering Adrian Ratiu
2026-03-20 11:52 ` [PATCH v2 08/10] hook: introduce hook_config_cache_entry for per-hook data Adrian Ratiu
2026-03-20 11:52 ` [PATCH v2 09/10] hook: show config scope in git hook list Adrian Ratiu
2026-03-24 8:37 ` Patrick Steinhardt
2026-03-25 11:28 ` Adrian Ratiu
2026-03-20 11:52 ` [PATCH v2 10/10] hook: show disabled hooks in "git hook list" Adrian Ratiu
2026-03-24 8:38 ` Patrick Steinhardt
2026-03-24 16:14 ` Junio C Hamano
2026-03-24 19:23 ` Adrian Ratiu
2026-03-23 16:11 ` [PATCH v2 00/10] config-hook cleanups and two small 'git hook list' features Junio C Hamano
2026-03-24 8:38 ` Patrick Steinhardt
2026-03-24 18:56 ` Adrian Ratiu
2026-03-25 19:54 ` [PATCH v3 00/12] config-hook cleanups and three small git-hook features Adrian Ratiu
2026-03-25 19:54 ` [PATCH v3 01/12] hook: move unsorted_string_list_remove() to string-list.[ch] Adrian Ratiu
2026-03-25 19:54 ` [PATCH v3 02/12] builtin/receive-pack: properly init receive_hook strbuf Adrian Ratiu
2026-03-25 19:54 ` [PATCH v3 03/12] hook: fix minor style issues Adrian Ratiu
2026-03-25 19:54 ` [PATCH v3 04/12] hook: rename cb_data_free/alloc -> hook_data_free/alloc Adrian Ratiu
2026-03-25 19:54 ` [PATCH v3 05/12] hook: detect & emit two more bugs Adrian Ratiu
2026-03-25 19:54 ` [PATCH v3 06/12] hook: replace hook_list_clear() -> string_list_clear_func() Adrian Ratiu
2026-03-25 19:54 ` [PATCH v3 07/12] hook: make consistent use of friendly-name in docs Adrian Ratiu
2026-03-25 19:54 ` [PATCH v3 08/12] t1800: add test to verify hook execution ordering Adrian Ratiu
2026-03-25 19:55 ` [PATCH v3 09/12] hook: introduce hook_config_cache_entry for per-hook data Adrian Ratiu
2026-03-25 19:55 ` [PATCH v3 10/12] hook: show config scope in git hook list Adrian Ratiu
2026-03-25 19:55 ` [PATCH v3 11/12] hook: show disabled hooks in "git hook list" Adrian Ratiu
2026-03-25 19:55 ` [PATCH v3 12/12] hook: reject unknown hook names in git-hook(1) Adrian Ratiu
2026-03-25 21:17 ` [PATCH v3 00/12] config-hook cleanups and three small git-hook features Junio C Hamano
2026-03-26 10:21 ` Adrian Ratiu
2026-03-27 8:04 ` Patrick Steinhardt
2026-03-27 16:11 ` Junio C Hamano
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=abFC6pEEmicjG6a9@pks.im \
--to=ps@pks.im \
--cc=adrian.ratiu@collabora.com \
--cc=emilyshaffer@google.com \
--cc=git@vger.kernel.org \
--cc=gitster@pobox.com \
--cc=sandals@crustytoothpaste.net \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.