zoukankan      html  css  js  c++  java
  • python日志浅析

    输出日志对于追踪问题比较重要。

    默认logger(root)

    python使用logging模块来处理日志。通常下面的用法就能满足常规需求:

    import logging
    logging.debug('some debug level info....')#debug级别消息
    logging.info('some info level info...')#info级别消息
    logging.warn('some warning level info...')#warning级别消息
    logging.critical('some critical level info...')#critical级别消息
    logging.error('some error level info...')#error级别消息
    

    输出类似:

    [2015-01-07 10:11:34,579](DEBUG)root : adsfaf
    

    即:

    [时间](级别)logger名称:消息

    默认输出到console。 

    自定义logger

    如果某个模块有个性的需求,比如,记录到文件,或者发送邮件。那么问题来了,怎么破?

    如果发生了某种严重的情况,想要发送邮件的话,需要自己定义一个logger,并设置好级别(setLevel(logging.CRITICAL))以及处理器(logging.handlers.SMTPHandler),demo如下:

    import logging
    logger = logging.getLogger('email_logger')
    logger.setLevel(logging.CRITICAL)
    mail_handler= logging.handlers.SMTPHandler('your_mail_host_ip','from_addr','to_addr','critical and above level msg from xxx ')
    
    logging.info('blablabla...')
    logging.error('notice please, an error happens when ...')
    

    记录文件,需要有文件处理器(logging.FileHandler)。demo如下:

    import logging
    logger = logging.getLogger('file_logger')
    logger.addHandler(logging.FileHandler('all.log'))
    logger.info('some info...')
    

    还需要其他的handler?参考这里

    配置型logger

    是否已经厌倦了写代码的方式来自定义logger?好吧,它可以有更多的配置。可以参考这里

    三种方式: 

    1. 上面已经提到了

    2. 通过fileConfig读取配置文件

    以下来自官方demo

    import logging
    import logging.config
    
    logging.config.fileConfig('logging.conf')
    
    # create logger
    logger = logging.getLogger('simpleExample')
    
    # 'application' code
    logger.debug('debug message')
    logger.info('info message')
    logger.warn('warn message')
    logger.error('error message')
    logger.critical('critical message')
    

    配置文件:

    [loggers]
    keys=root,simpleExample
    
    [handlers]
    keys=consoleHandler
    
    [formatters]
    keys=simpleFormatter
    
    [logger_root]
    level=DEBUG
    handlers=consoleHandler
    
    [logger_simpleExample]
    level=DEBUG
    handlers=consoleHandler
    qualname=simpleExample
    propagate=0
    
    [handler_consoleHandler]
    class=StreamHandler
    level=DEBUG
    formatter=simpleFormatter
    args=(sys.stdout,)
    
    [formatter_simpleFormatter]
    format=%(asctime)s - %(name)s - %(levelname)s - %(message)s
    

    输出:

    $ python simple_logging_config.py
    2005-03-19 15:38:55,977 - simpleExample - DEBUG - debug message
    2005-03-19 15:38:55,979 - simpleExample - INFO - info message
    2005-03-19 15:38:56,054 - simpleExample - WARNING - warn message
    2005-03-19 15:38:56,055 - simpleExample - ERROR - error message
    2005-03-19 15:38:56,130 - simpleExample - CRITICAL - critical message
    

     

    配置文件说明:

    声明部分:

    [loggers]
    
    keys = xxx,xxxx
    
    [handlers]
    
    keys = xxx,xxx
    
    [formatters]
    
    keys =xxx,xxx
    

     

    赋值部分

    logger赋值

    [logger_xxx]
    level = DEBUG/INFO/WARN/CRITICAL/ERROR
    handlers = [handlers]里定义的handler
    qualname = logger名
    propagate = 1/0 #是否将log丢给上一级处理
    

      

    handler赋值

    [handler_xxx]
    class = StreamHander/FileHander/handlers.SMTPHandler...
    args = 传递给上面class的参数
    level = DEBUG/INFO/WARN/CRITICAL/ERROR #是否处理,可以和logger的不同
    formatter = [formatters]中定义的格式器
    

    比较有用的一个handlers配置

    [handler_rotateFileHandler]
    class=handlers.RotatingFileHandler
    args=('xxx.log', 'a', 2000000, 9)#日志超过2000000 d的时候,重新另外生成一个文件,保存9天的记录
    ...
    

      

    formatter赋值

    [formatter_xxx]
    format = %(var)s # var:asctime/name/levelname/message/ip/user/module/process/thread...
    

      

    logging.config.fileConfig的特别说明:

    disable_existing_loggers是一个可选参数,默认为True。它会阻止在fileConfig语句前面的logger的正常执行。其设计目的是为了反向兼容。

    要使得所有的logger都有效,要么在配置文件中,将前面的logger给配置进去。

    要么将它改为False。

    3. 通过dictConfig读取配置dict

    django 就使用了这种方式,配置dict如下:

    LOGGING = {
        'version': 1,
        'disable_existing_loggers': True,
        'formatters': {
            'verbose': {
                'format': '%(levelname)s %(asctime)s %(module)s %(process)d %(thread)d %(message)s'
            },
            'simple': {
                'format': '%(levelname)s %(message)s'
            },
        },
        'filters': {
            'special': {
                '()': 'project.logging.SpecialFilter',
                'foo': 'bar',
            }
        },
        'handlers': {
            'null': {
                'level':'DEBUG',
                'class':'django.utils.log.NullHandler',
            },
            'console':{
                'level':'DEBUG',
                'class':'logging.StreamHandler',
                'formatter': 'simple'
            },
            'mail_admins': {
                'level': 'ERROR',
                'class': 'django.utils.log.AdminEmailHandler',
                'filters': ['special']
            }
        },
        'loggers': {
            'django': {
                'handlers':['null'],
                'propagate': True,
                'level':'INFO',
            },
            'django.request': {
                'handlers': ['mail_admins'],
                'level': 'ERROR',
                'propagate': False,
            },
            'myproject.custom': {
                'handlers': ['console', 'mail_admins'],
                'level': 'INFO',
                'filters': ['special']
            }
        }
    }

    转载请注明,本文来自Tommy.Yu的博客。谢谢!

  • 相关阅读:
    .net注册iis
    hdu 1081To The Max
    hdu 1312Red and Black
    hdu 1016Prime Ring Problem
    hdu 1159Common Subsequence
    hdu 1372Knight Moves
    hdu 1686Oulipo
    hdu 1241Oil Deposits
    hdu 1171Big Event in HDU
    hdu 4006The kth great number
  • 原文地址:https://www.cnblogs.com/Tommy-Yu/p/4208072.html
Copyright © 2011-2022 走看看