Python日誌處理logging模組詳解
- 2020 年 1 月 26 日
- 筆記
logging模組簡介
logging模組是Python內置的標準模組,主要用於輸出運行日誌,可以設置輸出日誌的等級、日誌保存路徑、日誌文件回滾等;相比print,具備如下優點
1、可以通過設置不同的日誌等級,在release版本中只輸出重要資訊,而不必顯示大量的調試資訊
2、print將所有資訊都輸出到標準輸出中,嚴重影響開發者從標準輸出中查看其它數據;logging則可以由開發者決定將資訊輸出到什麼地方,以及怎麼輸出
日誌等級(level)
DEBUG < INFO < WARNING < ERROR < CRITICAL
DEBUG 最詳細的日誌資訊,典型應用場景是 問題診斷
INFO 資訊詳細程度僅次於DEBUG,通常只記錄關鍵節點資訊,用於確認一切都是按照我們預期的那樣進行工作
WARNING 當某些不期望的事情發生時記錄的資訊(如,磁碟可用空間較低),但是此時應用程式還是正常運行的
ERROR 由於一個更嚴重的問題導致某些功能不能正常運行時記錄的資訊
CRITICAL 當發生嚴重錯誤,導致應用程式不能繼續運行時記錄的資訊
logging模組可以指定日誌記錄器的日誌級別,只有級別大於或等於該指定日誌級別的日誌記錄才會被輸出,小於該等級的日誌記錄將會被丟棄
logger
logger:日誌對象,logging模組中最基礎的對象,用logging.getLogger(name)方法進行初始化,name可以不填。通常logger的名字我們對應模組名,如聊天模組、資料庫模組、驗證模組等
1. 為程式提供記錄日誌的介面
2. 判斷日誌所處級別,並判斷是否要過濾
3. 根據其日誌級別將該條日誌分發給不同handler
其常用函數有:
Logger.setLevel() 設置日誌級別
Logger.addHandler() 和 Logger.removeHandler() 添加和刪除一個Handler
Logger.addFilter() 添加一個Filter
setLevel:設置日誌等級
logger=logging.getLogger()
logger.setLevel(logging.DEBUG) #設置日誌等級
logging
1、Formatter用於控制日誌資訊的最終輸出格式
logging.Formatter(參數)
formatter=logging.Formatter('[%(asctime)s]-%(filename)s]-%(levelname)s:%(message)s')
%(name)s Logger的名字
%(levelno)s 數字形式的日誌級別
%(levelname)s 文本形式的日誌級別
%(pathname)s 調用日誌輸出函數的模組的完整路徑名,可能沒有
%(filename)s 調用日誌輸出函數的模組的文件名
%(module)s 調用日誌輸出函數的模組名
%(funcName)s 調用日誌輸出函數的函數名
%(lineno)d 調用日誌輸出函數的語句所在的程式碼行
%(created)f 當前時間,用UNIX標準的表示時間的浮 點數表示
%(relativeCreated)d 輸出日誌資訊時的,自Logger創建以 來的毫秒數
%(asctime)s 字元串形式的當前時間。默認格式是 「2003-07-08 16:49:45,896」。逗號後面的是毫秒
%(thread)d 執行緒ID。可能沒有
%(threadName)s 執行緒名。可能沒有
%(process)d 進程ID。可能沒有
%(message)s 用戶輸出的消息
2、Handler基於日誌級別對日誌進行分發,如設置為WARNING級別的Handler只會處理WARNING及以上級別的日誌。具體的應用如一個應用要把所有的日誌打在文件中,並把ERROR以上級別的日誌列印到螢幕,把CRITICAL級別的日誌發郵件
常用函數有:
setLevel() 設置級別
setFormatter() 設置Formatter
logging.FileHandler(參數)創建一個FileHandler
logger.addHandler(fh)添加
logging.StreamHandler()創建一個 StreamHandler
logger.addHandler(ch)添加
# 創建一個FileHandler,用於寫到本地
fh=logging.FileHandler(logname,'a',"utf-8")
fh.setLevel(logging.DEBUG)
fh.setFormatter(formatter)
logger.addHandler(fh)
# 創建一個 StreamHandler,用於輸出到控制台
ch = logging.StreamHandler()
ch.setLevel(logging.DEBUG)
ch.setFormatter(formatter)
logger.addHandler(ch)
import os,time,logging# 日誌存放路徑 log_path=os.path.join(os.path.dirname(os.path.dirname(os.path.realpath(__file__))),'logs') # 如果不存在這個logs文件夾,就自動創建一個 if not os.path.exists(log_path):os.mkdir(log_path) class Log(): def __init__(self): #再日誌路徑下添加日誌文件名 self.logname=os.path.join(log_path,'%s.log'%time.strftime('%Y_%m_%d')) #logger日誌對象初始化 self.logger=logging.getLogger() #設置日誌等級 self.logger.setLevel(logging.DEBUG) #日誌輸出格式 self.formatter=logging.Formatter('[%(asctime)s]-%(filename)s]-%(levelname)s:%(message)s') def __console(self,level,message): # 創建一個 FileHandler,用於寫到本地 fh=logging.FileHandler(self.logname,'a',"utf-8") fh.setLevel(logging.DEBUG) fh.setFormatter(self.formatter) self.logger.addHandler(fh) # 創建一個 StreamHandler,用於輸出到控制台 ch = logging.StreamHandler() ch.setLevel(logging.DEBUG) ch.setFormatter(self.formatter) self.logger.addHandler(ch) if level=='info': self.logger.info(message) elif level=='debug': self.logger.debug(message) elif level=='warning': self.logger.warning(message) elif level=='error': self.logger.error(message) # 這兩行程式碼是為了避免日誌輸出重複問題 self.logger.removeHandler(ch) self.logger.removeHandler(fh) # 關閉打開的文件 fh.close() def debug(self, message): self.__console('debug', message) def info(self, message): self.__console('info', message) def warning(self, message): self.__console('warning', message) def error(self, message): self.__console('error', message) if __name__ == "__main__": log=Log() log.info("---測試開始---") log.info("操作步驟1,2,3") log.warning("---測試結束---") C:UserswangliPycharmProjectsAutoMationvenvScriptspython.exe C:/Users/wangli/PycharmProjects/AutoMation/case/test.py [2019-04-10 17:17:18,025]-test.py]-INFO:---測試開始--- [2019-04-10 17:17:18,026]-test.py]-INFO:操作步驟1,2,3 [2019-04-10 17:17:18,028]-test.py]-WARNING:---測試結束--- Process finished with exit code 0