• Unittest单元测试


    Unittest 单元测试

    基本实例

    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.无条件跳过某方法

    @unittest.skip("skipping")
    2.使用变量的方式,指定忽略测试方法

    a=10
    @unittest.skipIf(a > 5, "condition is not satisfied!")
    表示if a>5为真,就跳过此方法

    3.指定测试平台忽略测试方法  
    @unittest.skipUnless(sys.platform.startswith("Linux"), "requires Linux")
      如果不是liunx ,就直接跳过,python可以使用sys,查看自己的平台信息

    案例

    import random
    import unittest
    import sys

    class TestSequenceFunctions(unittest.TestCase):
       a = 10
       def setUp(self):
           self.seq = list(range(10))

       @unittest.skip("skipping") # 无条件忽略该测试方法
       def test_shuffle(self):
           random.shuffle(self.seq)
           self.seq.sort()
           self.assertEqual(self.seq, list(range(10)))
           self.assertRaises(TypeError, random.shuffle, (1, 2, 3))

       # 如果变量a > 5,则忽略该测试方法
       @unittest.skipIf(a > 5, "condition is not satisfied!")
       def test_choice(self):
           element = random.choice(self.seq)
           self.assertTrue(element in self.seq)

       # 除非执行测试用例的平台是Linux平台,否则忽略该测试方法 win32是windows
       @unittest.skipUnless(sys.platform.startswith("Linux"), "requires Linux")
       def test_sample(self):
           with self.assertRaises(ValueError):
               random.sample(self.seq, 20)
           for element in random.sample(self.seq, 5):
               self.assertTrue(element in self.seq)


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

    基本断言方法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

    复杂的断言判断

    img

    简单的case

    img

    代码

    # 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)  #运行用例(用例集合)

    打开浏览器,如图所示:

    img

    方法二

    报告模板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是啥时候运行的')

       @classmethod
       def setUpClass(cls):  #在所有用例执行之前运行的
           print('我是setUpclass,我位于所有用例的开始')

       @classmethod
       def tearDownClass(cls): #在所有用例都执行完之后运行的
           print('我是tearDownClass,我位于多有用例运行的结束')

       def testcc(self):    #函数名要以test开头,否则不会被执行
           '''这是第一个测试用例'''       #用例描述,在函数下,用三个单引号里面写用例描述
           self.assertEqual(1,1)
           print('第一个用例')

       def testaa(self):
           '''这个是第二个测试用例'''
           self.assertEqual(1,1)
           print('第二个用例')

       def testdd(self):
           '''用例描述3'''
           print('第三个用例')

       def testbb(self):
           '''用例描述4'''
           print('第四个用例')

    suite = unittest.TestSuite()  #定义一个测试集合
    suite.addTest(unittest.makeSuite(TestCalc))  #把写的用例加进来(将TestCalc类)加进来
    run = bf(suite) #实例化BeautifulReport模块
    run.report(filename='test',description='这个描述参数是必填的')

    如图:

    img

     

     

     

     

     

     

     

     

     

     

     

     

     

     

  • 相关阅读:
    最长公共前缀
    无重复字符的最长子串
    文章采集代码
    网络验证常见的攻击方式与防御手段
    初创公司如何避免服务器被攻击
    拒绝ssh远程暴力破解
    我公司开了7年,靠的就是这套顶级销售打法撑下来!
    顶级销售的十个习惯,轻松签下百万千万合同!(值得背下来)
    顶级销售高手总结的 9 个方面
    一位顶级销售高手总结的“销售心得”!
  • 原文地址:https://www.cnblogs.com/Gaimo/p/16098168.html
Copyright © 2020-2023  润新知