logging
是python自帶的標準庫,無需使用pip
進行安裝挺智。
import logging
日志模塊作用
- 用于程序開發(fā)過程中的調(diào)試和運行記錄
- 可以輸出到日志文件矾瑰,方便開發(fā)人員和運維人員對已經(jīng)在現(xiàn)場部署程序的運行狀態(tài)的掌握衷佃,若程序報錯或運行結(jié)果不對欺冀,可根據(jù)日志文件進行錯誤定位。
日志級別
logging
模塊預(yù)定義了5種日志級別试幽,并根據(jù)它們所跟蹤的事件的級別或嚴重程度來命名筝蚕,具體如下:
Level | Numeric Value | When it's used |
---|---|---|
DEBUG |
10 | 報告詳細的程序運行結(jié)果,用于調(diào)試 |
INFO |
20 | 報告程序正常運行期間發(fā)生的事件铺坞,或一些結(jié)果記錄饰及,確認程序在按照預(yù)期進行。 |
WARNING |
30 | 發(fā)出關(guān)于特定運行時事件的警告康震,說明程序本身對這種情況的處理是無能為力的燎含,但是依然需要報告該情況。(例如輸入數(shù)據(jù)小于0等不是由于算法造成的情況) |
ERROR |
40 | 報告異常腿短,由于一個更嚴重的問題屏箍,程序已經(jīng)不能執(zhí)行一些功能。 |
CRITICAL |
50 | 表明程序本身可能無法繼續(xù)運行橘忱。 |
注意:
在配置日志模塊時赴魁,需要設(shè)定日志級別,低于該日志級別的日志記錄將不會被打印輸出钝诚。(默認級別是
WARNING
)可以自己自定義新的日志級別颖御,當新定義的numeric value與預(yù)定義的value重復時,預(yù)定義的級別將會被覆蓋
日志模塊的四個重要組件
Loggers:算法與日志模塊的接口
Handlers:將日志記錄發(fā)送到指定的目標(控制臺凝颇、文件潘拱、郵件等)
Formatters:指定最終輸出中日志記錄的樣式。
Filters:為確定輸出哪些日志記錄提供了更細粒度的工具拧略。
Loggers
Logger
對象有三個功能:
- 提供接口給算法芦岂,算法在運行時通過調(diào)用這些接口來記錄日志
- 根據(jù)級別或過濾對象確定要對哪些日志消息進行操作(to
Handles
)。 - 將日志消息傳遞給所有與之相關(guān)的處理器垫蛆。
Logger
對象的使用最廣泛的方法主要是:配置和記錄消息
常用配置:
-
Logger.setLever()
: 用于設(shè)置日志級別 -
Logger.addHandler()
: 添加處理器 -
Logger.addFilter()
: 添加過濾器
記錄消息
當配置了Logger
對象后禽最,就可以使用Logger.debug()
, Logger.info()
, Logger.warning
, Logger.error
, Logger.critical()
方法來創(chuàng)建日志消息,只需將需要記錄的消息寫進括號內(nèi)即可
所有需要被記錄的消息實際上是一個字符串袱饭,它可以包含標準字符串替換語法
%s
川无、%d
、%f
等來實現(xiàn)具體數(shù)據(jù)的輸出虑乖。
Handlers
Handler
對象負責將日志消息(基于日志消息的嚴重性)分派給處理器的指定目標懦趋。在上一步中提到,可以使用Logger.addHandler()
來添加零個或多個處理器對象决左。例如愕够,算法可以將所有日志消息都發(fā)送到控制臺,將ERROR
或者更高級別的消息發(fā)送到磁盤文件佛猛。這就需要兩個單獨的處理器惑芭。
處理器有很多種類,常用的主要有以下幾種:
StreamHandler: 將日志記錄輸出到數(shù)據(jù)流(例如sys.stdout, sys.stderr, 或者任何文件類對象)
FileHandler:將日志記錄輸出到磁盤文件中继找,它繼承了
StreamHandler
的輸出RotatingFileHandler:支持磁盤日志文件按文件大小輪換遂跟。當文件即將超出預(yù)定大小時,將關(guān)閉舊文件并打開一個新文件用于輸出婴渡。
TimedRotatingFileHandler:支持磁盤日志文件按照特定時間間隔輪換幻锁。
Formatters
Formatter
對象是用來配置日志消息的最終輸出形式。其格式由%(<dictionary key>)s
這樣的表達形式來組合成字符串边臼。例如:
'%(asctime)s - %(levelname)s - %(message)s'
其中哄尔,可以設(shè)置的<dictionary key>可參考LogRecord屬性
配置日志模塊
將日志記錄輸出在控制臺
import logging
# 創(chuàng)建一個logger實例并設(shè)置日志級別
logger = logging.getLogger('alg_name')
logger.setLevel(logging.DEBUG)
# 配置handler,擬將日志記錄輸出在控制臺
stdout_handler = logging.StreamHandler()
# 配置formatter
formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')
stdout_handler.setFormatter(formatter)
# 添加handler至logger
logger.addHandler(stdout_handler)
配置完后柠并,我們就可以在我們算法想要進行日志記錄的地方調(diào)用Logger.debug()
, Logger.info()
, Logger.warning
, Logger.error
, Logger.critical()
來進行日志輸出了岭接。比如:
# 下面的內(nèi)容都是寫在算法文件里你需要的地方
logger.debug('debug message')
logger.info('info message')
logger.warning('warn message')
logger.error('error message')
logger.critical('critical message')
當運行算法時,你會看到控制臺輸出以下內(nèi)容
2005-03-19 15:10:26,618 - alg_name - DEBUG - debug message
2005-03-19 15:10:26,620 - alg_name - INFO - info message
2005-03-19 15:10:26,695 - alg_name - WARNING - warn message
2005-03-19 15:10:26,697 - alg_name - ERROR - error message
2005-03-19 15:10:26,773 - alg_name - CRITICAL - critical message
將日志記錄輸出至日志文件
import logging
# 創(chuàng)建一個logger實例并設(shè)置日志級別
logger = logging.getLogger('alg_name')
logger.setLevel(logging.DEBUG)
# 配置handler臼予,擬將日志記錄輸出至/log/文件夾
file_name = './log/alg_name_log.log' # 注意:如果/log/文件夾不存在鸣戴,則需要新建
file_handler = logging.handlers.TimedRotatingFileHandler(file_name, when='MIDNIGHT', interval=1, backupCount=30) # 每天午夜生成alg_name_log.log文件,最多保留30天
# 配置formatter
formatter = logging.Formatter('%(levelname)s - %(asctime)s [%(filename)s:%(lineno)d] %(message)s \n')
file_handler.setFormatter(formatter)
# 添加handler至logger
logger.addHandler(file_handler)