import typing as t
from gettext import gettext as _
from gettext import ngettext
from . _compat import get_text_stderr
from . utils import echo
from . utils import format_filename
if t . TYPE_CHECKING :
from . core import Command
from . core import Context
from . core import Parameter
def _join_param_hints (
param_hint : t . Optional [ t . Union [ t . Sequence [ str ] , str ] ]
) - > t . Optional [ str ] :
if param_hint is not None and not isinstance ( param_hint , str ) :
return " / " . join ( repr ( x ) for x in param_hint )
return param_hint
class ClickException ( Exception ) :
""" An exception that Click can handle and show to the user. """
#: The exit code for this exception.
exit_code = 1
def __init__ ( self , message : str ) - > None :
super ( ) . __init__ ( message )
self . message = message
def format_message ( self ) - > str :
return self . message
def __str__ ( self ) - > str :
return self . message
def show ( self , file : t . Optional [ t . IO [ t . Any ] ] = None ) - > None :
if file is None :
file = get_text_stderr ( )
echo ( _ ( " Error: {message} " ) . format ( message = self . format_message ( ) ) , file = file )
class UsageError ( ClickException ) :
""" An internal exception that signals a usage error. This typically
aborts any further handling .
: param message : the error message to display .
: param ctx : optionally the context that caused this error . Click will
fill in the context automatically in some situations .
"""
exit_code = 2
def __init__ ( self , message : str , ctx : t . Optional [ " Context " ] = None ) - > None :
super ( ) . __init__ ( message )
self . ctx = ctx
self . cmd : t . Optional [ " Command " ] = self . ctx . command if self . ctx else None
def show ( self , file : t . Optional [ t . IO [ t . Any ] ] = None ) - > None :
if file is None :
file = get_text_stderr ( )
color = None
hint = " "
if (
self . ctx is not None
and self . ctx . command . get_help_option ( self . ctx ) is not None
) :
hint = _ ( " Try ' {command} {option} ' for help. " ) . format (
command = self . ctx . command_path , option = self . ctx . help_option_names [ 0 ]
)
hint = f " { hint } \n "
if self . ctx is not None :
color = self . ctx . color
echo ( f " { self . ctx . get_usage ( ) } \n { hint } " , file = file , color = color )
echo (
_ ( " Error: {message} " ) . format ( message = self . format_message ( ) ) ,
file = file ,
color = color ,
)
class BadParameter ( UsageError ) :
""" An exception that formats out a standardized error message for a
bad parameter . This is useful when thrown from a callback or type as
Click will attach contextual information to it ( for instance , which
parameter it is ) .
. . versionadded : : 2.0
: param param : the parameter object that caused this error . This can
be left out , and Click will attach this info itself
if possible .
: param param_hint : a string that shows up as parameter name . This
can be used as alternative to ` param ` in cases
where custom validation should happen . If it is
a string it ' s used as such, if it ' s a list then
each item is quoted and separated .
"""
def __init__ (
self ,
message : str ,
ctx : t . Optional [ " Context " ] = None ,
param : t . Optional [ " Parameter " ] = None ,
param_hint : t . Optional [ str ] = None ,
) - > None :
super ( ) . __init__ ( message , ctx )
self . param = param
self . param_hint = param_hint
def format_message ( self ) - > str :
if self . param_hint is not None :
param_hint = self . param_hint
elif self . param is not None :
param_hint = self . param . get_error_hint ( self . ctx ) # type: ignore
else :
return _ ( " Invalid value: {message} " ) . format ( message = self . message )
return _ ( " Invalid value for {param_hint} : {message} " ) . format (
param_hint = _join_param_hints ( param_hint ) , message = self . message
)
class MissingParameter ( BadParameter ) :
""" Raised if click required an option or argument but it was not
provided when invoking the script .
. . versionadded : : 4.0
: param param_type : a string that indicates the type of the parameter .
The default is to inherit the parameter type from
the given ` param ` . Valid values are ` ` ' parameter ' ` ` ,
` ` ' option ' ` ` or ` ` ' argument ' ` ` .
"""
def __init__ (
self ,
message : t . Optional [ str ] = None ,
ctx : t . Optional [ " Context " ] = None ,
param : t . Optional [ " Parameter " ] = None ,
param_hint : t . Optional [ str ] = None ,
param_type : t . Optional [ str ] = None ,
) - > None :
super ( ) . __init__ ( message or " " , ctx , param , param_hint )
self . param_type = param_type
def format_message ( self ) - > str :
if self . param_hint is not None :
param_hint : t . Optional [ str ] = self . param_hint
elif self . param is not None :
param_hint = self . param . get_error_hint ( self . ctx ) # type: ignore
else :
param_hint = None
param_hint = _join_param_hints ( param_hint )
param_hint = f " { param_hint } " if param_hint else " "
param_type = self . param_type
if param_type is None and self . param is not None :
param_type = self . param . param_type_name
msg = self . message
if self . param is not None :
msg_extra = self . param . type . get_missing_message ( self . param )
if msg_extra :
if msg :
msg + = f " . { msg_extra } "
else :
msg = msg_extra
msg = f " { msg } " if msg else " "
# Translate param_type for known types.
if param_type == " argument " :
missing = _ ( " Missing argument " )
elif param_type == " option " :
missing = _ ( " Missing option " )
elif param_type == " parameter " :
missing = _ ( " Missing parameter " )
else :
missing = _ ( " Missing {param_type} " ) . format ( param_type = param_type )
return f " { missing } { param_hint } . { msg } "
def __str__ ( self ) - > str :
if not self . message :
param_name = self . param . name if self . param else None
return _ ( " Missing parameter: {param_name} " ) . format ( param_name = param_name )
else :
return self . message
class NoSuchOption ( UsageError ) :
""" Raised if click attempted to handle an option that does not
exist .
. . versionadded : : 4.0
"""
def __init__ (
self ,
option_name : str ,
message : t . Optional [ str ] = None ,
possibilities : t . Optional [ t . Sequence [ str ] ] = None ,
ctx : t . Optional [ " Context " ] = None ,
) - > None :
if message is None :
message = _ ( " No such option: {name} " ) . format ( name = option_name )
super ( ) . __init__ ( message , ctx )
self . option_name = option_name
self . possibilities = possibilities
def format_message ( self ) - > str :
if not self . possibilities :
return self . message
possibility_str = " , " . join ( sorted ( self . possibilities ) )
suggest = ngettext (
" Did you mean {possibility} ? " ,
" (Possible options: {possibilities} ) " ,
len ( self . possibilities ) ,
) . format ( possibility = possibility_str , possibilities = possibility_str )
return f " { self . message } { suggest } "
class BadOptionUsage ( UsageError ) :
""" Raised if an option is generally supplied but the use of the option
was incorrect . This is for instance raised if the number of arguments
for an option is not correct .
. . versionadded : : 4.0
: param option_name : the name of the option being used incorrectly .
"""
def __init__ (
self , option_name : str , message : str , ctx : t . Optional [ " Context " ] = None
) - > None :
super ( ) . __init__ ( message , ctx )
self . option_name = option_name
class BadArgumentUsage ( UsageError ) :
""" Raised if an argument is generally supplied but the use of the argument
was incorrect . This is for instance raised if the number of values
for an argument is not correct .
. . versionadded : : 6.0
"""
class FileError ( ClickException ) :
""" Raised if a file cannot be opened. """
def __init__ ( self , filename : str , hint : t . Optional [ str ] = None ) - > None :
if hint is None :
hint = _ ( " unknown error " )
super ( ) . __init__ ( hint )
self . ui_filename : str = format_filename ( filename )
self . filename = filename
def format_message ( self ) - > str :
return _ ( " Could not open file {filename!r} : {message} " ) . format (
filename = self . ui_filename , message = self . message
)
class Abort ( RuntimeError ) :
""" An internal signalling exception that signals Click to abort. """
class Exit ( RuntimeError ) :
""" An exception that indicates that the application should exit with some
status code .
: param code : the status code to exit with .
"""
__slots__ = ( " exit_code " , )
def __init__ ( self , code : int = 0 ) - > None :
self . exit_code : int = code