-
2013-11-24 22:30:06
一、前言
一直想多学习一下Linux,总得找一个方向吧。书太多,也看过许许多多的Linux书,代码太多,看过比较多的代码,可是为啥一直在入门ing,从未进入过。。。。。。好吧,最近找完工作,时间也蛮多,于是想系统的学习一下Linux下的驱动程序设计。一是为了学习,二是为了实验室实际项目需要。所以我买了传说中的经典书籍LDD<<Linux设备驱动程序>>,之前早已听闻这本书。
花了大概大半个月时间把这本书的前十二章看完了,于是想自己动手写写驱动程序,来实际验证究竟是不是像书上讲的那样写,就能在Linux下实现驱动程序控制设备的功能。于是找了书中的例子,拿并口驱动程序做实验。此文主要想记录我实验的详细过程和实验过程中遇到的问题和解决办法。
以下是我的实验环境:
1、一台带并口的PC机:研华工业计算机,酷睿CPU
2、ubuntu11.04,安装盘原装内核2.6.38.8。
二、实验过程
1、确保并口是功能完好的。
我刚开始没想到先验证并口是否可用,于是就先按照书上讲的方法先写了一个简单的驱动程序测试并口。结果当然是并口并不能受我的驱动程序控制,于是就很难定位问题出在哪里,很可能是驱动程序问题吧?因为我第一次写驱动,于是一遍一遍的查找是不是程序有问题。。。。。最后发现我找的第一台电脑的并口就是坏的,然后才找到研华工控机的并口是好的。
检查方法我试过二种,第一种是在windows系统下,上网上找并口测试程序,然后用万用表去量并口电压是否受能按设定改变。第二种是在Ubuntu下用原装系统自带的并口驱动程序提供的接口写用户空间测试程序,照样是用万用表去量并口管脚,主要参照http://mockmoon-cybernetics.ch/computer/linux/programming/parport.html。以下是我亲自在我平台上测试通过的:
//Access via raw IO (not recommended)在用户空间获得权限直接访问并口I/O端口,只在X86平台支持。 #include <stdio.h> #include <sys/io.h> #define BASEADDR 0x378 int main(int argc, char **argv) { int i; if(ioperm(BASEADDR, 4, 1) < 0) { fprintf(stderr, "could not get i/o permission. are you root ?\n"); return 5; } for(i=0; i < 256; i++) { outb(i, BASEADDR); } ioperm(BASEADDR, 4, 0); return 0; }
//这是利用UBUNTU自带的并口驱动ppdev和并口设备/dev/parport0(ubuntu已建好)进行并口测试。 //lsmod可以看见lp,ppdev parport_pc parport等并口驱动,cat /dev/ioports能看见并口端口被占的情况 #include<stdio.h> #include<fcntl.h> #include<sys/types.h> #include<sys/stat.h> #include<asm/ioctl.h> #include<linux/parport.h> #include<linux/ppdev.h> #define DEVICE "/dev/parport0" int main() { struct ppdev_frob_struct frob; int fd; int mode; char data = 0xFF; fd = open(DEVICE, O_RDWR); if(fd < 0) { printf("open error:\n"); return -1; } if(ioctl(fd, PPCLAIM)) //这里也可以是其它一些测试代码,按照上面网站教程所说。 { perror("PPCLAIM"); close(fd); return -1; } ioctl(fd, PPWDATA, &data ); ioctl(fd, PPRELEASE); close(fd); return 0; }
2、按照LDD书或者网上各种资料写自己的并口驱动程序,简单的主要完成控制并口电压,驱动程序通过ioctl或者write方法都行。主要的步骤是:在module_init(init_function)的初始化函数init_function()中注册一个字符设备cdev,动态静态注册都行。我是用register_chardev()静态注册。如果注册成功,再用request_region(0x378, 8, DEV_NAME)去申请独占并口端口。这个表示这一并口的I/O端口寄存器是从0x378-0x37F的8个连续地址,可以在BIOS设置基址。然后就是实现ioctl了或者write方法了,ioctl用copy_from_user()将用户空间数据拷贝到内核或者直接用arg参数都行。write()方法必须用copy_from_user()将需要写的数据从用户空间拷贝到内核。然后调用outb(value, 0x378),就能设置0x378地址的I/O端口了。以下是我参照网上一网友的程序:#include <linux/init.h> #include <linux/module.h> #include <linux/kernel.h> #include <linux/fs.h> #include <linux/errno.h> #include <linux/types.h> #include <linux/fcntl.h> #include <asm/uaccess.h> #include <asm/io.h> #define DEV_NAME "phoenix_port" #define DEV_MAJOR 223 #define PORT_WRITE_ADDR 0X378 #define PORT_READ_ADDR 0X379 int phoenix_open(struct inode *inode,struct file *filp) { return 0; } int phoenix_release(struct inode *inode,struct file *filp) { return 0; } ssize_t phoenix_read(struct file *filp, char *buf, size_t count, loff_t *f_pos) { //this fun read one char,not the count you pass unsigned char status; //inb is a function that can read a byte form addr status=inb(PORT_READ_ADDR); //put the byte to usr buf put_user(status, (char *)buf); return 1; } ssize_t phoenix_write(struct file *filp, char *buf, size_t count, loff_t *fpos) {//write one char ,no matter how many you want to write; //get param from usr to kernel unsigned char status; get_user(status, (char*)buf); outb(status, PORT_WRITE_ADDR); printk(KERN_ALERT "write io value:%x",status); return 1; } struct file_operations oper_struct= { .owner=THIS_MODULE, .open=phoenix_open, .release=phoenix_release, .read=phoenix_read, .write=phoenix_write, }; int phoenix_init(void) { int tmp; tmp=register_chrdev(DEV_MAJOR, DEV_NAME, &oper_struct); if(tmp<0) { printk(KERN_ALERT "module_init error !\n"); return tmp; } if(request_region(0x378, 8, DEV_NAME)) { printk(KERN_ALERT "get io port region"); } else { printk(KERN_ALERT "can not get io port region"); } return 0; } void phoenix_exit(void) { release_region(0x378, 8); unregister_chrdev(DEV_MAJOR,DEV_NAME); } module_init(phoenix_init); module_exit(phoenix_exit); MODULE_LICENSE("Dual BSD/GPL");
这段程序是看不出有问题的,然后编译通过生成port.ko文件,用sudo insmod port.ko载入我们写的驱动模块。然后用命令sudo mknod /dev/myport c 223 0生成一个和并口驱动对应的设备文件,其中223必须和驱动一致,次设备号应该是0-255任一个都行,主设备号也可以通过cat /proc/devices查看加载驱动对应的主设备号。系统通过主设备号才能将设备文件和驱动中定义的方法联起来,具体内核怎么实现的,还有待研究,我只知道在主次设备号是设备文件的inode结点的一部分,然后这个inode节点会传给驱动程序的write(),read()方法,在驱动程序中可以通过imajor(inode),iminor(inode)读出设备文件的主次设备号,通常只读次设备号来区分用同一驱动程序的几个类似功能的设备文件,在驱动程序中实现不同的方法。上述过程可能遇到的问题有:1、虚拟控制台看不到内核printk输出信息,用dmesg可以看到。或者切换到真实控制台tty下(非界面UBUNTU)也可以看到。2、insmod port.ko会出现request_region()失败,是因为UBUNTU自带的并口驱动已经把端口占了,所以需要sudo rmmod lp ppde parport_pc相关的驱动,然后再insmod port.ko就行了。然后就可以写用户空间测试程序了,我参照网上,修改成如下的测试程序:#include <stdio.h> #include <sys/types.h> #include <sys/ioctl.h> #include <fcntl.h> #include <sys/stat.h> #include <unistd.h> #define DEV_NAME "/dev/phoenix_port" //必须和mknod建立的文件名一致 int main() { //open phoenix_port int dev; dev=open(DEV_NAME,O_RDWR|O_NDELAY); if(dev<0) { printf("open dev error!\n"); return -1; } //open right printf("have open dev!\n"); int count = 1; char state =0x00; while(1) { if(!(count % 2)) //every two second { state = state ^ 0x01; printf("write state:%x",state); write(dev, &state, 1); } if(!(count % 1)) //every one second { state = state ^ 0x04; printf("write state:%x",state); write(dev, &state, 1); } count++; sleep(1); } //close dev close(dev); return 0; }
然后gcc 编译上面的的用户空间测试程序,sudo ./out执行程序,用demsg查看内核输出信息知道驱动程序ssize_t phoenix_write(struct file *filp, char *buf, size_t count, loff_t *fpos) 已经执行,并且写入了用户空间write()调用传入的数据。至此,我已经以为驱动程序成功的时候,拿万用表去测量并口管脚,发现管脚并无任何变化。然后就是各种寻找可能的问题了。3、解决步骤2中遇到的问题上面遇到的问题很费解了,差不多花了我一个多星期的时间各种寻找解决办法。去上网查过许多教程都是说request_region()成功后,用outb()写端口就行了问过一些驱动交流群也是如此。我只得改驱动程序进行各种尝试了:比如不用write(),而用ioctl()方法比如不用直接访问I/O端口,而是用remap()将端口映射到内存,X86是有独立的端口编址访问才对,所以我只是尝试。比如不用老式的注册设备方法register_chrdev()。而用新的 cdev_init() + cdev_add()。以上所有方法,均能注册设备成功,request_region()成功获得端口,用cat /proc/devices能看见设备驱动名称和主设备号, cat /proc/ioports能看见占用的端口,dmesg也能看见往端口0x386写数据了,但是结果都一样,并口没反应。最费力的方法是我去读内核的ppdev.h ppdev.c驱动文件,想看看它怎么写的。然后想把我的一部分驱动程序利用ppdev.h提供的接口,来定位我的驱动程序的问题所在。比如想把request_region替换为用ppdev.h中的if(ioctl(fd, PPCLAIM)) //方法,或者把write()替换为ppdev.h中的PPWDATA方法,来定位问题,都失败了。最后最后最后,折腾的我有点疯了。就在今天,我想起以前在哪看过一句话,大意是:写驱动开发,最好不要用LINUX发行版本带的内核,因为有的做过修改。而是要自己去下一个标准的内核源码,编译,安装,在这个标准内核源码上做开发。。。像快死的人抓住最后的救命稻草,我只得去一试,结果就刚刚的,经过换成标准内核,并口可以受驱动程序控制了。至此驱动程序勉强算是测试成功。
4、结论虽然最后是测试成功了,但是为啥Ubuntu自带的内核测试不成功,还找不到原因,很奇怪。。。。。总不能产品厂商发行驱动时候,都得要普通Ubuntu用户自己去编译内核吧。5、过程中遇到的一些杂问题和解决办法。刚装的较老版本的UBUNTU,想用sudo apt-get install装任何软件都说找不到安装包,这时需要更新源信息。参 http://www.cnblogs.com/eastson/archive/2012/08/24/2654163.html文章。即编辑/etc/apt/sources.list源文件(添加一些源,比如校内的或者搜狐之类的),再sudo apt-get update即可。好像有不用编制源文件的方法,是直接用一个什么命令。编译驱动的时候说file_operation op结构中的 ioctl()方法无定义,去查找内核asm/ 下ioctl的头文件发现 3.0.0的内核中,ioctl()接口已经更名为unlocked_ioctl()和另外一种ioctl()。所以把取其中一个。6、下一步计划
用FPGA开发外围设备卡,通过PCI总线或者ISA总线挂在研华的工控机上,自己做外围电路和写驱动程序。
更多相关内容 -
24针打印机断针测试程序
2018-09-17 11:37:35适用大部分品牌的24针针式打印机,USB和并口都可,绿色免安装,使用简单。 -
电脑并口测试盒的制作方法及测试程序下载
2011-01-08 15:42:04电脑并口测试盒的制作方法及测试程序下载! 不知各位是否遇到像我这样的尴尬情况,辛辛苦苦花了大半天的工夫和一大把接口芯片银子把HP6L修好。(HP6L不联机)。客户把电脑搬来要求试打一下, 天啦,刚刚修好的机子又... -
液晶TG12864E 并行接口简体测试程序
2010-06-12 11:57:56液晶TG12864E 并行接口简体测试程序 -
1.8寸LCD-STM32F103C8测试程序
2020-10-10 10:09:55基于STM32F103C8T6单片机的1.8寸TFT_LCD液晶屏(ST7735S)测试程序,完整版测试程序代码。 -
并口控制液晶Lcd6963的测试程序
2010-10-08 09:18:23并行接口,简称并口,也就是LPT接口,是采用并行通信协议的扩展接口。本文介绍是用并口控制液晶Lcd6963的测试程序 -
POS小票机测试程序
2015-08-19 22:54:40一个pos机的测试程序,支持并口,串口,网口和usb口 -
小白也能读懂的接口测试,接口测试并没有那么难
2021-08-30 15:14:37接口测试入门,部分人员主要从事功能测试,有的同学不了解接口测试,本文简要介绍了接口测试的定义与相关流程,适合刚入门的同学。 1 接口的定义 现实中我们的接口比如插销、插座等都是遵循一定的标准和规范制作的,...
接口测试入门,部分人员主要从事功能测试,有的同学不了解接口测试,本文简要介绍了接口测试的定义与相关流程,适合刚入门的同学。1 接口的定义
现实中我们的接口比如插销、插座等都是遵循一定的标准和规范制作的,以至于不同厂家生产出来的插头、插座可以共用。那么程序的接口也跟现实的接口的类似。
什么是程序接口,就是程序之间协作要遵循一套规范和标准,开发人员按照规范和标准进行工作,接口一般都是由高级开发人员设计出来的。
2 接口的优点
程序系统一般分为前端和后端,前端就是咱们看到的浏览器或者客户端,后端是后台的一些逻辑检查和控制,接口可以有效的将前端和后端区分出来。
责任划分清晰,找到问题能够划分出是前台的问题还是后台的问题,这样能够很快的定位问题,检查是否前台传值传错还是后台错误,这样能够很快的给开发人员修改问题。
缩短开发周期,标准一致,前台与后台按照同样的标准、规范,各自干各自的工作,并行开发,能够缩短开发周期。
可扩展性强。
3 API接口的概念
应用程序接口(API,Application Programming Interface),以某种协议的形式提供,定义输入、输出规范和相关功能的描述。
举例:登录功能,前端输入用户名和密码,提交后,后台收到前台请求进行处理,然后返回给前台响应结果。
接口文档定义字段为
用户名:user_name
密码:user_passwrod
前端开发人员与后台开发人员都应按照接口约定去传值和取值,当前台浏览器传值为name和password的时候,后台程序取的是user_name ,user_passwrod,导致数据无法获取,最终报错,因为前台没有按照接口文档来传值导致,很容易能判断出是谁的问题。
需要前后台开发人员都遵循接口的标准来传值与取值就可以了,也就是都用
用户名:user_name
密码:user_passwrod
这样就不会有问题了。
4 接口的测试流程
1)接口功能是正确的,保证基础功能是正确的
2)接口的测试数据(特殊数据)检查是否有问题,各种特殊数据对接口进行验证,边界值、特殊字符、空值等
3)自动化脚本的编辑与测试,接口测试过程中,需要多次进行测试,为了提高效率,可以使用工具进行测试,编写脚本,后续可以多次回归运行,比如jmeter
4)接口的性能和压力测试,基础功能都验证完毕后,也要检验下接口的性能,自动化脚本编辑好后,根据要测试要点,设置好测试数据,进行接口的性能和压力测试,检查是否存在瓶颈。
5 普及客户端、服务器、请求、响应概念
客户端:移动应用,web应用等,比如微信、网银、还有柜面程序等。
服务器:为客户端提供服务、提供数据、提供资源的那台机器,比如手机银行查询账户余额,余额的相关信息都保存在核心的服务器上,那想要获取数据,就要访问核心的服务器。
请求:客户端向服务器索取数据的一种行为,比如手机查询余额时,点提交按钮,这就是发出了一个请求。
响应:服务器对客户端的请求,做出的反应,一般指的就是返回数据给客户端。
6 http协议与URL
协议:计算机网络两台机器之间进行通信所必须共同遵守的规则或者规定。
http协议:超文本传输协议,是一个基于请求与响应模式的、无状态的、应用层的协议,只有遵循统一的 HTTP 请求格式,服务器才能正确解析不同客户端发的请求,同样地,服务器遵循统一的响应格式,客户端才得以正确解析不同网站发过来的响应。
URL(统一资源定位符):简单来说,就是互联网上的地址、位置,每一个资源都有一个唯一的URL
格式:协议://主机地址/路径
比如:
# URL格式 https://host:port/path?xxx=aba&ooo=bbc ## http/https:这个是协议类型 ## host:服务器的IP地址或者域名 ## port:HTTP服务器的默认端口是80 ## path:访问资源的路径 ## url里面的?这个符号是个分割线,用来区分问号前面的是path,问号后面的是参数 ## url-params:问号后面的是请求参数,格式:xxx=aaa ## 多个参数用&符号连接
7 get与post请求
1、get请求重点在从服务器上获取资源,而post请求重点在向服务器发送数据。
2、get传输数据是通过URL请求,以字段=value的形式,用?连接置于URL之后,多个请求数据之间用&连接,这个过程用户可见,不安全,参数暴露。post传输数据是将字段与对应值封存在请求实体中发送给服务器,这个过程用户不可见,隐藏式的请求,相比是安全的。
3,get传输的数据量小,受URL长度的限制,但是效率高。post传输数据量不受限制,可以传输大量数据,所以传输文件时只能使用post,但是效率较低。请求较多时可能形成一个请求队列。
4,get方式只支持ASCII字符,因此向服务器传输中文有可能出现乱码。post支持标准字符集,可以正确传递中文字符。
7 测试工具
jmeter:Jmeter是一款优秀的开源测试工具, 是每个资深测试工程师,必须掌握的测试工具,熟练使用Jmeter能大大提高工作效率。
Jmeter 是一款使用Java开发的,开源免费的,测试工具, 主要用来做功能测试和性能测试(压力测试/负载测试),而且用Jmeter 来测试 Restful API, 非常好用。
官方网站:http://jmeter.apache.org/
解压后, 运行 “bin/jmeter.bat”
8 测试实战
目的:获取某个城市的地区代码
发送request 请求获取城市的城市代号,http://toy1.weather.com.cn/search?cityname=北京 ,从这个请求的response 中获取到北京的城市代码. 比如:北京的地区代码是101010100beijing北京
jmeter配置:
1)建立线程组
2)线程组下建立http请求
3)配置http请求参数
4)添加查看结果树,便于查询运行结果
5)试着运行,查看
请求数据如下:
响应结果数据如下
获取到了城市代码,说明接口已经调通,然后就可以根据接口的测试流程来验证整个接口的功能。
本文主要介绍了接口方面的测试知识,相对比较初级,希望能对刚入行的伙伴有一点帮助,喜欢的话可以点个“在看”哟,鼓励一下。
最后: 可以关注公众号:伤心的辣条 ! 进去有许多资料共享!资料都是面试时面试官必问的知识点,也包括了很多测试行业常见知识,其中包括了有基础知识、Linux必备、Shell、互联网程序原理、Mysql数据库、抓包工具专题、接口测试工具、测试进阶-Python编程、Web自动化测试、APP自动化测试、接口自动化测试、测试高级持续集成、测试架构开发测试框架、性能测试、安全测试等。
如果我的博客对你有帮助、如果你喜欢我的博客内容,请 “点赞” “评论” “收藏” 一键三连哦!
好文推荐
转行面试,跳槽面试,软件测试人员都必须知道的这几种面试技巧!
-
各式热敏打印机测试程序 小票打印机测试
2011-03-05 22:56:29用来测试热敏小票打印机 提供单张测试、走纸、疲劳测试等功能 支持并口串口 -
GPS测试程序12864液晶(并行方式).zip
2014-09-07 22:36:36一个简单GPS模块,C51程序,注释详细,功能齐全。 -
并口128964通过测试.rar
2021-05-11 11:09:57基于stm32的12864液晶并口程序(完全通过测试本人亲写) -
CH375B USB读写模块/U盘读写模块模块测试程序+原理图+相关资料-电路方案
2021-04-22 06:42:46功能特点: 1、CH375B是一个USB总线的通用接口芯片,具有8 位数据总线和读、写、片选控制线以及中断输出,可以方便地挂接到单片机/DSP/MCU/MPU等控制器的系统总线上。在USB 主机方式下,CH...U盘读写模块测试程序截图: -
Jmeter接口测试实战分享,你一定要知道的问题总结!
2021-09-23 14:38:06Jmeter是一款性能测试工具,因轻量级、开源、社区接受度高、容易入门等优点,也被测试人员广泛用于做接口测试。在使用Jmeter做较大规模、复杂场景的接口测试时,往往会遇到一些困难。阅读本文你将了解: 在工作时间...
Jmeter是一款性能测试工具,因轻量级、开源、社区接受度高、容易入门等优点,也被测试人员广泛用于做接口测试。在使用Jmeter做较大规模、复杂场景的接口测试时,往往会遇到一些困难。阅读本文你将了解:- 在工作时间紧张情况下,如何做好自动化测试?
- 如何设计一套完整的、结构优化的jmeter接口自动化测试方案?
- 如何设计复杂的Jmeter接口测试用例?
- 如何提升编写Jmeter自动化脚本的能力?
项目背景
被测系统是泰康云TDS平台,该平台整合敏捷开发与DevOps研发管理工具,提供产品规划、项目管理、代码托管、代码检查、持续集成和持续发布、制品管理等能力,简化研发协作过程,帮助研发团队完成软件生命周期管理。本篇内容以TDS平台测试为背景,介绍测试人员如何设计接口自动化测试。
遇到的问题
本文从我们工作中常遇到的问题入手,展开问题,详细解答。
问题一:被测项目迭代频繁,测试用例设计、维护、执行已经占用了测试工程师大部分工作时间,没有时间搞自动化怎么办?问题二:为什么选jmeter做接口自动化测试?
问题三:多人协同测试情况下,自动化脚本结构如何设计?
问题四:单接口测试用例设计、执行、断言比较简单,但是涉及多接口、异步等复杂场景该如何设计用例?
问题五:接口测试用例如何断言?只断言被测接口返回值就可以了吗?
问题六:Jmeter与流水线集成,除了jmeter+ant+jenkins,还有更优的方案吗?
问题七:如何度量接口自动化结果?接口用例成功率达到100%就够了吗?
问题八:测试脚本执行过程中遇到的稳定性、执行效率等问题如何解决?
实践分享
问题一:没有时间搞自动化测试?
下面将从敏捷项目迭代特点和自动化测试时间规划这两个方面,介绍我们是如何确认自动化测试目标、安排自动化测试时间的。
1>分析敏捷项目迭代特点,确认自动化测试目标
下图展示了在敏捷开发模式中,随着项目迭代进行,新功能特性与已有功能特性的数量变化。每个迭代新特性的测试工作量变化不大,但是已有特性的回归测试任务量却是累计增加的。
因此我们自动化接口测试的目标是针对已有特性做自动化回归测试,提升回归测试效率。而对当前迭代的新特性以手工测试为主,自动化测试为辅。-
针对当前迭代新特性,手工测试为主,自动化测试为辅。原因分析:
当前迭代中的新功能是逐渐成长起来的。功能可能不稳定,需要修改优化,对新功能立即开发自动化测试脚本投入成本大;
当前迭代中的新功能,借助沟通,通过手动形式直接验证更有效;
每天发好几个版本,增加什么就测试什么,手工测试灵活性高。
-
针对上一个迭代已有特性,采用自动化回归测试。原因分析:
上一个迭代已有功能相对稳定,自动化脚本开发和调试都没有障碍,脚本开发效率更高;
自动化测试发现缺陷的能力比手动测试弱,用于回归测试更符合自动化测试的特点。
2>为自动化测试腾出时间
方法:
- 在迭代初期,通过思维导图梳理测试点,而不一定要写详尽的测试用例,从而节省时间编写上一个迭代特性的自动化测试脚本和脚本维护;
- 在迭代测试过程中,利用探索式测试风格,持续开展测试学习、设计、执行、结果分析,提高测试效率,积累测试经验,节省测试时间。
问题二:为什么要用Jmeter做自动化接口测试?
用Jmeter做接口测试工具有以下优势:
- 支持测试脚本录制,badboy、blazemeter等;
- 支持多平台部署,易于与流水线集成;
- 开源免费,提供丰富组件及第三方插件库;
- 支持多线程组并行,提高接口测试效率;
- 一学多用,接口测试->性能测试。
问题三:多人协同测试,自动化脚本结构如何设计?
Jmeter元件组合是非常灵活的,为了提升用例维护效率、方便多人协作,我们参考相关资料及项目实践经验,总结了如下图脚本结构:
以下为主要脚本结构及对应Jmeter元件说明:测试计划:项目根节点
jmeter相关元件说明:
TestPlan:控制测试用例执行方式:并行/串行
全局参数配置:
jmeter相关元件说明:
User Defined Variables:存放测试环境(dev/test)配置信息
JDBC Connection Configuration:存放数据库连接配置
HTTP Request Defaults:配置http接口默认参数,全局生效,eg:请求timeout=10000ms
当前脚本通用模块库:存放所有测试相关采样器,由用例模块通过模块控制器调用
包含健康检查相关、webShell相关、数据准备模块、变量初始化模块、数据断言模块、登录模块、团队管理模块、流水线模块、制品管理模块等业务模块
jmeter相关元件:
Transaction Controller
HTTP Request Sampler
JDBC Request Sampler
WebSocket request-response Sampler
WebSocket Open Connection Sampler
Response Assertion
JSON Assertion
BeanShell Assertion
历史组件/模块设计参考
接口测试模板
用例模块:存放接口测试用例,通过模块控制器调用当前脚本通用模块库
包含:项目管理、部署组管理、svn管理、团队管理、流水线管理、代码库管理、制品管理等相关测试用例集合
jmeter相关元件
Test Fragment:作为用例分割符
Thread Group:用例组,存放一组相关测试用例
Transaction Controller:事务控制器
Module Controller:调用当前脚本通用模块库
User Defined Variables:存放用例相关测试数据
BeanShell Sampler:实现用例编号自增,参数传递等
测试结果展示
View Results Tree
Summary Report
问题四:复杂场景如何设计用例?
复杂场景用例设计之前,先分享下从功能角度出发,我们是如何设计用例的。如下图所示:
除此之外,结合项目实际情况,还需要考虑其他非功能场景:- 异常测试,eg:幂等(重复提交、超时重试)、接口事务、分布式场景、环境异常、大数据量等;
- 性能测试,eg:响应时间、吞吐量、资源利用率等;
- 安全测试,eg:敏感信息是否加密、接口权限控制、sql注入等。
下面以实际项目中的两个场景为例,来分享我们是如何应对复杂测试场景的。
1、多接口实例:流水线执行场景测试,涉及6个接口
方法:
步骤1、分析相关接口调用顺序、阶段。
前置准备
新建项目接口、项目关联代码库接口、新建部署组接口
用例执行
新建流水线接口、流水线执行接口
后置处理
项目删除接口
步骤2、测试数据梳理:
需要在运行前初始化的数据,包含:
环境配置信息,eg:ip、端口、数据库配置等
测试场景共享数据,eg:代码库信息
单接口测试数据
运行时动态生成的数据,包含:
某个接口的返回数据,其他接口需要使用,eg:项目id、部署组id、流水线id等
需要调用相关函数或工具动态生成的数据,eg:uuid、时间戳等
步骤3、梳理测试用例,编写相关脚本,脚本图示如下:
2、异步实例:流水线配置定时任务后,验证定时任务是否按照配置时间成功触发
难点分析:流水线配置定时任务不会立即执行,定时任务触发需要等待websocket推送消息
方法:步骤1:新建流水线配置定时任务执行时间为当前时间+1min
使用beanshell采样器实现
Calendar calendar = Calendar.getInstance();//获取当前时间 calendar.set(Calendar.MINUTE,calendar.get(Calendar.MINUTE)+1);
步骤2:通过WebSocket request-response Sampler监听定时任务推送的消息,完成断言。脚本图示如下:
问题五:接口测试用例如何断言?
对于接口的正确性验证,只验证被测接口返回body很明显是不够的,这里总结了如下断言方法:
-
基础断言:
响应断言
正则匹配
响应码匹配
jackson + beanshell断言
import com.fasterxml.jackson.databind.JsonNode; import com.fasterxml.jackson.databind.ObjectMapper; //获取接口返回body--实际结果 String json_response = prev.getResponseDataAsString(); ObjectMapper mapper = new ObjectMapper(); JsonNode rootNode = mapper.readTree(json_response); JsonNode dataNode = rootNode.path("data"); JsonNode totalNode = dataNode.path("total"); String actual = totalNode.toString(); //接口返回的总条数--期望结果 String except = vars.getObject("program_source_data").size().toString(); if(actual.toString().equals(except)){ Failure = false; }else{ Failure = true; FailureMessage = "期待数量:"+except+" VS 实际数量:"+actual+"不一致"; }
- 相关接口辅助验证:
- 数据库匹配,JDBC Request + BeanShell断言,示例如下:
// JDBC Request 采样器 获取返回结果 -> triggers_count SELECT count(*) FROM qrtz_triggers a WHERE a.JOB_NAME LIKE '%${search_key}%' ORDER BY JOB_NAME desc; // BeanShell断言 String except = vars.get("except_count");//期望结果 String actual = vars.get("triggers_count_1");//数据库查询到的总条数 if(actual.equals(except)){ Failure = false; }else{ Failure = true; FailureMessage = "期待数量:"+except+" VS 实际数量:"+actual+"不一致"; }
问题六:jmeter+ant+jenkins如何改进?
jmeter+ant+jenkins是一种常用的流水线集成方法,但在集成过程中存在环境配置繁琐的问题,比如:
-
需要安装jdk、ant、jmeter环境,版本变更还需要重新卸载安装
-
jmeter依赖第三方jar包,每次都需要手动打包上传服务器
-
jmeter配置文件变更,需要去服务器手动修改
-
jenkins中不同流水线依赖jmeter版本不一致时,需要手工安装多个jmeter版本
针对以上问题,我们采用的替代方案是 jmeter-maven-plugin + mvnw ,运行环境只需要安装jdk就可以了,将maven、jmeter版本以及第三方jar包管理,都托管到gitlab一个代码库中进行集中管理。
进行接口测试只需要git clone代码,然后执行 mvnw clean verify就可以触发测试执行。代码库配置如下图:
工具依赖
问题七:如何度量接口自动化结果?
1、jmeter原生报告优化
jmeter CLI运行方式产生的测试报告统计信息偏向性能指标,无法满足jmeter接口测试需求。因此使用dom4j解析jmeter生成的xml结果文件,使用ExtentReports5生成html报告,报告示例如下:
2、使用jacoco统计接口测试代码级覆盖率报告
接口测试用例成功率即使达到100%,仍然会存在漏测。因此使用jacoco来统计代码覆盖率,分析接口测试未覆盖的代码,进行测试用例补充完善。
关键步骤说明:
步骤1:被测服务打桩
java -javaagent:jacocoagent.jar=includes=*,output=tcpserver,port=9002,address= * -jar 被测服务.jar
步骤2:调用jmeter脚本执行测试
./mvnw clean verify --settings=settings.xml
步骤3:dump覆盖率报告
java -jar jacococli.jar dump --address 被测服务IP --port 9002 --destfile ./jacoco1.exec
步骤4:生成覆盖率报告
java -jar jacococli.jar report ./jacoco1.exec --classfiles BOOT-INF/classes --sourcefiles /src/main/java --encoding utf-8 --html jacoReport
报告展示如下图 :
问题八:如何提升用例执行稳定性和效率?
当测试case数量持续增加时,需要考虑执行稳定性和效率。
总结如下:
预置数据代替创建过程
由于操作越多稳定性越低,使用预置数据而非实时生成的数据,速度更快,稳定性更高。
隔离
使用不同账号等进行隔离。通过隔离,用例执行失败的脏数据就不会影响其他用例;
自动化脚本测试数据与功能测试数据隔离。
jmeter配置优化
设置全局采样器超时等待,eg:timeout=12000ms , 超时自动失败;
针对性能较差的接口配置jmeter定时器 , 防止被测服务压力过大;
设置JMeterProcessJVMSettings,增大内存。
防御式编程
编写测试代码时 , 不能假设数据已存在或者没有脏数据残留,所以预先的判断和清理很重要,比如检查到数据缺失就实时修复、用例运行之前考虑清除临时数据。
不足之处,欢迎指正。
最后: 可以在公众号:伤心的辣条 ! 免费领取一份216页软件测试工程师面试宝典文档资料。以及相对应的视频学习教程免费分享!,其中包括了有基础知识、Linux必备、Shell、互联网程序原理、Mysql数据库、抓包工具专题、接口测试工具、测试进阶-Python编程、Web自动化测试、APP自动化测试、接口自动化测试、测试高级持续集成、测试架构开发测试框架、性能测试、安全测试等。
如果我的博客对你有帮助、如果你喜欢我的博客内容,请 “点赞” “评论” “收藏” 一键三连哦!喜欢软件测试的小伙伴们,可以加入我们的测试技术交流扣扣群:914172719(里面有各种软件测试资源和技术讨论)
好文推荐
转行面试,跳槽面试,软件测试人员都必须知道的这几种面试技巧!
-
接口测试-Mock测试方法
2019-05-26 22:29:02一、关于Mock测试 1、什么是Mock测试? Mock 测试就是在测试过程中,对于某些不容易构造(如 HttpServletRequest 必须在Servlet 容器中才能构造出来)或者不容易获取的比较复杂的对象(如 JDBC 中的ResultSet 对象...一、关于Mock测试
1、什么是Mock测试?
Mock 测试就是在测试过程中,对于某些不容易构造(如 HttpServletRequest 必须在Servlet 容器中才能构造出来)或者不容易获取的比较复杂的对象(如 JDBC 中的ResultSet 对象),用一个虚拟的对象(Mock 对象)来创建以便测试的测试方法。
2、为什么要进行Mock测试?
Mock是为了解决不同的单元之间由于耦合而难于开发、测试的问题。所以,Mock既能出现在单元测试中,也会出现在集成测试、系统测试过程中。Mock 最大的功能是帮你把单元测试的耦合分解开,如果你的代码对另一个类或者接口有依赖,它能够帮你模拟这些依赖,并帮你验证所调用的依赖的行为。比如一段代码有这样的依赖:
当我们需要测试A类的时候,如果没有 Mock,则我们需要把整个依赖树都构建出来,而使用 Mock 的话就可以将结构分解开,像下面这样:
3、Mock对象适用场景
(1)需要将当前被测单元和其依赖模块独立开来,构造一个独立的测试环境,不关注被测单元的依赖对象,只关注被测单元的功能逻辑。
-----比如被测代码中需要依赖第三方接口返回值进行逻辑处理,可能因为网络或者其他环境因素,调用第三方经常会中断或者失败,无法对被测单元进行测试,这个时候就可以使用mock技术来将被测单元和依赖模块独立开来,使得测试可以进行下去。
(2)被测单元依赖的模块尚未开发完成,而被测单元需要依赖模块的返回值进行后续处理。
1)前后端项目中,后端接口开发完成之前,接口联调;
2)依赖的上游项目的接口尚未开发完成,需要接口联调测试;
-----比如service层的代码中,包含对Dao层的调用,但是,DAO层代码尚未实现
(3)被测单元依赖的对象较难模拟或者构造比较复杂。
-----比如,支付宝支付的异常条件有很多,但是模拟这种异常条件很复杂或者无法模拟,比如,查询聚划算的订单结果,无法在测试环境进行模拟。
4、Mock测试的优势
(1) 团队可以并行工作
有了Mock,前后端人员只需要定义好接口文档就可以开始并行工作,互不影响,只在最后的联调阶段往来密切;后端与后端之间如果有接口耦合,也同样能被Mock解决;测试过程中如果遇到依赖接口没有准备好,同样可以借助Mock;不会出现一个团队等待另一个团队的情况。这样的话,开发自测阶段就可以及早开展,从而发现缺陷的时机也提前了,有利于整个产品质量以及进度的保证。
(2)开启TDD模式,即测试驱动开发
单元测试是TDD实现的基石,而TDD经常会碰到协同模块尚未开发完成的情况,但是有了mock,这些一切都不是问题。当接口定义好后,测试人员就可以创建一个Mock,把接口添加到自动化测试环境,提前创建测试。
(3)可以模拟那些无法访问的资源
比如说,你需要调用一个“墙”外的资源来方便自己调试,就可以自己Mock一个。
(4)隔离系统
假如我们需要调用一个post请求,为了获得某个响应,来看当前系统是否能正确处理返回的“响应”,但是这个post请求会造成数据库中数据的污染,那么就可以充分利用Mock,构造一个虚拟的post请求,我们给他指定返回就好了。
(5)可以用来演示
假如我们需要创建一个演示程序,并且做了简单的UI,那么在完全没有开发后端服务的情况下,也可以进行演示。说到演示了,假如你已经做好了一个系统,并且需要给客户进行演示,但是里面有些真实数据并不想让用户看到,那么同样,你可以用Mock接口把这些敏感信息接口全部替换。
(6)测试覆盖度
假如有一个接口,有100个不同类型的返回,我们需要测试它在不同返回下,系统是否能够正常响应,但是有些返回在正常情况下基本不会发生,比如,我们需要测试在当接口发生500错误的时候,app是否崩溃,别告诉我你一定要给服务端代码做些手脚让他返回500 。而使用mock,这一切就都好办了,想要什么返回就模拟什么返回,不用再担心我的测试覆盖度了!
5、Mock测试存在的问题
使用Mock测试有时可以提高团队的开发效率,但当B、C都开发完成代码后,这时应该把E2E测试代码从使用Mock测试改为调用真实的模块,以避免出现模块之间集成部分漏测的问题。这里说mock存在的问题,主要是让开发和测试不要过分的依赖/相信mock接口。
使用mock时,切记的几点:
1)测试人员不应该被覆盖率高的E2E自动化测试所迷惑,覆盖率高不代表没有问题。尤其在接手新项目中,需要查看E2E测试中有没有使用Mock测试,进一步去判断这些地方使用Mock测试是否合理,这些Mock测试是否应该换成真实模块间的调用和集成。
2)当把mock接口换成实际接口后,测试/开发也必须把之前的测试重新做一遍。
ps: 当你使用mock接口来提高效率,请注意:你的工作量其实是比 直接只用实际接口 多了 一倍的。如果测试时,偷懒,替换成实际接口后,只是简单测试,那么 当实际接口和mock预期接口有差异时,故障便和你相遇了。
建议: mock接口只能主流程联调/ 异常返回测试,不要过分依赖mock接口进行测试。
3)测试完毕,上线前,请一定确保 为了mock而做的相关代码/配置文件的修改,已经完全恢复了。
建议:上线checklist中条条列出,并上线前review
---------------------
原文:https://blog.csdn.net/huazhongkejidaxuezpp/article/details/67018676
二、Mock测试方式
1. Mock Server-Moco
这是一个jar包,只要执行该jar包,指定配置文件,就可开启一个http服务器提供服务,并且修改配置文件后也无需重启服务,支持动态加载。我使用的是moco-runner-0.10.2-standalone.jar,运行方式如下:
```java -jar moco-runner-0.10.2-standalone.jar start -p 8080 -c XXX.json```
XXX.json就是我们的mock配置文件,比如:
[ { "description": "api 1", "request" :{ "method" : "get", "uri" : "/foo" }, "response": { "json": {"foo":"bar"} } } ]
以上就可以实现当我们访问127.0.0.0:8080/foo时,返回一个json为{"foo":"bar"}。
具体其他使用方法请参照官方文档:https://github.com/dreamhead/moco/blob/master/moco-doc/apis.md
2. fiddler
fiddler大家都很熟了,在windows环境可以随便自定义返回内容,但一个很大的缺点是,它不跨平台,而我们平时的很多场景下,是需要在Linux下进行mock的。
还有一些其他mock工具,大多都是通过编写js代码或者python、java等代码来达到mock目的,此处就不再介绍了。
在选择mock工具时,可参考以下几个方面:
一是数据要好管理,别让我管理一堆文件;
二是mock接口最好可以设置成和真实接口完全一致,这样就只需要切换hosts就可以切换mock接口和真实接口,不需要修改代码;
三是跨平台,mock接口在windows和Linux下都需要可用。至于跨域、动态加载什么的,这是必须条件。
三、Mock测试示例
1、使用Fiddler进行Mock测试
------这种调试方式适用于rest接口调试,web界面调试等。
测试工程师在做测试时,也需要服务器返回一些特殊的数据来做测试,使用 Fiddler AutoResponder功能来伪造测试数据(创建虚拟对象),能大大减少测试工程师的工作量。
1.1 Fiddler AutoResponder工作原理
使用Fiddler可以替换自动返回的一个【伪造】的HTTP响应,这与使用断点修改HTTP响应类似,只不过AutoResponder是自动的,操作更加方便。即,浏览器发出的HTTP请求并没有到达服务器,而是被Fiddler直接返回了一个【伪造】的HTTP响应。
1.2 使用Fiddler进行Mock测试
(1)接口抓包-----找到要mock的接口
以掘金首页为例,找到下面的接口 https://gold-tag-ms.juejin.im/v1/categories
(2)复制接口数据到本地
在接口上进行右键点击,选择save -> …and Open as Local File -> 默认会保存至桌面,示例中的数据,保存到了桌面的test.json
(3)修改数据
修改保存到本地的json文件,示例中仅修改了页面的标签数据。
(4)替换json文件
在web session 面板中找到对应的请求,然后将其拖到AutoResponder面板中,在RuleEditor中单击“Find a file...”,选择本地json文件的路径。
(5)激活规则
选中“Enable rules”,激活规则。选中“Unmatched requests passthrough",放行不匹配的HTTP请求。
(6)save,刷新页面
单击“Save”按钮。只需修改本地保存的json文件,然后刷新浏览器(或直接访问接口),就可以看到效果了。
*PS:部分内容根据网上资源整理,此博客仅作个人学习使用。
-
DELPHI串口通讯测试
2020-01-31 10:18:38一个全面的DELPHI串口通讯软件,内有多个实例,包括传输数据、串口组件、二级管测试、数字输入、通信事件、线程处理、自动通讯以及多个专题范例,基全包含了DELPHI串口通讯的基本方法与实例,是编写DELPHI串口通讯... -
【每日1刷系列】接口测试常见面试题
2021-08-09 21:34:55本文整理了面试中经常被问到的接口测试题目,也是项目中经常遇到的实际问题,希望能通过这些题目提高对接口测试的理解。 后续也会持续更新一些题目进来,希望能对大家有所帮助。 1、请详细阐述接口测试和UI测试在... -
1.77彩屏测试程序,以及接线图
2011-01-11 20:46:351.77彩屏测试程序,以及接线图,包括贪吃蛇游戏程序 -
针式打印机打印针测试(并口)
2013-07-04 09:39:28这是一款打印针断针测试程序,包括针测试内容 和 并口发送批处理文件。可以应用在所有的正规厂商的含并口的针式打印机上。 -
接口测试的面试题集
2021-07-12 18:16:04一、你对接口测试是怎么理解的? 我理解的接口是功能数据传递的通道,是实现某个功能的一个函数。接口参数就是函数的参数,接口的响应数据就是函数的返回值。接口有分内部接口,即同一个系统项目包含的接口;还有... -
DOS串口测试工具
2017-06-09 12:53:59在DOS下测试串口的工具。 -
接口测试 & Jmeter面试题
2021-11-11 19:24:03一、接口测试 1、接口测试流程 1、首先是从开发那里拿到API接口文档,了解接口业务、包括接口地址、请求方式,入参、出参,token鉴权,返回格式等信息。 2、然后使用Postman或Jmeter工具执行接口测试,一般使用... -
mpu6050TestInC:用C语言编写的简单树莓派程序来测试mpu6050
2021-05-17 09:25:57用C语言编写的简单树莓派程序来测试mpu6050 只是做gcc -lm -o AccTest AccTest.c mpu6050.c I2CWrapper.c Python版本 MPU6050.py MPU6050的接口类。 VibrationTest.py用于检测加速度峰值的应用程序。 GetFFTmpu... -
12864并口显示程序
2014-03-24 11:41:45绝对好用,不显示图片,并口驱动,已经烧写测试通过了哦 -
Delphi 7票据打印机测试程序
2009-12-14 10:04:17用Delphi 7写的一个票据打印机测试程序,可以向串并口传输数据,采用Createfile、Writefile、Readfile,可发送开钱箱、倍高倍宽等可用的ESC/POS指令。 -
职场人们天天说的接口Mock测试,今天我终于搞懂了
2021-11-11 14:15:0401 关于Mock测试 01 含义和目的 1、什么是Mock测试? Mock 测试就是在测试过程中,对于某些不容易构造(如 HttpServletRequest 必须在Servlet 容器中才能构造出来)或者不容易获取的比较复杂的对象(如 JDBC 中的... -
程序人生丨如何体现测试工程师的价值
2021-05-04 21:06:45接口测试,由于目前已经有比较完善的用例集,想把接口测试结果作为条件之一放进提测标准中。但是目前接口测试没有集成到 Jenkins 中,且提测标准应该达到多少通过率,如果达不到,失败的用例又该谁来处理,想来想去... -
热敏打印机测试程序 小票打印机测试
2010-08-06 15:06:29用来测试热敏小票打印机 提供单张测试、走纸、疲劳测试等功能 支持并口串口 -
为什么要做接口测试以及怎么做,接口测试用例编写
2020-05-05 14:52:05一、为什么要做接口测试 1、更容易实现持续集成 ps:怎么样理解持续集成。工作中怎么用的?由于现在的大型系统更多更复杂,系统间模块越来越多,不同的模块由不同的人员开发,不断的进行迭代组装,为了更好的发现问题... -
关于小程序mock数据测试手机调试不显示数据问题
2020-12-09 14:59:36使用mock,前后端人员只需要定义好接口文档就可以开始并行工作;测试过程中如果遇到依赖接口没有准备好,同样可以借助mock;不会出现一个团队等待另一个团队的情况。这样的话,开发自测阶段就可以及早开展,发现问题... -
并口AVR-ISP测试软件
2011-08-22 21:48:25并口ISP测试软件 说明:本软件的编写过程中,本人参考了网站上并口控制LCD液晶的程序,使用了其中的并口操作! 本软件只是测试版,支持MEGA8、MEGA16、MEGA32、MEGA64、MEGA128。但本人只测试过MEGA16和MEGA128...