1. logging模块简介
logging模块是Python内置的标准模块,无需pip安装。主要用于输出运行日志,可以设置输出日志的等级、日志保存路径、日志文件回滚等;相比print,具备如下优点:
1.可以通过设置不同的日志等级,在release版本中只输出重要信息,而不必显示大量的调试信息;
2.print将所有信息都输出到标准输出中,严重影响开发者从标准输出中查看其它数据;logging则可以由开发者决定将信息输出到什么地方,以及怎么输出。
2. logging模块使用介绍
2.1 基本使用语法
配置logging基本的设置,然后在控制台输出日志
import logging
# 基本配置,这里选择level为INFO
logging.basicConfig(level = logging.INFO,format = '%(asctime)s - %(name)s - %(levelname)s - %(message)s')
# 获取logger日志记录器实例
logger = logging.getLogger(__name__)
# 设置日志记录器层级和内容
logger.info("Start print log")
logger.debug("Do something")
logger.warning("Something maybe fail.")
logger.info("Finish")
运行时,控制台输出:
2016-10-09 19:11:19,434 - __main__ - INFO - Start print log
2016-10-09 19:11:19,434 - __main__ - WARNING - Something maybe fail.
2016-10-09 19:11:19,434 - __main__ - INFO - Finish
2.2 函数简要介绍
· 日志记录器层级
logging模块将日志分为了五个等级(level=):
层级 | 信息介绍 |
DEBUG | 调试信息,通常在诊断问题的时候用得着 |
INFO | 普通信息,确认程序安装预期运行 |
WARNING | 警告信息,表示发生了意想不到的事情,或者指示接下来可能会出现一些问题,但是程序还是继续运行 |
ERROR | 错误信息,程序运行中出现了一些问题,一些功能没有执行 |
CRITICAL | 危险信息,一个严重的错误,导致程序无法继续运行 |
级别排序存在顺序关系:DEBUG<INFO<WARNING<ERROR<CRITICAL。
五个等级的日志信息分别使用:logging模块的debug()、info()、warning()、error()、critical()方法来实现。
默认情况下,logging使用的日志级别是warning,这表示只有在这个级别及其以上级别的日志信息才会被记录,所以默认情况下debug信息和info信息都不会被显示出来。
了解到日志记录器层级后,我们将logger的级别改为DEBUG,再修改2.1的代码,观察一下输出结果:
logging.basicConfig(level = logging.DEBUG,format = '%(asctime)s - %(name)s - %(levelname)s - %(message)s')
控制台输出,可以发现,输出了debug的信息:
2016-10-09 19:12:08,289 - __main__ - INFO - Start print log
2016-10-09 19:12:08,289 - __main__ - DEBUG - Do something
2016-10-09 19:12:08,289 - __main__ - WARNING - Something maybe fail.
2016-10-09 19:12:08,289 - __main__ - INFO - Finish
· 格式器Famatter
设置日志信息的规则、结构和内容。Formatters 指定了最终某条记录打印的格式布局。Formatter会将传递来的信息拼接成一条具体的字符串,默认情况下Format只会将信息%(message)s直接打印出来。Format中有一些自带的LogRecord属性可以使用。
属性 | 描述含义 |
asctime | 将日志的时间构造成可读的形式,默认情况下是‘2016-02-08 12:00:00,123’精确到毫秒 |
filename | 包含path的文件名 |
funcName | 由哪个function发出的log |
levelname | 日志的最终等级(被filter修改后的) |
message | 日志信息 |
lineno | 当前日志的行号 |
pathname | 完整路径 |
process | 当前进程 |
thread | 当前线程 |
2.3 将日志写入到文件
2.3.1 将日志写入到文件
设置logging,创建一个FileHandler,并对输出消息的格式进行设置,将其添加到logger,然后将日志写入到指定的文件中
import logging
logger = logging.getLogger(__name__)
logger.setLevel(level = logging.INFO)
# 文件的path
handler = logging.FileHandler("log.txt")
handler.setLevel(logging.INFO)
formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')
handler.setFormatter(formatter)
logger.addHandler(handler)
logger.info("Start print log")
logger.debug("Do something")
logger.warning("Something maybe fail.")
logger.info("Finish")
log.txt中日志数据为:
2016-10-09 19:01:13,263 - __main__ - INFO - Start print log
2016-10-09 19:01:13,263 - __main__ - WARNING - Something maybe fail.
2016-10-09 19:01:13,263 - __main__ - INFO - Finish
2.3.2 将日志同时输出到屏幕和日志文件
logger中添加StreamHandler,可以将日志输出到屏幕上:
import logging
logger = logging.getLogger(__name__)
# Log等级总开关,下面输出到屏幕和文件,都以此为基础
logger.setLevel(level = logging.INFO)
handler = logging.FileHandler("log.txt")
# Log等级总开关,下面输出到log文件的层级
handler.setLevel(logging.INFO)
formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')
handler.setFormatter(formatter)
console = logging.StreamHandler()
# Log等级总开关,下面输出到屏幕的层级
console.setLevel(logging.INFO)
logger.addHandler(handler)
logger.addHandler(console)
logger.info("Start print log")
logger.debug("Do something")
logger.warning("Something maybe fail.")
logger.info("Finish")
可以在log.txt文件和控制台中看到:
2016-10-09 19:20:46,553 - __main__ - INFO - Start print log
2016-10-09 19:20:46,553 - __main__ - WARNING - Something maybe fail.
2016-10-09 19:20:46,553 - __main__ - INFO - Finish
2.3.3 日志回滚
使用RotatingFileHandler,可以实现日志回滚:
import logging
from logging.handlers import RotatingFileHandler
logger = logging.getLogger(__name__)
logger.setLevel(level = logging.INFO)
#定义一个RotatingFileHandler,最多备份3个日志文件,每个日志文件最大1K
rHandler = RotatingFileHandler("log.txt",maxBytes = 1*1024,backupCount = 3)
rHandler.setLevel(logging.INFO)
formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')
rHandler.setFormatter(formatter)
console = logging.StreamHandler()
console.setLevel(logging.INFO)
console.setFormatter(formatter)
logger.addHandler(rHandler)
logger.addHandler(console)
logger.info("Start print log")
logger.debug("Do something")
logger.warning("Something maybe fail.")
logger.info("Finish")
这也是很有用的功能,限制log文件大小。