区分py文件的两种用途
def f1():
print("x")
print(__name__) # 运行文件的时候打印结果为__main__
运行文件的时候__name__等于__main__
当文件被导入使用的时候__name__等于模块名
也就是说下面的if判断下的函数运行只能被当成执行文件运行,当成模块导入是不会运行函数f1的
if __name__ == "__main__":
f1()
使用if判断main可以使文件导入的时候只导入代码文件,不运行文件代码。只有run的时候才会运行文件
包的使用
包的文件只能被导入,不能运行
首次导入包发生的事情
import导入文件,会先执行一个_init_.py文件,申请一个包的名称空间,执行_init_.py文件,将_init_.py文件运行过程中产生的名字导入包的名称空间
在当前位置拿到一个aaaa,指向该名称空间,导入包就是导入_init_.py文件。
向aaaa的文件要名字,就是向aaaa下的_init_.py文件要名字
import aaaa
print(aaaa.x)
print(aaaa.y)
aaaa.m1.f1()
import aaaa
aaaa.bbbb.m3.f3()
绝对导入与相对导入
绝对导入: 以执行文件的sys.path为起始点开始导入,称之为绝对导入
优点: 执行文件与被导入的模块中都可以使用
缺点: 所有导入都是以sys.path为起始点,导入麻烦
相对导入: 参照当前所在文件的文件夹为起始开始查找,称之为相对导入
符号: .代表当前所在文件的文件加,..代表上一级文件夹,...代表上一级的上一级文件夹
优点: 导入更加简单
缺点: 只能在导入包中的模块时才能使用
总结包的使用
导包就是在导包下的_init_.py文件
包内部的导入应该使用相对导入,相对导入也只能在包内部使用,而且...取上一级不能出包
使用语句中的点代表的是访问属性
m.n.x---->向m要n,向n要x
而导入语句中的点代表的是路径分隔符
import a.b.c---->a/b/c,文件夹下的a下有子文件夹b,文件夹b下有子文件或文件夹c
所以导入语句中的点的左边必须是一个包
日志模板图
1、定义三种日志输出格式,日志中可能用到的格式化串如下
%(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用户输出的消息
2、强调:其中的%(name)s为getlogger时指定的名字
standard_format = '[%(asctime)s][%(threadName)s:%(thread)d][task_id:%(name)s][%(filename)s:%(lineno)d]' \
'[%(levelname)s][%(message)s]'
simple_format = '[%(levelname)s][%(asctime)s][%(filename)s:%(lineno)d]%(message)s'
test_format = '%(asctime)s] %(message)s'
3、日志级别
critical => 50
error => 40
warning => 30
info => 20
debug => 10
日志级别是自下而上的,如果把级别设置成debug,那么所有的日志级别都能通过
如果日志级别设置成error的,那么只能error和critical日志级别能通过
配置日志格式
standard_format = "%(asctime)s %(filename)s:%(lineno)d %(name)s %(levelname)s %(message)s " # 标准格式
simple_format = "%(asctime)s %(message)s" # 简单格式
LOGGING_DIC = {
'version': 1, # 日志配置版本
'disable_existing_loggers': False, # 禁用现有的日志记录器
'formatters': {
'standard': {
'format': standard_format
},
'simple': {
'format': simple_format
},
# 'test': {
# 'format': test_format
# },
}, # 控制日志格式
'filters': {}, # 过滤器
'handlers': {
# 打印到文件的日志,收集info及以上的日志
# 'file1': {
# 'level': 'DEBUG',
# 'class': 'logging.handlers.RotatingFileHandler', # 保存到文件,日志轮转
# 'formatter': 'standard',
# # 可以定制日志文件路径
# # BASE_DIR = os.path.dirname(os.path.abspath(__file__)) # log文件的目录
# # LOG_PATH = os.path.join(BASE_DIR,'a1.log')
# 'filename': 'a1.log', # 日志文件
# 'maxBytes': 1024 * 1024 * 5, # 日志大小 5M
# 'backupCount': 5,
# 'encoding': 'utf-8', # 日志文件的编码,再也不用担心中文log乱码了
# },
'file1': {
'level': 'DEBUG',
'class': 'logging.FileHandler', # 保存到文件
'formatter': 'standard',
'filename': 'a1.log', # 注意:这个是文件路径,在项目中需要换成项目中需要改的文件路径
'encoding': 'utf-8',
},
'file2': {
'level': 'DEBUG',
'class': 'logging.FileHandler', # 保存到文件
'formatter': 'standard',
'filename': 'a2.log', # 注意:这个是文件路径,在项目中需要换成项目中需要改的文件路径
'encoding': 'utf-8',
},
# 打印到终端的日志
'stream': {
'level': 'DEBUG',
'class': 'logging.StreamHandler', # 打印到屏幕
'formatter': 'simple'
},
}, # 控制日志输出的地方
'loggers': {
# logging.getLogger(__name__)拿到的logger配置
"安全相关": {
'handlers': ['file1', 'file2', 'stream'], # 这里把上面定义的两个handler都加上,即log数据既写入文件又打印到屏幕
'level': 'ERROR', # loggers(第一层日志级别关限制)--->handlers(第二层日志级别关卡限制)
'propagate': False, # 默认为True,向上(更高level的logger)传递,通常设置为False即可,否则会一份日志向上层层传递
},
"": {
'handlers': ['file1', 'file2', 'stream'], # 这里把上面定义的两个handler都加上,即log数据既写入文件又打印到屏幕
'level': 'CRITICAL', # loggers(第一层日志级别关限制)--->handlers(第二层日志级别关卡限制)
'propagate': False, # 默认为True,向上(更高level的logger)传递,通常设置为False即可,否则会一份日志向上层层传递
},
},
}
# 设置loggers时,如果我们寻找的日志名称在loggers中,那么以找到的名称为准,如果没有找到loggers,那么会以""中的设置为准
调用模块设置
import settings
import logging.config # 内置的子模块
def get_logger(name):
logging.config.dictConfig(settings.LOGGING_DIC)
#加载配置,把settings文件中的LOGGING_DIC加载到logging.config.dictConfig中
return logging.getLogger(name)
logger1 = get_logger("用户交易")
logger1.info("nana给了吴彦祖1个亿")
logger1.debug("调试日志")
logger1.warning("警告")
logger1.error("错误")
logger1.critical("危机")
logger1 = get_logger("安全相关")
logger1.info("常规")
logger1.debug("调试日志")
logger1.warning("警告")
logger1.error("错误")
logger1.critical("危机")