Как отключить и повторно включить консольный вход в Python?
Я использую в 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 logger.handlers
# this will print [<logging.StreamHandler instance at ...>]
# but I may have other handlers there that I want to keep
logger.debug("bla bla")
приведенный выше код выводит bla bla
на stdout и я не знаю, как я могу спокойно отключить обработчик консоли. Как я могу быть уверен, что временно удаляю консольный StreamHandler, а не другой?
11 ответов:
Я нашел решение для этого:
logger = logging.getLogger('my-logger') logger.propagate = False # now if you use logger it will not log to console.
это предотвратит отправку журнала в верхний регистратор, который включает ведение журнала консоли.
Я использую:
logger = logging.getLogger() logger.disabled = True ... whatever you want ... logger.disabled = False
вы можете использовать:
logging.basicConfig(level=your_level)
здесь your_level одна из них:
'debug': logging.DEBUG, 'info': logging.INFO, 'warning': logging.WARNING, 'error': logging.ERROR, 'critical': logging.CRITICAL
Итак, если вы установите your_level до ведение журнала.Критический, вы получите только критические сообщения, отправленные:
logging.critical('This is a critical error message')
задание your_level до ведение журнала.Отладка показать все уровни ведения журнала.
для более подробной информации, пожалуйста, взгляните на примеры ведения журнала.
в таким же образом, чтобы изменить уровень для каждого обработчика использовать обработчик.setLevel()
(давно мертв вопрос, но для будущих искателей)
ближе к исходному коду/намерению плаката, это работает для меня под 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 я должен был работать, чтобы удалить обработчик stdout после добавление нового; код регистратора появляется автоматически повторно добавить устройство stdout, если никаких обработчиков нет.
контекст менеджер
import logging class DisableLogger(): def __enter__(self): logging.disable(logging.CRITICAL) def __exit__(self, a, b, c): logging.disable(logging.NOTSET)
пример использования:
with DisableLogger(): do_something()
здесь есть несколько действительно хороших ответов, но, по-видимому, самый простой не слишком учитывается (только от infinito).
root_logger = logging.getLogger() root_logger.disabled = True
это отключает корневой регистратор, и, таким образом, все другие регистраторы. Я не проверял, но он должен быть самым быстрым.
из кода регистрации в python 2.7 я вижу это
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)
это означает, что когда он отключен, никакой обработчик не вызывается, и он должен быть более эффективным, что фильтрация очень например, высокое значение или установка обработчика no-op.
полностью отключить ведение журнала:
logging.disable(sys.maxint)
чтобы включить ведение журнала:
logging.disable(logging.NOTSET)
другие ответы обеспечивают обходные пути, которые не полностью решают проблему, такие как
logging.getLogger().disabled = True
и, для некоторых
n
больше 50,logging.disable(n)
проблема с первым решением является то, что он работает только для корневого регистратора. Другие регистраторы, созданные с помощью, скажем,
logging.getLogger(__name__)
не инвалид метод.второе решение влияет на все журналы. Но он ограничивает выход до уровней выше заданного, поэтому его можно переопределить, зарегистрировав уровень выше 50.
это можно предотвратить с помощью
logging.disable(sys.maxint)
который, насколько я могу судить (после просмотра источник) - это единственный способ полностью отключить ведение журнала.
нет необходимости отвлекать stdout. Вот лучший способ сделать это:
import logging class MyLogHandler(logging.Handler): def emit(self, record): pass logging.getLogger().addHandler(MyLogHandler())
еще более простой способ-это:
logging.getLogger().setLevel(100)
Я не очень хорошо знаю модуль ведения журнала, но я использую его так, как обычно хочу отключить только отладочные (или информационные) сообщения. Вы можете использовать
Handler.setLevel()
для установки критического или более высокого уровня ведения журнала.кроме того, вы можете заменить sys.stderr и sys.stdout с помощью файла, открытого для записи. См.http://docs.python.org/library/sys.html#sys.stdout. но я бы не рекомендовал этого делать.
вы можете также:
handlers = app.logger.handlers # detach console handler app.logger.handlers = [] # attach app.logger.handlers = handlers
import logging log_file = 'test.log' info_format = '%(asctime)s - %(levelname)s - %(message)s' logging.config.dictConfig({ 'version': 1, 'disable_existing_loggers': False, 'formatters': { 'info_format': { 'format': info_format }, }, 'handlers': { 'console': { 'level': 'INFO', 'class': 'logging.StreamHandler', 'formatter': 'info_format' }, 'info_log_file': { 'class': 'logging.handlers.RotatingFileHandler', 'level': 'INFO', 'filename': log_file, 'formatter': 'info_format' } }, 'loggers': { '': { 'handlers': [ 'console', 'info_log_file' ], 'level': 'INFO' } } }) class A: def __init__(self): logging.info('object created of class A') self.logger = logging.getLogger() self.console_handler = None def say(self, word): logging.info('A object says: {}'.format(word)) def disable_console_log(self): if self.console_handler is not None: # Console log has already been disabled return for handler in self.logger.handlers: if type(handler) is logging.StreamHandler: self.console_handler = handler self.logger.removeHandler(handler) def enable_console_log(self): if self.console_handler is None: # Console log has already been enabled return self.logger.addHandler(self.console_handler) self.console_handler = None if __name__ == '__main__': a = A() a.say('111') a.disable_console_log() a.say('222') a.enable_console_log() a.say('333')
консоль вывода:
2018-09-15 15:22:23,354 - INFO - object created of class A 2018-09-15 15:22:23,356 - INFO - A object says: 111 2018-09-15 15:22:23,358 - INFO - A object says: 333