2012-11-23 27 views
7

我想在一個函數中實現一個可選的記錄器。例如:在代碼中實現一個可選的記錄器

def foo(arg1, arg2, arg3, logger=None): 
    logger = logger or (lambda *x: None) 

    ... 
    self.logger.debug("The connection is lost.") 

我希望在記錄器存在的情況下進行記錄。否則,記錄器的調試將不會執行任何操作。

基本上簡單的方法去實現它是窩在一個if logger塊每一個調試語句,但是當有許多調試語句看起來凌亂。

+0

不知道如何在你的情況下工作,但是如果記錄器存在,你可以通過檢查來引導該函數嗎?如果不存在,創建一個相同名稱的記錄器('logger',看起來)並且路由輸出到'os.devnul'? – RocketDonkey

+0

@iTayb嗨,你有一個相當簡單的描述你想要什麼(有一個虛擬記錄器)。但據我所知,python的日誌通常不會以這種方式使用。由於您可以使用記錄器的名稱實現日誌過濾,請問爲什麼(在什麼情況下)您仍然需要這種解決方法? – tdihp

+0

@tdihp我想開發一個代碼片斷,可以將它的活動記錄到提供的記錄器中。此代碼必須是便攜式的。它(希望)將在許多不同的項目中實現,並且我不提供日誌記錄環境。開發者決定是否要記錄函數的活動。我只是給他選擇。 – iTayb

回答

7

幾個選項:

創建一個虛擬記錄器(我的最愛):

class DummyObject(object): 
    def __getattr__(self, name): 
     return lambda *x: None 

logger = logger or DummyObject() 

嵌套:

logger = logger or logging.getLogger('dummy') # without configuring dummy before. 

一個水平null效果創建虛擬對象塊中的每個調試語句:

if logger: 
    logger.debug("abc") 
2

那麼,這就是logging模塊的用途。 How to useCookbook

如果你真的想推出自己的,我看到了幾個備選方案:

  • self.logger屬性。在構造對象時設置或從基類繼承。每個對象都有自己的記錄器,因此每個實例可以有選擇性的記錄。

  • 採用靜態方法的記錄器類或獨立模塊。可能有默認方法什麼都不做,但用戶可以隨時用真正的處理程序替換它們,只要有需要就可以。所有類訪問相同的對象或模塊。失去粒度,但更少的工作設置。

  • Decorators。在您想要記錄的每個方法上面放置一個@log('message', LEVEL),這將在方法被調用時自動調用日誌。相當乾淨,不夠靈活。

+0

這對項目很有好處。我所需要的只是一個非常基本的功能,它帶有一個可選日誌記錄,其中記錄器可以作爲參數傳遞。 – iTayb

+0

爲什麼不使用您發佈的代碼?你只需要爲記錄器創建一個非常簡單的類,或者甚至只需要一個函數來打印參數中傳遞的內容即可。 – BoppreH

+0

我想知道python中是否存在一個允許寫入的對象,儘管它不存在,並且支持子類化(就像調用class1.class2.func(a,b,c)一樣,並且什麼都不會發生)。 – iTayb

1

我想你想的記錄過濾,什麼 所以我的答案是關於如何實現簡單的登錄過濾。

Python的日誌包已經這樣做了,你有很多方法來做日誌過濾。

兩種基本方式是:

  • 日誌記錄級別的過濾
  • 記錄器名稱過濾

兩個人都使用日誌的配置,因此可以很容易地配置。

例如:

import logging 

logging.basicConfig() # easily setup a StreamHandler output 

logging.getLogger("realm1").setLevel(logging.WARNING) 
logging.getLogger("realm2").setLevel(logging.INFO) 

def test(): 
    r1logger = logging.getLogger("realm1") 
    r2logger = logging.getLogger("realm2") 
    r1logger.info('r1 info') # won't print 
    r2logger.info('r2 info') # will print 

if __name__ == '__main__': 
    test() 

所以,除非你需要採伐政策的運行時動態局部變化, 仔細記錄配置使用默認記錄器就足夠了。

+0

誰說我不打算使用WARNING日誌級別?但我明白了你的想法。 – iTayb