我在Pyramid框架上编写了一个Python应用程序。
我们真的利用标准导入库来登录(用于调试)。
当我们对生产进行分析时,我们的日志活动似乎有相当多的开销。所有的字符串格式和循环加起来。我想删除它,但我们不能 - 我们确实需要将其保留用于测试,有时需要在生产环境中进行调试。
我想知道是否有人根据需要有最小化日志记录的有效策略,因此这些代码可以在我们的生产环境执行期间“优化掉”而不会运行。
例如,在mod_perl下,编译器将“优化”在False常量下运行的语句
在psuedocode中...(我很久没有碰过perl了!)
use constant DEBUG => False ;
if ( DEBUG ) {
log.debug("stuff here " + string );
}
或
use constant DEBUG => False ;
DEBUG && log.debug("stuff here " + string );
在这些情况下,调用log.debug甚至字符串插值都不会发生。
有人可以推荐一种在Python下模仿这种行为的有效方法吗?
答案 0 :(得分:7)
当您可以使用log.debug('stuff here %s', string)
时,请勿使用连接;记录模块推迟插值,直到记录时实际格式化字符串。如果已禁用DEBUG
日志级别,则不会进行插值。
您还可以测试日志记录级别,以避免收集昂贵的日志记录信息,除非需要:
if logger.isEnabledFor(logging.DEBUG):
logger.debug('Message with %s, %s', expensive_func1(),
expensive_func2())
答案 1 :(得分:6)
使用__debug__
。当Python使用False
命令行标志运行时,此标志设置为-O
,Python将在编译时优化调试代码。 I wrote a blog post on it几个月前。
答案 2 :(得分:0)
我建议将assert
用于此目的,因为它在优化模式下很好地进行了优化。
在这种情况下,无需手动检查是否启用了日志记录级别。这在执行可用于日志记录的昂贵格式化操作时非常有用(例如使用pprint
模块)。
一个例子:
而不是
logging.debug('my message %s', pprint.pformat(mycomplexdata))
assert(logging.debug('my message %s', pprint.pformat(mycomplexdata)) or True)
(部分or True
确保断言不会失败。)
在这种情况下甚至可以使用.format
而不会因使用-O
而造成性能损失。
assert(logging.debug('my message {}'.format(pprint.pformat(mycomplexdata))) or True)
使用-O
运行python时,assert()中的所有内容都被优化了。