UnitTest框架 - API

本章讨论unittest模块中定义的类和方法.该模块中有五个主要类.

TestCase类

此类的对象表示最小的可测试单元.它保存测试程序,并提供准备每个例程和之后清理的挂钩.

以下方法在TestCase类中定义 :

Sr.No.Method& ;描述
1

setUp()

调用方法来准备测试夹具.在调用测试方法之前立即调用它

2

tearDown()

测试方法完成后立即调用的方法调用并记录结果.即使测试方法引发异常,也会调用此方法,

3

setUpClass()

测试前调用的类方法在个别课程中.

4

tearDownClass()

在单个类中的测试运行后调用的类方法.

5

run(result = None)

运行测试,将结果收集到作为传递的测试结果对象中结果.

6

skipTest(reason)

在测试方法或setUp期间调用此方法()跳过当前测试.

7

debug()

运行测试而不收集结果.

8

shortDescription()

返回单行描述测试.

Fixtures

可以有在TestCase类中编写的大量测试.这些测试方法可能需要数据库连接,临时文件或其他要初始化的资源.这些被称为fixtures.TestCase包含一个特殊的钩子来配置和清理测试所需的任何灯具. fixtures,override setUp().要清理,请覆盖tearDown().

在下面的示例中,两个测试写在TestCase类中.它们测试两个加法和减法的结果values()方法基于每个测试的shortDescription()初始化参数.Teardown()方法将在每个测试结束时执行.

import unittest

class simpleTest2(unittest.TestCase):
   def setUp(self):
      self.a = 10
      self.b = 20
      name = self.shortDescription()
      if name == "Add":
         self.a = 10
         self.b = 20
         print name, self.a, self.b
      if name == "sub":
         self.a = 50
         self.b = 60
         print name, self.a, self.b
   def tearDown(self):
      print '\nend of test',self.shortDescription()

   def testadd(self):
      """Add"""
      result = self.a+self.b
      self.assertTrue(result == 100)
   def testsub(self):
      """sub"""
      result = self.a-self.b
      self.assertTrue(result == -10)
      
if __name__ == '__main__':
   unittest.main()


从命令行运行上面的代码.它给出了以下输出 :

C:\Python27>python test2.py
Add 10 20
F
end of test Add
sub 50 60
end of test sub
.
================================================================
FAIL: testadd (__main__.simpleTest2)
Add
----------------------------------------------------------------------
Traceback (most recent call last):
   File "test2.py", line 21, in testadd
      self.assertTrue(result == 100)
AssertionError: False is not true
----------------------------------------------------------------------
Ran 2 tests in 0.015s

FAILED (failures = 1)


类夹具

TestCase类有一个setUpClass()方法,可以是在TestCase类中执行单个测试之前重写以执行.同样,tearDownClass()方法将在类中进行所有测试后执行.这两种方法都是类方法.因此,它们必须用@classmethod指令进行修饰.

以下示例演示了这些类方法的使用 :

import unittest

class TestFixtures(unittest.TestCase):

   @classmethod
   def setUpClass(cls):
      print 'called once before any tests in class'

   @classmethod
   def tearDownClass(cls):
      print '\ncalled once after all tests in class'

   def setUp(self):
      self.a = 10
      self.b = 20
      name = self.shortDescription()
      print '\n',name
   def tearDown(self):
      print '\nend of test',self.shortDescription()

   def test1(self):
      """One"""
      result = self.a+self.b
      self.assertTrue(True)
   def test2(self):
      """Two"""
      result = self.a-self.b
      self.assertTrue(False)
      
if __name__ == '__main__':
unittest.main()


TestSuite Class

Python的测试框架提供了一种有用的机制,通过它可以根据测试的功能将测试用例实例组合在一起.这个机制由单元测试模块中的TestSuite类提供.

以下步骤涉及创建和运行测试套件.

第1步 : 创建一个TestSuite类的实例.

suite = unittest.TestSuite()


第2步 : 在套件中的TestCase类中添加测试.

suite.addTest(testcase class)


第3步 : 您还可以使用makeSuite()方法从类中添加测试

suite = unittest.makeSuite(test case class)


第4步 : 单个测试也可以在套件中添加.

suite.addTest(testcaseclass(""testmethod")


第5步 : 创建TestTestRunner类的对象.

runner = unittest.TextTestRunner()


步骤6 : 调用run()方法运行套件中的所有测试

runner.run (suite)


定义了以下方法在TestSuite类 :

Sr.No.方法和描述
1

addTest()

添加测试方法测试套件.

2

addTests ()

从多个TestCase类添加测试.

3

run()

运行与此相关的测试套件,将结果收集到测试结果对象中

4

debug()

运行与此相关的测试套件没有收集结果.

5

countTestCases()

返回代表的测试数量通过此测试对象

以下示例显示如何使用TestSuite class :

import unittest
class suiteTest(unittest.TestCase):
   def setUp(self):
      self.a = 10
      self.b = 20
      
   def testadd(self):
      """Add"""
      result = self.a+self.b
      self.assertTrue(result == 100)
   def testsub(self):
      """sub"""
      result = self.a-self.b
      self.assertTrue(result == -10)
      
def suite():
   suite = unittest.TestSuite()
##   suite.addTest (simpleTest3("testadd"))
##   suite.addTest (simpleTest3("testsub"))
   suite.addTest(unittest.makeSuite(simpleTest3))
   return suite
   
if __name__ == '__main__':
   runner = unittest.TextTestRunner()
   test_suite = suite()
   runner.run (test_suite)


您可以通过以下方法试验addTest()方法取消注释具有makeSuite()方法的行和注释语句.

TestLoader类

unittest包具有TestLoader类,用于创建测试套件来自课程和模块.默认情况下,在调用unittest.main(0方法)时会自动创建unittest.defaultTestLoader实例.但是显式实例会启用某些属性的自定义.

在以下代码中,使用TestLoader对象在List中收集两个类的测试.

import unittest
testList = [Test1, Test2]
testLoad = unittest.TestLoader()

TestList = []
for testCase in testList:
   testSuite = testLoad.loadTestsFromTestCase(testCase)
   TestList.append(testSuite)
   
newSuite = unittest.TestSuite(TestList)
runner = unittest.TextTestRunner()
runner.run(newSuite)


下表显示了TestLoader类中的方法列表 :

Sr.No方法和说明
1

loadTestsFromTestCase()

返回所有测试套件包含在TestCase类中的案例

2

loadTestsFromModule()

返回所有测试套件给定模块中包含的案例.

3

loadTestsFromName()

返回所有测试套件给定字符串说明符的情况.

4

discover()

查找所有测试模块从指定的开始目录递归到子目录,并返回TestSuite对象

TestResult类

此类用于编译有关已成功完成的测试和已遇到失败的测试的信息.TestResult对象存储一组测试的结果.TestRunult实例由TestRunner返回.run()方法.

TestResult实例具有以下属性 :

Sr.No.属性和描述
1

Errors

包含2元组TestCase的列表持有格式化回溯的实例和字符串.每个元组代表一个引发意外异常的测试.

   2

Failures

包含2元组TestCase的列表实例和字符串保存格式化的回溯.每个元组代表一个测试,其中使用TestCase.assert *()方法显式地发出故障信号.

3

Skipped

包含2元组TestCase的列表保存跳过测试原因的实例和字符串.

4

wasSuccessful()

如果所有测试都运行则返回True到目前为止已经过去了,否则返回False.

5

stop()

此方法可以调用表示正在运行的测试集应该被中止.

6

startTestRun()

在任何测试之前调用一次执行.

7

stopTestRun()

所有测试结束后调用一次执行.

8

testsRun

到目前为止运行的测试总数.

9

Buffer

如果设置为true,则sys.stdout和sys.stderr将在调用的startTest()和stopTest()之间进行缓冲。

以下代码执行测试套件 :

if __name__ == '__main__':
   runner = unittest.TextTestRunner()
   test_suite = suite()
   result = runner.run (test_suite)
   
   print "---- START OF TEST RESULTS"
   print result

   print "result::errors"
   print result.errors

   print "result::failures"
   print result.failures

   print "result::skipped"
   print result.skipped

   print "result::successful"
   print result.wasSuccessful()
   
   print "result::test-run"
   print result.testsRun
   print "---- END OF TEST RESULTS"


执行时的代码显示以下输出 :

---- START OF TEST RESULTS
<unittest.runner.TextTestResult run = 2 errors = 0 failures = 1>
result::errors
[]
result::failures
[(<__main__.suiteTest testMethod = testadd>, 'Traceback (most recent call last):\n
   File "test3.py", line 10, in testadd\n 
   self.assertTrue(result == 100)\nAssert
   ionError: False is not true\n')]
result::skipped
[]
result::successful
False
result::test-run
2
---- END OF TEST RESULTS