大家看一段下面的代码,我们写的程序中有如下的一个 类 Widget, 代表了界面的一个控件,这是我们要测试的类:
class Widget:
def __init__(self,msg):
# print(msg)
self._size = 50,50
def size(self):
return self._size
def resize(self,w,h):
self._size = w, h
为了方便理解,这个类做的很简单,初始化方法里面定义了控件的大小是50像素宽,50像素高。记录在属性 _size 中size方法返回该控件的长和宽。resize改变控件的长和宽。
现在,我们使用unittest来测试它,测试代码如下所示:
import unittest
class Widget:
def __init__(self,msg):
# print(msg)
self._size = 50,50
def size(self):
return self._size
def resize(self,w,h):
self._size = w, h
class WidgetTestCase(unittest.TestCase):
def setUp(self):
print('in setUp')
self.widget = Widget('The widget')
def tearDown(self):
print('in tearDown')
def test_1(self):
print('in test_1')
self.assertEqual(self.widget.size(), (50,50),
'incorrect default size')
def test_2(self):
print('in test_2')
self.widget.resize(100,150)
self.assertEqual(self.widget.size(), (100,150),
'wrong size after resize')
现在来分析一下代码,我们导入unittest库:
import unittest
定义了一个继承自unittest.TestCase 的测试类WidgetTestCase:
class WidgetTestCase(unittest.TestCase)
注意,这个类名是可以随便起的,只要继承自WidgetTestCase即可。
里面有setup, teardown 两个方法,和两个测试方法test_1 , test_2。注意代表测试方法一定要以test开头,不然不会被认为是测试方法。
测试需要检查某个结果是否符合预期, 这个检查点 就是通过 TestCase方法的assert系列的函数实现的。
这里就是assertEqual, 判断前两个参数是否相等,如果相等测试通过,如果不相等,测试不通过。显示的错误信息就是第3个参数。
这些assert系列的函数哪里来的?对了,是父类WidgetTestCase里面的。
而 setup, teardown 这两个方法就是前面说过的 初始化环境和清除环境的方法,这 setup 方法会在该类的每个测试方法执行前先执行,这 teardown 方法会在该类的每个测试方法执行后执行。
注意是每个测试方法执行前后, 都会 执行一下 setup 和teardown。我们可以在终端里面执行该测试,执行命令如下:
python -m unittest test1.py
执行结果如下:
D:\ut>python -m unittest test1.py
in setUp
in test_1
in tearDown
.in setUp
in test_2
in tearDown
.
----------------------------------------------------------------------
Ran 2 tests in 0.000s
OK
结果是OK 表示全部通过,看看上面的输出,发现执行次序是:
· 先setup
· 执行测试方法
· 最后 teardown
如果想看到更详细一些的输出信息,我们可以加上参数 -v
python -m unittest test1.py -v
这样会显示当前正在执行的是哪个测试方法,和每个测试方法的执行结果
D:\ut>python -m unittest test1.py -v
test_1 (test1.WidgetTestCase) ... in setUp
in test_1
in tearDown
ok
test_2 (test1.WidgetTestCase) ... in setUp
in test_2
in tearDown
ok
----------------------------------------------------------------------
Ran 2 tests in 0.000s
OK
如果我们修改一下,故意让一个验证出错,比如:
def resize(self,w,h):
self._size = w, h+6
执行测试结果就会报错:
D:\gsync\workspace\sq\python\samples\ut>python -m unittest test1.py -v
test_1 (test1.WidgetTestCase) ... in setUp
in test_1
in tearDown
ok
test_2 (test1.WidgetTestCase) ... in setUp
in test_2
in tearDown
FAIL
======================================================================
FAIL: test_2 (test1.WidgetTestCase)
----------------------------------------------------------------------
Traceback (most recent call last):
File "D:\gsync\workspace\sq\python\samples\ut\test1.py", line 33, in test_2
'wrong size after resize')
AssertionError: Tuples differ: (100, 156) != (100, 150)
First differing element 1:
156
150
- (100, 156)
? ^
+ (100, 150)
? ^
: wrong size after resize
----------------------------------------------------------------------
Ran 2 tests in 0.000s
FAILED (failures=1)
注意:只有setup成功,才会执行测试,如果setup失败,就不会执行测试方法了。因为unittest框架会认为初识化失败了。
什么就被认为 setup失败?就是setup里面抛出了异常。但是要注意的是: 执行一个测试方法前初始化失败了,只是这个测试方法不执行了。但是还是会执行下一个测试方法,当然也包括再次执行初始化方法。
再强调一遍,测试方法必须以test开头,如果不是, 比如tes,就不会被执行。
执行次序
测试方法的执行次序是由方法名称的 字符串排序决定的,通常是ascii顺序。本例中就是:test_1 先执行,test_2 后执行。如果test_1 改为test_case3 ,就会test_2 先执行。
本文内容不用于商业目的,如涉及知识产权问题,请权利人联系51Testing小编(021-64471599-8017),我们将立即处理