Source code for core4.logger.handler

#
# Copyright 2018 Plan.Net Business Intelligence GmbH & Co. KG
#
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at https://mozilla.org/MPL/2.0/.

"""
Implements :class:`.MongoLoggingHandler` to log into MongoDB collection
``sys.log`` and :func:`make_record` to customise MongoDB documents representing
the logging record.
"""
import logging.config
import os
import traceback

import datetime
import time

from core4.util.tool import Singleton


[docs]def make_record(record): """ Internal method to translate a :class:`logging.LogRecord` into a Python dict ready to feed. The document carries the following keys: * _id * created * username * hostname * qual_name * ,message * level * exception.info (``repr`` string of :class:`Exception`) * exception.text (traceback) :param record: :class:`logging.LogRecord` :return: dict """ ts = time.gmtime(record.created) doc = { "created": datetime.datetime(ts.tm_year, ts.tm_mon, ts.tm_mday, ts.tm_hour, ts.tm_min, ts.tm_sec), "message": record.getMessage(), "level": record.levelname, "levelno": record.levelno } for k in ["username", "hostname", "identifier", "qual_name", "epoch"]: doc[k] = getattr(record, k, None) if doc["identifier"] is not None: doc["identifier"] = str(doc["identifier"]) if doc["qual_name"] is None: doc["qual_name"] = "basename:" + os.path.basename(record.pathname) if record.exc_info or record.exc_text: doc["exception"] = { "info": repr(record.exc_info[1]), "text": traceback.format_exception(*record.exc_info) } return doc
[docs]class MongoLoggingHandler(logging.Handler, metaclass=Singleton): """ This class implements logging into a MongoDB database/collection. """ def __init__(self, connection): """ Connects the logging handler with the passed MongoDB connection. :param connection: :class:`pymongo.collection.Collection` object """ super(MongoLoggingHandler, self).__init__() self._collection = connection
[docs] def handle(self, record): """ Handles the logging record by translating it into a mongo database document. The following attributes are saved for each :class:`logging.LogRecord`. * ``_id`` - the document id as created by :class:`core4.logger.MongoAdapter` * ``created`` - the logging datetime in UTC * ``level`` - the log level as string (``DEBUG``, ``INFO``, ``WARNING``, ``ERROR``, ``CRITICAL``) * ``hostname`` - the name of the host sending the message * ``user`` - the name of the user sending * ``qual_name`` - the qualified name of the class as created by :meth:`.CoreBase.qual_name` * ``identifier`` - the core object identifier; this identifier qualifies core workers with the worker name, core jobs with the worker and job id and API requests with its request id * ``message`` - the log message :param record: the log record (:class:`logging.LogRecord`) """ doc = make_record(record) self._collection.insert_one(doc)