基于 python 的接口自动化测试,最简单实用的教学
off999 2024-10-17 11:46 128 浏览 0 评论
一、简介
本文从一个简单的登录接口测试入手,一步步调整优化接口调用姿势;
然后简单讨论了一下接口测试框架的要点;
最后介绍了一下我们目前正在使用的接口测试框架 pithy。
期望读者可以通过本文对接口自动化测试有一个大致的了解。
二、引言
为什么要做接口自动化测试?
在当前互联网产品迭代频繁的背景下,回归测试的时间越来越少,很难在每个迭代都对所有功能做完整回归。
但接口自动化测试因其实现简单、维护成本低,容易提高覆盖率等特点,越来越受重视。
为什么要自己写框架呢?
使用 requets + unittest 很容易实现接口自动化测试,而且 requests 的api已经非常人性化,非常简单。
但通过封装以后(特别是针对公司内特定接口),再加上对一些常用工具的封装,可以进一步提高业务脚本编写效率。
三、环境准备
确保本机已安装 python2.7 以上版本,然后安装如下库:
pip install flask
pip install requests后面我们会使用 flask 写一个用来测试的接口,使用requests去测试。
四、测试接口准备
下面使用 flask 实现两个 http 接口,一个登录,另外一个查询详情,但需要登录后才可以,新建一个 demo.py 文件(注意,不要使用windows记事本),把下面代码 copy 进去,然后保存、关闭。
接口代码
#!/usr/bin/python# coding=utf-8from flask import Flask, request, session, jsonify
USERNAME = 'admin'PASSWORD = '123456'app = Flask(__name__)
app.secret_key = 'pithy'@app.route('/login', methods=['GET', 'POST'])def login():
error = None
if request.method == 'POST': if request.form['username'] != USERNAME:
error = 'Invalid username'
elif request.form['password'] != PASSWORD:
error = 'Invalid password'
else:
session['logged_in'] = True
return jsonify({'code': 200, 'msg': 'success'}) return jsonify({'code': 401, 'msg': error}), 401@app.route('/info', methods=['get'])def info():
if not session.get('logged_in'): return jsonify({'code': 401, 'msg': 'please login !!'}) return jsonify({'code': 200, 'msg': 'success', 'data': 'info'})if __name__ == '__main__':
app.run(debug=True)最后执行如下命令:
python demo.py响应如下:
* Running on http://127.0.0.1:5000/ (Press CTRL+C to quit)
* Restarting with sta大家可以看到服务已经起来了。
接口信息
登录接口
请求url
/login
请求方法
post
请求参数
| 参数名称 | 参数类型 | 参数说明 |
| :————: | :——-: | :——: |
| username | String | 登录名称 |
| password | String | 登录密码 |
响应信息
| 参数名称 | 参数类型 | 参数说明 |
| :————: | :——-: | :——: |
| code | Integer | 结果code |
| msg | String | 结果信息 |
详情接口
请求url
/info
请求方法
get
请求 cookies
| 参数名称 | 参数类型 | 参数说明 |
| :————: | :——-: | :——: |
| session | String | session |
响应信息
| 参数名称 | 参数类型 | 参数说明 |
| :————: | :——-: | :——: |
| code | Integer | 结果code |
| msg | String | 结果信息 |
| data | String | 数据信息 |
五、编写接口测试
测试思路
- 使用 requests库模拟发送 HTTP 请求。
- 使用 python 标准库里 unittest 写测试 case。
脚本实现
#!/usr/bin/python# coding=utf-8import requestsimport unittestclass TestLogin(unittest.TestCase):
@classmethod
def setUpClass(cls):
cls.login_url = 'http://127.0.0.1:5000/login'
cls.info_url = 'http://127.0.0.1:5000/info'
cls.username = 'admin'
cls.password = '123456'
def test_login(self):
"""
测试登录
"""
data = { 'username': self.username, 'password': self.password
}
response = requests.post(self.login_url, data=data).json() assert response['code'] == 200
assert response['msg'] == 'success'
def test_info(self):
"""
测试info接口
"""
data = { 'username': self.username, 'password': self.password
}
response_cookies = requests.post(self.login_url, data=data).cookies
session = response_cookies.get('session') assert session
info_cookies = { 'session': session
}
response = requests.get(self.info_url, cookies=info_cookies).json() assert response['code'] == 200
assert response['msg'] == 'success'
assert response['data'] == 'info'六、优化
封装接口调用
写完这个测试登录脚本,你或许会发现,在整个项目的测试过程,登录可能不止用到一次,如果每次都这么写,会不会太冗余了?
对,确实太冗余了,下面做一下简单的封装,把登录接口的调用封装到一个方法里,把调用参数暴漏出来,示例脚本如下:
#!/usr/bin/python# coding=utf-8import requestsimport unittesttry: from urlparse import urljoinexcept ImportError: from urllib.parse import urljoinclass DemoApi(object):
def __init__(self, base_url):
self.base_url = base_url def login(self, username, password):
"""
登录接口
:param username: 用户名
:param password: 密码
"""
url = urljoin(self.base_url, 'login')
data = { 'username': username, 'password': password
} return requests.post(url, data=data).json() def get_cookies(self, username, password):
"""
获取登录cookies
"""
url = urljoin(self.base_url, 'login')
data = { 'username': username, 'password': password
} return requests.post(url, data=data).cookies def info(self, cookies):
"""
详情接口
"""
url = urljoin(self.base_url, 'info') return requests.get(url, cookies=cookies).json()class TestLogin(unittest.TestCase):
@classmethod
def setUpClass(cls):
cls.base_url = 'http://127.0.0.1:5000'
cls.username = 'admin'
cls.password = '123456'
cls.app = DemoApi(cls.base_url) def test_login(self):
"""
测试登录
"""
response = self.app.login(self.username, self.password) assert response['code'] == 200
assert response['msg'] == 'success'
def test_info(self):
"""
测试获取详情信息
"""
cookies = self.app.get_cookies(self.username, self.password)
response = self.app.info(cookies) assert response['code'] == 200
assert response['msg'] == 'success'
assert response['data'] == 'info'OK,在这一个版本中,我们不但在把登录接口的调用封装成了一个实例方法,实现了复用,而且还把 host(self.base_url)提取了出来。
但问题又来了,登录之后,登录接口的 http 响应会把 session 以 cookie 的形式 set 到客户端,之后的接口都会使用此 session 去请求。
还有,就是在接口调用过程中,希望可以把日志打印出来,以便调试或者出错时查看。
好吧,我们再来改一版。
保持 cookies &增加 log 信息
使用 requests 库里的同一个 Session 对象 (它也会在同一个 Session 实例发出的所有请求之间保持 cookie ),即可解决上面的问题,示例代码如下:
#!/usr/bin/python# coding=utf-8import unittestfrom pprint import pprintfrom requests.sessions import Sessiontry: from urlparse import urljoinexcept ImportError: from urllib.parse import urljoinclass DemoApi(object):
def __init__(self, base_url):
self.base_url = base_url # 创建session实例
self.session = Session() def login(self, username, password):
"""
登录接口
:param username: 用户名
:param password: 密码
"""
url = urljoin(self.base_url, 'login')
data = { 'username': username, 'password': password
}
response = self.session.post(url, data=data).json()
print('\n*****************************************')
print(u'\n1、请求url: \n%s' % url)
print(u'\n2、请求头信息:')
pprint(self.session.headers)
print(u'\n3、请求参数:')
pprint(data)
print(u'\n4、响应:')
pprint(response) return response def info(self):
"""
详情接口
"""
url = urljoin(self.base_url, 'info')
response = self.session.get(url).json()
print('\n*****************************************')
print(u'\n1、请求url: \n%s' % url)
print(u'\n2、请求头信息:')
pprint(self.session.headers)
print(u'\n3、请求cookies:')
pprint(dict(self.session.cookies))
print(u'\n4、响应:')
pprint(response) return responseclass TestLogin(unittest.TestCase):
@classmethod
def setUpClass(cls):
cls.base_url = 'http://127.0.0.1:5000'
cls.username = 'admin'
cls.password = '123456'
cls.app = DemoApi(cls.base_url) def test_login(self):
"""
测试登录
"""
response = self.app.login(self.username, self.password) assert response['code'] == 200
assert response['msg'] == 'success'
def test_info(self):
"""
测试获取详情信息
"""
self.app.login(self.username, self.password)
response = self.app.info() assert response['code'] == 200
assert response['msg'] == 'success'
assert response['data'] == 'info'大功告成,我们把多个相关接口调用封装到一个类中,使用同一个 requests Session 实例来保持 cookies,并且在调用过程中打印出了日志,我们所有目标都实现了。
但再看下脚本,又会感觉不太舒服,在每个方法里,都要写一遍print 1、2、3… 要拼url、还要很多细节等等。
但其实我们 真正需要做的只是拼出关键的参数(url 参数、body 参数或者传入 headers 信息),可不可以只需定义必须的信息,然后把其它共性的东西都封装起来呢,统一放到一个地方去管理?
感谢每一个认真阅读我文章的人!!!
如果下面这些资料用得到的话可以直接拿走:
1、自学开发或者测试必备的完整项目源码与环境
2、测试工作中所有模板(测试计划、测试用例、测试报告等)
3、软件测试经典面试题
4、Python/Java自动化测试实战.pdf
5、Jmeter/postman接口测试全套视频获取
我个人整理了我这几年软件测试生涯整理的一些技术资料,包含:电子书,简历模块,各种工作模板,面试宝典,自学项目等。需要的评论区找我谢谢
相关推荐
- 安全教育登录入口平台(安全教育登录入口平台官网)
-
122交通安全教育怎么登录:122交通网的注册方法是首先登录网址http://www.122.cn/,接着打开网页后,点击右上角的“个人登录”;其次进入邮箱注册,然后进入到注册页面,输入相关信息即可完...
- 大鱼吃小鱼经典版(大鱼吃小鱼经典版(经典版)官方版)
-
大鱼吃小鱼小鱼吃虾是于谦跟郭麒麟的《我的棒儿呢?》郭德纲说于思洋郭麒麟作诗的相声,最后郭麒麟做了一首,师傅躺在师母身上大鱼吃小鱼小鱼吃虾虾吃水水落石出师傅压师娘师娘压床床压地地动山摇。...
-
- 哪个软件可以免费pdf转ppt(免费的pdf转ppt软件哪个好)
-
要想将ppt免费转换为pdf的话,我们建议大家可以下一个那个wps,如果你是会员的话,可以注册为会员,这样的话,在wps里面的话,就可以免费将ppt呢转换为pdfpdf之后呢,我们就可以直接使用,不需要去直接不需要去另外保存,为什么格式转...
-
2026-02-04 09:03 off999
- 电信宽带测速官网入口(电信宽带测速官网入口app)
-
这个网站看看http://www.swok.cn/pcindex.jsp1.登录中国电信网上营业厅,宽带光纤,贴心服务,宽带测速2.下载第三方软件,如360等。进行在线测速进行宽带测速时,尽...
- 植物大战僵尸95版手机下载(植物大战僵尸95 版下载)
-
1可以在应用商店或者游戏平台上下载植物大战僵尸95版手机游戏。2下载教程:打开应用商店或者游戏平台,搜索“植物大战僵尸95版”,找到游戏后点击下载按钮,等待下载完成即可安装并开始游戏。3注意:确...
- 免费下载ppt成品的网站(ppt成品免费下载的网站有哪些)
-
1、Chuangkit(chuangkit.com)直达地址:chuangkit.com2、Woodo幻灯片(woodo.cn)直达链接:woodo.cn3、OfficePlus(officeplu...
- 2025世界杯赛程表(2025世界杯在哪个国家)
-
2022年卡塔尔世界杯赛程公布,全部比赛在卡塔尔境内8座球场举行,2022年,决赛阶段球队全部确定。揭幕战于当地时间11月20日19时进行,由东道主卡塔尔对阵厄瓜多尔,决赛于当地时间12月18日...
- 下载搜狐视频电视剧(搜狐电视剧下载安装)
-
搜狐视频APP下载好的视频想要导出到手机相册里方法如下1、打开手机搜狐视频软件,进入搜狐视频后我们点击右上角的“查找”,找到自已喜欢的视频。2、在“浏览器页面搜索”窗口中,输入要下载的视频的名称,然后...
- 永久免费听歌网站(丫丫音乐网)
-
可以到《我爱音乐网》《好听音乐网》《一听音乐网》《YYMP3音乐网》还可以到《九天音乐网》永久免费听歌软件有酷狗音乐和天猫精灵,以前要跳舞经常要下载舞曲,我从QQ上找不到舞曲下载就从酷狗音乐上找,大多...
- 音乐格式转换mp3软件(音乐格式转换器免费版)
-
有两种方法:方法一在手机上操作:1、进入手机中的文件管理。2、在其中选择“音乐”,将显示出手机中的全部音乐。3、点击“全选”,选中所有音乐文件。4、点击屏幕右下方的省略号图标,在弹出菜单中选择“...
- 电子书txt下载(免费的最全的小说阅读器)
-
1.Z-library里面收录了近千万本电子书籍,需求量大。2.苦瓜书盘没有广告,不需要账号注册,使用起来非常简单,直接搜索预览下载即可。3.鸠摩搜书整体风格简洁清晰,书籍资源丰富。4.亚马逊图书书籍...
- 最好免费观看高清电影(播放免费的最好看的电影)
-
在目前的网上选择中,IMDb(互联网电影数据库)被认为是最全的电影网站之一。这个网站提供了各种类型的电影和电视节目的海量信息,包括剧情介绍、演员表、评价、评论等。其还提供了有关电影制作背后的详细信息,...
- 孤单枪手2简体中文版(孤单枪手2简体中文版官方下载)
-
要将《孤胆枪手2》游戏的征兵秘籍切换为中文,您可以按照以下步骤进行操作:首先,打开游戏设置选项,通常可以在游戏主菜单或游戏内部找到。然后,寻找语言选项或界面选项,点击进入。在语言选项中,选择中文作为游...
欢迎 你 发表评论:
- 一周热门
- 最近发表
- 标签列表
-
- python计时 (73)
- python安装路径 (56)
- python类型转换 (93)
- python进度条 (67)
- python吧 (67)
- python的for循环 (65)
- python格式化字符串 (61)
- python静态方法 (57)
- python列表切片 (59)
- python面向对象编程 (60)
- python 代码加密 (65)
- python串口编程 (77)
- python封装 (57)
- python写入txt (66)
- python读取文件夹下所有文件 (59)
- python操作mysql数据库 (66)
- python获取列表的长度 (64)
- python接口 (63)
- python调用函数 (57)
- python多态 (60)
- python匿名函数 (59)
- python打印九九乘法表 (65)
- python赋值 (62)
- python异常 (69)
- python元祖 (57)
