Guía completa del módulo logging en Python: niveles, uso básico y mejores prácticas

1. ¿Qué es el módulo logging de Python?

El módulo logging de Python es una herramienta estándar para registrar el estado de ejecución del programa y la información de errores, utilizada tanto en depuración como en la monitorización en producción. A diferencia de la instrucción print, el módulo logging ofrece más funcionalidades, permitiendo controlar de forma precisa los niveles de los registros, el destino de salida y el formato. Gracias a esto, los desarrolladores pueden identificar de manera eficiente anomalías y el estado del programa.

Tipos de niveles de log y sus usos

  • DEBUG: Información detallada para depuración. Se usa principalmente en la etapa de desarrollo.
  • INFO: Información general de ejecución. Útil para confirmar que todo funciona correctamente.
  • WARNING: Problemas leves o advertencias. No afectan la ejecución inmediata, pero señalan posibles riesgos.
  • ERROR: Mensajes de error cuando ciertas funciones no se ejecutan correctamente. Indican problemas que afectan la ejecución del programa.
  • CRITICAL: Errores graves. Señalan fallos críticos que impiden continuar la ejecución del sistema.

Al usar correctamente cada nivel de log, se mejora la calidad de la información obtenida y se facilita una depuración y monitorización más eficiente.

2. Uso básico de logging

Veamos cómo generar registros utilizando el módulo logging.

import logging

# Configuración del nivel de log y el formato
logging.basicConfig(level=logging.DEBUG, format='%(asctime)s - %(levelname)s - %(message)s')

# Salida de log en cada nivel
logging.debug('Información de depuración: detalles para diagnóstico')
logging.info('Mensaje informativo: confirmación de operación correcta')
logging.warning('Mensaje de advertencia: situación que requiere atención')
logging.error('Mensaje de error: se produjo un problema')
logging.critical('Mensaje crítico: el sistema se detuvo')

Con logging.basicConfig() se define el destino de salida de los registros (por defecto la salida estándar), el nivel de log y el formato. En el ejemplo, al usar level=logging.DEBUG, se muestran todos los registros de nivel DEBUG o superior.

3. Personalización del destino y formato de salida

También es posible modificar el destino de los registros y personalizar el formato. Por ejemplo, para guardar los logs en un archivo se utiliza FileHandler.

Salida en archivo y formato

import logging

# Configuración del manejador de archivo
file_handler = logging.FileHandler('app.log')
formatter = logging.Formatter('%(asctime)s - %(name)s - %(levelname)s - %(message)s')
file_handler.setFormatter(formatter)

# Configuración del logger
logger = logging.getLogger()
logger.setLevel(logging.DEBUG)
logger.addHandler(file_handler)

# Salida de log
logger.debug('Información de depuración en archivo')
logger.info('Mensaje informativo en archivo')

En este código, FileHandler redirige los registros al archivo app.log. Con Formatter se define el formato en el que se escribirán los mensajes de log.

4. Rotación de archivos de log

En sistemas en producción, es importante evitar que los archivos de log crezcan demasiado. Para esto se utiliza RotatingFileHandler, que controla el tamaño y número de archivos.

Ejemplo de uso de RotatingFileHandler

import logging
from logging.handlers import RotatingFileHandler

# Configuración del manejador con rotación
handler = RotatingFileHandler('app.log', maxBytes=5000, backupCount=3)
formatter = logging.Formatter('%(asctime)s - %(levelname)s - %(message)s')
handler.setFormatter(formatter)

# Configuración del logger
logger = logging.getLogger()
logger.setLevel(logging.DEBUG)
logger.addHandler(handler)

# Salida de log
for i in range(100):
    logger.debug(f'Prueba de rotación {i}')

En este caso, maxBytes establece el tamaño máximo del archivo en 5000 bytes y backupCount define el número de copias de respaldo (3). Cuando el archivo excede el tamaño definido, se crea un nuevo archivo y los anteriores se renombran como copias.

年収訴求

5. Salida de log en archivos según nivel

Separar los registros por nivel en diferentes archivos mejora la legibilidad y facilita el análisis. Para esto se utilizan filtros personalizados junto con múltiples FileHandler.

Ejemplo de salida por nivel

import logging

class ErrorFilter(logging.Filter):
    def filter(self, record):
        return record.levelno == logging.ERROR

# Logs de nivel ERROR en archivo separado
error_handler = logging.FileHandler('error.log')
error_handler.setLevel(logging.ERROR)
error_handler.addFilter(ErrorFilter())
error_handler.setFormatter(formatter)

# Configuración del logger
logger.addHandler(error_handler)

# Salida de log
logger.error('Este log de ERROR se guarda en error.log')

En este ejemplo, la clase ErrorFilter filtra solo los registros de nivel ERROR, que se guardan en error.log. Así, los errores quedan en un archivo independiente.

6. Buenas prácticas y precauciones

Para aprovechar al máximo los logs, considera las siguientes prácticas recomendadas:

Uso adecuado de niveles de log

  • Durante el desarrollo utiliza DEBUG para registrar detalles, y en producción cambia a INFO o WARNING para registrar solo lo importante.
  • Un exceso de registros puede afectar el rendimiento, así que registra solo lo necesario.

Seguridad y privacidad en los logs

  • No registres información personal o confidencial. Si es necesario, aplica técnicas de anonimización o enmascaramiento.
  • Asegura que los archivos de log tengan permisos adecuados para evitar accesos no autorizados.

7. Conclusión

El módulo logging es una herramienta esencial para registrar y supervisar la ejecución de programas en Python. Configurar adecuadamente niveles, destinos, formatos y rotación de archivos permite identificar problemas rápidamente y mejorar la estabilidad del sistema. Aplica las buenas prácticas y gestiona tus logs de manera correcta para optimizar tus desarrollos.

侍エンジニア塾