2828 'command' ,
2929 'CommandHandler' ,
3030 'Application' ,
31+ 'InternalCommandHook' ,
3132)
3233
3334from .helpers import iscoroutinefunction , resolve_coroutine , resolve_function
@@ -86,6 +87,13 @@ class Command:
8687 description : Optional [str ] = None
8788 usage : Optional [str ] = None
8889 ignore_hooks : bool = False
90+ ignore_middleware : bool = False
91+
92+ def should_ignore_internal_hooks (self ) -> bool :
93+ return self .ignore_hooks and self .name in ['-h' , '--help' , '-v' , '--version' ]
94+
95+ def should_ignore_middleware (self ) -> bool :
96+ return self .ignore_middleware and self .name in ['-h' , '--help' , '-v' , '--version' ]
8997
9098
9199def command (
@@ -269,7 +277,7 @@ async def self_handler() -> int:
269277 _ = self ._parser .parse_args ([name ])
270278 return default_exit_code
271279
272- return Command (name = name , handler = self_handler , deprecated = False , ignore_hooks = True )
280+ return Command (name = name , handler = self_handler , deprecated = False , ignore_hooks = True , ignore_middleware = True )
273281
274282 self ._commands = {
275283 '-h' : self_command ('-h' ),
@@ -303,7 +311,7 @@ async def __call__(self, args: List[str]) -> int:
303311 self ._exit_code = self ._exit_code if exit_code is None else exit_code
304312 return self ._exit_code
305313
306- async def _execute_command (self , name : str , args : List [ str ] ) -> Optional [ int ] :
314+ def _ensure_command_exists (self , name : str ) -> None :
307315 if name not in self ._parsers :
308316 if name :
309317 self ._log (msg = '{0}Command got "{1}".' .format ('[deprecated] ' if self ._deprecated else '' , name ))
@@ -314,6 +322,9 @@ async def _execute_command(self, name: str, args: List[str]) -> Optional[int]:
314322 '[deprecated] ' if self ._deprecated else '' , self ._commands [name ].handler .__name__
315323 )
316324 )
325+
326+ async def _execute_command (self , name : str , args : List [str ]) -> Optional [int ]:
327+ self ._ensure_command_exists (name = name )
317328 kwargs = await self ._resolve_command_handler_args (name , args )
318329 kwargs = await self ._resolve_command_handler_kwargs (self ._commands [name ].handler , kwargs )
319330 try :
@@ -386,14 +397,22 @@ def decorator(handler: CommandHandler) -> CommandHandler:
386397
387398 return decorator
388399
389- def should_ignore_hooks (self , args : List [str ]) -> bool :
400+ def _get_command_from_args (self , args : List [str ]) -> Optional [ Command ] :
390401 cmd : Optional [Command ] = None
391402 if len (args ) > 0 :
392403 cmd = self .get_command (name = args [0 ])
393404 if not cmd :
394405 cmd = self .get_command (name = self ._default_command )
406+ return cmd
407+
408+ def should_ignore_hooks (self , args : List [str ]) -> bool :
409+ cmd = self ._get_command_from_args (args = args )
395410 return not cmd or cmd .ignore_hooks
396411
412+ def should_ignore_internal_hooks (self , args : List [str ]) -> bool :
413+ cmd = self ._get_command_from_args (args = args )
414+ return not cmd or cmd .should_ignore_internal_hooks () or args [- 1 ] in ['-h' , '--help' , '-v' , '--version' ]
415+
397416 def add_commands (self , commands : Sequence [Command ]) -> None :
398417 for cmd in commands :
399418 self ._add_command (cmd )
@@ -469,22 +488,22 @@ def exit(self) -> None:
469488 def on_startup (self ) -> List [CommandHook ]:
470489 return self ._on_startup
471490
472- async def startup (self , all_hooks : bool = True ) -> None :
473- await self ._execute_command_hooks (self .on_startup , all_hooks )
491+ async def startup (self , all_hooks : bool = True , ignore_internal_hooks : bool = False ) -> None :
492+ await self ._execute_command_hooks (self .on_startup , all_hooks , ignore_internal_hooks )
474493
475494 @property
476495 def on_shutdown (self ) -> List [CommandHook ]:
477496 return self ._on_shutdown
478497
479- async def shutdown (self ) -> None :
480- await self ._execute_command_hooks (self ._on_shutdown )
498+ async def shutdown (self , all_hooks : bool = True , ignore_internal_hooks : bool = False ) -> None :
499+ await self ._execute_command_hooks (self ._on_shutdown , all_hooks , ignore_internal_hooks )
481500
482501 @property
483502 def on_cleanup (self ) -> List [CommandHook ]:
484503 return self ._on_cleanup
485504
486- async def cleanup (self ) -> None :
487- await self ._execute_command_hooks (self ._on_cleanup )
505+ async def cleanup (self , all_hooks : bool = True , ignore_internal_hooks : bool = False ) -> None :
506+ await self ._execute_command_hooks (self ._on_cleanup , all_hooks , ignore_internal_hooks )
488507
489508 def _add_command (self , cmd : Command ) -> None :
490509 if cmd .deprecated is None :
@@ -523,6 +542,9 @@ async def _execute_command_middleware(
523542 cmd : Command ,
524543 kwargs : Dict [str , Any ],
525544 ) -> None :
545+ if cmd .should_ignore_middleware ():
546+ self ._log (msg = 'Command middleware ignored' )
547+ return
526548 for handler in command_middleware :
527549 self ._log (
528550 msg = 'Executing middleware {0} with {1}({2})...' .format (
@@ -535,13 +557,22 @@ async def _execute_command_middleware(
535557 * ([handler ] if len (signature (handler ).parameters ) == 0 else [handler , cmd , kwargs ]) # type: ignore
536558 )
537559
538- async def _execute_command_hooks (self , command_hooks : List [CommandHook ], all_hooks : bool = True ) -> None :
560+ async def _execute_command_hooks (
561+ self ,
562+ command_hooks : List [CommandHook ],
563+ all_hooks : bool = True ,
564+ ignore_internal_hooks : bool = False ,
565+ ) -> None :
539566 command_hooks_ = (
540- command_hooks if all_hooks else [hook for hook in command_hooks if isinstance (hook , InternalCommandHook )]
567+ command_hooks
568+ if all_hooks
569+ else [
570+ hook .__call__
571+ for hook in command_hooks
572+ if isinstance (hook , InternalCommandHook ) and not ignore_internal_hooks
573+ ]
541574 )
542575 for hook in command_hooks_ :
543- if isinstance (hook , InternalCommandHook ):
544- hook = hook .__call__
545576 self ._log (
546577 msg = 'Executing hook "{0}" ({1})' .format (
547578 hook .__name__ if hasattr (hook , '__name__' ) else 'unknown' , id (hook )
0 commit comments