Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Can Python's logging format be modified depending on the message log level?

I'm using Python's logging mechanism to print output to the screen. I could do this with print statements, but I want to allow a finer-tuned granularity for the user to disable certain types of output. I like the format printed for errors, but would prefer a simpler format when the output level is "info."

For example:

  logger.error("Running cmd failed")   logger.info("Running cmd passed") 

In this example, I would like the format of the error to be printed differently:

# error Aug 27, 2009 - ERROR: Running cmd failed # info Running cmd passed 

Is it possible to have different formats for different log levels without having multiple logging objects? I'd prefer to do this without modifying the logger once it's created since there are a high number of if/else statements to determine how the output should be logged.

like image 489
bedwyr Avatar asked Aug 27 '09 19:08

bedwyr


People also ask

What are the five levels of logging in Python?

In Python, the built-in logging module can be used to log events. Log messages can have 5 levels - DEBUG, INGO, WARNING, ERROR and CRITICAL. They can also include traceback information for exceptions. Logs can be especially useful in case of errors to help identify their cause.

What is the highest logging level in Python?

Python Logging Levels There are six log levels in Python; each level is associated with an integer that indicates the log severity: NOTSET=0, DEBUG=10, INFO=20, WARN=30, ERROR=40, and CRITICAL=50. All the levels are rather straightforward (DEBUG < INFO < WARN ) except NOTSET, whose particularity will be addressed next.

What is the default log level in Python?

The default level is WARNING , which means that only events of this level and above will be tracked, unless the logging package is configured to do otherwise. Events that are tracked can be handled in different ways. The simplest way of handling tracked events is to print them to the console.


1 Answers

I just ran into this issue and had trouble filling in the "holes" left in the above example. Here's a more complete, working version that I used. Hopefully this helps someone:

# Custom formatter class MyFormatter(logging.Formatter):      err_fmt  = "ERROR: %(msg)s"     dbg_fmt  = "DBG: %(module)s: %(lineno)d: %(msg)s"     info_fmt = "%(msg)s"       def __init__(self, fmt="%(levelno)s: %(msg)s"):         logging.Formatter.__init__(self, fmt)       def format(self, record):          # Save the original format configured by the user         # when the logger formatter was instantiated         format_orig = self._fmt          # Replace the original format with one customized by logging level         if record.levelno == logging.DEBUG:             self._fmt = MyFormatter.dbg_fmt          elif record.levelno == logging.INFO:             self._fmt = MyFormatter.info_fmt          elif record.levelno == logging.ERROR:             self._fmt = MyFormatter.err_fmt          # Call the original formatter class to do the grunt work         result = logging.Formatter.format(self, record)          # Restore the original format configured by the user         self._fmt = format_orig          return result 

Edit:

Compliments of Halloleo, here's an example of how to use the above in your script:

fmt = MyFormatter() hdlr = logging.StreamHandler(sys.stdout)  hdlr.setFormatter(fmt) logging.root.addHandler(hdlr) logging.root.setLevel(DEBUG) 

Edit 2:

Python3 logging has changed a bit. See here for a Python3 approach.

like image 174
JS. Avatar answered Oct 02 '22 19:10

JS.