Reputation: 5187
I am trying to put logging in python python project. For that, I have written a method called get_logger
in my common.py that returns the logger.
import logging
def get_logger(name='app'):
log_config = config.LOG_CONFIG
logging.config.dictConfig(log_config)
logger = logging.getLogger(name)
return logger
Note that the log configurations are put in config.LOG_CONFIG
LOG_CONFIG = {
'version': 1,
'disable_existing_loggers': False, # this fixes the problem
'formatters': {
'standard': {
'format': '%(asctime)s [%(levelname)8s] %(name)s: %(message)s'
},
# more formatters
},
'handlers': {
'file': {
'filename': '%s/%s' % (_cwd, '../logs/app/logging.log'),
'formatter': 'standard',
'when': 'midnight',
'class': 'logging.handlers.TimedRotatingFileHandler'
},
},
'loggers': {
# Works for
# 1. application logs (flask) and
# 2. all other logs where below logger name is passed to getLogger
'app': {
'handlers': ['file'],
'level': 'DEBUG',
'propagate': True
},
# For all the remaining logs
# Important: Don't include for production??
'': {
'handlers': ['file'],
'level': 'INFO',
'propagate': True
}
}
}
I have two modules
a class from sf_apis.py extends a class from base.py. I have called get_logger in base.py.
base.py
from common import get_logger
log = get_logger()
class Base:
// .. some code ..
Then just called getLogger
from logging
to get that logger in sf_apis.py
sf_apis.py
import logging
log = logging.getLogger('app')
class SfBulk(Base):
// .. some code ..
But when my another module called sync_data.py
that runs by calling some methods from sf_apis.py
, I see duplicate log statements in my log
2015-11-04 13:05:58,605 [ INFO] app: close_the_job :: job id = 75090000003sf4YAAQ
2015-11-04 13:05:58,605 [ INFO] app: close_the_job :: job id = 75090000003sf4YAAQ
I read it here that
The logging module already implements a singleton pattern
so I didn't go and create a singleton Logger class (There are many examples on internet)
What did I miss? Please help.
Upvotes: 2
Views: 1203
Reputation: 761
Python loggers have hierarchical structure. You've created two: 'app'
and ''
. By convention, hierarchy is defined as dot-separated path to the module. In a particular case, empty string logger becomes a parent for all other first-level loggers. Specifically, ''
is parent of 'app'
.
Now you set propagate = True
for 'app'
logger. It means that a message sent to this logger would be also propagated to its parent, i.e. ''
. That's how you have duplicated messages.
You can either set propagate = False
to 'app'
logger or set another file handler for ''
logger such that the messages would be still duplicated, but in different files.
Upvotes: 2