先前有家供应商与我们合作开发自动化工程,采用的py unittest作为脚本运行框架。我发现他们出的脚本都是挨个手写的,格式上也是参差不齐。所以有了根据用例表批量生成脚本的一段小代码
供应商提供的测试脚本
贴一个经删减修饰后的脚本代码举例(因原脚本很难看,我有代码整洁强迫症 必需加以修饰后贴出 哈哈)。
1 import unittest 2 import base64 3 import time 4 from common import objUtil 5 from common import MQTT_Client 6 from common import MQTT_Server 7 from common import objwrite_excle 8 9 10 11 class test_TEM(unittest.TestCase): 12 global TestResult 13 14 def setUp(self): 15 print("开始测试XXXX") 16 #开启Log输出 17 objUtil.outputLog("用例编号") 18 # Publish MSG 到被测设备 19 requestStr = request.SerializeToString() 20 sMessage = str(base64.b64encode(requestStr), 'utf-8') 21 22 pub = MQTT_Client.PubMsg('127.0.0.1') 23 pub.publish("XXX_PC/Administrator/Request", sMessage, 1) 24 pub.loop(5) 25 26 # 订阅 MSG、解码、 27 sub = MQTT_Server.mqtt.Client() 28 while MQTT_Server.message == None: 29 sub.loop() 30 returnStr = MQTT_Server.message 31 print("收到MSG:", str(returnStr)) 32 33 34 def tearDown(self): 35 print(self.TestResult) 36 #统计测试结果 37 objwrite_excle.great_excle() 38 39 40 def test_ui(self): 41 #连接手机 42 objUtil.setDriver(platformVersion="8.0", deviceName='123456') 43 objUtil.sleep(1) 44 #滑动出来APP主页 45 objUtil.swpie_up() 46 objUtil.sleep(1) 47 #刷新 48 objUtil.refresh() 49 objUtil.sleep(1) 50 #进行判断比较 错误截图 51 textValue = driver.get_attribute("text") 52 if textValue != "多云": 53 objUtil.screenshot_NG() 54 self.TestResult = 'FAIL' 55 else: 56 self.TestResult = 'PASS' 57 58 59 if __name__ == '__main__': 60 unittest.main()
此处只讲述我们对一个测试脚本必须存在内容的需求。我认为若满足以下三点要求,就算一个合格的测试脚本了。
1、测试用例的描述,包含测试目的,测试详细步骤,预期结果等
2、简洁,易于阅读和维护的代码结构
3、详细的运行LOG记录与测试报告
所以很明显以上脚本结构上是不够完整的,测试执行人员可能都不知道这个脚本测的什么内容。改之
根据用例表批量生成脚本
我的用例管理表如下,xlsx的表格。以下内容是随便举的一个例子(可能测试用例写得不正确)
代码实现的逻辑:解析用例管理表,生成测试脚本框架
# !/usr/bin/env python # -*- coding:utf-8 -*- # !python3 __author__ = "xxx" """自动化脚本生成工具""" import os import xlrd import time TestCaseName = "" TestCaseDescription = "" TestCasePreCondition = "" TestCaseStep = "" TestCaseExpectResult = "" TestEnvironment = "" TestScriptName = "" cur_path = os.getcwd() def scripts_template(): testcases = os.path.join(cur_path, u"用例模板.xlsx") data = xlrd.open_workbook(r'%s' % testcases) table = data.sheet_by_index(0) n_rows = table.nrows n_cols = table.ncols for i in range(1, n_rows): TestCaseName = table.cell_value(i, 1) TestCaseDescription = table.cell_value(i, 2) TestCasePreCondition = table.cell_value(i, 3) TestCaseStep = table.cell_value(i, 4) TestCaseExpectResult = table.cell_value(i, 5) TestEnvironment = table.cell_value(i, 0) TestScriptName = "test_{0}".format(TestCaseName) #符合unittest测试用例定义的识别条件, 以"test"开头 filename = os.path.join(cur_path, "{0}.py".format(TestScriptName)) with open(filename, 'w', encoding='utf-8') as out: out.write('''# !/usr/bin/env python # -*- coding:utf-8 -*- """ #----------------------------------------------------------------------- 用例名称: {0} 用例描述: {1} 前置条件: {2} 测试步骤: {3} 预期结果: {4} 测试环境: {5} 作者:{6} 日期:{7} #----------------------------------------------------------------------- """ import unittest class {8}(unittest.TestCase): def setUp(self): #TODO 添加用例执行前置条件 pass def testRun(self): #TODO 添加用例执行测试步骤 pass def tearDown(self): #TODO 添加恢复测试环境操作 pass if __name__ == '__main__': unittest.main()'''.format(TestCaseName, TestCaseDescription, TestCasePreCondition, TestCaseStep, TestCaseExpectResult, TestEnvironment, __author__, time.strftime('%Y-%m-%d'), TestScriptName)); print("generate scripts finished!") if __name__ == "__main__": scripts_template()
运行一下以上测试脚本生成代码。生成的脚本如下:
1 # !/usr/bin/env python 2 # -*- coding:utf-8 -*- 3 4 """ 5 #----------------------------------------------------------------------- 6 用例名称: case_01_01_01_01 7 用例描述: 测试天气提示刷新 8 前置条件: 9 打开天气APP 10 测试步骤: 11 1.后台设置今日天气为多云,查看App提示是否更新。 12 预期结果: 13 页面天气提示刷新为多云 14 测试环境: Phone 15 作者:xxx 16 日期:2019-01-08 17 #----------------------------------------------------------------------- 18 """ 19 20 import unittest 21 22 23 class test_case_01_01_01_01(unittest.TestCase): 24 25 def setUp(self): 26 #TODO 添加用例执行前置条件 27 pass 28 29 def testRun(self): 30 #TODO 添加用例执行测试步骤 31 pass 32 33 def tearDown(self): 34 #TODO 添加恢复测试环境操作 35 pass 36 37 if __name__ == '__main__': 38 unittest.main()
以上生成的脚本看起来就比较清晰了,再添加自己封装后的测试接口,整体结构上非常简洁明了。