Avoid check if logger exists

5.3k Views Asked by At

When using logging in python like this

import logging
logging.basicConfig(level=logging.INFO)
logger = None
if <some condition>:
   logger = logging.getLogger(__name__)
... some code ...
logger.debug('message')

is it possible to avoid calling logger.debug if it does not exist without if statement?

3

There are 3 best solutions below

0
On BEST ANSWER

You could construct a wrapper object and use that everywhere:

class LoggerWrapper(object):

    def __init__(self, logger):
        self.logger = logger

    def debug(self, *args, **kwargs):
        if self.logger is None:
            return
        self.logger.debug(*args, **kwargs)

my_wrapper = LoggerWrapper(logger)
my_wrapper.debug('message')

That being said, this is not specific to Python's logging module. Any variable var that can also be None will need to be checked before you call a method on it (var.method()).

It may be easier to always define a logger and to simply disable the logging through the logging configuration / settings. That keeps the code clean, all logger calls will succeed but the output won't go anywhere if that particular logger is disabled.

Lastly, you could opt to indeed use an if statement as it's not inherently that much more code:

if logger:
    logger.debug('message')
0
On

is it possible to avoid calling logger.debug if it does not exist without if statement?

Well, you could (ab)use an if expression, or an or expression, or various other things, but otherwise, not really.

You can, however, always write a wrapper function:

def logdebug(*args):
    if logger:
        logger.debug(*args)

logdebug('message')
logdebug('other message')

You can do other, similar tricks. For example, instead of having logger = None, you can create an object that has a debug method that does nothing:

class Dummy(object):
    def debug(self, *args): pass
logger = Dummy()

Or, even better, always create a logger and configure it with a null handler, or—simplest of all—just set its logging level higher than debug.


But note that none of these will completely replace the if statement. Consider, for example:

if logger:
    logger.debug(very_expensive_function())

logdebug(very_expensive_function())

The first one will only call very_expensive_function to create the log message if you actually need it; the second one will always call it and then just throw it away if you don't need it.

2
On

That's not how you use logging: it's missing the point entirely. The point is to always just log, and then (at the app level) configure handlers appropriately so that they either record the debug level or not. Your app-level configuration can even set the handler for loggers in each module. See the Python logging docs for more info.