diff --git a/src/common/log_decorators.py b/src/common/log_decorators.py new file mode 100644 index 000000000..9838717f9 --- /dev/null +++ b/src/common/log_decorators.py @@ -0,0 +1,107 @@ +import functools +import inspect +from typing import Callable, Any +from .logger import logger, add_custom_style_handler + + +def use_log_style( + style_name: str, + console_format: str, + console_level: str = "INFO", + # file_format: Optional[str] = None, # 暂未支持文件输出 + # file_level: str = "DEBUG", +) -> Callable: + """装饰器:为函数内的日志启用特定的自定义样式。 + + Args: + style_name (str): 自定义样式的唯一名称。 + console_format (str): 控制台输出的格式字符串。 + console_level (str, optional): 控制台日志级别. Defaults to "INFO". + # file_format (Optional[str], optional): 文件输出格式 (暂未支持). Defaults to None. + # file_level (str, optional): 文件日志级别 (暂未支持). Defaults to "DEBUG". + + Returns: + Callable: 返回装饰器本身。 + """ + + def decorator(func: Callable) -> Callable: + # 获取被装饰函数所在的模块名 + module = inspect.getmodule(func) + if module is None: + # 如果无法获取模块(例如,在交互式解释器中定义函数),则使用默认名称 + module_name = "unknown_module" + logger.warning(f"无法确定函数 {func.__name__} 的模块,将使用 '{module_name}'") + else: + module_name = module.__name__ + + # 在函数首次被调用(或模块加载时)确保自定义处理器已添加 + # 注意:这会在模块加载时执行,而不是每次函数调用时 + # print(f"Setting up custom style '{style_name}' for module '{module_name}' in decorator definition") + add_custom_style_handler( + module_name=module_name, + style_name=style_name, + console_format=console_format, + console_level=console_level, + # file_format=file_format, + # file_level=file_level, + ) + + @functools.wraps(func) + def wrapper(*args: Any, **kwargs: Any) -> Any: + # 创建绑定了模块名和自定义样式标记的 logger 实例 + custom_logger = logger.bind(module=module_name, custom_style=style_name) + # print(f"Executing {func.__name__} with custom logger for style '{style_name}'") + # 将自定义 logger 作为第一个参数传递给原函数 + # 注意:这要求被装饰的函数第一个参数用于接收 logger + try: + return func(custom_logger, *args, **kwargs) + except TypeError as e: + # 捕获可能的类型错误,比如原函数不接受 logger 参数 + logger.error( + f"调用 {func.__name__} 时出错:请确保该函数接受一个 logger 实例作为其第一个参数。错误:{e}" + ) + # 可以选择重新抛出异常或返回特定值 + raise e + + return wrapper + + return decorator + + +# --- 示例用法 (可以在其他模块中这样使用) --- + +# # 假设这是你的模块 my_module.py +# from src.common.log_decorators import use_log_style +# from src.common.logger import get_module_logger, LoguruLogger + +# # 获取模块的标准 logger +# standard_logger = get_module_logger(__name__) + +# # 定义一个自定义样式 +# MY_SPECIAL_STYLE = "special" +# MY_SPECIAL_FORMAT = " SPECIAL [{time:HH:mm:ss}] | {message}" + +# @use_log_style(style_name=MY_SPECIAL_STYLE, console_format=MY_SPECIAL_FORMAT) +# def my_function_with_special_logs(custom_logger: LoguruLogger, x: int, y: int): +# standard_logger.info("这是一条使用标准格式的日志") +# custom_logger.info(f"开始执行特殊操作,参数: x={x}, y={y}") +# result = x + y +# custom_logger.success(f"特殊操作完成,结果: {result}") +# standard_logger.info("标准格式日志:函数即将结束") +# return result + +# @use_log_style(style_name="another_style", console_format="任务: {message}") +# def another_task(task_logger: LoguruLogger, task_name: str): +# standard_logger.debug("准备执行另一个任务") +# task_logger.info(f"正在处理任务 '{task_name}'") +# # ... 执行任务 ... +# task_logger.warning("任务处理中遇到一个警告") +# standard_logger.info("另一个任务的标准日志") + +# if __name__ == "__main__": +# print("\n--- 调用 my_function_with_special_logs ---") +# my_function_with_special_logs(10, 5) +# print("\n--- 调用 another_task ---") +# another_task("数据清理") +# print("\n--- 单独使用标准 logger ---") +# standard_logger.info("这是一条完全独立的标准日志") diff --git a/src/common/logger.py b/src/common/logger.py index 2b2208419..48d476e6d 100644 --- a/src/common/logger.py +++ b/src/common/logger.py @@ -1,5 +1,5 @@ from loguru import logger -from typing import Dict, Optional, Union, List +from typing import Dict, Optional, Union, List, Tuple import sys import os from types import ModuleType @@ -26,12 +26,17 @@ LoguruLogger = logger.__class__ # 全局注册表:记录模块与处理器ID的映射 _handler_registry: Dict[str, List[int]] = {} +_custom_style_handlers: Dict[Tuple[str, str], List[int]] = {} # 记录自定义样式处理器ID # 获取日志存储根地址 current_file_path = Path(__file__).resolve() LOG_ROOT = "logs" -SIMPLE_OUTPUT = os.getenv("SIMPLE_OUTPUT", "false") +SIMPLE_OUTPUT = os.getenv("SIMPLE_OUTPUT", "false").strip().lower() +if SIMPLE_OUTPUT == "true": + SIMPLE_OUTPUT = True +else: + SIMPLE_OUTPUT = False print(f"SIMPLE_OUTPUT: {SIMPLE_OUTPUT}") if not SIMPLE_OUTPUT: @@ -42,10 +47,7 @@ if not SIMPLE_OUTPUT: "file_level": "DEBUG", # 格式配置 "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " - "{level: <8} | " - "{extra[module]: <12} | " - "{message}" + "{time:YYYY-MM-DD HH:mm:ss} | {extra[module]: <12} | {message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | {message}", "log_dir": LOG_ROOT, @@ -59,7 +61,7 @@ else: "console_level": "INFO", "file_level": "DEBUG", # 格式配置 - "console_format": "{time:MM-DD HH:mm} | {extra[module]} | {message}", + "console_format": "{time:MM-DD HH:mm} | {extra[module]} | {message}", "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | {message}", "log_dir": LOG_ROOT, "rotation": "00:00", @@ -68,13 +70,30 @@ else: } +MAIN_STYLE_CONFIG = { + "advanced": { + "console_format": ( + "{time:YYYY-MM-DD HH:mm:ss} | " + "{level: <8} | " + "主程序 | " + "{message}" + ), + "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 主程序 | {message}", + }, + "simple": { + "console_format": ( + "{time:MM-DD HH:mm} | 主程序 | {message}" + ), + "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 主程序 | {message}", + }, +} + # 海马体日志样式配置 MEMORY_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "海马体 | " "{message}" ), @@ -82,7 +101,7 @@ MEMORY_STYLE_CONFIG = { }, "simple": { "console_format": ( - "{time:MM-DD HH:mm} | 海马体 | {message}" + "{time:MM-DD HH:mm} | 海马体 | {message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 海马体 | {message}", }, @@ -92,9 +111,8 @@ MEMORY_STYLE_CONFIG = { PFC_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "PFC | " "{message}" ), @@ -102,7 +120,7 @@ PFC_STYLE_CONFIG = { }, "simple": { "console_format": ( - "{time:MM-DD HH:mm} | PFC | {message}" + "{time:MM-DD HH:mm} | PFC | {message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | PFC | {message}", }, @@ -112,16 +130,15 @@ PFC_STYLE_CONFIG = { MOOD_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "心情 | " "{message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 心情 | {message}", }, "simple": { - "console_format": "{time:MM-DD HH:mm} | 心情 | {message}", + "console_format": "{time:MM-DD HH:mm} | 心情 | {message}", "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 心情 | {message}", }, } @@ -129,16 +146,15 @@ MOOD_STYLE_CONFIG = { TOOL_USE_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "工具使用 | " "{message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 工具使用 | {message}", }, "simple": { - "console_format": "{time:MM-DD HH:mm} | 工具使用 | {message}", + "console_format": "{time:MM-DD HH:mm} | 工具使用 | {message}", "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 工具使用 | {message}", }, } @@ -148,16 +164,15 @@ TOOL_USE_STYLE_CONFIG = { RELATION_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "关系 | " "{message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 关系 | {message}", }, "simple": { - "console_format": "{time:MM-DD HH:mm} | 关系 | {message}", + "console_format": "{time:MM-DD HH:mm} | 关系 | {message}", "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 关系 | {message}", }, } @@ -166,16 +181,15 @@ RELATION_STYLE_CONFIG = { CONFIG_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "配置 | " "{message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 配置 | {message}", }, "simple": { - "console_format": "{time:MM-DD HH:mm} | 配置 | {message}", + "console_format": "{time:MM-DD HH:mm} | 配置 | {message}", "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 配置 | {message}", }, } @@ -183,16 +197,15 @@ CONFIG_STYLE_CONFIG = { SENDER_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "消息发送 | " "{message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 消息发送 | {message}", }, "simple": { - "console_format": "{time:MM-DD HH:mm} | 消息发送 | {message}", + "console_format": "{time:MM-DD HH:mm} | 消息发送 | {message}", "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 消息发送 | {message}", }, } @@ -200,9 +213,8 @@ SENDER_STYLE_CONFIG = { HEARTFLOW_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "麦麦大脑袋 | " "{message}" ), @@ -210,7 +222,7 @@ HEARTFLOW_STYLE_CONFIG = { }, "simple": { "console_format": ( - "{time:MM-DD HH:mm} | 麦麦大脑袋 | {message}" + "{time:MM-DD HH:mm} | 麦麦大脑袋 | {message}" ), # noqa: E501 "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 麦麦大脑袋 | {message}", }, @@ -219,16 +231,15 @@ HEARTFLOW_STYLE_CONFIG = { SCHEDULE_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "在干嘛 | " "{message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 在干嘛 | {message}", }, "simple": { - "console_format": "{time:MM-DD HH:mm} | 在干嘛 | {message}", + "console_format": "{time:MM-DD HH:mm} | 在干嘛 | {message}", "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 在干嘛 | {message}", }, } @@ -236,16 +247,15 @@ SCHEDULE_STYLE_CONFIG = { LLM_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "麦麦组织语言 | " "{message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 麦麦组织语言 | {message}", }, "simple": { - "console_format": "{time:MM-DD HH:mm} | 麦麦组织语言 | {message}", + "console_format": "{time:MM-DD HH:mm} | 麦麦组织语言 | {message}", "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 麦麦组织语言 | {message}", }, } @@ -255,16 +265,15 @@ LLM_STYLE_CONFIG = { TOPIC_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "话题 | " "{message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 话题 | {message}", }, "simple": { - "console_format": "{time:MM-DD HH:mm} | 主题 | {message}", + "console_format": "{time:MM-DD HH:mm} | 主题 | {message}", "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 话题 | {message}", }, } @@ -273,9 +282,8 @@ TOPIC_STYLE_CONFIG = { CHAT_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "见闻 | " "{message}" ), @@ -283,7 +291,7 @@ CHAT_STYLE_CONFIG = { }, "simple": { "console_format": ( - "{time:MM-DD HH:mm} | 见闻 | {message}" + "{time:MM-DD HH:mm} | 见闻 | {message}" ), # noqa: E501 "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 见闻 | {message}", }, @@ -292,9 +300,8 @@ CHAT_STYLE_CONFIG = { SUB_HEARTFLOW_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "麦麦小脑袋 | " "{message}" ), @@ -302,7 +309,7 @@ SUB_HEARTFLOW_STYLE_CONFIG = { }, "simple": { "console_format": ( - "{time:MM-DD HH:mm} | 麦麦小脑袋 | {message}" + "{time:MM-DD HH:mm} | 麦麦小脑袋 | {message}" ), # noqa: E501 "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 麦麦小脑袋 | {message}", }, @@ -311,16 +318,15 @@ SUB_HEARTFLOW_STYLE_CONFIG = { WILLING_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "意愿 | " "{message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 意愿 | {message}", }, "simple": { - "console_format": "{time:MM-DD HH:mm} | 意愿 | {message} ", # noqa: E501 + "console_format": "{time:MM-DD HH:mm} | 意愿 | {message} ", # noqa: E501 "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 意愿 | {message}", }, } @@ -329,16 +335,15 @@ WILLING_STYLE_CONFIG = { MAI_STATE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "麦麦状态 | " "{message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 麦麦状态 | {message}", }, "simple": { - "console_format": "{time:MM-DD HH:mm} | 麦麦状态 | {message} ", # noqa: E501 + "console_format": "{time:MM-DD HH:mm} | 麦麦状态 | {message} ", # noqa: E501 "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 麦麦状态 | {message}", }, } @@ -347,9 +352,8 @@ MAI_STATE_CONFIG = { LPMM_STYLE_CONFIG = { "advanced": { "console_format": ( - "{time:YYYY-MM-DD HH:mm:ss} | " + "{time:YYYY-MM-DD HH:mm:ss} | " "{level: <8} | " - "{extra[module]: <12} | " "LPMM | " "{message}" ), @@ -357,18 +361,38 @@ LPMM_STYLE_CONFIG = { }, "simple": { "console_format": ( - "{time:MM-DD HH:mm} | LPMM | {message}" + "{time:MM-DD HH:mm} | LPMM | {message}" ), "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | LPMM | {message}", }, } +# 兴趣log +INTEREST_STYLE_CONFIG = { + "advanced": { + "console_format": ( + "{time:YYYY-MM-DD HH:mm:ss} | " + "{level: <8} | " + "兴趣 | " + "{message}" + ), + "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 兴趣 | {message}", + }, + "simple": { + "console_format": ( + "{time:MM-DD HH:mm} | 兴趣 | {message}" + ), + "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | 兴趣 | {message}", + }, +} + CONFIRM_STYLE_CONFIG = { "console_format": "{message}", # noqa: E501 "file_format": "{time:YYYY-MM-DD HH:mm:ss} | {level: <8} | {extra[module]: <15} | EULA与PRIVACY确认 | {message}", } # 根据SIMPLE_OUTPUT选择配置 +MAIN_STYLE_CONFIG = MAIN_STYLE_CONFIG["simple"] if SIMPLE_OUTPUT else MAIN_STYLE_CONFIG["advanced"] MEMORY_STYLE_CONFIG = MEMORY_STYLE_CONFIG["simple"] if SIMPLE_OUTPUT else MEMORY_STYLE_CONFIG["advanced"] TOPIC_STYLE_CONFIG = TOPIC_STYLE_CONFIG["simple"] if SIMPLE_OUTPUT else TOPIC_STYLE_CONFIG["advanced"] SENDER_STYLE_CONFIG = SENDER_STYLE_CONFIG["simple"] if SIMPLE_OUTPUT else SENDER_STYLE_CONFIG["advanced"] @@ -387,6 +411,7 @@ CONFIG_STYLE_CONFIG = CONFIG_STYLE_CONFIG["simple"] if SIMPLE_OUTPUT else CONFIG TOOL_USE_STYLE_CONFIG = TOOL_USE_STYLE_CONFIG["simple"] if SIMPLE_OUTPUT else TOOL_USE_STYLE_CONFIG["advanced"] PFC_STYLE_CONFIG = PFC_STYLE_CONFIG["simple"] if SIMPLE_OUTPUT else PFC_STYLE_CONFIG["advanced"] LPMM_STYLE_CONFIG = LPMM_STYLE_CONFIG["simple"] if SIMPLE_OUTPUT else LPMM_STYLE_CONFIG["advanced"] +INTEREST_STYLE_CONFIG = INTEREST_STYLE_CONFIG["simple"] if SIMPLE_OUTPUT else INTEREST_STYLE_CONFIG["advanced"] def is_registered_module(record: dict) -> bool: @@ -451,7 +476,7 @@ def get_module_logger( sink=sys.stderr, level=os.getenv("CONSOLE_LOG_LEVEL", console_level or current_config["console_level"]), format=current_config["console_format"], - filter=lambda record: record["extra"].get("module") == module_name, + filter=lambda record: record["extra"].get("module") == module_name and "custom_style" not in record["extra"], enqueue=True, ) handler_ids.append(console_id) @@ -470,7 +495,7 @@ def get_module_logger( retention=current_config["retention"], compression=current_config["compression"], encoding="utf-8", - filter=lambda record: record["extra"].get("module") == module_name, + filter=lambda record: record["extra"].get("module") == module_name and "custom_style" not in record["extra"], enqueue=True, ) handler_ids.append(file_id) @@ -487,6 +512,87 @@ def get_module_logger( return logger.bind(module=module_name) +def add_custom_style_handler( + module_name: str, + style_name: str, + console_format: str, + console_level: str = "INFO", + # file_format: Optional[str] = None, # 暂时只支持控制台 + # file_level: str = "DEBUG", + # config: Optional[LogConfig] = None, # 暂时不使用全局配置 +) -> None: + """为指定模块和样式名添加自定义日志处理器(目前仅支持控制台).""" + handler_key = (module_name, style_name) + + # 如果已存在该模块和样式的处理器,则不重复添加 + if handler_key in _custom_style_handlers: + # print(f"Custom handler for {handler_key} already exists.") + return + + handler_ids = [] + + # 添加自定义控制台处理器 + try: + custom_console_id = logger.add( + sink=sys.stderr, + level=os.getenv(f"{module_name.upper()}_{style_name.upper()}_CONSOLE_LEVEL", console_level), + format=console_format, + filter=lambda record: record["extra"].get("module") == module_name + and record["extra"].get("custom_style") == style_name, + enqueue=True, + ) + handler_ids.append(custom_console_id) + # print(f"Added custom console handler {custom_console_id} for {handler_key}") + except Exception as e: + logger.error(f"Failed to add custom console handler for {handler_key}: {e}") + # 如果添加失败,确保列表为空,避免记录不存在的ID + handler_ids = [] + + # # 文件处理器 (可选,按需启用) + # if file_format: + # current_config = config.config if config else DEFAULT_CONFIG + # log_dir = Path(current_config["log_dir"]) + # log_dir.mkdir(parents=True, exist_ok=True) + # # 可以考虑将自定义样式的日志写入单独文件或模块主文件 + # log_file = log_dir / module_name / f"{style_name}_{{time:YYYY-MM-DD}}.log" + # log_file.parent.mkdir(parents=True, exist_ok=True) + # try: + # custom_file_id = logger.add( + # sink=str(log_file), + # level=os.getenv(f"{module_name.upper()}_{style_name.upper()}_FILE_LEVEL", file_level), + # format=file_format, + # rotation=current_config["rotation"], + # retention=current_config["retention"], + # compression=current_config["compression"], + # encoding="utf-8", + # filter=lambda record: record["extra"].get("module") == module_name + # and record["extra"].get("custom_style") == style_name, + # enqueue=True, + # ) + # handler_ids.append(custom_file_id) + # except Exception as e: + # logger.error(f"Failed to add custom file handler for {handler_key}: {e}") + + # 更新自定义处理器注册表 + if handler_ids: + _custom_style_handlers[handler_key] = handler_ids + + +def remove_custom_style_handler(module_name: str, style_name: str) -> None: + """移除指定模块和样式名的自定义日志处理器.""" + handler_key = (module_name, style_name) + if handler_key in _custom_style_handlers: + for handler_id in _custom_style_handlers[handler_key]: + try: + logger.remove(handler_id) + # print(f"Removed custom handler {handler_id} for {handler_key}") + except ValueError: + # 可能已经被移除或不存在 + # print(f"Handler {handler_id} for {handler_key} already removed or invalid.") + pass + del _custom_style_handlers[handler_key] + + def remove_module_logger(module_name: str) -> None: """清理指定模块的日志处理器""" if module_name in _handler_registry: diff --git a/src/heart_flow/interest_logger.py b/src/heart_flow/interest_logger.py index c2af9ba6b..15a08b64d 100644 --- a/src/heart_flow/interest_logger.py +++ b/src/heart_flow/interest_logger.py @@ -5,7 +5,7 @@ import os import traceback from typing import TYPE_CHECKING, Dict, List -from src.common.logger import get_module_logger +from src.common.logger import get_module_logger, LogConfig, INTEREST_STYLE_CONFIG # Need chat_manager to get stream names from src.plugins.chat.chat_stream import chat_manager @@ -15,7 +15,11 @@ if TYPE_CHECKING: from src.heart_flow.sub_heartflow import SubHeartflow from src.heart_flow.heartflow import Heartflow # 导入 Heartflow 类型 -logger = get_module_logger("interest_logger") +interest_logger_config = LogConfig( + console_format=INTEREST_STYLE_CONFIG["console_format"], + file_format=INTEREST_STYLE_CONFIG["file_format"], +) +logger = get_module_logger("interest_logger", config=interest_logger_config) # Consider moving log directory/filename constants here LOG_DIRECTORY = "logs/interest" diff --git a/src/main.py b/src/main.py index 75ab2ae72..62fa70a6e 100644 --- a/src/main.py +++ b/src/main.py @@ -13,12 +13,16 @@ from .plugins.chat.message_sender import message_manager from .plugins.storage.storage import MessageStorage from .config.config import global_config from .plugins.chat.bot import chat_bot -from .common.logger import get_module_logger +from .common.logger import get_module_logger, LogConfig, MAIN_STYLE_CONFIG from .plugins.remote import heartbeat_thread # noqa: F401 from .individuality.individuality import Individuality from .common.server import global_server -logger = get_module_logger("main") +main_log_config = LogConfig( + console_format=MAIN_STYLE_CONFIG["console_format"], + file_format=MAIN_STYLE_CONFIG["file_format"], +) +logger = get_module_logger("main", config=main_log_config) class MainSystem: diff --git a/src/plugins/knowledge/src/lpmmconfig.py b/src/plugins/knowledge/src/lpmmconfig.py index 7f59bc897..753562f45 100644 --- a/src/plugins/knowledge/src/lpmmconfig.py +++ b/src/plugins/knowledge/src/lpmmconfig.py @@ -2,6 +2,7 @@ import os import toml import sys import argparse +from .global_logger import logger PG_NAMESPACE = "paragraph" ENT_NAMESPACE = "entity" @@ -63,8 +64,8 @@ def _load_config(config, config_file_path): if "persistence" in file_config: config["persistence"] = file_config["persistence"] - print(config) - print("Configurations loaded from file: ", config_file_path) + # print(config) + logger.info(f"从文件中读取配置: {config_file_path}") parser = argparse.ArgumentParser(description="Configurations for the pipeline")