Use fileConfig para configurar manejadores personalizados en Python

Estoy usando un archivo de configuración para configurar mi registrador en una aplicación de Python. Este es el archivo:

[loggers] keys=root [logger_root] level=INFO handlers=console [handlers] keys=console,file_rotating [handler_console] class=StreamHandler level=WARNING formatter=console args=(sys.stderr,) [handler_file_rotating] class=TimeRotatingFileHandler level=DEBUG formatter=file args=('../logs/twicker.log', 'd', 1, 5) [formatters] keys=console,file [formatter_console] format=%(levelname)s - %(message)s [formatter_file] format=%(asctime)s - %(levelname)s - %(module)s - %(message)s 

Mi problema es con TimeRotatingFileHandler. Cada vez que ejecuto la aplicación me sale el siguiente error:

ImportError: ningún módulo llamado ‘TimeRotatingFileHandler’

¿Qué estoy haciendo mal? También intenté cambiar la línea de class=handlers.TimeRotatingFileHandler a class=handlers.TimeRotatingFileHandler pero en ese caso me sale el siguiente error:

ImportError: Ningún módulo llamado ‘manejadores’

Me encontré con el mismo problema al usar dictConfig La solución para mí fue calificar completamente la ruta del módulo de esta manera:

 [handler_file_rotating] class=logging.handlers.TimeRotatingFileHandler level=DEBUG formatter=file args=('../logs/twicker.log', 'd', 1, 5) 

Es posible que desee intentarlo

La class= se evalúa en el espacio de nombres del módulo de logging y, de forma predeterminada, no tiene un enlace con los handlers . Para que pudieras hacer

 import logging, logging.handlers logging.handlers = logging.handlers 

antes de llamar a fileConfig() , y luego class=handlers.TimedRotatingHandler debería funcionar.

Para ampliar esto un poco, si decide hacer un controlador personalizado, todo lo que necesita hacer es definir ese controlador cerca de la parte superior de su código y luego definirlo como un objeto en logging.handlers.

Ejemplo:

 class MyCustomRotatingClass(logging.handlers.RotatingFileHandler): """custom handler that queues messages to be uploaded in batches to the portal in a background thread """ def __init__(self, basedir, mode='a', maxBytes=0, backupCount=0, encoding=None, delay=0): logging.handlers.RotatingFileHandler.__init__(self, 'TestSavvyExecute.log','a',250000,40,'utf-8',0) self.maxBytes = maxBytes def emit(self, record): try: if logging.handlers.RotatingFileHandler.shouldRollover(self, record): logging.handlers.RotatingFileHandler.doRollover(self) #ASCII characters use 1 byte each if len(record.msg) > self.maxBytes: oldMsg = record.msg record.msg = record.msg[0:self.maxBytes] logging.FileHandler.emit(self, record) record.msg = oldMsg[self.maxBytes + 1:] self.emit(record) else: logging.FileHandler.emit(self, record) except (KeyboardInterrupt, SystemExit): raise except: logging.handlers.RotatingFileHandler.handleError(self, record) logging.handlers.MyCustomRotatingClass = MyCustomRotatingClass logging.config.fileConfig('translator.log.config') 

Ahora puedes referenciarlo fácilmente en tu archivo de configuración.

 [handler_rollinglog] class=handlers.MyCustomRotatingClass