Skip to content

set_log_level

anomaly_match.utils.set_log_level

Logging level configuration.

set_log_level(log_level, cfg, log_to_file=True)

Set the log level for the logger.

Parameters:

Name Type Description Default
log_level str

The log level to set. Options are 'TRACE', 'DEBUG', 'INFO', 'SUCCESS', 'WARNING', 'ERROR', 'CRITICAL'.

required
cfg DotMap

The configuration object.

required
log_to_file bool

If True, logs will be saved to a file. Default is True.

True
Source code in anomaly_match/utils/set_log_level.py
def set_log_level(log_level: str, cfg: DotMap, log_to_file: bool = True):
    """Set the log level for the logger.

    Args:
        log_level: The log level to set. Options are 'TRACE', 'DEBUG', 'INFO',
            'SUCCESS', 'WARNING', 'ERROR', 'CRITICAL'.
        cfg: The configuration object.
        log_to_file: If True, logs will be saved to a file. Default is True.
    """
    # Define valid log levels
    valid_log_levels = ["TRACE", "DEBUG", "INFO", "SUCCESS", "WARNING", "ERROR", "CRITICAL"]

    # Assert that the provided log_level is valid
    assert log_level.upper() in valid_log_levels, (
        f"Invalid log level: {log_level}. Expected one of {valid_log_levels}."
    )

    # Remove only the sinks this module added last time (plus loguru's built-in
    # default stderr sink on the first call), leaving externally-registered
    # sinks — the per-session session.log and the UI live-log widget — intact.
    global _own_sink_ids
    for sink_id in _own_sink_ids or [0]:
        try:
            logger.remove(sink_id)
        except ValueError:
            pass  # already removed (e.g. default sink cleared elsewhere)
    _own_sink_ids = []

    # Bypass ipykernel's OutStream (replaces sys.stderr in a kernel): its
    # parent_header walk spins forever when ThreadPoolExecutor ident reuse
    # creates a cycle in _thread_to_parent, hanging the scoring thread.
    console_stream = sys.__stderr__ if sys.__stderr__ is not None else sys.stderr
    _own_sink_ids.append(
        logger.add(
            console_stream,
            colorize=True,
            level=log_level.upper(),
            format="<green>{time:HH:mm:ss}</green>|AnomalyMatch-<blue>{level}</blue>| <level>{message}</level>",
        )
    )

    logger.debug(f"Setting LogLevel to {log_level.upper()}")

    # Per-process timestamped log file — no rotation needed, so no
    # rename that could fail with PermissionError on Windows.
    if log_to_file:
        _own_sink_ids.append(
            logger.add(
                _get_log_path(),
                enqueue=True,
                format="{time:YYYY-MM-DD HH:mm:ss}|{level}|{message}",
            )
        )

    # Store the log level in the config
    cfg.log_level = log_level.upper()