Created
July 27, 2023 14:25
-
-
Save norweeg/14b089057405a91abce27b360091659e to your computer and use it in GitHub Desktop.
Setup console logging with Python standard library logging module
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import logging | |
from sys import stderr, stdout | |
# Handle log messages from only these loggers. | |
# We will always log messages from "root" logger | |
# by appending names to this list, we can add additional loggers | |
# that should be handled | |
terminal_logger_names = [] | |
# Format for terminal output: only show the log message | |
terminal_formatter = logging.Formatter("{message}", style="{") | |
# handler for log message with level < warning, prints to stdout | |
output_handler = logging.StreamHandler(stdout) | |
output_handler.setLevel(logging.INFO) | |
# only log messages INFO <= log record level < WARNING to stdout | |
output_handler.addFilter(lambda r: r.levelno < logging.WARNING) | |
# only log messages handled by the root logger (i.e. within __main__) or in a list of names of other log names to handle | |
output_handler.addFilter(lambda r: any([r.name.startswith(name) for name in terminal_logger_names]) or r.name == "root") | |
output_handler.setFormatter(terminal_formatter) | |
# handler for log message with level >= warning, prints to stderr | |
error_handler = logging.StreamHandler(stderr) | |
# Only handle log records >= WARNING on stderr | |
error_handler.setLevel(logging.WARNING) | |
# Intentionally NOT filtering source of message for log messages > WARNING. | |
# You proabably want to know these regardless of source so you can fix them | |
error_handler.setFormatter(terminal_formatter) | |
# typically, you would only configure in the __main__ module of your code | |
# with the log output of anything imported by it also configured here if | |
# if you want to handle it differently. The below config shows configuring | |
# the root logger i.e. the logger to which all logging messages eventually | |
# propagate unless handled and not propagated by a child logger | |
if __name__ == "__main__": | |
# sets up the root logger to log all messages as terminal output, with | |
# messages that are warnings or higher going to stderr and the rest to stdout | |
logging.basicConfig( | |
handlers=[output_handler, error_handler], | |
level=logging.INFO | |
) | |
# capture any warnings produced with using the warnings module | |
logging.captureWarnings(True) | |
try: | |
# Your code goes here | |
... | |
except Exception as e: | |
# catch and log any unhandled exceptions from your code | |
logging.exception(str(e)) | |
exit(1) | |
finally: | |
# ensures any log data not written to file or terminal is handled before exiting | |
logging.shutdown() | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment