Unittest由4部分组成TestFixture(测试固件)、TestCase(测试用例)、TestSuite(测试套件)、   TestRunner(测试执行)

 命名规范:

  • 测试类:类名必须以Test开头(如TestMath),否则默认的测试发现机制(discover)可能无法识别。

  • 测试方法:方法名必须以test_开头(如test_add),否则不会被自动加载。

  • 非测试方法:非测试方法(如辅助函数)不应以test_开头。

  • 测试模块: 以test_xx.py开头或xx_test.py结尾

一、TestFixture 测试固件

        用于测试用例执行前作准备和测试用例执行后做清理工作

                setUp(): 测试用例执行前的准备工作,执行每个测试用例的前置条件

                tearDown(): 测试用例执行后的善后工作,执行每个测试用例的后置条件

                setUpClass(): 结合@classmethod 装饰器一起使用,所有测试用例的前置条件

                tearDownClass(): 结合@classmethod 装饰器一起使用,所有测试用例的后置条件

        方法执行顺序: setupClass -> setup ->test_02 -> teardown -> setup -> test_03 -> teardown -> teardownClass

import unittest

# 单元测试框架unittest
from selenium import webdriver
from selenium.webdriver.chrome.service import Service

class MyTestCase(unittest.TestCase):
    # 类方法只执行一次
    @classmethod
    def setUpClass(cls) -> None:
        # cls 指当前类对象MyTestCase
        # 这里可以初始化WebDriver实例
        print('setupClass')

    @classmethod
    def tearDownClass(cls) -> None:
        # 这里可以添加退出浏览器
        print('tearDownClass')

    # 执行测试用例之前做的
    def setUp(self) -> None:
        print('setup...')

    # 执行测试用例之后做的
    def tearDown(self) -> None:
        print('teardown...')


if __name__ == '__main__':
    # 方法执行顺序: setupClass -> setup ->test_02 -> teardown -> setup -> test_03 -> teardown -> teardownClass
    unittest.main()

二、TestCase 测试用例

        1.继承unittest.TestCase的测试类的方法名必须要以test开头才能被执行

        2.每个测试用例都会执行setup(),teardown()方法

        3.测试用例方法执行顺序: 0~9,A~Z,ASCll码字母

import unittest

# 单元测试框架unittest
from selenium import webdriver
from selenium.webdriver.chrome.service import Service

class MyTestCase(unittest.TestCase):
    # 类方法只执行一次
    @classmethod
    def setUpClass(cls) -> None:
        # cls 指当前类对象MyTestCase
        # 这里可以初始化WebDriver实例
        print('setupClass')

    @classmethod
    def tearDownClass(cls) -> None:
        # 这里可以添加退出浏览器
        print('tearDownClass')

    # 执行测试用例之前做的
    def setUp(self) -> None:
        print('setup...')

    def test_03(self):
        print('test_03')
        # 断言方法:等于
        self.assertEqual(1 + 2, 3)

    # 每个测试用例都会执行setup,teardown方法
    def test_02(self):
        print('test_02')
        # 断言方法:大于等于
        self.assertGreaterEqual(5, 4)

    # 继承unittest.TestCase的测试类的方法名必须要以test开头才能被执行
    def aaa(self):
        print('aaa')

    # 执行测试用例之后做的
    def tearDown(self) -> None:
        print('teardown...')


if __name__ == '__main__':
    # 方法执行顺序: setupClass -> setup ->test_02 -> teardown -> setup -> test_03 -> teardown -> teardownClass
    # 测试用例方法执行: 0~9,A~Z,ASCll码字母
    unittest.main()

        5.断言Assert(Unittest提供的断言)

assertEqual(a,b)判断a等于b
assertNotEqual(a,b)判断a不等于b
assertIs(a,b)判断a是b
assertIsNot(a,b)判断a不是b
assertIsNone(a)判断a是None
assertIsNotNone(a)判断a不是None
assertIn(a,b)判断a在b中,包含相等
assertNotIn(a,b)判断a不在b中
assertGreater(a,b)判断a大于b
assertGreaterEqual(a,b)判断a大于等于b
assertLess(a,b)判断a小于b
assertLessEqual(a,b)判断a小于等于b

三、TestSuit 测试套件

import unittest

class TestSuit(unittest.TestCase):
     def test_1(self):
         print('test1')

     def test_2(self):
         print('test2')

     def test_3(self):
         print('test3')

        TestSuite可以组织多个测试用例,也可以将多个测试套件组织在一起

        1.TestSuite 直接构建测试集

        map(function,iterable,...)     第一个参数function表示以参数序列中的每一个元素调用function函数,返回包含每次function函数返回值的新列表,这样讲可能有点官方不好理解,换个讲法->

         map()函数会对可迭代对象(iterable)中的每个元素应用指定的函数(function):

                funtion: 一个接受参数的函数(或可调用对象,这里使用的是测试类对象TestSuit)

                iterable:一个可迭代对象(如列表、元组,这里使用的是['test_3','test_1'])

        TestSuit在被调用时,可以通过传递方法名来创建特定测试方法的实例。

if __name__ == '__main__':
    # 构造测试集
    suit = unittest.TestSuite(map(TestSuit,['test_3','test_1']))
    # 等效于:
    test_cases = [TestSuit('test_3'), TestSuit('test_1')]
    suit = unittest.TestSuite(test_cases)
    # 测试执行
    unittest.TextTestRunner().run(suit)

        2.addTest() 构建测试集

if __name__ == '__main__':
    # 构造测试集
    suit = unittest.TestSuite()
    # 一次只能添加一个测试用例
    suit.addTest(TestSuit('test_1'))
    suit.addTest(TestSuit('test_3'))
    # 执行测试用例
    unittest.TextTestRunner().run(suit)

        3.addTests() 构建测试集

                将测试用例添加进测试集,与addTest()方法不同的是,addTests()允许一次添加多条测试用例

if __name__ == '__main__':
    # 构造测试集
    suit = unittest.TestSuite()
    # 如果这里提供测试类没有的测试方法,将会报AttributeError
    suit.addTests(map(TestSuit,['test_1','test_3']))
    # 执行测试用例
    unittest.TextTestRunner().run(suit)

四、TestLoader 测试加载

        将测试用例TestCase添加到测试套件TestSuit中 

        1.unittest.TestLoader().loadTestsFromTestCase(testCaseClass)  返回测试类中所包含的所有测试用例的套件

import unittest

class TestMath(unittest.TestCase):
    def test_add(self):
        self.assertEqual(1 + 1, 2)
    def test_sub(self):
        self.assertEqual(3 - 1, 2)
if __name__ == '__main__':
    # 加载 TestMath 类中的所有测试方法
    suite = unittest.TestLoader().loadTestsFromTestCase(TestMath)
    unittest.TextTestRunner().run(suite)

        2.unittest.TestLoader().loadTestsFromModule(module)  返回给定模块中所包含的所有测试用例的套件

# 文件: test_math.py
import unittest

class TestMath(unittest.TestCase):
    def test_add(self):
        self.assertEqual(1 + 1, 2)

class TestString(unittest.TestCase):
    def test_upper(self):
        self.assertEqual('foo'.upper(), 'FOO')
if __name__ == '__main__':
    # 加载模块中的所有测试类
    suite = unittest.TestLoader().loadTestsFromModule(test_math)  # 假设模块已导入
    unittest.TextTestRunner().run(suite)

        3.unittest.TestLoader().loadTestsFromName(name,module=None)  返回一组给定字符串说明符的所有测试用例,名称可以为模块、测试用例类、测试用例类中的测试方法,或其中可调用的对象,返回一个TestCase或TestSuite实例

if __name__ == '__main__':
    # 加载特定测试方法
    suite = unittest.TestLoader().loadTestsFromName('TestMath.test_add', module=test_math)
    unittest.TextTestRunner().run(suite)

        4.unittest.TestLoader().loadTestsFromNames(names,module=None)  返回使用给定序列找到的所有测试用例的套件说明符的字符串        

if __name__ == '__main__':
    # 加载多个测试方法或类
    names = ['TestMath.test_add', 'TestString.test_upper']
    suite = unittest.TestLoader().loadTestsFromNames(names, module=test_math)
    unittest.TextTestRunner().run(suite)

        5.unittest.TestLoader().getTestCaseNames(testCaseclass)  返回在testCaseclass中找到的方法名的排序序列        

class TestMath(unittest.TestCase):
    def test_add(self): pass
    def test_sub(self): pass
    def helper(self): pass  # 不会被识别为测试方法

names = unittest.TestLoader().getTestCaseNames(TestMath)
print(names)  # 输出: ['test_add', 'test_sub']

        6.unittest.TestLoader().discover(start_dir,pattern='test*.py',top_level_dir=None) 从 Python文件中获取测试用例,递归扫描目录,自动发现所有匹配pattern的测试文件

if __name__ == '__main__':
    unittest.TestLoader().discover(start_dir='./', pattern="test*.py")
    unittest.TextTestRunner().run(discover)

五、TestRunner 测试运行

        verbosity 用来控制输出错误报告的详细程度,有3个等级:

                0: 只显示全局执行结果和执行结果中用例的总数

                1:默认值,显示全局执行结果和执行结果中用例的总数,并且对每一条用例的执行结果都有标注

                2:显示全局执行结果和执行结果中用例的总数,并输出每一个用例的详细结果

if __name__ == '__main__':
    unittest.TestLoader().discover(start_dir='./', pattern="test*.py")
    unittest.TextTestRunner(verbosity=2).run(discover)

        六、skip装饰器

                1.@unittest.skip(reason): 无条件跳过,reason可用来描述跳过的原因

                2.@unittest.skipIf(condition,reason): 有条件跳过,当condition条件满足时跳过该条测试用例

                3.@unittest.skipUnless(condition,reason):  有条件跳过,当condition条件不满足时跳过该条测试用例

                4.@unittest.expectedFailure  用于标记期望执行失败的测试方法,如果该测试方法执行失败,则被认为成功,如果执行成功,则认为失败

不想营造篇幅太长,想了解pytest框架,点击下方连接
python自动化测试框架——pytesthttps://blog.csdn.net/lrk__/article/details/149903366?sharetype=blogdetail&sharerId=149903366&sharerefer=PC&sharesource=lrk__&spm=1011.2480.3001.8118

更多推荐