44#include "environment.h"
55#include "gettext.h"
66#include "hook.h"
7+ #include "hook-list.h"
78#include "parse-options.h"
8- #include "strvec.h"
9- #include "abspath.h"
109
1110#define BUILTIN_HOOK_RUN_USAGE \
12- N_("git hook run [--ignore-missing] [--to-stdin=<path>] <hook-name> [-- <hook-args>]")
11+ N_("git hook run [--allow-unknown-hook-name] [-- ignore-missing] [--to-stdin=<path>] <hook-name> [-- <hook-args>]")
1312#define BUILTIN_HOOK_LIST_USAGE \
14- N_("git hook list [-z] <hook-name>")
13+ N_("git hook list [--allow-unknown-hook-name] [-z] [--show-scope] <hook-name>")
14+
15+ static int is_known_hook (const char * name )
16+ {
17+ const char * * p ;
18+ for (p = hook_name_list ; * p ; p ++ )
19+ if (!strcmp (* p , name ))
20+ return 1 ;
21+ return 0 ;
22+ }
1523
1624static const char * const builtin_hook_usage [] = {
1725 BUILTIN_HOOK_RUN_USAGE ,
@@ -35,11 +43,17 @@ static int list(int argc, const char **argv, const char *prefix,
3543 struct string_list_item * item ;
3644 const char * hookname = NULL ;
3745 int line_terminator = '\n' ;
46+ int show_scope = 0 ;
47+ int allow_unknown = 0 ;
3848 int ret = 0 ;
3949
4050 struct option list_options [] = {
4151 OPT_SET_INT ('z' , NULL , & line_terminator ,
4252 N_ ("use NUL as line terminator" ), '\0' ),
53+ OPT_BOOL (0 , "show-scope" , & show_scope ,
54+ N_ ("show the config scope that defined each hook" )),
55+ OPT_BOOL (0 , "allow-unknown-hook-name" , & allow_unknown ,
56+ N_ ("allow running a hook with a non-native hook name" )),
4357 OPT_END (),
4458 };
4559
@@ -51,15 +65,22 @@ static int list(int argc, const char **argv, const char *prefix,
5165 * arguments later they probably should be caught by parse_options.
5266 */
5367 if (argc != 1 )
54- usage_msg_opt (_ ("You must specify a hook event name to list. " ),
68+ usage_msg_opt (_ ("you must specify a hook event name to list" ),
5569 builtin_hook_list_usage , list_options );
5670
5771 hookname = argv [0 ];
5872
73+ if (!allow_unknown && !is_known_hook (hookname )) {
74+ error (_ ("unknown hook event '%s';\n"
75+ "use --allow-unknown-hook-name to allow non-native hook names" ),
76+ hookname );
77+ return 1 ;
78+ }
79+
5980 head = list_hooks (repo , hookname , NULL );
6081
6182 if (!head -> nr ) {
62- warning (_ ("No hooks found for event '%s'" ), hookname );
83+ warning (_ ("no hooks found for event '%s'" ), hookname );
6384 ret = 1 ; /* no hooks found */
6485 goto cleanup ;
6586 }
@@ -71,16 +92,27 @@ static int list(int argc, const char **argv, const char *prefix,
7192 case HOOK_TRADITIONAL :
7293 printf ("%s%c" , _ ("hook from hookdir" ), line_terminator );
7394 break ;
74- case HOOK_CONFIGURED :
75- printf ("%s%c" , h -> u .configured .friendly_name , line_terminator );
95+ case HOOK_CONFIGURED : {
96+ const char * name = h -> u .configured .friendly_name ;
97+ const char * scope = show_scope ?
98+ config_scope_name (h -> u .configured .scope ) : NULL ;
99+ if (scope )
100+ printf ("%s\t%s%s%c" , scope ,
101+ h -> u .configured .disabled ? "disabled\t" : "" ,
102+ name , line_terminator );
103+ else
104+ printf ("%s%s%c" ,
105+ h -> u .configured .disabled ? "disabled\t" : "" ,
106+ name , line_terminator );
76107 break ;
108+ }
77109 default :
78110 BUG ("unknown hook kind" );
79111 }
80112 }
81113
82114cleanup :
83- hook_list_clear (head , NULL );
115+ string_list_clear_func (head , hook_free );
84116 free (head );
85117 return ret ;
86118}
@@ -91,8 +123,11 @@ static int run(int argc, const char **argv, const char *prefix,
91123 int i ;
92124 struct run_hooks_opt opt = RUN_HOOKS_OPT_INIT ;
93125 int ignore_missing = 0 ;
126+ int allow_unknown = 0 ;
94127 const char * hook_name ;
95128 struct option run_options [] = {
129+ OPT_BOOL (0 , "allow-unknown-hook-name" , & allow_unknown ,
130+ N_ ("allow running a hook with a non-native hook name" )),
96131 OPT_BOOL (0 , "ignore-missing" , & ignore_missing ,
97132 N_ ("silently ignore missing requested <hook-name>" )),
98133 OPT_STRING (0 , "to-stdin" , & opt .path_to_stdin , N_ ("path" ),
@@ -124,6 +159,14 @@ static int run(int argc, const char **argv, const char *prefix,
124159 repo_config (the_repository , git_default_config , NULL );
125160
126161 hook_name = argv [0 ];
162+
163+ if (!allow_unknown && !is_known_hook (hook_name )) {
164+ error (_ ("unknown hook event '%s';\n"
165+ "use --allow-unknown-hook-name to allow non-native hook names" ),
166+ hook_name );
167+ return 1 ;
168+ }
169+
127170 if (!ignore_missing )
128171 opt .error_if_missing = 1 ;
129172 ret = run_hooks_opt (the_repository , hook_name , & opt );
0 commit comments