python--unittest测试框架

unittest中最核心的四个概念是:test case, test suite, test runner, test fixture

    • 一个TestCase的实例就是一个测试用例。什么是测试用例呢?就是一个完整的测试流程,包括测试前准备环境的搭建(setUp),执行测试代码(run),以及测试后环境的还原(tearDown)。元测试(unit test)的本质也就在这里,一个测试用例是一个完整的测试单元,通过运行这个测试单元,可以对某一个问题进行验证。
    • 而多个测试用例集合在一起,就是TestSuite,而且TestSuite也可以嵌套TestSuite。
    • TestLoader是用来加载TestCase到TestSuite中的,其中有几个loadTestsFrom__()方法,就是从各个地方寻找TestCase,创建它们的实例,然后add到TestSuite中,再返回一个TestSuite实例。
    • TextTestRunner是来执行测试用例的,其中的run(test)会执行TestSuite/TestCase中的run(result)方法。
      测试的结果会保存到TextTestResult实例中,包括运行了多少测试用例,成功了多少,失败了多少等信息。
    • 而对一个测试用例环境的搭建和销毁,是一个fixture。

一个class继承了unittest.TestCase,便是一个测试用例,但如果其中有多个以 test 开头的方法,那么每有一个这样的方法,在load的时候便会生成一个TestCase实例,如:一个class中有四个test_xxx方法,最后在load到suite中时也有四个测试用例。

写好TestCase,然后由TestLoader加载TestCase到TestSuite,然后由TextTestRunner来运行TestSuite,运行的结果保存在TextTestResult中,我们通过命令行或者unittest.main()执行时,main会调用TextTestRunner中的run来执行,或者我们可以直接通过TextTestRunner来执行用例。这里加个说明,在Runner执行时,默认将执行结果输出到控制台,我们可以设置其输出到文件,在文件中查看结果(你可能听说过HTMLTestRunner,是的,通过它可以将结果输出到HTML中,生成漂亮的报告,它跟TextTestRunner是一样的,从名字就能看出来,这个我们后面再说)

用到TestSuite原因:1添加到TestSuite中的case是会按照添加的顺序执行的。2但如果有多个测试文件,怎么进行组织,总不能一个个文件执行吧,答案也在TestSuite中。TestSuite 相当于一个容器,用来装testcase

一:编写测试用例

编写自己的测试用例必须继承TestCase类:class xx(unittest.TestCase):

初始化测试环境:setUp和tearDown在每次执行case前后都执行了一次。

如果想要在所有case执行之前准备一次环境,并在所有case执行结束之后再清理环境,我们可以用 setUpClass() 与 tearDownClass():

        class TestMathFunc(unittest.TestCase):
        """Test mathfuc.py"""
        @classmethod
        def setUpClass(cls):
                print "This setUpClass() method only called once."
        @classmethod
        def tearDownClass(cls):

               print "This tearDownClass() method only called once too."

二:执行测试用例
执行测试用例有两种方法:

  1. 若是在测试用例所在的文件内执行用例,直接用 Unittest.main() 方法执行,main()方法会自动执行本文件中所有以test* 命名的函数,
  2. 如果想将测试用例的文件和执行测试用例的文件分开来执行,需要以下顺序来写执行用例的代码:
A)导入模块:unittest,HTMLTestRunner(或TextTestRunner),测试用例模块

   B):suite = unittest.TestSuite() 创建一个名字为suite 的容器,用来装testcase

C):suite.addTest(TestMathFunc("test_multi"))   用addTest()方法将case添加容器中 添加的是某一个测试用例
suite.addTests(unittest.TestLoader().loadTestsFromTestCase(TestMathFunc))  通过loadTestsFromTestCase()将case传入TestCase中,添加的是测试类中的所有用例,loadTestsFromModule(module):返回一个给定的模块中所有测试用例,
打包成一个套件返回。该类创建一个testsuites然后加载一个module并执行其中所有的测试用例,,执行的顺序是根据测试用例的名称来的: suite = unittest.TestLoader().loadTestsFromTestCase(WidgetTestCase)
D):1) with open('UnittestTextReport.txt', 'a') as f:
        runner = unittest.TextTestRunner(stream=f, verbosity=2)
        通过TextTestRunner()方法来规定执行的测试用例结果输出到unittestTextReport.txt 文件中
    2) with open('HTMLReport.html', 'w') as f:
          runner = HTMLTestRunner(stream=f,
                       title='MathFunc Test Report',
                       description='generated by HTMLTestRunner.',
                       verbosity=2
                                )

测试用例执行后的输出结果可以通过
TextTestRunner()方法放到指定的txt文件中,或者通过HTMLTestRunner()方法放到指定的html文件中,以网页形式展现,
E):runner.run(suite) 执行用例
 
3)若在某个目录下写了很多Python文件,每个文件中都有测试测试用例,现在想让这个文件中的所以测试用例都自动执行,需要以下方法:
        import unittest,HTMLTestRunner
        suite = unittest.TestSuite()#创建测试套件
        all_cases = unittest.defaultTestLoader.discover('.','test_*.py')
        #找到某个目录下所有的以test开头的Python文件,
        for case in all_cases:
            suite.addTests(case)#把所有的测试用例添加进来
      fp = open('res.html','wb')
      runner = HTMLTestRunner.HTMLTestRunner(stream=fp,title='all_tests',description='所有测试情况')
      runner.run(suite)
      #运行测试

discover(start_dir, pattern='test*.py',top_level_dir=None)

递归查找指定目录(start_dir)及其子目录下的全部测试模块,将这些测试模块放入一个TestSuite 对象并返回。只有匹配pattern的测试文件才会被加载到TestSuite中。

如果一个测试文件的名称符合pattern,将检查该文件是否包含 load_tests() 函数,如果 load_tests() 函数存在,则由该函数负责加载本文件中的测试用例。如果不存在,就会执行loadTestsFromModule(),查找该文件中派生自TestCase 的类包含的 test 开头的方法。

 
    @unittest.skip("I don't want to run this case.")
    def test_divide(self):
        """Test method divide(a, b)"""
        print "divide"
        self.assertEqual(2, divide(6, 3))
        self.assertEqual(2.5, divide(5, 2))

@unittest.skip:此方法用来跳过某个testcase不去执行

Unittest 中的方法:1.检测元素是否相等:assertEqual(a,b [,msg]):检测a==b,这个方法检查a是否等于b,常用语检测元素属性等。assertNotEqual(a,b [,smg]):检测a!==b.

2. 检测表达式是否为Ture,或者 False: assertTrue(x [,msg]) assertFalse(x [,msg])

3. 逻辑运算
assertGreater(a, b) # 检测a > b.
assertGreaterEqual(a ,b) # 检测a >= b.
assertLess(a, b) #检测a < b.
assertLessEqual(a, b) #检测a <= b.="" <="" code=""></=>

 

猜你喜欢

转载自www.cnblogs.com/luckycn/p/9064805.html