2012-11-23 33 views
7

Tôi muốn triển khai trình ghi nhật ký tùy chọn trong một hàm. Một cái gì đó như:Thực hiện trình ghi nhật ký tùy chọn trong mã

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

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

Tôi muốn đăng nhập xảy ra trong trường hợp trình ghi nhật ký tồn tại. Nếu không, quá trình gỡ lỗi của trình ghi nhật ký sẽ không làm gì cả.

Về cơ bản, cách dễ dàng để đạt được điều này là lồng mọi câu lệnh gỡ lỗi vào khối if logger, nhưng có vẻ lộn xộn khi có nhiều câu lệnh gỡ lỗi.

+0

Bạn không chắc chắn cách thức này sẽ hoạt động trong tình huống của mình, nhưng bạn có thể dẫn hàm bằng kiểm tra nếu trình ghi nhật ký tồn tại không, và nếu không, hãy tạo trình ghi nhật ký có cùng tên ('logger') và định tuyến đầu ra tới 'os.devnul'? – RocketDonkey

+0

@iTayb Xin chào, bạn có một mô tả khá đơn giản về những gì bạn muốn (để có một trình đăng nhập giả). nhưng khai thác python thường không được sử dụng theo cách này theo như tôi biết. Như bạn có thể đạt được đăng nhập lọc sử dụng tên của logger, Tôi có thể hỏi tại sao (trong tình huống nào) bạn vẫn cần loại giải pháp này? – tdihp

+0

@tdihp Tôi muốn phát triển một đoạn mã, có thể ghi nhật ký hoạt động của nó vào trình ghi được cung cấp. Mã này phải di động. Nó (hy vọng) sẽ được thực hiện trong nhiều dự án khác nhau, và tôi không cung cấp môi trường khai thác gỗ. Nhà phát triển có quyết định xem anh ấy có muốn ghi lại hoạt động của chức năng hay không. Tôi chỉ cho anh ta tùy chọn. – iTayb

Trả lời

7

vài lựa chọn:

Tạo một logger giả (yêu thích của tôi):

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

Tạo một đối tượng giả với một mức null hiệu lực thi hành:

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

logger = logger or DummyObject() 

lồng nhau mọi câu lệnh gỡ lỗi trong một khối:

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

Vâng, đó là những gì mô-đun logging dành cho. How to use, Cookbook.

Nếu bạn thực sự muốn cuộn của riêng bạn, tôi thấy một vài lựa chọn:

  • self.logger thuộc tính. Đặt khi xây dựng đối tượng hoặc được kế thừa từ một lớp cơ sở. Mỗi đối tượng có logger riêng của nó, vì vậy bạn có thể có khai thác chọn lọc cho mỗi thể hiện.

  • Lớp trình ghi nhật ký với phương thức tĩnh hoặc mô-đun độc lập. Có thể có các phương thức mặc định không làm gì cả, nhưng người dùng được tự do thay thế chúng bằng các trình xử lý thực bất cứ khi nào có nhu cầu. Tất cả các lớp đều truy cập cùng một đối tượng hoặc mô-đun. Mất chi tiết, nhưng ít công việc để thiết lập.

  • Decorators. Đặt @log('message', LEVEL) phía trên mỗi phương thức bạn muốn đăng nhập và thao tác này sẽ tự động gọi nhật ký khi phương thức được gọi. Sạch sẽ hơn, ít linh hoạt hơn.

+0

Tốt cho các dự án. Tất cả những gì tôi cần ở đây là một hàm rất cơ bản, với một tùy chọn đăng nhập, nơi mà trình ghi nhật ký có thể được chuyển như một đối số. – iTayb

+0

Tại sao không sử dụng mã bạn đã đăng? Bạn chỉ cần tạo một lớp rất đơn giản cho trình ghi nhật kí, hoặc thậm chí chỉ là một hàm để in những gì được truyền vào các tham số. – BoppreH

+0

Tôi tự hỏi nếu có một đối tượng trong python cho phép ghi vào, mặc dù nó không tồn tại và hỗ trợ lớp con (như gọi class1.class2.func (a, b, c) và không có gì xảy ra). – iTayb

1

Tôi nghĩ điều bạn muốn là ghi nhật ký lọc, vì vậy câu trả lời của tôi là về cách đơn giản để đạt được tính năng ghi nhật ký.

Gói ghi nhật ký của Python đã thực hiện việc này, bạn có nhiều cách để thực hiện lọc nhật ký.

Hai cách cơ bản là:

  • mức ghi lọc
  • tên logger lọc

Cả hai đều sử dụng cấu hình khai thác gỗ, do đó nó có thể dễ dàng cấu hình.

Ví dụ:

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() 

Vì vậy, trừ khi bạn cần thời gian chạy thay đổi địa phương năng động của chính sách khai thác gỗ, sử dụng logger mặc định với cấu hình logging cẩn thận sẽ là đủ.

+0

Ai nói tôi sẽ không sử dụng mức ghi nhật ký CẢNH BÁO? Nhưng tôi có ý tưởng của bạn. – iTayb

Các vấn đề liên quan