精品欧美一区二区三区在线观看 _久久久久国色av免费观看性色_国产精品久久在线观看_亚洲第一综合网站_91精品又粗又猛又爽_小泽玛利亚一区二区免费_91亚洲精品国偷拍自产在线观看 _久久精品视频在线播放_美女精品久久久_欧美日韩国产成人在线

神器 Logging,你真的了解嗎?

開發(fā) 前端
logging 是 python 標準模塊,用于記錄和處理程序中的日志。功能很強大,官方文檔很詳細,網(wǎng)上也有大量的說明和教程,但是對很多初次接觸的同學來說,存在一些障礙。

[[434022]]

本文轉(zhuǎn)載自微信公眾號「Python技術(shù)」,作者派森醬。轉(zhuǎn)載本文請聯(lián)系Python技術(shù)公眾號。

logging 是 python 標準模塊,用于記錄和處理程序中的日志。

功能很強大,官方文檔很詳細,網(wǎng)上也有大量的說明和教程,但是對很多初次接觸的同學來說,存在一些障礙。

一是因為標準庫文檔太過繁瑣,需要較高的理論基礎(chǔ),著急用時,常常被文檔搞暈。

二是大部分說明材料要么是官方文檔的羅列,要么是簡單的應用,對實際應用幫助不大。

今天,我們從應用上的一些問題開始,探討一下日志神器 logging 極其背后的原理,讓它能真正的幫助到我們。

該用 logging.debug 還是 logger.debug ?

debug 是日志模塊中的一個日志等級為 DEBUG 的日志生成方法,還有 info、warning、error、critial,這里用 debug 做為代表進行說明。

我們常會看到,一會兒用 logging.debug 記錄日志,一會兒又用 logger.debug 記錄日志,到底該用什么?

先看代碼:

  1. import logging 
  2.  
  3. logging.debug('調(diào)試信息'
  4.  
  5. logger = logging.getLogger() 
  6.  
  7. logger.debug('調(diào)試信息'

首先 logging 是作為一個模塊被引入的。logging.debug 用的是 logging 模塊的模塊方法。

logger 是用 logging.getLogger() 生成的,是一個 日志對象,logger.debug 調(diào)用的是 logger 這個日志對象的方法。

上面的代碼中 logging.debug 和 logger.debug 的效果完全是一樣的。

這是因為,為了讓開發(fā)者方便使用,logging 模塊提供了一些列模塊方法,如 debug,在引入模塊后,就可以直接使用。這樣開發(fā)者就不必關(guān)心日志模塊的細節(jié),像用 print 一樣輸出日志。

如果需要對日志輸出進行定制化,比如將日志輸出到文件中,過濾某些級別的日志,就需要創(chuàng)建或者得到一個實際的日志對象來處理,如上面代碼中通過 getLogger 方法得到的日志對象。

我們知道,程序設(shè)計里要避免重復的設(shè)計,如果模塊方法采用一套機制,日志對象上的方法采用另一套機制,就會出現(xiàn)重復造輪子的問題。

所以在使用模塊方法,logging 其實創(chuàng)建了一個日志對象 —— root logger。

也就是 logging.debug 這個調(diào)用,實質(zhì)上是調(diào)用 root logger 的日志方法。

相當于默認情況下 root logger 會作為日志處理對象。

如何獲得 root logger 對象呢?

通過不帶參數(shù)的 logging.getLogger() 方法獲得。

那么 logging.debug 和 rootLogger.debug 是一會事,可以理解(但不嚴謹)為 logging.debug 是 rootlogger.debug 的快捷方式。

日志樹

稍加留意就會觀察到,程序是有層次結(jié)構(gòu)的,通過相互引用,調(diào)用形成一個樹狀結(jié)構(gòu)。

程序加載的地方是樹根,比如 python 中要運行的代碼文件,我們稱之為 main。從樹根開始長出其他枝葉。對于一個模塊來說,又會形成一個自己的樹。

如何用日志清楚地記錄層次結(jié)構(gòu)呢?

雖然直接打印出調(diào)用堆棧也可以看到調(diào)用結(jié)構(gòu),不過不太直觀,缺乏業(yè)務邏輯描述。

而用 print 來打印出層次結(jié)構(gòu),需要編寫大量的代碼才能反射出(通過運行狀態(tài)獲取代碼狀態(tài)的一種方式)調(diào)用環(huán)境。

logging 提供了完畢的解決方案。

前面提到的 root logger 就是整個日志樹的根,其他所有的 logger 都是從 root logger 伸展出來的枝葉。只要通過 getLogger(loggername) 方法獲得的 logger 對象,都是伸展自 root logger 的。

如何向下伸展呢?

很簡單,就像引用模塊的層次關(guān)系一樣,用 . 分隔層次就好了,例如:

  1. logger = logging.getLogger('mod1.mod2.mod3'
  2.  
  3. logger.debug("調(diào)試信息"

語句 logging.getLogger('mod1.mod2.mod3') 實際上創(chuàng)建了三個 logger,名稱分別是 mod1、mod1.mod2 和 mod1.mod2.mod3

mod1 為根,mod1.mod2 為子,mod1.mod2.mod3 為孫。

如果在 mod1 上設(shè)置了日志處理器(handler),那么其他兩個的日志對象都會用到這個處理器。

這樣不但記錄的日志更清晰而且,可以為同一個根的日志對象設(shè)置可以共享的日志處理方式。

這樣感覺也不方便,需要些那么多層次,如何才能更方便呢?在下面的 實踐參考 里會有說明。

logging.basicConfig 的功與過

說完了日志模塊的樹狀結(jié)構(gòu),來看看一個很常用的設(shè)置方法 basicConfig。

它可以方便的設(shè)置日志處理和記錄方式,如沒必要,不用為每個日志對象單獨設(shè)置。

根據(jù)第一節(jié)的分析,我們知道,直接使用模塊方法,用的其實是 root logger,那么就能明白 basicConfig 設(shè)置了 root logger 的日志處理方式。

這就意味著:

一旦設(shè)置了通過 logging.basicConfig 設(shè)置了日志處理方式,其他所有日志都很受到影響。

另外 basicConfig 是個一次性方法,即:

只有第一次設(shè)置有效,其后設(shè)置無效

本來是個一勞永逸的方法。

但用錯了地方,就會很麻煩。

看下例子:

  1. __all__ = ['Connection''ConnectionPool''logger'
  2.  
  3. warnings.filterwarnings('error', category=pymysql.err.Warning) 
  4. # use logging module for easy debug 
  5. logging.basicConfig(format='%(asctime)s %(levelname)8s: %(message)s', datefmt='%m-%d %H:%M:%S'
  6. logger = logging.getLogger(__name__) 
  7. logger.setLevel('WARNING'

這段代碼中,用 logging.basicConfig 對日志做了設(shè)置,意思是后面的日志都按照這樣的方式輸出。

但它是一個底層模塊 —— pymysqlpool[1]。

pymysqlpool 封裝了 pymysql[2] 模塊,提供了鏈接池特性,在多線程處理數(shù)據(jù)庫場景下很有用。

也就是說,pymysqlpool 只會被引用加載,不會作為 main 被加載,這就比較尷尬了,因為 main 中對日志的設(shè)置就沒有效果。

作為一個服務類模塊(相對于業(yè)務的底層模塊),不要通過 basicConfig 來設(shè)置日志模式,要么通過自己專屬的日志對象來設(shè)置,要么不去設(shè)置,統(tǒng)一交給 main 去設(shè)置,例如:

  1. logger = logging.getLogger(__name__) 
  2.  
  3. fmt = logging.Formatter("%(asctime)s %(levelname)8s: %(message)s", datefmt='%m-%d %H:%M:%S'
  4. hdl = logging.StreamHandler() 
  5. hdl.setFormatter(fmt) 
  6. logger.addHandler(hdl) 
  7.  
  8. logger.setLevel('WARNING'

如果為了測試,可以在測試的初始化方法中,使用 basicConfig 來設(shè)置,因為測試時,模塊往往是被作為程序入庫加載的。

實踐參考

了解了日志模塊的一下特性,和其中的原理之后,這里有幾條實踐參考。

  • 不要再子模塊中使用 logging.basicConfig 設(shè)置日志模式
  • 強烈建議在任何模塊中通過 logger = logging.getLogger(__name__) 來創(chuàng)建日志對象 因為 __name__ 代表的就是模板被加載的引用名稱。

例如 from a.b.c import b 模塊 c 中的 __name__ 值就為 a.b.c。

  • 而且這個引用名稱剛好符合 logger 定義的層次結(jié)構(gòu)。

通過命令行參數(shù)設(shè)置不同類型的日志,見代碼:

  1. import logging 
  2. import argparse 
  3. logger = logging.getLogger(__name__) 
  4.  
  5. def create_args_parse(): 
  6.     parser = argparse.ArgumentParser(description="參數(shù)列表"
  7.     parser.add_argument('-d''--debug'action='store_true', help='調(diào)試模式'
  8.     # 加入其他命令行參數(shù) 
  9.          
  10.     return parser 
  11.  
  12. def set_logger(debug): 
  13.     formatter = logging.Formatter('%(asctime)s - %(levelname)8s - %(name)s - %(filename)s:%(lineno)d - %(thread)d- %(funcName)s:\t%(message)s'
  14.     if debug: 
  15.         hd = logging.StreamHandler() 
  16.         logger.setLevel(logging.DEBUG) 
  17.         hd.setFormatter(formatter) 
  18.     else
  19.         hd = logging.FileHandler(f'{__name__}.log''a', encoding='utf-8'
  20.         logger.setLevel(logging.INFO) 
  21.         hd.setFormatter(formatter) 
  22.     logger.addHandler(hd) 
  23.  
  24. if __name__ == '__main__'
  25.    parser = create_args_parse() 
  26.    args = parser.parse_args() 
  27.    debug = args.debug 
  28.    set_logger(debug) 
  29.    ... 

代碼有點長,但不難懂。

  • create_args_parse 方法用于解析命令行參數(shù),其中定義了一個 debug 參數(shù),表示開啟調(diào)試模式
  • set_logger 方法接收一個是否為調(diào)試模式的參數(shù),根據(jù)是否為調(diào)試模式,設(shè)置不同的日志模式
  • main 中,首先調(diào)用 create_args_parse 獲得命令行參數(shù)對象,然后從中解析出參數(shù),提取 debug 模式,傳送給 set_logger 方法,設(shè)置日志模式
  • 這樣只需要在運行程序時,加上參數(shù) -d 就可以讓日志打印到終端上,不加,日志就會自動去 __main__.log 日志文件中去了。

總結(jié)

python 為我們提供了很多便利的功能,有些需要真的用到才能有所體會,所以在遇到問題時,需要多研究一下,找到其中的特點和內(nèi)在的原理或機制,這樣就能更好的應用了。

在我理解了 logging 的原理之后,已經(jīng)在我的很多項目中發(fā)揮了巨大作用,而且再也不必糾結(jié)于怎么用,如何更合理等這些問題了。

期望這篇文章也能對你有所幫助,比心。

參考資料

[1]pymysqlpool: https://pypi.org/project/pymysql-pool/

[2]pymysql: https://pypi.org/project/PyMySQL/

 

責任編輯:武曉燕 來源: Python技術(shù)
相關(guān)推薦

2014-04-17 16:42:03

DevOps

2022-07-26 00:00:22

HTAP系統(tǒng)數(shù)據(jù)庫

2021-01-15 07:44:21

SQL注入攻擊黑客

2020-02-27 10:49:26

HTTPS網(wǎng)絡協(xié)議TCP

2019-09-16 08:40:42

2014-11-28 10:31:07

Hybrid APP

2023-03-16 10:49:55

2012-05-31 09:56:54

云安全

2022-12-12 08:46:11

2022-03-14 07:53:27

ELTETL大數(shù)據(jù)

2023-10-24 08:53:24

FutureTas并發(fā)編程

2015-07-31 10:35:18

實時計算

2019-11-06 09:52:01

JavaScript單線程非阻塞

2017-10-18 22:01:12

2025-01-03 08:09:15

2024-02-02 08:50:20

Node.js元數(shù)據(jù)自動化

2023-11-01 13:48:00

反射java

2022-06-29 10:21:33

3d打印輔助工具

2021-11-26 08:07:16

MySQL SQL 語句數(shù)據(jù)庫

2016-11-02 12:06:27

分布式系統(tǒng)大數(shù)據(jù)
點贊
收藏

51CTO技術(shù)棧公眾號

4388成人网| 日韩欧美一区二区免费| 日本精品视频一区| 一二三四区在线| 亚洲无线视频| 亚洲欧美国产一区二区三区| 亚洲综合婷婷久久| av丝袜在线| 国产亚洲污的网站| 91视频国产一区| 国产精品100| 97人人精品| 日韩av在线网站| av亚洲天堂网| 国产精欧美一区二区三区蓝颜男同| 久久丝袜美腿综合| 亚洲最大成人在线| 最近中文字幕免费观看| 国产综合精品一区| www.亚洲一区| 国产全是老熟女太爽了| 91视频亚洲| 在线观看网站黄不卡| 成人在线国产视频| 麻豆电影在线播放| 91亚洲精品久久久蜜桃| 91精品久久久久久久久久入口| 国产网站在线看| 91精品二区| 中文字幕精品在线| 魔女鞋交玉足榨精调教| 国产精品17p| 欧美一级午夜免费电影| 91插插插插插插插插| 成人短视频app| 午夜精品久久久久久| 国产盗摄视频在线观看| a√在线中文网新版址在线| 97精品国产露脸对白| 国产精品10p综合二区| 97人妻精品一区二区三区视频| 日日摸夜夜添夜夜添国产精品| 久久青草福利网站| 北条麻妃在线观看视频| 欧美日韩水蜜桃| 亚洲日本aⅴ片在线观看香蕉| 中文字幕a在线观看| jizz18欧美18| 日韩欧美国产三级| 手机在线观看日韩av| 日韩久久99| 欧美狂野另类xxxxoooo| 九九热免费在线观看| 日韩不卡免费高清视频| 一本一道久久a久久精品综合蜜臀| 精品少妇在线视频| www.51av欧美视频| 天天色综合成人网| 韩国日本在线视频| 国产高清不卡| 欧美视频一区在线| 奇米视频7777| 亚洲天堂中文字幕在线观看| 精品少妇一区二区三区日产乱码 | 成人av资源网| 亚洲第一天堂影院| 成人av影院在线| 韩国成人一区| 免费毛片在线| 欧美激情资源网| 在线视频不卡一区二区三区| 久草免费在线| 亚洲一区成人在线| 成人在线免费在线观看| 97久久香蕉国产线看观看| 欧美亚洲综合一区| 日韩视频在线观看一区二区三区| 亚洲国产一区二区三区网站| 亚洲成人久久久| www.久久av| 91综合网人人| 久久久久久久久久久av| 亚洲黄色激情视频| 免费高清成人在线| 亚洲xxxx在线| 欧美日韩国产亚洲沙发| 国产精品久久久久影院| 中文字幕日韩精品无码内射| 九九色在线视频| 日韩欧美aⅴ综合网站发布| 午夜视频你懂的| 一区二区三区四区高清视频| 亚洲精品视频网上网址在线观看| 刘亦菲国产毛片bd| 亚洲第一区色| 国产精品嫩草影院一区二区| 亚洲国产综合一区| 久久久久国产免费免费| 91视频成人免费| 中文在线а√在线8| 91精品国产综合久久精品图片 | 久久影视三级福利片| 在线视频免费一区二区| 久久精品国产亚洲av高清色欲| 久久午夜电影| yellow视频在线观看一区二区| 日本私人网站在线观看| 亚洲黄色在线视频| 牛夜精品久久久久久久| 久久精品亚洲成在人线av网址| 在线看国产精品| 日韩网红少妇无码视频香港| 久久av资源站| 日本公妇乱淫免费视频一区三区| 色综合999| 欧美另类久久久品| 91视频免费观看网站| 国产真实久久| 91亚洲永久免费精品| 精品电影在线| 欧美日韩国产在线看| 中文字幕avav| 日韩精品一区二区三区免费观影 | 97国产一区二区| 国产一二三四区在线观看| 精品123区| 精品香蕉一区二区三区| 国产十六处破外女视频| 久久精品国产在热久久| 日韩经典在线视频| av日韩电影| 亚洲国产精品美女| 久热这里有精品| 极品少妇xxxx精品少妇| 天堂精品视频| 日韩不卡在线| 伊人久久久久久久久久久| 日产精品久久久| aaa欧美色吧激情视频| 欧美黄网在线观看| 精品视频成人| 欧美成人精品一区二区三区| 国产免费黄色大片| 亚洲天堂精品在线观看| 成人不卡免费视频| 午夜欧美在线| 成人有码在线视频| а√天堂资源地址在线下载| 欧美精三区欧美精三区| 性生交大片免费全黄| 国产综合色产在线精品| 黄色一级视频播放| 天堂精品久久久久| 久久久久久久电影一区| 涩涩视频免费看| 亚洲香肠在线观看| 午夜不卡久久精品无码免费| 日韩午夜黄色| 欧美一区二区三区电影在线观看| 欧美日韩精品免费观看视完整| 亚洲欧洲黄色网| 中文字幕+乱码+中文乱码www| 中文字幕二三区不卡| 亚洲36d大奶网| 影视一区二区| 国产不卡一区二区三区在线观看| av男人的天堂在线观看| 亚洲欧美激情另类校园| 在线观看xxxx| 一区二区三区在线免费视频| 男人网站在线观看| 久久福利一区| 伊人久久大香线蕉综合75| 国产亚洲久久| 97超级碰在线看视频免费在线看| 日韩在线无毛| 精品视频123区在线观看| 久久久久久视频| 不卡欧美aaaaa| 粉嫩虎白女毛片人体| 婷婷精品进入| 国产九色精品| 日韩一区精品| 久久免费观看视频| 福利成人在线观看| 日韩免费观看高清完整版在线观看| 国产精品自拍视频一区| 欧美激情资源网| 日本精品一二三| 日韩精品欧美精品| 免费极品av一视觉盛宴| 国产一区二区区别| 91国产丝袜在线放| 日本免费一区二区三区四区| 欧美超级乱淫片喷水| 三级理论午夜在线观看| 日韩视频一区在线观看| 手机看片久久久| 亚洲精品视频一区| 一道本在线观看| 国产精品1区2区3区| 久久国产乱子伦免费精品| 99久久影视| 欧美日韩三区四区| 136国产福利精品导航网址应用| 日韩免费高清在线观看| 天堂av最新在线| 中文字幕欧美日韩在线| 五月婷婷六月丁香| 日韩欧美亚洲国产另类| 少妇又紧又色又爽又刺激视频| 亚洲福中文字幕伊人影院| 久久久久99精品成人| 91在线观看一区二区| 国产在线a视频| 久久精品国产在热久久| 男人天堂成人在线| 99av国产精品欲麻豆| 最近中文字幕免费mv| 精品国产91乱码一区二区三区四区 | 国产乱码精品一区二区三区av | 成人免费黄色| 青青草成人在线| 丁香花电影在线观看完整版| 久久久精品一区二区三区| 高清av在线| 亚洲人免费视频| 四虎在线视频| 亚洲国产精品久久| www.色播.com| 欧美一级一区二区| 国产精品久久久久毛片| 欧美日韩一级二级三级| 日韩电影在线观看一区二区| 黄色一区二区在线观看| 国产亚洲精品久久777777| 亚洲男同1069视频| 91麻豆精品成人一区二区| 国产精品人成在线观看免费| 国产熟女一区二区| 久久久高清一区二区三区| 国产精品无码久久久久久| 91免费小视频| 中文字幕一区二区三区人妻不卡| www.成人在线| 美国黄色一级毛片| 91毛片在线观看| 欧美性xxxx图片| 26uuu国产一区二区三区| 亚洲av无码一区二区三区网址 | 一级黄色录像毛片| 国产精品无遮挡| 免费一级suv好看的国产网站 | 日韩精品一区二区三| 亚洲电影一区二区| 日韩成人av毛片| 黑人精品xxx一区一二区| 欧美亚洲精品天堂| 91传媒视频在线播放| 在线观看毛片av| 91麻豆精品国产| 国内精品久久久久久久久久久| 欧美成人猛片aaaaaaa| 日韩在线一区二区三区四区| 日韩高清不卡av| 国产香蕉视频在线看| 中文日韩在线观看| 成人短视频在线| 久久久免费观看视频| 人成在线免费网站| 国产精品久久久久久久久久尿| jizz免费一区二区三区| 91探花福利精品国产自产在线| 视频成人永久免费视频| 粉嫩av一区二区三区免费观看| 欧美重口另类| 亚洲精品日韩在线观看| 欧美日韩a区| avav在线看| 久久精品理论片| 久久性爱视频网站| 国产农村妇女毛片精品久久麻豆 | 欧美日韩国产影院| 91丨porny丨在线中文 | 欧美黄色大片网站| 国产中文字幕视频在线观看| 青青草原综合久久大伊人精品优势| 国产精品久久久久久9999| 成人97人人超碰人人99| 久久美女免费视频| 一区二区欧美精品| 国产精品久久久久久久久夜色| 91精品国产色综合久久不卡蜜臀| 午夜影院免费视频| 日韩资源在线观看| 老牛影视精品| 成人有码在线视频| 色狼人综合干| 免费日韩在线观看| 日韩经典一区二区| 中文视频在线观看| 国产精品成人一区二区三区夜夜夜| 日本一区二区不卡在线| 欧美精品自拍偷拍| 国产午夜在线视频| 久久久久亚洲精品成人网小说| 国产精品第一国产精品| 精品久久精品久久| 中文精品久久| 在线观看的毛片| 91麻豆高清视频| 乱h高h女3p含苞待放| 91激情在线视频| 五月天婷婷激情网| 欧美激情一区二区三区在线视频观看| 成人久久网站| 欧美日韩一区在线观看视频| 国产综合视频| 永久免费黄色片| 中文字幕第一区| 在线免费观看国产精品| 亚洲国产精品久久| 高h视频在线播放| 91啪国产在线| 99久久99久久精品国产片桃花 | 国产伦精品一区二区三区在线观看| 亚洲图片另类小说| 欧美日韩国产中文精品字幕自在自线| 国产日韩精品suv| 久久精视频免费在线久久完整在线看| 日本一区免费网站| 日韩精品一线二线三线| 久久蜜桃精品| 国产全是老熟女太爽了| 欧美日韩在线视频一区| 天天色综合av| 午夜精品一区二区三区在线 | 日韩成人av电影在线| 国产农村妇女精品一区二区| 久久久久国产精品无码免费看| 亚洲一区在线免费观看| 亚洲成人第一区| 欧美国产日本高清在线 | 国产福利精品导航| 国产a免费视频| 日韩精品一区二区三区三区免费| 在线看女人毛片| 成人欧美一区二区| 亚洲第一黄网| 亚洲一级中文字幕| 一本久久综合亚洲鲁鲁五月天| 天堂а√在线8种子蜜桃视频| 2018国产精品视频| 国际精品欧美精品| 超碰在线人人爱| 亚洲精品成人在线| 亚洲成人久久精品| 91精品国产91久久久久久不卡| 日韩欧美天堂| 一道本视频在线观看| 国产精品毛片久久久久久| 91精品国自产| 九九热99久久久国产盗摄| 高潮久久久久久久久久久久久久| 拔插拔插海外华人免费| 久久综合色8888| 在线视频1卡二卡三卡| 免费91在线视频| 老司机aⅴ在线精品导航| 激情综合在线观看| 国产精品久久久一本精品| www.五月婷婷| 欧美最顶级的aⅴ艳星| 精品一区二区三| 在线能看的av网站| 亚洲午夜激情网站| 国产一二在线观看| 51午夜精品| 性久久久久久| 亚洲国产精品一区二区久久hs| 日韩欧美在线网站| 电影一区二区三| 可以免费看的黄色网址| 91免费国产在线观看| 夜夜躁狠狠躁日日躁av| 国模私拍视频一区| 成人毛片免费看| 性农村xxxxx小树林| 在线区一区二视频| 丁香花在线电影小说观看| 色综合久久88色综合天天提莫| 国产91精品精华液一区二区三区 | 国精产品99永久一区一区| 视频一区二区三区入口| 欧美xxxx黑人xyx性爽| 亚洲区中文字幕| 91亚洲无吗| 特黄视频免费观看| 日韩欧美精品中文字幕| 欧美日韩经典丝袜|