我想为每个测试用例设置一个新的日志文件。如下所示:
import unittest
import logging
log = logging.getLogger()
class TestExample(unittest.TestCase):
def setUp(self):
next_testcase = ???
self.hdl = logging.FileHandler(
'testcase_%s.log' % next_testcase, mode='w')
log.addHandler(self.hdl)
def tearDown(self):
log.removeHandler(self.hdl)
如何找到名称测试用例?
或者您将如何实现上述内容?
答案 0 :(得分:2)
棘手! : - )
这里的问题是你无法知道下一个要调用哪个函数 - 不是 不直接干扰unittest代码。
但是,如果可以将每个测试用例更改为另一种方法, 这将调用为该测试用例制作的“设置”自定义,然后执行原始 测试用例,它将被解决。
换句话说:需要在声明的类中自动更改每个测试用例 进入另一个功能:执行个性化设置,然后执行 原始测试。这应该在课堂创建时完成。
这可能看起来很复杂,但它更适合“元类” - 因为我们正在做他们的意图:定制类创建。
因此,通过将TestCase的元类更改为检查类中每个项目的元类 - 如果是测试(即,如果其名称以“test”开头),则创建一个新的包装函数 如果能够实现上述功能,您就可以实现这一目标。
(还需要一个步骤:因为方法名称和原始测试方法的(对象)必须保持一致,所以必须创建一个中间函数来保留每个测试用例的闭包。 ,下面的代码中的变量method_name
和original_method
都将为for
循环结束时类中最后一个函数的名称和内容设置
你去了:
# -*- coding: utf-8 -*-
import unittest
import logging
#template method:
def log_setup(self, name):
#self.hdl = logging.FileHandler('testcase_%s.log' % name, mode='w')
#log.addHandler(self.hdl)
self.name = name
class MetaTestCase(type):
def __new__(cls, cls_name, bases, dict):
for name, item in dict.items():
if name.startswith("test"):
def scope_freezer(method_name, original_method):
def wrapper(self, *args, **kw):
log_setup(self, method_name)
return original_method(self, *args, **kw)
return wrapper
dict[name] = scope_freezer(name, item)
return type.__new__(cls, cls_name, bases, dict)
class TestExample(unittest.TestCase):
__metaclass__ = MetaTestCase
def test_a(self):
print self.name
def test_b(self):
print self.name
def tearDown(self):
pass
#log.removeHandler(self.hdl)
unittest.main()
(为了简化我的测试,我注释掉了实际的日志记录行 - “打印”工作正常 - log_setup函数中的任何代码都将与self
和name
正确运行集。)
当然,您可以在另一个模块中分解这个元类,然后将其导入以用于测试。
答案 1 :(得分:1)
import unittest
import logging
def log_setup(self, name):
print name
class TestExample(unittest.TestCase):
def test_method_name(self):
print self.method_name
def __getattribute__(self, name):
safe_getattr = super(TestExample, self).__getattribute__
if name.startswith("test_"):
self.method_name = name
log_setup(self, name)
return safe_getattr(name)
if __name__ == "__main__":
unittest.main()