SHELL实现自动化测试框架(Linux命令行测试)

6 篇文章 0 订阅
4 篇文章 0 订阅

SHELL实现自动化测试框架

相关术语

缩写全称描述
SATShell Automated Test使用Shell实现的自动化测试

背景

用以下功能用例举例

用例标题步骤预期
基础命令:验证which基础命令功能正确1、在命令行输入:which bash1、输出:/usr/bin/bash
2、在命令行输入:which ls whereis cp2、输出:/usr/bin/ls /usr/bin/whereis /usr/bin/cp

手工测试,我们要执行该用例需进行4个步骤:

  • 执行步骤1:命令行中输入命令which bash
  • 验证步骤1:查看步骤1输出结果,验证结果与用例中预期是否一致
  • 执行步骤2:命令行中输入命令which ls whereis cp
  • 验证步骤2:查看步骤2输出结果,验证结果与用例中预期是否一致

模拟命令行中测试实例:

mars@mars-PC:~$ which bash  # 步骤1
/usr/bin/bash  # 步骤1输出结果

mars@mars-PC:~$ which ls whereis cp  # 步骤2
/usr/bin/ls
/usr/bin/whereis
/usr/bin/cp  # 步骤2输出结果

若从人工执行转换为自动化执行:自动执行命令、自动验证输出结果、生成测试报告,这样除了在全量测试时减少巨大的工作量,还能在回归测试、边缘测试时执行多覆盖大部分测试范围。

方案

实现该自动化方案,这里选择使用Shell来实现。Shell是一个命令解释器,它不仅是Linux操作系统内核与用户之间的绝缘层(俗称壳),同时也是一种功能相当强大的编程语言,可直接执行linux系统命令,它类似于DOS下的cmd.exe。

该方案除了Shell以外也可使用其他语言实现,比如Python,但是Python只能通过os、subprocess库来调用linux系统命令,不像Shell可直接执行系统命令,在脚本的编写和调式都不如Shell简洁、方便,所以最终方案的实现为Shell。这里对该技术方案命名为SAT方便后续说明使用。

使用场景【查询xx应用进程状态】的Shell、Python代码作为对比:

  • Python
import subprocess

ps_state=subprocess.run('ps aux|grep -v grep|grep -q xx', shell=True).returncode
print(ps_state)
  • Shell
ps aux|grep -v grep|grep -q xx
echo $?

通过以上对比可发现,实现一个相同的功能,Shell编写的代码要更为直接、简洁,命令越复杂这个优势越明显。

设计

SAT是一个简单的自动化测试框架,主要实现命令行用例的自动执行并输出测试报告,体现出用例的执行情况,可快速对失败用例进行定位。总体可以划分为下面几个模块:

  • 用例模块(case):存放转换为自动化测试用例的代码,最小单位为函数,该框架支持多个用例模块文件。

  • 方法封装模块(method):存放一些公用方法函数,比如:断言、测试报告等。

  • 启动测试模块(run_repor):存放启动测试的主代码,对用例模块文件进行批量处理并生成测试报告。

  • SAT目录结构如下:

       SAT					      #主目录
       ├── case                      # 存放用例模块的目录
       │   ├── case_a.sh             	# 测试人员A用例文件
       │   └── case_b.sh             	# 测试人员B用例文件
       ├── method                    # 存放方法封装模块的目录
       │   ├── assertion.sh				# 断言函数封装模块文件
       │   └── other.sh					# 其他函数封装模块文件
       ├── report					 # 存放测试报告的目录
       │   ├── report_0817231130		# 测试报告文件
       │   └── report_0819115441
       └── run_report.sh			 # 启动测试模块文件
    
  • SAT框架运行流程图如下:

运行流程
步骤描述
依次调用函数
模块导入+变量初始化定义与赋值
依次执行导入的用例模块文件
统计用例通过与失败数量+失败用例编号
记录整个过程与结果落地归档
SAT
启动测试
环境初始化
执行测试用例
收集用例执行数据
生成测试报告
用例模块(case)

实际项目中每个人负责的模块与用例不同,所以自动化测试用例需要自己编写负责部分,不像其他模块中的代码都是公用的,那么在编写格式上需要做统一的约定:

  • 用例模块文件命名统一,测试人员A、B的用例模块文件:case_a.sh、case_b.sh。
  • 测试用例最小单位统一:每一条测试用例为一条函数,通过函数来管理用例。
  • 用例函数命名统一,测试人员A的第1、2条用例:test_a1(){}、test_a2(){}。
  • 用例函数元素统一,需要包含变量:title、case_id、断言函数。

格式统一之后,每人完成自己部分的用例文件,在启动测试时只要汇总全部用例模块文件,即可完成所有人的测试用例执行。

以下为测试人员A的用例模块文件 “case_a.sh” 部分内容:

#! /bin/bash
# 文件:case_a.sh
# 说明:基础镜像自动化测试用例
# 作者:黄先生
# 日期:2020/01/16


# 测试人员A的第一条用例
test_a1(){
	
    title="检查内核启动信息"   # 用例标题
	case_id=xxxxx			# 用例编号
    a="error|fail|warning|call\ trace"  # 用例执行命令结果
    b=`sudo dmesg`						# 用例预期结果
    assertNoIn "${a}" "${b}"  			# 断言比较用例执行情况,若b中不包含a则通过

}

# 测试人员A的第二条用例
test_a2(){

	pass

}
方法封装模块(method)

该模块主要用于存放公共方法函数,集中管理方便后期维护,封装的函数主要实现以下功能:

  • 用例断言:判断用例执行结果与预期是否一致,给出对应输出结果。
  • 用例处理:批量处理不同的用例模块文件:执行不同的用例模块文件,输出用例执行结果。
  • 用例统计:统计用例执行的数据:统计执行用例数量、通过用例数量、失败用例数量、失败用例编号。
  • 测试报告:结合以上全部内容输出本地文档,方便测试结果归档保存。

通过以上公共方法函数的封装,其他模块直接调用即可,代码更为清晰简洁,并减少冗余。

启动测试模块(run_repor)

该模块为执行测试的主模块,主要是对测试开始前环境做初始化并运行测试,主要包含:

  • 模块初始化:导入方法模块;根据对用例模块文件的分析,导入对应的模块文件。

  • 变量初始化:针对一些数据统计相关的函数做初始化赋值:用例数量、用例通过/失败数量、定义数组变量等。

  • 运行测试:调用测试执行函数、测试报告生成函数、提示用户测试报告生成路径。

关键技术

这里主要选取了部分关键功能,其他部分则不细说了,针对这部分功能说明通过Shell是如何的实现,功能如下:

  • 初始化
  • 断言
  • 测试执行
  • 测试报告
初始化功能的实现

该功能是为后续测试提供良好的运行环境,主要分为两部分:

  • 导入模块

    • 首先会导入方法封装模块,然后判断存放用例模块的目录下是否有用例文件,根据判断结果对用例模块的导入和对应统计用例数量变量赋值。
  • 初始化变量

    • 对所有变量进行初始化定义与赋值,为后续的数据统计提供环境。
  • 代码实现如下:

    # 初始化函数
    setup(){
    
    	if [ "`whoami`" != "root" ]
    	then
    		read -p "请已root用户运行该脚本,点击Enter退出" end
    		exit
    	fi
    	source ./method/assertion.sh   # 导入方法封装模块
    	source ./method/other.sh   	   # 导入方法封装模块
    	if test -f ./case/case_a.sh	   # 判断是否存在用例模块
    	then
    		source ./case/case_a.sh	   # 若存在用例模块则导入
    		num_a="`cat ./case/case_a.sh|grep test_a|wc -l`"  # 若存在用例模块则获取用例数量并赋值给对应用例数量变量
    	else
    		num_a=0  # 若不存在用例模块则对应用例数量变量赋值为0
    	fi
    	if test -f ./case/case_b.sh
    	then
    		source ./case/case_b.sh
    		num_b="`cat ./case/case_b.sh|grep test_b|wc -l`"
    	else
    		num_b=0
    	fi
    	if test -f ./case/case_c.sh
    	then
    		source ./case/case_c.sh
    		num_c="`cat ./case/case_c.sh|grep test_c|wc -l`"
    	else
    		num_c=0
    	fi
    	fail=0 # 统计不通过用例数量
    	pass=0 # 统计通过用例数量
    	total=0 # 统计执行用例数量
    	declare -a fail_id  # 定义失败用例ID数组变量
    	
    }
    
断言功能的实现

该功能实现的是在每一条用例执行之后,对用例执行结果与预期结果对比,判断用例执行结果为通过、失败,并且对结果进行输出;与此同时也参与了一些数据收集工作,递增通过/失败/执行用例数量。

断言对比的方法多种多样,这里拿部分举例,详情见下方代码:

# assertEqual ${1}等于${2}则为true
assertEqual(){

	if [ "${1}" = "${2}" ]     # ${1}、${2}变量为用例执行的过程中传入的执行结果与预期结果
    then
        r="pass"   # 输出通过测试结果
    else
        r="fail"   # 输出失败测试结果
		fail_id[${fail}]=${case_id}  # 提取结果为失败的测试用例ID,并添加进数组
    fi
	case_pf   # 已封装函数:判断用例执行情况,操作对应数据统计变量,递增通过/失败/执行用例数量
	
}

# assertNoIn ${1}不在${2}中则为true
assertNoIn(){

    result=`echo "${2}"|grep -E "${1}"`
    if [ "${result}" ]
    then
        r="fail"
		fail_id[${fail}]=${case_id}
    else
        r="pass"
    fi
	case_pf
	
}
测试执行功能的实现

该功能主要是实现不同用例模块中用例的批量执行,与此同时会辅助做一些其他工作:

  • 创建测试报告文件,并初始化部分内容:记录测试开始时间、记录各测试模块中用例数量
  • 实时输出结果至终端与测试报告文件
  • 对输出结果进行排版设计
  • 具体代码如下:
# 执行测试
test_start(){

	t_start=$(date +"%m%d%H%M%S")  # 获取当前时间戳并格式化
	report="report_${t_start}" && report_path=./report/${report} && touch ${report_path}  # 创建测试报告文件并赋值路径变量
	# sl
	# clear
	echo "_____________________________________________________________________________" >>  ${report_path} && cat ${report_path}
	echo "" >>  ${report_path} && cat ${report_path}| tail -1    # 此类追加格式为追加内容进测试报告并展示在终端
	echo " # 测试开始 #" >>  ${report_path} && cat ${report_path}| tail -1
	echo " # 测试人员A:本轮测试,用例数量:${num_a}条 #" >>  ${report_path} && cat ${report_path}| tail -1
	echo " # 测试人员B:本轮测试,用例数量:${num_b}条 #" >>  ${report_path} && cat ${report_path}| tail -1
	echo " # 测试人员C:本轮测试,用例数量:${num_c}条 #" >>  ${report_path} && cat ${report_path}| tail -1
	echo "_____________________________________________________________________________" >>  ${report_path} && cat ${report_path}| tail -1
	echo "" >>  ${report_path} && cat ${report_path}| tail -1
	printf "%-20s %-20s%20s\n" 用例ID 执行结果 用例标题 >> ${report_path} && cat ${report_path}| tail -1   # 用例执行输出结果格式化

	if [ "${num_a}" != "0" ]
	then
		for i in `seq 1 ${num_a}`  # 批量执行测试人员A用例
		do
			test_a${i}
			test_result;sleep 1    # 已封装用例执行输出结果函数,输出用例ID、测试结果、用例标题,并格式化排版
		done
	fi
	
	if [ "${num_b}" != "0" ]
	then
		for i in `seq 1 ${num_b}`  # 批量执行测试人员B用例
		do
			test_b${i}
			test_result;sleep 1
		done
	fi
	
	if [ "${num_c}" != "0" ]
	then
		for i in `seq 1 ${num_c}`  # 批量执行测试人员C用例
		do
			test_c${i}
			test_result;sleep 1
		done
	fi
}
测试报告功能的实现

该功能主要实现的是收集测试过程中与测试结束后的数据,并统一输出至文档文件中,并对每一次的测试结果做归档处理,方便后续跟踪某一次的测试结果。

具体实现代码如下:

# 测试报告统计通过、失败用例数量
case_pf(){

	if [ "${r}" == "pass" ]
	then
		let pass+=1
	elif [ "${r}" == "fail" ]
	then
		let fail+=1
	fi
	let total+=1

}

# 输出用例结果,并对结果进行格式化排版
test_result(){

	printf "%-20s %-20s %-20s\n" ${case_id} ${r} ${title} >> ${report_path} && cat ${report_path}| tail -1

}

# 测试报告结束
test_report(){
	t_end=$(date +"%m%d%H%M%S")  # 获取测试结束时间
	echo "_____________________________________________________________________________" >>  ${report_path} && cat ${report_path}| tail -1
	echo "" >>  ${report_path} && cat ${report_path}| tail -1
	echo "测试开始时间:${t_start}" >> ${report_path}    # 依次输出各关键信息
	echo "测试结束时间:${t_end}" >> ${report_path}	
	echo "测试电脑架构:`uname -m`" >> ${report_path}
	echo "执行用例合计:${total}" >> ${report_path}
	echo "用例通过数量:${pass}" >> ${report_path}
	echo "用例失败数量:${fail}" >> ${report_path}
	echo "失败用例ID:${fail_id[*]}" >> ${report_path}
	cat ${report_path} | tail -7
	echo "_____________________________________________________________________________" >>  ${report_path} && cat ${report_path}| tail -1

}

实验验证

为了说明SAT的工作流程,这里拿一个实际场景举例,本次测试需要自动化执行:测试人员A、测试人员B的用例,无需执行测试人员C的用例:

操作流程如下

  • 收集测试人员A、测试人员B最新的测试用例模块文件,放入目录"SAT/case/"下。
  • SAT目录下启动终端,运行命令su进入Root。
    • 因部分命令需要root权限,使用sudo+命令需要提示用户输入密码,不友好。
    • 若用户使用普通用户权限运行,则给出对应提示:请已root用户运行该脚本,点击Enter退出,并关闭。
  • 终端实时查看测试过程,过程中会输出用例数据与用例执行结果。
  • 等待测试完成后,终端可查看测试结果,重点关注失败用例ID,对其做二次验证并提交Bug单。
  • 关闭终端后若还需查看测试结果,进入"SAT/report/"目录,根据文件命名中时间戳定位测试报告文件并查看。

终端中与测试报告中内容展示一致,主要体现自动化测试流程与结果,可看到下方输入内容,展示各关键信息了:

_____________________________________________________________________________

 # 测试开始 #
 # 测试人员A:本轮测试,用例数量:5条 #
 # 测试人员B:本轮测试,用例数量:1条 #
 # 测试人员C:本轮测试,用例数量:0条 #
_____________________________________________________________________________

用例ID              执行结果                用例标题
xxxxxx               pass                 检查内核信息与版本号
xxxxxx               fail                 检查内核启动信息
xxxxxx               pass                 验证perl环境    
xxxxxx               pass                 验证python环境  
xxxxxx               pass                 验证系统预装软件包状态
xxxxxx               fail                 创建test文件夹 
_____________________________________________________________________________

测试开始时间:0818102422
测试结束时间:0818102428
测试电脑架构:x86_64
执行用例合计:6
用例通过数量:4
用例失败数量:2
失败用例ID:xxxxxx  xxxxxx 
_____________________________________________________________________________

#  测试完毕,测试报告生成在'./report'目录,点击Enter退出! #

小结

如此一个简单的自动化测试框架就完成了,已经可以很好的满足日常测试,以上是初期的一个简单设计。经过后续的迭代,目前已经支持各种功能配置、环境检测、测试流程控制、邮件发送测试报告、自动代码提交、代码格式/规范扫描等。大家可根据自己的项目需要做相应的完善,这里仅提供一个思路。

  • 4
    点赞
  • 34
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
对于Linux环境下的自动化测试,有几种常用的工具和技术可以使用。 1. Shell脚本:Linux系统自带的Shell脚本语言可以用于编写简单的自动化测试脚本。你可以使用Shell脚本调用命令行工具、执行测试命令、验证输出等。这种方式简单易用,适合于一些简单的测试任务。 2. Python:Python是一种流行的脚本语言,也是进行自动化测试的常用选择。Python拥有丰富的库和工具,可以进行各种测试任务,例如使用unittest或pytest框架编写测试脚本,使用selenium或requests库进行Web自动化测试,使用paramiko库进行SSH连接测试等。 3. Jenkins:Jenkins是一个流行的开源持续集成和持续交付工具,也可以用于自动化测试。你可以在Jenkins上配置和管理自动化测试任务,设置定期运行测试脚本,并生成测试报告。Jenkins提供了丰富的插件和集成选项,使得整个自动化测试过程更加灵活和可控。 4. Ansible:Ansible是一个自动化运维工具,也可以用于自动化测试。通过Ansible,你可以编写测试任务的Playbook,描述测试环境的配置和准备工作,并执行测试任务。Ansible具有强大的扩展性和可重用性,可以与其他工具和服务集成,实现全面的自动化测试流程。 以上是一些常见的Linux自动化测试工具和技术,具体选择取决于你的需求和项目要求。希望对你有所帮助!如果你对其他方面还有疑问,可以继续提问。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值