2010-02-15 13 views
95

J'utilise le module python logging et je veux désactiver la consignation de la console pendant un certain temps mais cela ne fonctionne pas.Comment désactiver et réactiver la consignation de la console en Python?


    #!/usr/bin/python 
    import logging 

    logger = logging.getLogger() # this gets the root logger 
    # ... here I add my own handlers 
    #logger.removeHandler(sys.stdout) 
    #logger.removeHandler(sys.stderr) 

    print logging.handlers 
    # this will print [<logging.StreamHandler instance at ...>] 
    # but I may have other handlers there that I want to keep 

    logger.debug("bla bla") 

Le code ci-dessus affiche le « bla bla » sur stdout et je ne sais pas comment puis-je désactiver en toute sécurité le gestionnaire de la console. Comment puis-je être sûr de retirer temporairement le streamhandler de la console et pas un autre?

Répondre

140

J'ai trouvé une solution pour cela:

logger = logging.getLogger('my-logger') 
logger.propagate = False 
# now if you use logger it will not log to console. 

Cela permettra d'éviter l'exploitation forestière d'être envoyé à l'enregistreur supérieur qui comprend l'enregistrement de la console.

+0

Cela fonctionne pour Python 3.5. Je vous remercie! –

+1

Je ne pense pas que ce soit une bonne solution. Ne pas propager à des enregistreurs plus élevés pourrait avoir d'autres conséquences indésirables. – lfk

+1

Si vous souhaitez filtrer uniquement le message en dessous d'un certain niveau de journal (par exemple, tous les messages 'INFO'), vous pouvez changer la deuxième ligne à quelque chose comme' logger.setLevel (logging.WARNING) ' –

2

Je ne connais pas très bien le module de journalisation, mais je l'utilise de la manière dont je souhaite généralement désactiver uniquement les messages de débogage (ou d'information). Vous pouvez utiliser Handler.setLevel() pour définir le niveau de journalisation sur CRITIQUE ou supérieur.

En outre, vous pouvez remplacer sys.stderr et sys.stdout par un fichier ouvert pour l'écriture. Voir http://docs.python.org/library/sys.html#sys.stdout. Mais je ne le recommanderais pas.

+0

Cela pourrait fonctionner si logger.handlers contenait quelque chose, est actuellement '[]'. – sorin

8

Pas besoin de détourner stdout. Voici une meilleure façon de le faire:

import logging 
class MyLogHandler(logging.Handler): 
    def emit(self, record): 
     pass 

logging.getLogger().addHandler(MyLogHandler()) 

Une façon encore plus simple est:

logging.getLogger().setLevel(100) 
+1

En Python 2.7+, il est disponible en tant que [NullHandler()] (https://docs.python.org/2/library/logging.handlers.html # nullhandler) – Pierre

52

Vous pouvez utiliser:

logging.basicConfig(level=your_level) 

your_level est l'un de ceux:

 'debug': logging.DEBUG, 
     'info': logging.INFO, 
     'warning': logging.WARNING, 
     'error': logging.ERROR, 
     'critical': logging.CRITICAL 

Donc, si vous définissez your_level à logging.CRITICAL, vous obtiendrez uniquement les messages critiques que:

logging.critical('This is a critical error message') 

Réglage your_level à logging.DEBUG montrera tous les niveaux de l'exploitation forestière.

Pour plus de détails, s'il vous plaît jeter un oeil à logging examples.

De la même manière de changer de niveau pour chaque gestionnaire utiliser Handler.setLevel() fonction.

import logging 
import logging.handlers 

LOG_FILENAME = '/tmp/logging_rotatingfile_example.out' 

# Set up a specific logger with our desired output level 
my_logger = logging.getLogger('MyLogger') 
my_logger.setLevel(logging.DEBUG) 

# Add the log message handler to the logger 
handler = logging.handlers.RotatingFileHandler(
      LOG_FILENAME, maxBytes=20, backupCount=5) 

handler.setLevel(logging.CRITICAL) 

my_logger.addHandler(handler) 
+1

Il s'agit généralement d'informations utiles, mais la question a été posée de savoir comment désactiver la consignation de la console, et non comment ajouter un gestionnaire supplémentaire. Si vous deviez examiner my_logger.handlers avec le code ci-dessus appliqué à l'exemple original, vous verriez deux gestionnaires - votre nouveau gestionnaire de fichiers et le gestionnaire de flux d'origine. – Joe

59

J'utilise:

logger = logging.getLogger() 
logger.disabled = True 
... whatever you want ... 
logger.disabled = False 
+2

cela fonctionne aussi' la journalisation 'niveau du module pour désactiver la journalisation * entièrement *, par exemple:' import logging; logging.disable (logging.CRITICAL); ': https://docs.python.org/2/library/logging.html#logging.disable – lsh

35

(longue question mort, mais pour les chercheurs futurs)

Plus près de code/intention de l'affiche originale, cela fonctionne pour moi sous python 2.6

#!/usr/bin/python 
import logging 

logger = logging.getLogger() # this gets the root logger 

lhStdout = logger.handlers[0] # stdout is the only handler initially 

# ... here I add my own handlers 
f = open("/tmp/debug","w")   # example handler 
lh = logging.StreamHandler(f) 
logger.addHandler(lh) 

logger.removeHandler(lhStdout) 

logger.debug("bla bla") 

Gotcha je devais travailler était d'enlever le gestionnaire stdout après l'ajout d'un nouveau; le code de l'enregistreur semble rajouter automatiquement la sortie standard si aucun gestionnaire n'est présent.

+2

D'accord. C'est la bonne réponse. – obsoleter

25

Il y a quelques très bonnes réponses ici, mais apparemment le plus simple n'est pas trop pris en compte (seulement de l'infinito).

root_logger = logging.getLogger() 
root_logger.disabled = True 

Ceci désactive l'enregistreur racine, et donc tous les autres enregistreurs. Je n'ai pas vraiment testé mais ça devrait être aussi le plus rapide.

À partir du code d'enregistrement en python 2.7 Je vois ce

def handle(self, record): 
    """ 
    Call the handlers for the specified record. 

    This method is used for unpickled records received from a socket, as 
    well as those created locally. Logger-level filtering is applied. 
    """ 
    if (not self.disabled) and self.filter(record): 
     self.callHandlers(record) 

Ce qui signifie que quand il est désactivé aucun gestionnaire est appelé, et il devrait être plus efficace que le filtrage à une valeur très élevée ou la fixation d'un no- gestionnaire d'opérations par exemple.

+0

Obtenir l'enregistreur de racine a résolu mon problème. Merci – cgl

+1

Ceci est la meilleure réponse à la question. – user1823280

+1

Sauf si je fais quelque chose de mal, cela ne désactive que l'enregistreur de racine et pas créé comme 'log = logging.getLogger (__ name __)' – starfry

28

Contexte gestionnaire

import logging 
class DisableLogger(): 
    def __enter__(self): 
     logging.disable(logging.CRITICAL) 
    def __exit__(self, a, b, c): 
     logging.disable(logging.NOTSET) 

Exemple d'utilisation:

with DisableLogger(): 
    do_something() 
+0

J'aime vraiment cet idiome, mais je préférerais pouvoir désactiver un espace de noms particulier. Par exemple, je veux juste que l'enregistreur de racine soit temporairement désactivé. Bien que l'utilisation de cette expression, nous devrions être en mesure d'ajouter/supprimer temporairement les gestionnaires et les tels. – Chris

2

Vous pouvez également:

handlers = app.logger.handlers 
# detach console handler 
app.logger.handlers = [] 
# attach 
app.logger.handlers = handlers 
6

Pour l'enregistrement désactiver complètement:

logging.disable(sys.maxint) 

Pour activer la journalisation:

logging.disable(logging.NOTSET) 

Autres réponses fournir contournements de travail qui ne résolvent pas complètement le problème, comme

logging.getLogger().disabled = True 

et, pour certains n supérieur 50,

logging.disable(n) 

Le problème avec la première solution est qu'elle ne fonctionne que pour l'enregistreur racine. D'autres enregistreurs créés en utilisant, disons, logging.getLogger(__name__) ne sont pas désactivés par cette méthode.

La deuxième solution affecte tous les journaux. Mais elle limite la production à des niveaux supérieurs qui données, donc on pourrait la remplacer en se connectant à un niveau supérieur à 50.

qui peut être évité par

logging.disable(sys.maxint) 

qui, autant que je peux dire (après avoir examiné le source) est le seul moyen de désactiver complètement la journalisation.