如何在Python中为整个应用使用自定义控制台日志记录器?
Python全局日志格式配置方案
核心思路
Python的日志系统是层级式的:所有logger实例都隶属于树形结构,子logger默认会将日志向上传播到父logger,直至根logger(logging.getLogger()不带参数获取的实例)。因此只需配置根logger或应用级顶级父logger,所有子logger(包括各模块的logging.getLogger(__name__))都会自动继承其格式、handler等配置,无需逐个模块设置。
实现步骤
1. 自定义带颜色的日志格式器
实现支持级别缩写和控制台颜色的自定义格式器:
import logging from logging import StreamHandler class ColoredFormatter(logging.Formatter): # ANSI控制台颜色码 _COLOR_MAP = { logging.DEBUG: "\033[94m", # 蓝色 logging.INFO: "\033[92m", # 绿色 logging.WARNING: "\033[93m", # 黄色 logging.ERROR: "\033[91m", # 红色 logging.CRITICAL: "\033[95m" # 紫色 } _RESET_CODE = "\033[0m" _LEVEL_ABBR = { "DEBUG": "DBG", "INFO": "INF", "WARNING": "WRN", "ERROR": "ERR", "CRITICAL": "CRT" } def format(self, record): # 替换级别为缩写 record.levelname = self._LEVEL_ABBR.get(record.levelname, record.levelname) # 为消息添加颜色 color = self._COLOR_MAP.get(record.levelno, self._RESET_CODE) record.msg = f"{color}{record.msg}{self._RESET_CODE}" # 调用父类完成最终格式化 return super().format(record)
2. 全局配置日志系统
在应用入口(如main.py)中配置根logger,覆盖默认日志处理规则:
def setup_global_logging(): # 获取根日志器 root_logger = logging.getLogger() # 设置全局日志级别(低于此级别的日志会被过滤) root_logger.setLevel(logging.DEBUG) # 移除默认handler(避免重复输出) for handler in root_logger.handlers[:]: root_logger.removeHandler(handler) # 创建控制台handler console_handler = StreamHandler() console_handler.setLevel(logging.DEBUG) # 绑定自定义格式器,可按需调整日志模板 formatter = ColoredFormatter( "%(asctime)s - %(levelname)s - %(name)s - %(message)s", datefmt="%Y-%m-%d %H:%M:%S" ) console_handler.setFormatter(formatter) # 将handler添加到根日志器 root_logger.addHandler(console_handler) # 应用启动时初始化 if __name__ == "__main__": setup_global_logging() main_logger = logging.getLogger(__name__) main_logger.info("主应用启动完成") # 导入并使用其他模块 import my_module my_module.run_task()
3. 模块中直接使用日志
各模块无需额外配置,直接通过logging.getLogger(__name__)获取logger即可自动继承根logger的格式:
# my_module.py import logging logger = logging.getLogger(__name__) def run_task(): logger.debug("模块内调试信息") logger.info("模块内常规信息") logger.warning("模块内警告提示") logger.error("模块内错误信息")
可选:隔离应用日志与第三方库日志
如果不想让第三方库的日志应用自定义格式,可以放弃配置根logger,转而创建应用级顶级logger,让所有业务模块的logger作为它的子节点:
# main.py中配置应用顶级logger def setup_app_logging(): app_logger = logging.getLogger("my_app") app_logger.setLevel(logging.DEBUG) app_logger.propagate = False # 避免向上传播到根logger # 移除默认handler(如果有) for handler in app_logger.handlers[:]: app_logger.removeHandler(handler) # 添加自定义handler和格式器(同之前的ColoredFormatter) console_handler = StreamHandler() console_handler.setFormatter(ColoredFormatter(...)) app_logger.addHandler(console_handler) # 模块中使用应用子logger # my_module.py logger = logging.getLogger(f"my_app.{__name__}") # 若模块在my_app包下,直接用__name__即可(自动成为my_app的子logger)
原有代码不生效的原因
你之前仅给名为test的logger添加了handler,但模块中的logger = logging.getLogger(__name__)是根logger的子节点,并未继承test logger的配置。只有当模块logger是test的子节点(如logging.getLogger("test.module")),或你将handler配置到根logger时,模块日志才会使用自定义格式。
内容的提问来源于stack exchange,提问作者ygoe
相关产品推荐
相关产品推荐

