Add captured log lines to test case details.
Change-Id: I9615842c9b36dab11aed6561a76cf721c03a6a62
This commit is contained in:
parent
2a064e9bdf
commit
335e90d873
@ -16,6 +16,7 @@ from __future__ import absolute_import
|
|||||||
from tobiko.common import _asserts
|
from tobiko.common import _asserts
|
||||||
from tobiko.common import _exception
|
from tobiko.common import _exception
|
||||||
from tobiko.common import _fixture
|
from tobiko.common import _fixture
|
||||||
|
from tobiko.common import _logging
|
||||||
from tobiko.common.managers import testcase as testcase_manager
|
from tobiko.common.managers import testcase as testcase_manager
|
||||||
from tobiko.common.managers import loader as loader_manager
|
from tobiko.common.managers import loader as loader_manager
|
||||||
from tobiko.common import _select
|
from tobiko.common import _select
|
||||||
@ -45,6 +46,9 @@ list_required_fixtures = _fixture.list_required_fixtures
|
|||||||
SharedFixture = _fixture.SharedFixture
|
SharedFixture = _fixture.SharedFixture
|
||||||
FixtureManager = _fixture.FixtureManager
|
FixtureManager = _fixture.FixtureManager
|
||||||
|
|
||||||
|
CaptureLogTest = _logging.CaptureLogTest
|
||||||
|
CaptureLogFixture = _logging.CaptureLogFixture
|
||||||
|
|
||||||
load_object = loader_manager.load_object
|
load_object = loader_manager.load_object
|
||||||
load_module = loader_manager.load_module
|
load_module = loader_manager.load_module
|
||||||
|
|
||||||
|
87
tobiko/common/_logging.py
Normal file
87
tobiko/common/_logging.py
Normal file
@ -0,0 +1,87 @@
|
|||||||
|
# Copyright 2019 Red Hat
|
||||||
|
#
|
||||||
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||||
|
# not use this file except in compliance with the License. You may obtain
|
||||||
|
# a copy of the License at
|
||||||
|
#
|
||||||
|
# http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
#
|
||||||
|
# Unless required by applicable law or agreed to in writing, software
|
||||||
|
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||||
|
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||||
|
# License for the specific language governing permissions and limitations
|
||||||
|
# under the License.
|
||||||
|
from __future__ import absolute_import
|
||||||
|
|
||||||
|
import logging
|
||||||
|
|
||||||
|
from oslo_log import log
|
||||||
|
|
||||||
|
import testtools
|
||||||
|
from testtools import content
|
||||||
|
|
||||||
|
from tobiko.common import _fixture
|
||||||
|
|
||||||
|
|
||||||
|
LOG = log.getLogger(__name__)
|
||||||
|
|
||||||
|
|
||||||
|
class CaptureLogFixture(_fixture.SharedFixture):
|
||||||
|
|
||||||
|
level = None
|
||||||
|
logger = logging.root
|
||||||
|
handler = None
|
||||||
|
|
||||||
|
def __init__(self, logger=None, level=None):
|
||||||
|
super(CaptureLogFixture, self).__init__()
|
||||||
|
if logger:
|
||||||
|
self.logger = logger
|
||||||
|
if level:
|
||||||
|
self.level = level
|
||||||
|
|
||||||
|
def setup_fixture(self):
|
||||||
|
self.handler = handler = CaptureLogHandler(level=self.level)
|
||||||
|
self.logger.addHandler(handler)
|
||||||
|
self.addCleanup(self.logger.removeHandler, handler)
|
||||||
|
|
||||||
|
def getDetails(self):
|
||||||
|
if self.handler:
|
||||||
|
return {'log': self.handler.content}
|
||||||
|
else:
|
||||||
|
return {}
|
||||||
|
|
||||||
|
|
||||||
|
class CaptureLogHandler(logging.Handler):
|
||||||
|
|
||||||
|
def __init__(self, level=None):
|
||||||
|
if level is None:
|
||||||
|
from tobiko import config
|
||||||
|
CONF = config.CONF
|
||||||
|
if CONF.tobiko.debug:
|
||||||
|
level = logging.DEBUG
|
||||||
|
else:
|
||||||
|
level = logging.INFO
|
||||||
|
super(CaptureLogHandler, self).__init__(level)
|
||||||
|
self.records = []
|
||||||
|
|
||||||
|
def emit(self, record):
|
||||||
|
self.records.append(record)
|
||||||
|
|
||||||
|
@property
|
||||||
|
def content(self):
|
||||||
|
return content.Content(content.UTF8_TEXT, self.format_all)
|
||||||
|
|
||||||
|
def format_all(self):
|
||||||
|
for record in self.records:
|
||||||
|
yield (self.format(record) + '\n').encode()
|
||||||
|
|
||||||
|
|
||||||
|
class CaptureLogTest(testtools.TestCase):
|
||||||
|
|
||||||
|
capture_log_level = logging.DEBUG
|
||||||
|
capture_log_logger = logging.root
|
||||||
|
|
||||||
|
def setUp(self):
|
||||||
|
self.useFixture(CaptureLogFixture(level=self.capture_log_level,
|
||||||
|
logger=self.capture_log_logger))
|
||||||
|
super(CaptureLogTest, self).setUp()
|
@ -20,9 +20,12 @@ import os
|
|||||||
|
|
||||||
from oslo_config import cfg
|
from oslo_config import cfg
|
||||||
from oslo_log import log
|
from oslo_log import log
|
||||||
|
import testtools
|
||||||
|
from testtools import monkey
|
||||||
|
|
||||||
import tobiko
|
import tobiko
|
||||||
|
|
||||||
|
|
||||||
LOG = log.getLogger(__name__)
|
LOG = log.getLogger(__name__)
|
||||||
|
|
||||||
CONFIG_MODULES = ['tobiko.openstack.glance.config',
|
CONFIG_MODULES = ['tobiko.openstack.glance.config',
|
||||||
@ -47,6 +50,14 @@ def _iter_config_dirs():
|
|||||||
|
|
||||||
CONFIG_DIRS = list(_iter_config_dirs())
|
CONFIG_DIRS = list(_iter_config_dirs())
|
||||||
|
|
||||||
|
LOGGING_CONF_GROUP_NAME = "logging"
|
||||||
|
|
||||||
|
LOGGING_OPTIONS = [
|
||||||
|
cfg.BoolOpt('capture_log',
|
||||||
|
default=True,
|
||||||
|
help="Whenever to capture LOG during test case excecution"),
|
||||||
|
]
|
||||||
|
|
||||||
HTTP_CONF_GROUP_NAME = "http"
|
HTTP_CONF_GROUP_NAME = "http"
|
||||||
|
|
||||||
HTTP_OPTIONS = [
|
HTTP_OPTIONS = [
|
||||||
@ -88,11 +99,17 @@ class GlobalConfig(object):
|
|||||||
CONF = GlobalConfig()
|
CONF = GlobalConfig()
|
||||||
|
|
||||||
|
|
||||||
def init_config():
|
class InitConfigFixture(tobiko.SharedFixture):
|
||||||
|
|
||||||
|
def setup_fixture(self):
|
||||||
init_tobiko_config()
|
init_tobiko_config()
|
||||||
init_environ_config()
|
init_environ_config()
|
||||||
|
|
||||||
|
|
||||||
|
def init_config():
|
||||||
|
tobiko.setup_fixture(InitConfigFixture)
|
||||||
|
|
||||||
|
|
||||||
def init_tobiko_config(default_config_dirs=None, product_name='tobiko',
|
def init_tobiko_config(default_config_dirs=None, product_name='tobiko',
|
||||||
version='unknown'):
|
version='unknown'):
|
||||||
default_config_dirs = default_config_dirs or CONFIG_DIRS
|
default_config_dirs = default_config_dirs or CONFIG_DIRS
|
||||||
@ -113,6 +130,9 @@ def init_tobiko_config(default_config_dirs=None, product_name='tobiko',
|
|||||||
|
|
||||||
def register_tobiko_options(conf):
|
def register_tobiko_options(conf):
|
||||||
|
|
||||||
|
conf.register_opts(
|
||||||
|
group=cfg.OptGroup(LOGGING_CONF_GROUP_NAME), opts=LOGGING_OPTIONS)
|
||||||
|
|
||||||
conf.register_opts(
|
conf.register_opts(
|
||||||
group=cfg.OptGroup(HTTP_CONF_GROUP_NAME), opts=HTTP_OPTIONS)
|
group=cfg.OptGroup(HTTP_CONF_GROUP_NAME), opts=HTTP_OPTIONS)
|
||||||
|
|
||||||
@ -151,6 +171,8 @@ def setup_tobiko_config(conf):
|
|||||||
warnings_logger.logger.setLevel(log.ERROR)
|
warnings_logger.logger.setLevel(log.ERROR)
|
||||||
|
|
||||||
tobiko.setup_fixture(HttpProxyFixture)
|
tobiko.setup_fixture(HttpProxyFixture)
|
||||||
|
if conf.logging.capture_log:
|
||||||
|
monkey.patch(testtools, 'TestCase', tobiko.CaptureLogTest)
|
||||||
|
|
||||||
for module_name in CONFIG_MODULES:
|
for module_name in CONFIG_MODULES:
|
||||||
module = importlib.import_module(module_name)
|
module = importlib.import_module(module_name)
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
# Copyright 2019 Red Hat
|
||||||
#
|
#
|
||||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||||
# not use this file except in compliance with the License. You may obtain
|
# not use this file except in compliance with the License. You may obtain
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
# Copyright 2019 Red Hat
|
||||||
#
|
#
|
||||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||||
# not use this file except in compliance with the License. You may obtain
|
# not use this file except in compliance with the License. You may obtain
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
# Copyright 2019 Red Hat
|
||||||
#
|
#
|
||||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||||
# not use this file except in compliance with the License. You may obtain
|
# not use this file except in compliance with the License. You may obtain
|
||||||
|
32
tobiko/tests/unit/test_logging.py
Normal file
32
tobiko/tests/unit/test_logging.py
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
# Copyright (c) 2019 Red Hat
|
||||||
|
# All Rights Reserved.
|
||||||
|
#
|
||||||
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||||
|
# not use this file except in compliance with the License. You may obtain
|
||||||
|
# a copy of the License at
|
||||||
|
#
|
||||||
|
# http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
#
|
||||||
|
# Unless required by applicable law or agreed to in writing, software
|
||||||
|
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||||
|
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||||
|
# License for the specific language governing permissions and limitations
|
||||||
|
# under the License.
|
||||||
|
from __future__ import absolute_import
|
||||||
|
|
||||||
|
from oslo_log import log
|
||||||
|
|
||||||
|
import tobiko
|
||||||
|
from tobiko.tests import unit
|
||||||
|
|
||||||
|
|
||||||
|
LOG = log.getLogger(__name__)
|
||||||
|
|
||||||
|
|
||||||
|
class CapureLogTest(unit.TobikoUnitTest):
|
||||||
|
|
||||||
|
def test_capture_log_content(self):
|
||||||
|
with tobiko.CaptureLogFixture() as capture:
|
||||||
|
LOG.warning('Some debug line')
|
||||||
|
content = capture.getDetails()['log']
|
||||||
|
self.assertEqual('Some debug line\n', content.as_text())
|
Loading…
Reference in New Issue
Block a user