您好,登錄后才能下訂單哦!
本文小編為大家詳細(xì)介紹“python標(biāo)準(zhǔn)庫logging模塊怎么用”,內(nèi)容詳細(xì),步驟清晰,細(xì)節(jié)處理妥當(dāng),希望這篇“python標(biāo)準(zhǔn)庫logging模塊怎么用”文章能幫助大家解決疑惑,下面跟著小編的思路慢慢深入,一起來學(xué)習(xí)新知識吧。
當(dāng)新增一條log記錄時(shí),最終將調(diào)用Logger類的_log方法,這個(gè)方法首先會(huì)創(chuàng)建一個(gè)LogRecord對象。LogRecord對象需要(filename, lineno, funcname)參數(shù)信息。這是通過如下語句得到的:
fn, lno, func = self.findCaller()
f = currentframe() #f是frame對象,每個(gè)方法調(diào)用生成一個(gè)frame對象,放在程序堆棧中。 if f is not None: f = f.f_back rv = "(unknown file)", 0, "(unknown function)" while hasattr(f, "f_code"): co = f.f_code #獲取code對象,它包含filename屬性,funcname屬性 filename = os.path.normcase(co.co_filename) if filename == _srcfile: #_srcfile是這個(gè)模塊文件自己的文件名,當(dāng)文件名不再相同時(shí) f = f.f_back # 得到外部調(diào)用者的frame,這就是需要的。 continue rv = (filename, f.f_lineno, co.co_name) break return rv
def currentframe(): """Return the frame object for the caller's stack frame.""" try: raise Exception #拋出異常,將生成traceback對象,其中包含frame對象。 except: #sys.exc_traceback.tb_frame當(dāng)前的frame, f_back調(diào)用著的frame return sys.exc_traceback.tb_frame.f_back #sys._getframe(3)返回的并不是當(dāng)前的frame,3應(yīng)該是計(jì)算好了的,減少循環(huán)的次數(shù),返回的是logger.error()的frame if hasattr(sys, '_getframe'): currentframe = lambda: sys._getframe(3)
首先,logging模塊中l(wèi)ogger層級關(guān)系是一個(gè)樹形關(guān)系的結(jié)構(gòu),這個(gè)關(guān)系的樹根是'root'。
root = RootLogger(WARNING) #RootLogger類是Logger的子類,無特殊功能,只是定義名字為‘root'。 Logger.root = root Logger.manager = Manager(Logger.root)
當(dāng)調(diào)用logging.getLogger(),用以獲取某個(gè)Logger時(shí),如果參數(shù)為空,則返回‘root’。否則,調(diào)用Manager的getLogger()方法獲取Logger。
def getLogger(name=None): """ Return a logger with the specified name, creating it if necessary. If no name is specified, return the root logger. """ if name: return Logger.manager.getLogger(name) else: return root
def getLogger(self, name): """ Get a logger with the specified name (channel name), creating it if it doesn't yet exist. This name is a dot-separated hierarchical name, such as "a", "a.b", "a.b.c" or similar. If a PlaceHolder existed for the specified name [i.e. the logger didn't exist but a child of it did], replace it with the created logger and fix up the parent/child references which pointed to the placeholder to now point to the logger. """ rv = None _acquireLock() try: if name in self.loggerDict: rv = self.loggerDict[name] if isinstance(rv, PlaceHolder): ph = rv rv = _loggerClass(name) rv.manager = self self.loggerDict[name] = rv self._fixupChildren(ph, rv) self._fixupParents(rv) else: rv = _loggerClass(name) rv.manager = self self.loggerDict[name] = rv self._fixupParents(rv) finally: _releaseLock() return rv
Manager對象中的loggerDict字典,存放logger名字和logger對象的映射關(guān)系。PlaceHolder類,是一個(gè)容器。
例如,名字為'sell'的PlaceHolder對象,首先還不存在'sell'的logger,然后,所以以'sell‘開頭的logger在這個(gè)對象內(nèi)都存在一個(gè)引用,如'sell.food','sell.cloth.china'等已有的logger對象。 當(dāng)調(diào)用getLogger()獲取一個(gè)未存在的logger時(shí),如名字為'level1.level2', 首先創(chuàng)建一個(gè)名字為'level1.level2'的logger對象,并存于loggerDict中。然后,調(diào)用_fixupParents()。
_fixupParents()的作用:
在這個(gè)名字的層級鏈上,找到第一個(gè)logger對象,將其作為父親,并返回。鏈上不是logger對象的名字,創(chuàng)建一個(gè)PlaceHolder對象(如果未創(chuàng)建),將自己加入其中。
例如,新增‘level1.level2.level3’的logger,調(diào)用_fixupParents將創(chuàng)建一個(gè)名字為'level1.level2‘的PlaceHolder對象,創(chuàng)建一個(gè)名字為’level1‘的PlaceHolder對象,并將’level1.level2.level3‘這個(gè)logger分別加入以上兩個(gè)PlaceHolder對象容器內(nèi),將它的父親設(shè)定為’root‘。
總之,_fixupParents是使logger對象指向真正的父親節(jié)點(diǎn)(logger對象),并將logger自己加入到所有上層的PlaceHolder對象容器內(nèi)。
如果獲取一個(gè)名字已存在于loggerDict中,并且這個(gè)名字對應(yīng)的是一個(gè)先前創(chuàng)建的PlaceHolder對象。首先,創(chuàng)建一個(gè)對應(yīng)名字的logger對象。然后,調(diào)用_fixupChild(),修正這個(gè)PlaceHolder對象所包含的下游logger對象的父親。最后,調(diào)用_fixupParent(),作用與上一步相同。
父子層級關(guān)系,主要作用是,當(dāng)logger對象的propagate屬性值1(默認(rèn)值)時(shí),每條logRecord記錄都會(huì)傳給父logger處理。這樣可以只需要定義好‘root’根logger對象,其他的logger定義個(gè)名字,根據(jù)模塊名,類名等,然后綁定一個(gè)NullHandler。最后,所有的logRecord將交給’root‘統(tǒng)一處理處理。這是多模塊產(chǎn)生統(tǒng)一格式log的方式。
讀到這里,這篇“python標(biāo)準(zhǔn)庫logging模塊怎么用”文章已經(jīng)介紹完畢,想要掌握這篇文章的知識點(diǎn)還需要大家自己動(dòng)手實(shí)踐使用過才能領(lǐng)會(huì),如果想了解更多相關(guān)內(nèi)容的文章,歡迎關(guān)注億速云行業(yè)資訊頻道。
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。