在Python中使用setLevel()设置日志级别

在任何程序员的生活中,日志是一个非常有效的工具。它不仅使我们更好地了解程序的流程,还能了解程序执行过程中可能发生的错误。

Python提供了一个单独的logging 模块,作为其标准库的一部分,使日志记录更加容易。本文将讨论日志setLevel ,以及它在Python中如何工作。

Python程序中的日志功能

日志是一个在软件运行时跟踪程序流程的过程。然而,如果你不在你的程序中实现日志记录,每当程序崩溃时,就很难找到发生问题的根源。

如果在你的程序中实现了日志记录,你可以很容易地找到问题的根源,并在短时间内解决它。在调试和开发软件时,它是非常有用的。

有时,人们使用print 语句来查找软件中的问题。打印可以解决简单脚本的问题,但对于更大更复杂的软件来说,它们并不是一个好的选择。

Python从其标准库中提供了一个叫做logging 的内置模块,它可以向任何输出流或文件写入状态信息,说明程序的哪个部分正在运行,以及出现了什么问题。

Python中日志信息的级别

Python中的logging 模块根据其重要性有不同的状态/日志信息级别。因此,一个日志消息的级别告诉你这个日志消息有多重要。

日志消息的不同级别如下:DEBUG,INFO,WARNING,ERROR, 和CRITICAL, 其中CRITICAL 的重要性最高。

日志级别 说明
DEBUG 它用于软件的调试目的。通常在问题发生时给出详细的信息。
INFO 它确保程序中的一切工作正常。
WARNING 它用来告诉人们一些问题可能在未来发生,应该解决以避免未来的问题。
ERROR 它用来标志着由于严重的问题,软件已经无法执行特定的功能。
CRITICAL 这个级别标志着一个严重的问题,导致了软件的停止运行。

所有这些级别都是为处理程序或记录器设置的,以便在错误发生时可以在适当的时间显示适当的信息。上面根据日志级别的重要性进行了解释,第一个级别是最不重要的,最后一个(CRITICAL 级别)是最重要的。

使用Python日志模块中的setLevel() 函数设置日志级别

setLevel(level) 函数用于将记录器的阈值设置为指定级别。小于指定级别的日志信息被忽略,而严重程度较高的信息则由服务于该日志器的相应处理程序发出。

Python中的日志有一个有效级别的概念。最初,当一个日志记录器被创建时,它被设置为一个级别NOTSET

然而,这个NOTSET 并不是有效级别。有效级别是在setLevel(level) 的帮助下被明确设置的级别。

当一个日志记录器被创建时,如果它的级别没有被明确设置,那么它的父日志记录器的级别将被检查,以获得该日志记录器的有效级别,该级别将通过setLevel(level) 明确设置。如果父日志记录器也没有被设置为有效级别,那么将检查它的父日志记录器。

这个过程一直持续到找到NOTSET 以外的级别或达到根记录器为止。根记录器的默认级别为WARNING ;因此,在这种情况下,根的默认级别将被视为有效级别。

现在,让我们通过一些代码实例来看看setLevel(level) 的用法。

import logging
logging.debug('Debug message')
logging.info('Info message')
logging.warning('Warning message')
logging.error('Error message')
logging.critical('Critical message')

输出:

WARNING:root:Warning message
ERROR:root:Error message
CRITICAL:root:Critical message

从上面的输出中可以看出,只有WARNING,ERROR, 和CRITICAL 的消息被打印出来,因为根记录器的默认级别WARNING 被认为是有效级别,因为没有指定其他记录器或其父级。因此,所有来自WARNING 及以后级别的消息都被打印出来,而不太重要的消息被忽略。

让我们看一个例子,记录器将有效级别视为父级的级别。

import logging
parent_logger = logging.getLogger('parent')
parent_logger.setLevel(4)
child_logger = logging.getLogger('parent.child')
print(parent_logger.getEffectiveLevel())
print(child_logger.getEffectiveLevel())

输出:

4
4

正如你所看到的,child_logger 还没有被设置为有效级别,所以parent_logger 的级别被用作有效级别。

Python中的日志处理程序

Python中的处理程序是负责将适当的日志信息记录到处理程序指定的目的地的对象;这些处理程序也像日志器一样工作。如果一个日志记录器没有设置处理程序,它的祖先会被搜索到一个处理程序。

现在让我们看看处理程序在日志中的用法:

import logging
logger = logging.getLogger('example')
logger.setLevel(logging.INFO)
fileHandler = logging.FileHandler('p1.log')
fileHandler.setLevel(logging.INFO)
chl = logging.StreamHandler()
chl.setLevel(logging.INFO)
logger.addHandler(fileHandler)
logger.addHandler(chl)
logger.info('Information')

输出:

Information

我们在上面的代码中创建了两个处理程序:fileHandlerchlfileHandler 将记录发送到p1.log 文件中,而chl 处理程序将记录发送到流中。

然而,如果没有指定流,那么就使用sys.stderr 。最后,处理程序被添加到记录器中,使用addHandler

现在你一定想知道为什么我们设置了两次级别:一次用于记录器,另一次用于处理程序。你可以删除处理程序上的setLevel() ,这将把消息的所有级别过滤留给记录器。

然而,如果你为处理程序和记录器设置了级别,就会出现不同的情况。日志器首先根据级别过滤消息;因此,如果你将日志器设置为WARNING,INFO, 或任何更高的级别,而处理程序设置为DEBUG ,你将不会收到任何DEBUG 的日志消息,因为日志器在第一时间忽略了它。

同样,如果你将日志记录器设置为DEBUG ,而处理程序设置为任何更高的级别,如INFO ,你也不会收到任何DEBUG 的消息,因为处理程序会拒绝它们。即使记录器批准了它,处理程序也会拒绝它(因为INFO >DEBUG )。

因此,在为记录器和处理程序设置级别时应足够小心,以确保软件的正常工作。

总结

在这篇文章中,我们已经讨论了日志setLevel() ,以及它是如何在Python中工作的。

日志是一个非常有效的工具,通过记录程序的流程和寻找错误的可能性来管理软件或程序的代码。对于Python中的日志记录,我们根据其重要性为不同的日志信息设置不同的级别。

所有这些级别都是通过setLevel ,在这篇文章中已经做了很详细的解释。