@@ -279,9 +279,38 @@ def _require_token(token, args):
279279
280280
281281def main ():
282+ command_help = [
283+ ("accept-invite" , "Accept an invite" ),
284+ ("assign-group" , "Assign group(s) to a user" ),
285+ ("config-example" , "Print a sample usermanager.toml" ),
286+ ("create-group" , "Create user group" ),
287+ ("deassign-group" , "Remove group(s) from a user" ),
288+ ("delete-group" , "Delete user group" ),
289+ ("delete-user" , "Delete user by id/email/username" ),
290+ ("generate-api-token" , "Print just the access token for a user" ),
291+ ("get-group" , "Get user group by id or name" ),
292+ ("get-user" , "Get user by id/email/username" ),
293+ ("invite" , "Invite a new user" ),
294+ ("invite-url" , "Preview invite URL base" ),
295+ ("list-groups" , "List user groups" ),
296+ ("list-users" , "List users" ),
297+ ("login" , "Get a full auth token response" ),
298+ ("update-user" , "Patch user by id/email/username" ),
299+ ("whoami" , "Show current user" ),
300+ ]
301+ command_list = "\n " .join (
302+ f" { name :<18} { desc } " for name , desc in command_help
303+ )
282304 default_paths = "\n " .join (f" - { path } " for path in DEFAULT_CONFIG_PATHS )
283305 parser = argparse .ArgumentParser (
284306 description = "KernelCI API user management helper" ,
307+ usage = (
308+ "usermanager.py [-h] [--config CONFIG] [--api-url API_URL] "
309+ "[--token TOKEN] [--instance INSTANCE] [--token-label TOKEN_LABEL]\n "
310+ " <command> [<args>]\n \n "
311+ "Commands:\n "
312+ f"{ command_list } "
313+ ),
285314 epilog = (
286315 "Examples:\n "
287316 " ./scripts/usermanager.py invite --username alice --email "
@@ -290,10 +319,12 @@ def main():
290319 " ./scripts/usermanager.py login --username alice\n "
291320 " ./scripts/usermanager.py whoami\n "
292321 " ./scripts/usermanager.py list-users --instance staging\n "
293- " ./scripts/usermanager.py print- config-example\n "
322+ " ./scripts/usermanager.py config-example\n "
294323 "\n "
295324 "Default config lookup (first match wins):\n "
296325 f"{ default_paths } \n "
326+ "\n "
327+ "Run '<command> -h' for command-specific help.\n "
297328 ),
298329 formatter_class = argparse .RawDescriptionHelpFormatter ,
299330 )
@@ -312,6 +343,57 @@ def main():
312343
313344 subparsers = parser .add_subparsers (dest = "command" , required = True )
314345
346+ accept = subparsers .add_parser ("accept-invite" , help = "Accept an invite" )
347+ accept .add_argument ("--token" )
348+ accept .add_argument ("--password" )
349+
350+ assign_group = subparsers .add_parser (
351+ "assign-group" , help = "Assign group(s) to a user"
352+ )
353+ assign_group .add_argument ("user_id" )
354+ assign_group .add_argument (
355+ "--group" ,
356+ action = "append" ,
357+ default = [],
358+ help = "Group name or id; can be used multiple times or with commas" ,
359+ )
360+
361+ subparsers .add_parser (
362+ "config-example" , help = "Print a sample usermanager.toml"
363+ )
364+
365+ create_group = subparsers .add_parser ("create-group" , help = "Create user group" )
366+ create_group .add_argument ("name" )
367+
368+ deassign_group = subparsers .add_parser (
369+ "deassign-group" , help = "Remove group(s) from a user"
370+ )
371+ deassign_group .add_argument ("user_id" )
372+ deassign_group .add_argument (
373+ "--group" ,
374+ action = "append" ,
375+ default = [],
376+ help = "Group name or id; can be used multiple times or with commas" ,
377+ )
378+
379+ delete_group = subparsers .add_parser ("delete-group" , help = "Delete user group" )
380+ delete_group .add_argument ("group_id" )
381+
382+ delete_user = subparsers .add_parser ("delete-user" , help = "Delete user by id" )
383+ delete_user .add_argument ("user_id" )
384+
385+ generate_token = subparsers .add_parser (
386+ "generate-api-token" , help = "Print just the access token for a user"
387+ )
388+ generate_token .add_argument ("--username" , required = True )
389+ generate_token .add_argument ("--password" )
390+
391+ get_group = subparsers .add_parser ("get-group" , help = "Get user group by id or name" )
392+ get_group .add_argument ("group_id" )
393+
394+ get_user = subparsers .add_parser ("get-user" , help = "Get user by id" )
395+ get_user .add_argument ("user_id" )
396+
315397 invite = subparsers .add_parser ("invite" , help = "Invite a new user" )
316398 invite .add_argument ("--username" , required = True )
317399 invite .add_argument ("--email" , required = True )
@@ -324,27 +406,14 @@ def main():
324406
325407 invite_url = subparsers .add_parser ("invite-url" , help = "Preview invite URL base" )
326408
327- accept = subparsers .add_parser ("accept-invite " , help = "Accept an invite " )
328- accept . add_argument ( "--token" )
329- accept . add_argument ( "--password " )
409+ list_groups = subparsers .add_parser ("list-groups " , help = "List user groups " )
410+
411+ list_users = subparsers . add_parser ( "list-users" , help = "List users " )
330412
331413 login = subparsers .add_parser ("login" , help = "Get an auth token" )
332414 login .add_argument ("--username" , required = True )
333415 login .add_argument ("--password" )
334416
335- generate_token = subparsers .add_parser (
336- "generate-api-token" , help = "Print just the access token for a user"
337- )
338- generate_token .add_argument ("--username" , required = True )
339- generate_token .add_argument ("--password" )
340-
341- whoami = subparsers .add_parser ("whoami" , help = "Show current user" )
342-
343- list_users = subparsers .add_parser ("list-users" , help = "List users" )
344-
345- get_user = subparsers .add_parser ("get-user" , help = "Get user by id" )
346- get_user .add_argument ("user_id" )
347-
348417 update_user = subparsers .add_parser ("update-user" , help = "Patch user by id" )
349418 update_user .add_argument ("user_id" )
350419 update_user .add_argument ("--data" , help = "JSON object with fields to update" )
@@ -396,49 +465,11 @@ def main():
396465 help = "Remove group(s); can be used multiple times or with commas" ,
397466 )
398467
399- delete_user = subparsers .add_parser ("delete-user" , help = "Delete user by id" )
400- delete_user .add_argument ("user_id" )
401-
402- assign_group = subparsers .add_parser (
403- "assign-group" , help = "Assign group(s) to a user"
404- )
405- assign_group .add_argument ("user_id" )
406- assign_group .add_argument (
407- "--group" ,
408- action = "append" ,
409- default = [],
410- help = "Group name or id; can be used multiple times or with commas" ,
411- )
412-
413- deassign_group = subparsers .add_parser (
414- "deassign-group" , help = "Remove group(s) from a user"
415- )
416- deassign_group .add_argument ("user_id" )
417- deassign_group .add_argument (
418- "--group" ,
419- action = "append" ,
420- default = [],
421- help = "Group name or id; can be used multiple times or with commas" ,
422- )
423-
424- list_groups = subparsers .add_parser ("list-groups" , help = "List user groups" )
425-
426- get_group = subparsers .add_parser ("get-group" , help = "Get user group by id or name" )
427- get_group .add_argument ("group_id" )
428-
429- create_group = subparsers .add_parser ("create-group" , help = "Create user group" )
430- create_group .add_argument ("name" )
431-
432- delete_group = subparsers .add_parser ("delete-group" , help = "Delete user group" )
433- delete_group .add_argument ("group_id" )
434-
435- subparsers .add_parser (
436- "print-config-example" , help = "Print a sample usermanager.toml"
437- )
468+ whoami = subparsers .add_parser ("whoami" , help = "Show current user" )
438469
439470 args = parser .parse_args ()
440471
441- if args .command == "print- config-example" :
472+ if args .command == "config-example" :
442473 print (
443474 'default_instance = "local"\n \n '
444475 "[instances.local]\n "
0 commit comments