Unittest单元测试
基本实例
这是一段简短的代码,来测试三种字符串方法:
import unittest
class TestStringMethods(unittest.TestCase):
def test_upper(self):
self.assertEqual('foo'.upper(), 'FOO')
def test_isupper(self):
self.assertTrue('FOO'.isupper())
self.assertFalse('Foo'.isupper())
def test_split(self):
s = 'hello world'
self.assertEqual(s.split(), ['hello', 'world'])
# check that s.split fails when the separator is not a string
with self.assertRaises(TypeError):
s.split(2)
if __name__ == '__main__':
unittest.main()
背景:
在执行单元测试中,有些方法执行耗时,不想全部执行,想忽略执行,那就需要跳过某方法执行
unittest中断言主要有三种类型:
1.基本的布尔断言,即:要么正确,要么错误的验证 2.比较断言,如比较两个变量的值(跟上面的布尔断言区别不大,主要是通过比较两个变量的值得出布尔值) 3.复杂断言(一般用的比较少,像断言两个列表、元组等)
1.无条件跳过某方法
案例
import random
import unittest
import sys
class TestSequenceFunctions(unittest.TestCase):
a = 10
def setUp(self):
self.seq = list(range(10))
基本断言方法assert
序号 | 断言方法 | 断言描述 |
---|---|---|
1 | assertEqual(arg1, arg2, msg=None) | 验证arg1=arg2,不等则fail |
2 | assertNotEqual(arg1, arg2, msg=None) | 验证arg1 != arg2, 相等则fail |
3 | assertTrue(expr, msg=None) | 验证expr是true,如果为false,则fail |
4 | assertFalse(expr,msg=None) | 验证expr是false,如果为true,则fail |
5 | assertIs(arg1, arg2, msg=None) | 验证arg1、arg2是同一个对象,不是则fail |
6 | assertIsNot(arg1, arg2, msg=None) | 验证arg1、arg2不是同一个对象,是则fail |
7 | assertIsNone(expr, msg=None) | 验证expr是None,不是则fail |
8 | assertIsNotNone(expr, msg=None) | 验证expr不是None,是则fail |
9 | assertIn(arg1, arg2, msg=None) | 验证arg1是arg2的子串,不是则fail |
10 | assertNotIn(arg1, arg2, msg=None) | 验证arg1不是arg2的子串,是则fail |
11 | assertIsInstance(obj, cls, msg=None) | 验证obj是cls的实例,不是则fail |
12 | assertNotIsInstance(obj, cls, msg=None) | 验证obj不是cls的实例,是则fail |
复杂的断言判断
简单的case
代码
# coding=utf-8
#1.先设置编码,utf-8可支持中英文,如上,一般放在第一行
#2.注释:包括记录创建时间,创建人,项目名称。
'''
Created on 2019-4-25
@author: 北京-宏哥
Project:学习和使用unittest框架编写断言
'''
#3.导入unittest模块
import unittest
#4.编写测试用例和断言
class Test(unittest.TestCase):
def test01(self):
'''判断 a == b '''
a = 1
b = 1
self.assertEqual(a, b)
def test02(self):
'''判断 a in b '''
a = "hello hongge"
b = "hello hongge and world!"
self.assertIn(a, b)
def test03(self):
'''判断 a is True '''
a = True
self.assertTrue(a)
def test04(self):
'''失败案例'''
a = "北京-宏哥"
b = "hongge"
self.assertEqual(a, b,msg='失败原因: %s!=%s'%(a,b))
if __name__ == "__main__":
unittest.main()
测试log
C:\Python\Python38\python.exe C:\pycharm\Pycharm_Professional_2021.2.1_Protable\Pycharm_Professional_2021.2.1_Protable\plugins\python\helpers\pycharm\_jb_pytest_runner.py --target test_fofa.py::MyTestCase
Testing started at 13:33 ...
Launching pytest with arguments test_fofa.py::MyTestCase --no-header --no-summary -q in C:\wuzhi-apps\shakespeare-apps\白帽汇\shakespeare-action-python-fofa_search_engine
============================= test session starts =============================
collecting ... collected 3 items
test_fofa.py::MyTestCase::test_get_all_results
test_fofa.py::MyTestCase::test_get_task_result
test_fofa.py::MyTestCase::test_search_ip
======================== 1 passed, 2 skipped in 1.26s =========================
Process finished with exit code 0
SKIPPED (skipping) [ 33%]
Skipped: skipping
SKIPPED (skipping) [ 66%]
Skipped: skipping
PASSED [100%]Test Start ----->
{'error': False, 'mode': 'extended', 'page': 1, 'query': 'ip=="35.185.132.195"', 'results': [['35.185.132.195:80', '35.185.132.195', '80'], ['35.185.132.195', '35.185.132.195', '80'], ['35.185.132.195:139', '35.185.132.195', '139'], ['35.185.132.195:445', '35.185.132.195', '445'], ['35.185.132.195:135', '35.185.132.195', '135'], ['35.185.132.195:3389', '35.185.132.195', '3389']], 'size': 6}
{'code': 200, 'msg': 'ip search succeeded', 'data': {'msg': '', 'value': ['35.185.132.195:3389', '35.185.132.195:135', '35.185.132.195', '35.185.132.195:445', '35.185.132.195:80', '35.185.132.195:139'], 'total': 6}}
status_code: 200
---------- test_save_data done ! ------------
Test Done! <-----
单元测试,生成报告
参考:https://www.cnblogs.com/fancyl/p/9134482.html
注:1.安装并导入HTMLTestRunner 模块,该模块是可以生成报告的模块。
2.运行代码时,要以Run xx.py方式运行,不能以unittest方式运行,否则不会生成报告。
import unittest #单元测试模块
import HTMLTestRunner #用来生成报告的模块
class TestCalc(unittest.TestCase):
def testcc(self): #函数名要以test开头,否则不会被执行
'''这是第一个测试用例''' #用例描述,在函数下,用三个单引号里面写用例描述
self.assertEqual(1,1)
print('第一个用例')
def testaa(self):
'''这个是第二个测试用例'''
self.assertEqual(1,2)
print('第二个用例')
def testdd(self):
'''用例描述3'''
print('第三个用例')
def testbb(self):
'''用例描述4'''
print('第四个用例')
suite = unittest.TestSuite() #定义一个测试集合
suite.addTest(unittest.makeSuite(TestCalc)) #把写的用例加进来(将TestCalc类)加进来
f = open('test.html','wb') #以二进制模式打开一个文件
runner = HTMLTestRunner.HTMLTestRunner(f,title='unittest用例标题',description='这是用例描述')
runner.run(suite) #运行用例(用例集合)
打开浏览器,如图所示:
方法二
报告模板BeautifulReport(模板相对好用)
import unittest #单元测试模块
from BeautifulReport import BeautifulReport as bf #导入BeautifulReport模块,这个模块也是生成报告的模块,但是比HTMLTestRunner模板好看
class TestCalc(unittest.TestCase):
def setUp(self): #每个用例运行之前运行的
print('setup是啥时候运行的')
def tearDown(self): #每个用例运行之后运行的
print('teardown是啥时候运行的')
如图:
本文来自博客园,作者:游走De提莫,转载请注明原文链接:https://www.cnblogs.com/Gaimo/p/16098168.html
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· 没有Manus邀请码?试试免邀请码的MGX或者开源的OpenManus吧
· 【自荐】一款简洁、开源的在线白板工具 Drawnix
· 园子的第一款AI主题卫衣上架——"HELLO! HOW CAN I ASSIST YOU TODAY
· Docker 太简单,K8s 太复杂?w7panel 让容器管理更轻松!