UnitTest笔记

简介: unittest学习笔记

UnitTest——测试模块

其他相关:使用coverage工具统计python单元测试覆盖率

一、简单示例

待测类/方法 book.py

# 待测类
class Book(object):
    _page = 2000
    def __init__(self, bookname, author):
        self.name = bookname
        self.author = author

    def get_page(self):
        return self._page
    
# 待测方法
def get_name(book):
    return book.name

测试类test_book.py

# 每个测试方法均以 test 开头,否则是不被unittest识别的。
class TestBook(unittest.TestCase):

    def test_init(self):
        print('test init()')
        book = main_class.Book('bookname', 'author')
        self.assertEquals(book.name, 'bookname')
        self.assertEquals(book.author, 'author')
        self.assertEquals(book._page, 2000)
        self.assertTrue(isinstance(book, main_class.Book))

    def test_get(self):
        print('test get_name()')
        self.assertEquals(main_class.get_name(main_class.Book('bookname', 'author')), 'bookname')

运行

if __name__ == '__main__':
    unittest.main()

结果

test get_name()
.
test init()
.
----------------------------------------------------------------------
Ran 2 tests in 0.001s

OK

​ 给出的结果标识,成功是 .,失败是 F,出错是 E,跳过是 S

​ 测试的执行跟方法的顺序没有关系。

二、测试类

创建

  • 继承unittest.TestCase。
  • 以“test”开头的测试方法,每一类分别添加一个测试方法。
  • 按需添加内置判断条件如:assertEquals()、assertRaises(Error)。

运行

1、pyCharm直接运行

​ pycharm还是比较智能的,可以直接运行测试,不过有个地方需要特别注意,pyCharm会自动识别并测试鼠标所在当前代码块,所以有可能你ctrl+shift+f10后,可能运行结果就只是测试一个方法(笔者可是让这个弄的莫名其妙,一顿不得其解)。

2、main方法

​ 在测试文件结尾添加

if __name__ == '__main__':
    unittest.main()

然后命令行运行

python xxxx.py
3、命令行运行

在命令行通过参数-m unittest直接运行单元测试:

$ python -m unittest xxxx

这是推荐的做法,因为这样可以一次批量运行很多单元测试,并且,有很多工具可以自动来运行这些单元测试。

环境准备和尾处理

如果每个测试之前都需要准备环境如连接数据库、打开文件,或尾处理如关闭数据库、关闭数据流,不可能每个测试方法都写一遍。

setUp()

​ 在每个测试方法运行之前运行

tearDown()

​ 在每个测试方法运行之后运行

setUpClass()

​ 在每个单元测试开始之前运行

tearDownClass()

​ 在每个单元测试结束之后运行

示例:

class TestBook(unittest.TestCase):

    def setUp(self):
        print('setUp++++++++')

    @classmethod
    def setUpClass(cls):
        print('setUpClass--------')

    def tearDown(self):
        print('tearDown++++++++++')

    @classmethod
    def tearDownClass(cls):
        print('tearDownClass--------')

    def test_init(self):
        print('test init()')

    def test_get(self):
        print('test get_name()')

运行结果:

(UnitTest) D:\sHui\learn\UnitTest>python -m  unittest test_class
setUpClass--------
setUp++++++++
test get_name()
tearDown++++++++++
.setUp++++++++
test init()
tearDown++++++++++
.tearDownClass--------

----------------------------------------------------------------------
Ran 2 tests in 0.003s

OK

跳过某case

测试跳过某个case?unittest提供了几种方法。

1、skip装饰器
  • unittest.skip(reason) skip无条件跳过
  • unittest.skipIf(condition, reason) skipIf当condition为True时跳过
  • unittest.skipUnless(condition, reason) skipUnless当condition为False时跳过。

示例:

class TestBook(unittest.TestCase):
    
    def test_init(self):
        print('test init()')

    @unittest.skip('skip this func ')
    def test_get(self):
        print('test get_name()')

结果:

Skipped: skip this func 
test init()


Ran 2 tests in 0.002s

OK (skipped=1)

运行了两个测试,但test_get被跳过了

2、TestCase.skipTest()

测试类的skipTest()方法可以跳过当前测试方法。

class TestBook(unittest.TestCase):
    def test_init(self):
        print('test init()')
    
    # 跳过此方法
    def test_get(self):
        self.skipTest('skip this func')
        print('test get_name()')

结果同上

调整测试顺序

新建文件test_suite.py

import unittest
import test_class


if __name__ == '__main__':
    suite = unittest.TestSuite()
    tests = [test_class.TestBook('test_init'), test_class.TestBook('test_get')]
    suite.addTests(tests)
    runner = unittest.TextTestRunner(verbosity=2)
    runner.run(suite)

输出:

test init()
test get_name()
test_init (test_class.TestBook) ... ok
test_get (test_class.TestBook) ... ok

----------------------------------------------------------------
Ran 2 tests in 0.000s
OK

三、测试输出

1、输出信息

verbosity参数可以控制执行结果的输出

  • 0 是简单报告
  • 1 是一般报告
  • 2 是详细报告。

2、输出到文件

if __name__ == '__main__':
    suite = unittest.TestSuite()
    suite.addTests(unittest.TestLoader().loadTestsFromTestCase(test_class.TestBook))

    with open('Unittest.txt', 'a') as f:
        runner = unittest.TextTestRunner(stream=f, verbosity=2)
        runner.run(suite)

运行结束会在同目录下生成了Unittest.txt

3、输出为HTML

HTMLTestRunner是一个第三方的unittest HTML报告库,首先我们下载HTMLTestRunner.py,并放到当前目录下,或者你的’C:Python27Lib’下,就可以导入运行了。

示例:

from HTMLTestRunner import HTMLTestRunner

if __name__ == '__main__':
    suite = unittest.TestSuite()
    suite.addTests(unittest.TestLoader().loadTestsFromTestCase(test_class.TestBook))
    with open('HTMLReport.html', 'w') as f:
        runner = HTMLTestRunner(stream=f,
                                title='MathFunc Test Report',
                                description='generated by HTMLTestRunner.',
                                verbosity=2)
        runner.run(suite)

四、Coverage的使用

1.命令行方式

详见:http://coverage.readthedocs.io/en/latest/cmd.html

可以使用help命令查看帮助:$ coverage help

关键命令如下:

A.run

执行代码覆盖率统计,只需要通过coverage的run参数执行被统计代码即可。

$ coverage run test.py arg1 arg2

test.py是测试脚本,arg1 arg2是test.py执行需要的参数。跑完后,会自动生成一个覆盖率统计结果文件(data file):.coverage。

B.report

有了覆盖率统计结果文件,只需要再运行report参数,就可以在命令里看到统计的结果。

Stmts/Miss表示语句总数/未执行到的语句数

Cover=(Stmts-Miss)/Stmts

c. html

生成html的测试报告。

$ coverage html -d covhtml

生成的报告直接关联代码,高亮显示覆盖和未覆盖的代码,支持排序。-d指定html文件夹。

2.API方式

除了使用命令行,还可以在python代码中直接调用coverage模块执行代码覆盖率的统计。使用方法也非常简单:

import coverage

cov = coverage.coverage(source = ['totest'])
cov.start()
#coding
cov.stop()
cov.report()
cov.html_report(directory='covhtml')

source指定要执行统计的文件,source = ['totest']只统计totest.py的覆盖率

directory指定生成html的路径

五、常用函数

Method Checks that
assertEqual(a, b) a == b
assertNotEqual(a, b) a != b
assertTrue(x) bool(x) is True
assertFalse(x) bool(x) is False
assertIs(a, b) a is b
assertIsNot(a, b) a is not b
assertIsNone(x) x is None
assertIsNotNone(x) x is not None
assertIn(a, b) a in b
assertNotIn(a, b) a not in b
assertIsInstance(a, b) isinstance(a, b)
assertNotIsInstance(a, b) not isinstance(a, b)
assertRaises(exc, fun, *args, **kwds) fun(*args, **kwds) raises exc
assertRaisesRegexp(exc, r, fun, *args, **kwds) fun(*args, **kwds) raises exc and the message matches regex r
assertAlmostEqual(a, b) round(a-b, 7) == 0
assertNotAlmostEqual(a, b) round(a-b, 7) != 0
assertGreater(a, b) a > b
assertGreaterEqual(a, b) a >= b
assertLess(a, b) a < b
assertLessEqual(a, b) a <= b
assertRegexpMatches(s, r) r.search(s)
assertNotRegexpMatches(s, r) not r.search(s)
assertItemsEqual(a, b) sorted(a) == sorted(b) and works with unhashable objs
assertDictContainsSubset(a, b) all the key/value pairs in a exist in b
assertMultiLineEqual(a, b) strings
assertSequenceEqual(a, b) sequences
assertListEqual(a, b) lists
assertTupleEqual(a, b) tuples

参考文章:

官方文档

Python必会的单元测试框架 —— unittest

廖雪峰

目录
相关文章
|
1天前
|
测试技术 Python
Python测试架构unittest
【4月更文挑战第19天】
6 3
|
4天前
|
前端开发 测试技术 C++
Python自动化测试面试:unittest、pytest与Selenium详解
【4月更文挑战第19天】本文聚焦Python自动化测试面试,重点讨论unittest、pytest和Selenium三大框架。unittest涉及断言、TestSuite和覆盖率报告;易错点包括测试代码冗余和异常处理。pytest涵盖fixtures、参数化测试和插件系统,要注意避免过度依赖unittest特性。Selenium的核心是WebDriver操作、等待策略和测试报告生成,强调智能等待和元素定位策略。掌握这些关键点将有助于提升面试表现。
17 0
|
2月前
|
测试技术 API Python
Python自动化测试:unittest与pytest的实战技巧
Python自动化测试:unittest与pytest的实战技巧
|
8月前
|
测试技术 Python
selenium-unittest基础使用
selenium-unittest基础使用
55 0
|
8月前
|
测试技术 Python
UnitTest框架学习(上)
UnitTest框架学习(上)
41 0
|
8月前
|
Java 测试技术
UnitTest框架学习(下)
UnitTest框架学习(下)
45 0
|
11月前
|
JSON 测试技术 数据库
unittest 测试框架的使用
1. unittest 框架解析 2. 批量执行测试脚本 1)构建测试套件 addTest() 方法 makeSuite() 方法 TestLoader() 方法 2)用例的执行顺序 3)忽略测试用例的执行 3. unittest 断言 4. HTML 报告生成 5. 异常捕获与错误截图 6. 数据驱动 1)测试多个不同数据 2)测试某个文件中的多组数据 txt 文件或者 csv 文件 JSON 文件
111 0
|
测试技术 C++ Python
【进阶Python】第九讲:单元测试之unittest
在开发中,为了保证项目的正常运行,能够按照预期正确的输出我们想要的结果,单元测试时必不可少的。在Python中,用于测试的库有很多,其中较为常用的就是本文的主角--unittest。本文会详细介绍unittest的两种常见用法,同时会介绍使用频率相对较少的跳过、复用等方法。
【进阶Python】第九讲:单元测试之unittest
|
测试技术 数据库
自动化测试教程(10)了解Unittest
1.Unittest最核心的是TestCase、TestSuite、TestRunner、TestFixture四部分。(1)TestCase:用户自定义测试用例的基类,调用run( )方法时,会依次调用setUp( )方
|
测试技术
自动化测试教程(11)使用Unittest框架
定义setUp( )方法、tearDown( )方法、setUpClass( )方法、tearDownClass( )方法。通过命令行或者unittest.main( )方法执行时,main会调用TextTestRunner中的run()方法
自动化测试教程(11)使用Unittest框架