Python日志的汇总计数

7 投票
2 回答
2838 浏览
提问于 2025-04-15 22:47

在我的Python程序结束时,我想要得到一个总结,显示通过标准的logging模块记录的项目数量。我特别想要能够获取每个指定名称的计数(可能还包括它的子项)。比如,如果我有:

input_logger = getLogger('input')
input_logger.debug("got input1")
input_logger.debug("got input2")
input_logger.debug("got input3")

network_input_logger = getLogger('input.network')
network_input_logger.debug("got network input1")
network_input_logger.debug("got network input2")

getLogger('output')
output_logger.debug("sent output1")

那么在最后我想得到一个这样的总结:

input: 5
input.network: 2
output: 1

我在想,是否可以通过调用一个getcount()的方法来实现,针对一个记录器或处理器。

有什么好的方法可以实现这个呢?我想这可能涉及到对logging模块中某个类的子类化,但我不太确定最好的方法是什么。

2 个回答

2

我觉得装饰器模式可能是实现这个功能最简洁的方法。

你会把一个Logger的实例传入LoggerDecorator,这个装饰器会和Logger有相同的接口。当调用其中一个方法时,就会根据需要增加一个成员变量的值。然后,实现getCount()方法就非常简单了。

这里有一个关于在Python中实现装饰器的参考资料:

http://wiki.python.org/moin/DecoratorPattern

3

使用装饰器可以让代码看起来很优雅,我还没测试过,但类似这样的写法可能会有效:

class myDecorator(object):
    def __init__(self, inner):
        self.inner = inner
        self.log = {}

    def __getattr__(self,name):
        self.log[name] = self.log.get(name,0)+1
        return getattr(self.inner,name)

    def __setattr__(self,name,value):
        setattr(self.inner,name,value)

我意识到你并不是想记录每个方法被调用的次数,而是想记录每个不同的日志记录器被调用的次数。不过我觉得用装饰器来实现这个功能还是挺优雅的。

我觉得我可能没睡好,想法是把对日志记录器的调用包裹起来,我把装饰器的用法和装饰器模式搞混了。(其实把这两者结合起来会是个很好的解决方案)

这里有一个更完整的解决方案。抱歉,我意识到我就是那个在网上犯错的人

class LoggerLogger(object):
    def __init__(self,inner,name):
        self.inner = inner
        self.calls = 0
    def __call__(self,*args,**kwargs):
        self.calls += 1
        return self.inner(*args,**kwargs)


def loggerDecorator(func):
    def inner(name):
        logger = func(name)
        logger.debug = LoggerLogger(logger.debug,name)
    return inner

getLogger = loggerDecorator(getLogger)

撰写回答