traceback回溯获取调用信息

我有一个警报服务,遇到异常会通过警报服务钉钉通知我,因为多层函数嵌套调用,某个子函数可能有异常,但是该异常又不会影响最后的程序执行,我只是希望能得到通知,于是有了下面这样的一个装饰器

def fault_tolerant(error_return: Any = None, send_alert: bool = True):
    """[装饰器]
    容错机制,捕获错误,发送警报消息

    Args:
        func (function): 函数体
    """
    def decorator_function(func):
        @wraps(func)
        def wrapper_function(*args, **kw):
            try:
                return func(*args, **kw)
            except Exception as e:                
                if send_alert:
                    alert(e)
                return error_return
        return wrapper_function
    return decorator_function

以上装饰器支持异常捕获,遇到异常可以返回默认值error_return,如果send_alert=True则发出警报通知

然后我的服务如下demo

from util import fault_tolerant


def task(msg: dict = {}):
    print(msg)
    fun1(msg['a'])


def fun1(a):
    print(a)
    fun2(a + 1)


def fun2(b):
    print(b)
    c = foo(1, 0)
    print(c)


@fault_tolerant(0)
def foo(x, y):
    return x / y


if __name__ == '__main__':
    task({'a': 1, 'b': 2})

这个时候从装饰器里想知道最初调用传入的msg是什么该怎么办呢?

仅从装饰器中只能获取到被装饰函数的传参而已,为了获取最初调用的传参我们就要用到traceback来实现,灵感来源于loguru的logger.exception(e),如下图:

 那以上这些信息是怎么获取到的呢? 就是利用了traceback来实现的,回溯函数如下:

# loguru/_get_frame.py

import sys
from sys import exc_info


def get_frame_fallback(n):
    try:
        raise Exception
    except Exception:
        frame = exc_info()[2].tb_frame.f_back
        for _ in range(n):
            frame = frame.f_back
        return frame


if hasattr(sys, "_getframe"):
    get_frame = sys._getframe
else:
    get_frame = get_frame_fallback

因为我们只是关注最初调用的task函数中的msg传参,于是我封装了以下函数用于获取该传参

def get_task_msg_fallback(function_name: str = 'task', key: str = 'msg', default: Any = {}) -> Any:
    try:
        raise Exception
    except Exception:
        frame = sys.exc_info()[2].tb_frame.f_back
        while frame:
            if function_name in frame.__str__():
                return frame.f_locals.get(key, default)
            frame = frame.f_back
        return default
    finally:
        del frame

然后我们的装饰器就可以获取最初传参数据了

def fault_tolerant(error_return: Any = None, send_alert: bool = True):
    """[装饰器]
    容错机制,捕获错误,发送警报消息

    Args:
        func (function): 函数体
    """
    def decorator_function(func):
        @wraps(func)
        def wrapper_function(*args, **kw):
            try:
                return func(*args, **kw)
            except Exception as e:
                task_msg = get_task_msg_fallback()
                print(task_msg)
                if send_alert:
                    alert(e, task_msg=task_msg)
                return error_return
        return wrapper_function
    return decorator_function

警报消息也带上了task_msg参数信息了

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Python的`traceback`模块是Python内置的一个标准库,用于处理和管理异常的回溯信息。当程序运行中发生异常时,`traceback`模块可以捕获并展示异常的详细信息,包括错误的位置、调用堆栈和代码行数等,帮助开发者定位和修复问题。 `traceback`模块提供了一系列的函数,用于获取和处理异常的回溯信息。其中最常用的函数是`print_exc()`和`format_exc()`。`print_exc()`函数将异常信息输出到标准错误流,并在最后输出当前堆栈的跟踪信息;`format_exc()`函数会将异常信息以字符串的形式返回,方便后续处理。 除了这两个函数,`traceback`模块还提供了一些其他的函数,如`print_exception()`、`print_tb()`等,用于在不同的场景下展示异常信息。此外,还有一些函数可以获取和处理堆栈信息,如`extract_tb()`、`extract_stack()`等。 `traceback`模块常常在调试程序、定位问题和日志记录中使用。通过查看异常回溯信息,我们可以追踪异常的发生位置、调用链路和代码行数,从而快速定位问题所在。在开发过程中,我们可以使用try/except结构,捕获并处理异常,当程序发生异常时,就可以利用`traceback`模块输出详细的异常回溯信息,方便我们进行debug。 总之,`traceback`模块是Python中用于处理和管理异常回溯信息的标准库之一。通过使用`traceback`模块,我们可以方便地查看异常的详细信息,从而确保程序的健壮性和高效性。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值