File size: 1,063 Bytes
729a1f7
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
import logging
import sys
from typing import Optional


_DEFAULT_FORMAT = "%(asctime)s %(levelname)s %(message)s"


def _ensure_root_handler() -> None:
    root_logger = logging.getLogger()
    if root_logger.handlers:
        return
    handler = logging.StreamHandler(stream=sys.stdout)
    formatter = logging.Formatter(_DEFAULT_FORMAT)
    handler.setFormatter(formatter)
    root_logger.addHandler(handler)
    root_logger.setLevel(logging.INFO)


class _TaggedAdapter(logging.LoggerAdapter):
    def process(self, msg, kwargs):
        tag = self.extra.get("tag", "")
        if tag and not str(msg).startswith(tag):
            msg = f"{tag} {msg}"
        return msg, kwargs


def get_logger(tag: str, name: Optional[str] = None) -> logging.Logger:
    """
    Return a logger that injects a [TAG] prefix into records.
    Example: logger = get_logger("APP") → logs like: [APP] message
    """
    _ensure_root_handler()
    logger_name = name or __name__
    base = logging.getLogger(logger_name)
    return _TaggedAdapter(base, {"tag": f"[{tag}]"})