mirror of https://github.com/scrapy/scrapy.git
Stdout redirect in configure_logging
This commit is contained in:
parent
ffd97f2f1b
commit
6acb3848fb
|
|
@ -72,6 +72,9 @@ def configure_logging(settings=None):
|
|||
if settings:
|
||||
logging.root.setLevel(logging.NOTSET)
|
||||
|
||||
if settings.getbool('LOG_STDOUT'):
|
||||
sys.stdout = StreamLogger(logging.getLogger('stdout'))
|
||||
|
||||
# Set up the default log handler
|
||||
filename = settings.get('LOG_FILE')
|
||||
if filename:
|
||||
|
|
@ -102,6 +105,22 @@ def log_scrapy_info(settings):
|
|||
logger.info("Overridden settings: %(settings)r", {'settings': d})
|
||||
|
||||
|
||||
class StreamLogger(object):
|
||||
"""Fake file-like stream object that redirects writes to a logger instance
|
||||
|
||||
Taken from:
|
||||
http://www.electricmonk.nl/log/2011/08/14/redirect-stdout-and-stderr-to-a-logger-in-python/
|
||||
"""
|
||||
def __init__(self, logger, log_level=logging.INFO):
|
||||
self.logger = logger
|
||||
self.log_level = log_level
|
||||
self.linebuf = ''
|
||||
|
||||
def write(self, buf):
|
||||
for line in buf.rstrip().splitlines():
|
||||
self.logger.log(self.log_level, line.rstrip())
|
||||
|
||||
|
||||
class LogCounterHandler(logging.Handler):
|
||||
"""Record log levels count into a crawler stats"""
|
||||
|
||||
|
|
|
|||
|
|
@ -1,12 +1,14 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
from __future__ import print_function
|
||||
import os
|
||||
import sys
|
||||
import logging
|
||||
import unittest
|
||||
|
||||
from testfixtures import LogCapture
|
||||
from twisted.python.failure import Failure
|
||||
|
||||
from scrapy.utils.log import FailureFormatter, LogCounterHandler
|
||||
from scrapy.utils.log import FailureFormatter, LogCounterHandler, StreamLogger
|
||||
from scrapy.utils.test import get_crawler
|
||||
|
||||
|
||||
|
|
@ -75,3 +77,20 @@ class LogCounterHandlerTest(unittest.TestCase):
|
|||
def test_filtered_out_level(self):
|
||||
self.logger.debug('test log msg')
|
||||
self.assertIsNone(self.crawler.stats.get_value('log_count/INFO'))
|
||||
|
||||
|
||||
class StreamLoggerTest(unittest.TestCase):
|
||||
|
||||
def setUp(self):
|
||||
self.stdout = sys.stdout
|
||||
logger = logging.getLogger('test')
|
||||
logger.setLevel(logging.WARNING)
|
||||
sys.stdout = StreamLogger(logger, logging.ERROR)
|
||||
|
||||
def tearDown(self):
|
||||
sys.stdout = self.stdout
|
||||
|
||||
def test_redirect(self):
|
||||
with LogCapture() as l:
|
||||
print('test log msg')
|
||||
l.check(('test', 'ERROR', 'test log msg'))
|
||||
|
|
|
|||
Loading…
Reference in New Issue