Team Ai
Apppublic

Arulkumar03/Fox_Sheep_Detector_Computer_Vision_model

sourceHugging Facemitupdated 3y agoView on Hugging Face
0likes
logger.py262 linesDownload Raw Back to utils
1# Copyright (c) Facebook, Inc. and its affiliates.2import atexit3import functools4import logging5import os6import sys7import time8from collections import Counter9import torch10from tabulate import tabulate11from termcolor import colored12 13from detectron2.utils.file_io import PathManager14 15__all__ = ["setup_logger", "log_first_n", "log_every_n", "log_every_n_seconds"]16 17D2_LOG_BUFFER_SIZE_KEY: str = "D2_LOG_BUFFER_SIZE"18 19DEFAULT_LOG_BUFFER_SIZE: int = 1024 * 1024  # 1MB20 21 22class _ColorfulFormatter(logging.Formatter):23    def __init__(self, *args, **kwargs):24        self._root_name = kwargs.pop("root_name") + "."25        self._abbrev_name = kwargs.pop("abbrev_name", "")26        if len(self._abbrev_name):27            self._abbrev_name = self._abbrev_name + "."28        super(_ColorfulFormatter, self).__init__(*args, **kwargs)29 30    def formatMessage(self, record):31        record.name = record.name.replace(self._root_name, self._abbrev_name)32        log = super(_ColorfulFormatter, self).formatMessage(record)33        if record.levelno == logging.WARNING:34            prefix = colored("WARNING", "red", attrs=["blink"])35        elif record.levelno == logging.ERROR or record.levelno == logging.CRITICAL:36            prefix = colored("ERROR", "red", attrs=["blink", "underline"])37        else:38            return log39        return prefix + " " + log40 41 42@functools.lru_cache()  # so that calling setup_logger multiple times won't add many handlers43def setup_logger(44    output=None,45    distributed_rank=0,46    *,47    color=True,48    name="detectron2",49    abbrev_name=None,50    enable_propagation: bool = False,51    configure_stdout: bool = True52):53    """54    Initialize the detectron2 logger and set its verbosity level to "DEBUG".55 56    Args:57        output (str): a file name or a directory to save log. If None, will not save log file.58            If ends with ".txt" or ".log", assumed to be a file name.59            Otherwise, logs will be saved to `output/log.txt`.60        name (str): the root module name of this logger61        abbrev_name (str): an abbreviation of the module, to avoid long names in logs.62            Set to "" to not log the root module in logs.63            By default, will abbreviate "detectron2" to "d2" and leave other64            modules unchanged.65        enable_propagation (bool): whether to propagate logs to the parent logger.66        configure_stdout (bool): whether to configure logging to stdout.67 68 69    Returns:70        logging.Logger: a logger71    """72    logger = logging.getLogger(name)73    logger.setLevel(logging.DEBUG)74    logger.propagate = enable_propagation75 76    if abbrev_name is None:77        abbrev_name = "d2" if name == "detectron2" else name78 79    plain_formatter = logging.Formatter(80        "[%(asctime)s] %(name)s %(levelname)s: %(message)s", datefmt="%m/%d %H:%M:%S"81    )82    # stdout logging: master only83    if configure_stdout and distributed_rank == 0:84        ch = logging.StreamHandler(stream=sys.stdout)85        ch.setLevel(logging.DEBUG)86        if color:87            formatter = _ColorfulFormatter(88                colored("[%(asctime)s %(name)s]: ", "green") + "%(message)s",89                datefmt="%m/%d %H:%M:%S",90                root_name=name,91                abbrev_name=str(abbrev_name),92            )93        else:94            formatter = plain_formatter95        ch.setFormatter(formatter)96        logger.addHandler(ch)97 98    # file logging: all workers99    if output is not None:100        if output.endswith(".txt") or output.endswith(".log"):101            filename = output102        else:103            filename = os.path.join(output, "log.txt")104        if distributed_rank > 0:105            filename = filename + ".rank{}".format(distributed_rank)106        PathManager.mkdirs(os.path.dirname(filename))107 108        fh = logging.StreamHandler(_cached_log_stream(filename))109        fh.setLevel(logging.DEBUG)110        fh.setFormatter(plain_formatter)111        logger.addHandler(fh)112 113    return logger114 115 116# cache the opened file object, so that different calls to `setup_logger`117# with the same file name can safely write to the same file.118@functools.lru_cache(maxsize=None)119def _cached_log_stream(filename):120    # use 1K buffer if writing to cloud storage121    io = PathManager.open(filename, "a", buffering=_get_log_stream_buffer_size(filename))122    atexit.register(io.close)123    return io124 125 126def _get_log_stream_buffer_size(filename: str) -> int:127    if "://" not in filename:128        # Local file, no extra caching is necessary129        return -1130    # Remote file requires a larger cache to avoid many small writes.131    if D2_LOG_BUFFER_SIZE_KEY in os.environ:132        return int(os.environ[D2_LOG_BUFFER_SIZE_KEY])133    return DEFAULT_LOG_BUFFER_SIZE134 135 136"""137Below are some other convenient logging methods.138They are mainly adopted from139https://github.com/abseil/abseil-py/blob/master/absl/logging/__init__.py140"""141 142 143def _find_caller():144    """145    Returns:146        str: module name of the caller147        tuple: a hashable key to be used to identify different callers148    """149    frame = sys._getframe(2)150    while frame:151        code = frame.f_code152        if os.path.join("utils", "logger.") not in code.co_filename:153            mod_name = frame.f_globals["__name__"]154            if mod_name == "__main__":155                mod_name = "detectron2"156            return mod_name, (code.co_filename, frame.f_lineno, code.co_name)157        frame = frame.f_back158 159 160_LOG_COUNTER = Counter()161_LOG_TIMER = {}162 163 164def log_first_n(lvl, msg, n=1, *, name=None, key="caller"):165    """166    Log only for the first n times.167 168    Args:169        lvl (int): the logging level170        msg (str):171        n (int):172        name (str): name of the logger to use. Will use the caller's module by default.173        key (str or tuple[str]): the string(s) can be one of "caller" or174            "message", which defines how to identify duplicated logs.175            For example, if called with `n=1, key="caller"`, this function176            will only log the first call from the same caller, regardless of177            the message content.178            If called with `n=1, key="message"`, this function will log the179            same content only once, even if they are called from different places.180            If called with `n=1, key=("caller", "message")`, this function181            will not log only if the same caller has logged the same message before.182    """183    if isinstance(key, str):184        key = (key,)185    assert len(key) > 0186 187    caller_module, caller_key = _find_caller()188    hash_key = ()189    if "caller" in key:190        hash_key = hash_key + caller_key191    if "message" in key:192        hash_key = hash_key + (msg,)193 194    _LOG_COUNTER[hash_key] += 1195    if _LOG_COUNTER[hash_key] <= n:196        logging.getLogger(name or caller_module).log(lvl, msg)197 198 199def log_every_n(lvl, msg, n=1, *, name=None):200    """201    Log once per n times.202 203    Args:204        lvl (int): the logging level205        msg (str):206        n (int):207        name (str): name of the logger to use. Will use the caller's module by default.208    """209    caller_module, key = _find_caller()210    _LOG_COUNTER[key] += 1211    if n == 1 or _LOG_COUNTER[key] % n == 1:212        logging.getLogger(name or caller_module).log(lvl, msg)213 214 215def log_every_n_seconds(lvl, msg, n=1, *, name=None):216    """217    Log no more than once per n seconds.218 219    Args:220        lvl (int): the logging level221        msg (str):222        n (int):223        name (str): name of the logger to use. Will use the caller's module by default.224    """225    caller_module, key = _find_caller()226    last_logged = _LOG_TIMER.get(key, None)227    current_time = time.time()228    if last_logged is None or current_time - last_logged >= n:229        logging.getLogger(name or caller_module).log(lvl, msg)230        _LOG_TIMER[key] = current_time231 232 233def create_small_table(small_dict):234    """235    Create a small table using the keys of small_dict as headers. This is only236    suitable for small dictionaries.237 238    Args:239        small_dict (dict): a result dictionary of only a few items.240 241    Returns:242        str: the table as a string.243    """244    keys, values = tuple(zip(*small_dict.items()))245    table = tabulate(246        [values],247        headers=keys,248        tablefmt="pipe",249        floatfmt=".3f",250        stralign="center",251        numalign="center",252    )253    return table254 255 256def _log_api_usage(identifier: str):257    """258    Internal function used to log the usage of different detectron2 components259    inside facebook's infra.260    """261    torch._C._log_api_usage_once("detectron2." + identifier)262