excutils

与异常相关的工具。

异常 oslo_utils.excutils.CausedByException(message, cause=None)

具有关联原因的异常的基础类。

注意(harlowja):在python的后续版本中,我们可能可以删除此处需要 cause 的需求,因为 PY3+ 已经实现了 PEP 3134,它以更优雅的方式处理链式调用。

参数:
  • message – 异常消息,通常是调试或分析故障时对用户有用的字符串。

  • cause – 引起异常的原因,如果提供,它本身应该是一个异常实例,这对于创建在python版本中尚未实现/支持的异常链很有用。

在版本 2.4 中添加。

pformat(indent=2, indent_text=' ', show_root_class=False)

美观地格式化一个引起异常 + 任何相关的原因。

oslo_utils.excutils.exception_filter(should_ignore_ex)

一个阻止某些异常被引发的上下文管理器。

当需要超出子类匹配的复杂逻辑时,使用此类作为装饰器,用于一个返回给定异常是否应该被忽略的函数。例如:

>>> @exception_filter
>>> def ignore_test_assertions(ex):
...     return isinstance(ex, AssertionError) and 'test' in str(ex)

然后可以使用过滤器匹配函数作为上下文管理器

>>> with ignore_test_assertions:
...     assert False, 'This is a test'

或直接调用

>>> try:
...     assert False, 'This is a test'
... except Exception as ex:
...     ignore_test_assertions(ex)

任何不匹配的异常都将被重新引发。当过滤器用作上下文管理器时,重新引发的异常的回溯始终被保留。当过滤器作为函数调用时,只要在中间没有引发其他异常,回溯就会被保留。出于这个原因,首选上下文管理器方法,除非忽略的异常会影响控制流。

oslo_utils.excutils.forever_retry_uncaught_exceptions(*args, **kwargs)

用无限重试行为装饰提供的函数。

函数的重试延迟**始终**为一秒,除非传递了关键字参数 retry_delay,该参数定义了一个与 1.0 不同的值(小于零的值会自动更改为 0.0)。

如果发生具有相同消息的重复异常,日志记录只会每 60.0 秒输出/触发这些等效消息一次,可以通过关键字参数 same_log_delay 更改为与 60.0 秒不同的值(消息更改的异常始终会被记录,无论此延迟设置为多少)。与 retry_delay 的情况一样,如果此值小于零,它会自动更改为 0.0。

oslo_utils.excutils.raise_with_cause(exc_cls, message, *args, **kwargs)

辅助函数,用于引发 + 链式异常(如果可能)并关联一个原因

注意(harlowja):由于在 py3.x 中异常可以被链式调用(由于 PEP 3134),我们应该尝试使用给定的原因引发所需的异常(或如果能够从当前堆栈中提取一个原因),以便异常在python的旧版本和新版本中都能很好地格式化。由于 py2.x 不支持异常链式调用(或格式化),提供的异常类应该接受一个 cause 关键字参数(它可以选择忽略),以便在 py2.x 上检查/保留它,从而获得与在 py3.x 中自动包含/获取的信息类似的信息。

参数:
  • exc_cls – 要引发的异常类(通常是从 CausedByException 或等效类派生的)。

  • message – 将作为其第一个位置参数传递给异常构造函数的文本/字符串消息。

  • args – 要传递给异常构造函数的任何其他位置参数。

  • kwargs – 要传递给异常构造函数的任何其他关键字参数。

在版本 1.6 中添加。

oslo_utils.excutils.save_and_reraise_exception(reraise=True, logger=None)

保存当前异常,运行一些代码,然后重新引发。

在某些情况下,异常上下文可能会被清除,导致在运行异常处理程序后尝试重新引发 None。当 eventlet 切换绿线程或在运行异常处理程序时,代码引发并捕获异常时,可能会发生这种情况。在两种情况下,异常上下文都会被清除。

为了解决这个问题,我们保存异常状态,运行处理程序代码,然后重新引发原始异常。如果发生另一个异常,保存的异常将被记录,并且会重新引发新的异常。

在某些情况下,调用者可能不想重新引发异常,并且对于这些情况,此上下文提供了一个重新引发标志,可用于抑制异常。例如

except Exception:
    with save_and_reraise_exception() as ctxt:
        decide_if_need_reraise()
        if not should_be_reraised:
            ctxt.reraise = False

如果发生另一个异常并且重新引发标志为 False,则保存的异常将不会被记录。

如果调用者想在异常处理期间引发新的异常,他/她最初将 reraise 设置为 False,并能够根据需要将其设置回 True

except Exception:
    with save_and_reraise_exception(reraise=False) as ctxt:
        [if statements to determine whether to raise a new exception]
        # Not raising a new exception, so reraise
        ctxt.reraise = True

版本 1.4 中更改: 添加了可选参数logger