| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354 |
- import logging
- import logging.handlers
- import json
- import sys
- import os
- from datetime import datetime, timezone
- class JsonFormatter(logging.Formatter):
- """JSON 日志格式化器 (适合生产环境日志聚合)"""
- def format(self, record: logging.LogRecord) -> str:
- log_entry = {
- "timestamp": datetime.now(timezone.utc).isoformat(),
- "level": record.levelname,
- "logger": record.name,
- "message": record.getMessage(),
- }
- if hasattr(record, "trace_id"):
- log_entry["trace_id"] = record.trace_id
- if record.exc_info and record.exc_info[0]:
- log_entry["exception"] = self.formatException(record.exc_info)
- return json.dumps(log_entry, ensure_ascii=False)
- def setup_logging(level: str = "INFO", json_format: bool = False):
- root = logging.getLogger()
- root.setLevel(getattr(logging, level.upper(), logging.INFO))
- root.handlers.clear()
- # 控制台 handler
- console_handler = logging.StreamHandler(sys.stdout)
- if json_format:
- console_handler.setFormatter(JsonFormatter())
- else:
- console_handler.setFormatter(logging.Formatter(
- "%(asctime)s [%(levelname)s] %(name)s: %(message)s",
- datefmt="%Y-%m-%d %H:%M:%S",
- ))
- root.addHandler(console_handler)
- # 可选:文件落盘 (LOG_FILE 环境变量指定路径,默认不开启)
- log_file = os.getenv("LOG_FILE")
- if log_file:
- file_handler = logging.handlers.RotatingFileHandler(
- log_file, maxBytes=10 * 1024 * 1024, backupCount=5, encoding="utf-8"
- )
- file_handler.setFormatter(JsonFormatter())
- root.addHandler(file_handler)
- logging.getLogger("httpx").setLevel(logging.WARNING)
- logging.getLogger("chromadb").setLevel(logging.WARNING)
- logging.getLogger("langchain").setLevel(logging.WARNING)
|