一、日志
1.1什么是日志
日志是跟蹤軟件運行時所發生的事件的一種方法,軟件開發者在代碼中調用日志函數,表明發生了特定的事件,事件由描述性消息描述,同時還包含事件的重要性,重要性也稱為級別或嚴重性。
1.2何時使用日志
logging模塊提供了一些函數,用來做一些簡單的日志,他們是debug()、info()、warning()、error()、critical()。要決定什么時候使用logging,見下表,描述了常見的任務及對應的最佳工具。
你想完成的任務 | 完成任務的最佳工具 |
---|---|
在控制臺上顯示命令行腳本或者程序的常規用法說明 | print() |
報告在程序的正常操作期間發生的事件(例如,用于狀態監視或故障調查) | logging.info() ?(或者?logging.debug() ?,非常詳細的輸出,用于診斷目的) |
對于特定的運行時事件發出警告 | 在庫代碼中使用 使用 |
對于特定的運行時事件報告錯誤 | 拋出異常 |
報告錯誤的抑制而不引發異常(例如,在長時間運行的服務器進程中的錯誤處理程序) | 根據特定的錯誤和應用領域,使用合適的logging.error() 、?logging.exception() ?或者logging.critical() |
?
1.3事件嚴重性(事件的級別)
?
級別 | 何時使用 |
---|---|
DEBUG | 詳細信息,一般只在調試問題時使用。 |
INFO | 證明事情按預期工作。 |
WARNING | 某些沒有預料到的事件的提示,或者在將來可能會出現的問題提示。例如:磁盤空間不足。但是軟件還是會照常運行。 |
ERROR | 由于更嚴重的問題,軟件已不能執行一些功能了。 |
CRITICAL | 嚴重錯誤,表明軟件已不能繼續運行了。 |
默認等級時warning。意味著只有warning以上的事件等級才會反饋信息,可以通過logging.setLevel()修改默認等級。
二、Logging簡介
logging模塊定義的類和函數位應用程序和庫實現了一個靈活的事件日志系統。由標準庫提供的日志記錄API的好處是所有的Python模塊都可以使用日志。
2.1使用logging記錄到控制臺
#1.使用logging 將日志打印到控制臺 logging.basicConfig(level=logging.DEBUG) #默認level時warning。所以需要修改一下級別 logging.debug('debug') logging.info('info') logging.warning('warning') logging.error('error') logging.critical('critical')
2.2使用logging將日志記錄到文件
#2.將日志記錄到文件 logging.basicConfig(filename='logging.log',filemode='a',level=logging.DEBUG) #默認level時warning。所以需要修改一下級別 logging.debug('debug') logging.info('info') logging.warning('warning') logging.error('error') logging.critical('critical')
2.3 如果程序由多個模塊,組織日志
# myapp.py import logging import mylibdef main():logging.basicConfig(filename='myapp.log', level=logging.INFO)logging.info('Started') mylib.do_something() logging.info('Finished') if __name__ == '__main__':main()
三、改變顯示消息格式Formatter
logger對象一般不會直接實例化得到,而是通過模塊級別的logging.getLogger()得到。以相同的名字多次調用getLogger()。永遠返回相同的logger對象的引用-->單例模式。
3.1 format 指定輸出格式和內容
?
import logging logging.basicConfig(format='%(levelname)s:%(message)s',level=logging.DEBUG) logging.debug('debug msg') logging.info('info msg') logging.warning('warning msg') logging.error('error msg') logging.critical('critical msg')
常用的format格式:


%(levelno)s: 打印日志級別的數值%(levelname)s: 打印日志級別名稱%(pathname)s: 打印當前執行程序的路徑,其實就是sys.argv[0]%(filename)s: 打印當前執行程序名%(funcName)s: 打印日志的當前函數%(lineno)d: 打印日志的當前行號%(asctime)s: 打印日志的時間%(thread)d: 打印線程ID%(threadName)s: 打印線程名稱%(process)d: 打印進程ID%(message)s: 打印日志信息
import os #format logging.basicConfig(level=logging.DEBUG,format='%(asctime)s:%(filename)s [line:%(lineno)d] %(levelname)s %(message)s',datefmt='%a, %d %b %Y %H:%M:%S',filename= os.path.join('format.txt'),filemode='w',) logging.debug('debug msg') logging.error('error msg')
四、Logger
Logger對象有三個作用,首先,它暴露給應用幾個方法以便應用可以在運行時寫log;其次,Logger對象按照log信息的嚴重程度或者根據filter對象來決定如何處理log信息(默認的過濾功能);最后,logger還負責把log信息傳送給相關的loghandlers。
4.1將日志記錄控制臺及文件
import logginglogger = logging.getLogger() # 創建一個handler,用于寫入日志文件 fh = logging.FileHandler('test.log',encoding='utf-8') # 再創建一個handler,用于輸出到控制臺 ch = logging.StreamHandler() formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s') fh.setLevel(logging.DEBUG)fh.setFormatter(formatter) ch.setFormatter(formatter) logger.addHandler(fh) #logger對象可以添加多個fh和ch對象 logger.addHandler(ch) logger.debug('logger debug message') logger.info('logger info message') logger.warning('logger warning message') logger.error('logger error message') logger.critical('logger critical message')
?
logging庫提供了多個組件:Logger、Handler、Filter、Formatter。Logger對象提供應用程序可直接使用的接口,Handler發送日志到適當的目的地,Filter提供了過濾日志信息的方法,Formatter指定日志顯示格式。另外,可以通過:logger.setLevel(logging.Debug)設置級別,當然,也可以通過
fh.setLevel(logging.Debug)單對文件流設置某個級別。