带错误代码和错误信息的自定义Python异常
class AppError(Exception):
pass
class MissingInputError(AppError):
pass
class ValidationError(AppError):
pass
...
def validate(self):
""" Validate Input and save it """
params = self.__params
if 'key' in params:
self.__validateKey(escape(params['key'][0]))
else:
raise MissingInputError
if 'svc' in params:
self.__validateService(escape(params['svc'][0]))
else:
raise MissingInputError
if 'dt' in params:
self.__validateDate(escape(params['dt'][0]))
else:
raise MissingInputError
def __validateMulti(self, m):
""" Validate Multiple Days Request"""
if m not in Input.__validDays:
raise ValidationError
self.__dCast = int(m)
validate() 和 __validateMulti() 是一个类的方法,用来验证和存储传入的参数。代码中可以看到,当某些输入参数缺失或验证失败时,我会抛出一些自定义的异常。
我想为我的应用定义一些特定的错误代码和错误信息,比如:
错误 1100: "找不到关键参数。请检查你的输入。"
错误 1101: "找不到日期参数。请检查你的输入。"
...
错误 2100: "多个日期参数无效。接受的值是 2、5 和 7。"
并将这些信息反馈给用户。
- 我该如何在自定义异常中定义这些错误代码和错误信息?
- 我该如何抛出或捕获异常,以便知道该显示哪个错误代码或信息?
(附注:这是针对 Python 2.4.3 的内容)。
Bastien Léonard 在这个 SO 评论 中提到,你不需要总是定义一个新的 __init__
或 __str__
;默认情况下,参数会被放在 self.args 中,并会通过 __str__
打印出来。
因此,我更倾向于的解决方案是:
class AppError(Exception): pass
class MissingInputError(AppError):
# define the error codes & messages here
em = {1101: "Some error here. Please verify.", \
1102: "Another here. Please verify.", \
1103: "One more here. Please verify.", \
1104: "That was idiotic. Please verify."}
用法:
try:
# do something here that calls
# raise MissingInputError(1101)
except MissingInputError, e
print "%d: %s" % (e.args[0], e.em[e.args[0]])
2 个回答
9
这是我创建的一个自定义异常的例子,它使用了一些预定义的错误代码:
class CustomError(Exception):
"""
Custom Exception
"""
def __init__(self, error_code, message='', *args, **kwargs):
# Raise a separate exception in case the error code passed isn't specified in the ErrorCodes enum
if not isinstance(error_code, ErrorCodes):
msg = 'Error code passed in the error_code param must be of type {0}'
raise CustomError(ErrorCodes.ERR_INCORRECT_ERRCODE, msg, ErrorCodes.__class__.__name__)
# Storing the error code on the exception object
self.error_code = error_code
# storing the traceback which provides useful information about where the exception occurred
self.traceback = sys.exc_info()
# Prefixing the error code to the exception message
try:
msg = '[{0}] {1}'.format(error_code.name, message.format(*args, **kwargs))
except (IndexError, KeyError):
msg = '[{0}] {1}'.format(error_code.name, message)
super().__init__(msg)
# Error codes for all module exceptions
@unique
class ErrorCodes(Enum):
ERR_INCORRECT_ERRCODE = auto() # error code passed is not specified in enum ErrorCodes
ERR_SITUATION_1 = auto() # description of situation 1
ERR_SITUATION_2 = auto() # description of situation 2
ERR_SITUATION_3 = auto() # description of situation 3
ERR_SITUATION_4 = auto() # description of situation 4
ERR_SITUATION_5 = auto() # description of situation 5
ERR_SITUATION_6 = auto() # description of situation 6
这里的枚举类型 ErrorCodes 用来定义错误代码。这个异常的创建方式是,把传入的错误代码放在异常信息的前面。
87
这里有一个简单的例子,展示了一个自定义的 Exception
类,并且它带有特别的代码:
class ErrorWithCode(Exception):
def __init__(self, code):
self.code = code
def __str__(self):
return repr(self.code)
try:
raise ErrorWithCode(1000)
except ErrorWithCode as e:
print("Received error with code:", e.code)
因为你问到了如何使用 args
,这里还有一个额外的例子...
class ErrorWithArgs(Exception):
def __init__(self, *args):
# *args is used to get a list of the parameters passed in
self.args = [a for a in args]
try:
raise ErrorWithArgs(1, "text", "some more text")
except ErrorWithArgs as e:
print("%d: %s - %s" % (e.args[0], e.args[1], e.args[2]))