day18 规范目录 logging

1.规范目录结构

使用规范结构目录的好处

-使项目结构更清晰

-提高可读性

规范目录结构不是固定的,可以根据实际需求进行添加修改

常见目录如下:

conf(config) 存放配置文件

db 存放数据处理相关

bin 存放执行文件

lib(commo) :存放公共代码和第三方模块

core:(存放核心业务逻辑)

log:存储输出日志

readme:是一个文本文件,用于描述应用程序

day18 规范目录 logging

 

如果你的执行文件不在最外层,name需要手动将要访问的模块路径加入到sys.path

import sys

sys.path.append(r'文件跟目录')#一般不用

__file__ (获取当前执行文件的完整路径)

BASE_DIR=os.path.dirname(os.path.dirname(__file__))

sys.path.append(BASE_DIR)

    

2.常用模块

loggin日志模块

什么是日志?

就像生活中的日记 用于记录什么时间发生了什么事情

为什么要记?

为了在以后程序出现问题的时候,能通过日志来找到问题的原因

怎么记日志

可以自己实现 当然有功能更强大的longing模块

 

logging模块将日志分为了五种级别

为什么要分级别?是为了在后期查看日志时候方便定位

logging的默认显示级别是WARNING,低于WARNING级别的都不会显示

默认的输出位置是终端

默认的输出格式 WARNING(级别):root(日志生成器名字):warning(输出的日志消息)

 

修改默认的行为

日志模块的四种角色

'''

    logger 日志生成器 生成一条日志(可以设置生成日志的级别)

    filter 日志过滤器    对logger生成的日志进行(面向对象)

    formatter格式化器 设置日志的输出格式

    handler 处理器    最终将日志输出到指定位置(也可以设置输出的日志级别)

'''

day18 规范目录 logging

流程如下:

1.获取生成器

2.格式处理器

3.创建handler处理器

(可以绑定多个handler Streamhandler 输出到终端)

4.将handler与格式处理器绑定

5.把handler生成器绑定

import logging

loger=logging.getLogger('logger1')

#设置日志级别

#loggingm模块内部使用整数区分级别

#此处可以直接写对应整数 但是建议写常量

loger.setLevel(logging.WARNING)

logging.warning('这是一个警告')

#创建一个处理器

handler=logging.FileHandler('tset.log','a',encoding='utf-8')

logging.FileHandler

fmt=logging.Formatter('%(asctime)s %(funcName)s %(message)s')

handler.setFormatter(fmt)

#将handler与生成器绑定

#可以为一个生成器指定多个处理器

loger.addHandler(handler)

loger.error('这是一个错误信息')

使用格式

%(name)s:Logger的名字,并非用户名,详细查看

 

%(levelno)s:数字形式的日志级别

 

%(levelname)s:文本形式的日志级别

 

%(pathname)s:调用日志输出函数的模块的完整路径名,可能没有

 

%(filename)s:调用日志输出函数的模块的文件名

 

%(module)s:调用日志输出函数的模块名

 

%(funcName)s:调用日志输出函数的函数名

 

%(lineno)d:调用日志输出函数的语句所在的代码行

 

%(created)f:当前时间,用UNIX标准的表示时间的浮 点数表示

 

%(relativeCreated)d:输出日志信息时的,自Logger创建以 来的毫秒数

 

%(asctime)s:字符串形式的当前时间。默认格式是 “2003-07-08 16:49:45,896”。逗号后面的是毫秒

 

%(thread)d:线程ID。可能没有

 

%(threadName)s:线程名。可能没有

 

%(process)d:进程ID。可能没有

 

%(message)s:用户输出的消息

使用字典配置

import logging.config

logging.config.dictconfig()

standard_format = '[%(asctime)s][%(threadName)s:%(thread)d][task_id:%(name)s][%(filename)s:%(lineno)d]' \

                  '[%(levelname)s][%(message)s]' #其中name为getlogger指定的名字

 

simple_format = '[%(levelname)s][%(asctime)s][%(filename)s:%(lineno)d]%(message)s'

 

id_simple_format = '[%(levelname)s][%(asctime)s] %(message)s'

logfile_path = "dd.log"

 

LOGGING_DIC = {

    'version': 1,

    'disable_existing_loggers': False,

    'formatters': {

        'standard': {

            'format': standard_format

        },

        'simple': {

            'format': simple_format

        },

    },

    'filters': {},

    'handlers': {

        #打印到终端的日志

        'console': {

            'level': 'DEBUG',

            'class': 'logging.StreamHandler',  # 打印到屏幕

            'formatter': 'simple'

        },

        #打印到文件的日志,收集info及以上的日志

        'default': {

            'level': 'DEBUG',

            'class': 'logging.handlers.RotatingFileHandler',  # 保存到文件

            'formatter': 'standard',

            'filename': logfile_path,  # 日志文件

            'maxBytes': 1024*1024*5,  # 日志大小 5M

            'backupCount': 5,

            'encoding': 'utf-8',  # 日志文件的编码,再也不用担心中文log乱码了

        },

    },

    'loggers': {

        #logging.getLogger(__name__)拿到的logger配置

        '': {

            'handlers': ['default', 'console'],  # 这里把上面定义的两个handler都加上,即log数据既写入文件又打印到屏幕

            'level': 'DEBUG',

            'propagate': True,  # 向上(更高level的logger)传递

        },

    },

}

 

 

import os

os.path.dirname()获取该路径的上一级路径