Files
apiautotest/README.md

372 lines
19 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
## 前言
公司突然要求你做自动化,但是没有代码基础不知道怎么做?或者有自动化基础,但是不知道如何系统性的做自动化, 放在yaml文件中维护不知道如何处理多业务依赖的逻辑
那么本自动化框架,将为你解决这些问题。
- 框架主要使用 python 语言编写,结合 pytest 进行二次开发,用户仅需要在 yaml 或者 excel 文件中编写测试用例, 编写成功之后,会自动生成测试用例代码,零基础代码小白,也可以操作。
- 如果是具备代码基础的,也可以直接通过 py 文件编写测试用例。
- 使用 Allure 生成报告,并针对测试报告样式进行了调整,使得报告更加美观;
- 测试完成后,支持发送 企业微信通知/ 钉钉通知/ 邮箱通知,灵活配置。
## 一、框架介绍
本框架主要是基于 Python + Pytest + Allure + Loguru + 邮件通知/企业微信通知/钉钉通知 实现的接口自动化框架。
* git地址: [https://www.gitlink.org.cn/floraachy/apiautotest](https://www.gitlink.org.cn/floraachy/apiautotest)
* 项目参与者: floraachy
* 个人主页: [https://www.gitlink.org.cn/floraachy](https://www.gitlink.org.cn/floraachy)
* 测试社区地址: [https://www.gitlink.org.cn/zone/tester](https://www.gitlink.org.cn/zone/tester)
* 入群二维码:[https://www.gitlink.org.cn/floraachy/apiautotest/issues/1](https://www.gitlink.org.cn/floraachy/apiautotest/issues/1)
如果对您有帮助,请点亮 小星星 以表支持,谢谢!
对于框架有任何问题,请先仔细阅读本文~ 如果还有不了解的,欢迎联系我!
## 二、实现功能
* 通过session会话方式解决了登录之后cookie关联处理`
* 动态多断言: 如接口需要同时校验响应数据和sql校验支持多场景断言
* 框架天然支持接口动态传参、关联灵活处理
* 支持测试数据分析,测试数据不符合规范有预警机制
* 支持通过用例数据动态配置pytest.mark 包括自定义标记pytest.mark.skip以及pytest,mark.usefixtures
* 支持利用allure设置用例优先级运行指定优先级的用例
* 测试数据隔离, 实现数据驱动
* 自动生成用例代码: 测试人员在yaml/excel文件中填写好测试用例, 程序可以直接生成用例代码,纯小白也能使用
* 支持参数多类型提取支持通过jsonpath从response.json提取数据支持通过正则表达式从response.text提取数据支持直接提取response本身的数据例如response.cookies
* 使用Allure生成测试报告并对测试报告进行了定制化修改使得测试报告更加美观
* 日志模块: 采用loguru管理日志可以输出更为优雅简洁的日志
* 钉钉、企业微信通知: 支持多种通知场景,执行成功之后,可选择发送钉钉、或者企业微信、邮箱通知
* 执行环境一键切换,解决多环境相互影响问题
* 使用pipenv管理虚拟环境和依赖文件提供了一系列命令和选项来帮助你实现各种依赖和环境管理相关的操作
* 支持将swagger.json接口文档转为YAML用例
## 三、依赖库
```
pymysql = "*"
loguru = "*"
requests-toolbelt = "*"
requests = "*"
openpyxl = "*"
sshtunnel = "*"
yagmail = "*"
pyyaml = "*"
click = "*"
faker = "*"
jsonpath = "*"
pytest = "==6.2.5"
pytest-rerunfailures = "*"
allure-pytest = "==2.9.45"
pydantic = "*"
xpinyin = "*"
"ruamel.yaml" = "*"
```
## 四、安装教程
1. 通过Git工具clone代码到本地 或者 直接下载压缩包ZIP
```
https://gitlink.org.cn/floraachy/apiautotest.git
```
2. 本地电脑搭建好 python环境我使用的python版本是3.9。包括allure测试报告所需的java环境安装jdk
3. 安装pipenv
```
# 建议在项目根目录下执行命令安装
pip install pipenv
```
4. 使用pipenv管理安装环境依赖包pipenv install (必须在项目根目录下执行)
```
注意使用pipenv install会自动安装Pipfile里面的依赖包该依赖包仅安装在虚拟环境里不安装在测试机。
```
如上环境都已经搭建好了,包括框架依赖包也都安装好了。
<br/>
注意:
- 很多同学不太熟悉pipenv会存在问题比如我按照上述操作安装了依赖包怎么运行报错呢一定要记住使用pipenv安装依赖包依赖包只安装在虚拟环境不安装在你的测试机器。所以你安装完成后直接运行肯定会报错。我们需要进入我们创建的虚拟环境再运行测试代码。具体步骤参考章节"运行自动化测试"。
- 如果存在Python版本与我的不一致的问题请移步最后的章节"初始化项目可能遇到的问题" 查找解决办法。
- 另外我们如果是使用pycharm直接右键run的情况我们需要pycharm解释器选择我们创建的虚拟环境才不会报少包的错误。
## 五、如何创建用例
注意:如果想用我框架中的用例执行运行测试,可以暂时跳过这一章节,直接看章节 "运行自动化测试"。
### 1. 修改配置文件 `config.settings.py`
1确认用例是通过YAML还是Excel编写由CASE_FILE_TYPE控制
2确认测试完成后是否发送测试结果由SEND_RESULT_TYPE控制并填充对应邮件/钉钉/企业微信配置信息
3确认测试是否需要进行数据库断言如有需求填充数据库配置信息
4指定日志收集级别由LOG_LEVEL控制
### 2. 修改全局变量,增加测试数据 `config.settings.py`
1) ENV_VARS["common"]是一些公共参数,如报告标题,报告名称,测试者,测试部门。后续会显示在测试报告上。如果还有其他,可自行添加
2ENV_VARS["test"]是保存test环境的一些测试数据。ENV_VARS["live"]是保存live环境的一些测试数据。如果还有其他环境可以继续增加例如增加ENV_VARS["dev"] = {"host": "", ......}
### 3. 删除框架中的示例用例数据
1删除 `data`目录下所有的YAML和EXCEL文件
2删除 `test_case/test_manual_case`目录下所有手动编写的用例,后续有需要可以在该目录下手动编写用例。
### 4. 编写测试用例(两种方式任选其一或者都选)
#### 1自动生成测试用例 `data` `test_case.test_auto_case`
- 在目录`data`下新建一个YAML/Excel文件。按照如下字段要求进行测试用例数据添加
- 注意如果需要自动创建测试用例文件YAML/Excel文件的文件名需要以"test"开头。
#### 2手动编写测试用例 `data` `test_case.test_manual_case`
- 原则上如果是手动编写测试用例python代码 测试用例数据文件不要以"test"开头。 如果以“test”开头可能导致用例运行多次。
1在目录`data`下新建一个YAML/Excel文件按照要求编写测试用例数据
2在test_case.test_manual_case下新建一个以"test"开头的测试方法,进行测试用例方法编写。
### 5. 用例中相关字段的介绍
```yaml
case_common :公共参数
allure_epic用作于@allure.epic()装饰器中的内容。
allure_feature用作于@allure.feature()装饰器中的内容。
allure_story用作于@allure.story()装饰器中的内容。
case_markers: 给测试方法添加标记支持自定义标记skip, usefixtures。 格式是列表嵌套字符串或者字典。例如: # ['glcc', {'skip': '跳过执行该用例'}]
case_info: 具体的用例数据,是以列表的形式进行管理
-
id用例id
title用例标题
severity: 用例优先级支持如下几种NORMAL BLOCKERCRITICALMINORTRIVIAL 为空和错误都认为是NORMAL
run是否执行用例为空或者True都会执行为False则不执行。
url请求路径可填写全路径 或者 资源路径。通常我们填写资源路径。在用例执行前会针对路径进行处理。具体可见case_utils.request_control.py.RequestPreDataHandle.url_handle。注请求路径=基准路径host/base_url+资源路径(url)。
method请求方式例如GET, POST, DELETE, PUT, PATCH等
headers请求头注意如果在headers里面防止cookies其值类型需要是字符串
cookies请求cookies格式是DICT CookieJar对象
request_type请求数据类型params, json, file, data
payload请求参数
files: 需要上传的文件,参考如下传参:{接口中文件参数的名称:'文件路径地址'}
extract后置提取参数
assert_response响应断言
assert_sql数据库断言
```
### 6. 参数提取说明
目前支持3种方式的参数提取type_jsonpath, type_re, type_response
#### type_jsonpath
如果采用jsonpath方式从响应数据提取参数`extract`的key是`type_jsonpath`; `extract[type_jsonpath]`的key是变量名value是提取表达式
参考示例:
```
extract:
type_jsonpath:
nickname: $.username
login: $.login
user_id: $.user_id
```
注意如果提取到的值是长度为1的列表会自动获取第一个元素其值类型由list变更为str。例如通过`name: $.data` 提取到的值是:`["flora"]`, 最后name的值会是`"flora"`
#### type_re
如果采用正则表达式方式从响应数据提取参数,`extract`的key是`type_re`; `extract[type_re]`的key是变量名value是提取表达式
参考示例:
```
# 注意:\是用来转译的保证yaml格式正确.也可以用引号包裹起来
extract:
type_re:
nickname: \"username":"(.*?)"
login: \"login":"(.*?)"
user_id: '"user_id":(.*?),'
```
注意如果提取到的值是长度为1的列表会自动获取第一个元素其值类型由list变更为str。例如通过`name: "username":"(.*?)"` 提取到的值是:`["flora"]`, 最后name的值会是`"flora"`
#### type_response
如果是直接从响应数据提取参数,`extract`的key是`type_response`; `extract[type_response]`的key是变量名value是提取表达式
基本上response所有方法都支持部分参考`response.status_code` `response.cookies`, `response.text`, `response.headers`, `response.is_redirect`
参考示例:
```
extract:
type_response:
cookies: response.cookies
```
### 6. 响应断言说明
#### 断言状态码
如果想要断言接口响应码,直接这样写即可:
参考示例:
```
assert_response:
status_code: 200
```
#### 响应数据断言
响应断言的参数说明:
```
断言标识(自定义,不为空即可,没有实际的意义):
message: 断言信息,非必填,可为空
expect_value: 预期结果
assert_type: 断言类型,支持如下:==, lt, le, gt, ge, not_eq, str_eq, len_eq, len_gt, len_ge, len_lt, len_le, contains, contained_by, startswith, endswith
type_jsonpath: 通过jsonpath表达式从response.json()提取实际结果与type_re任选其一
type_re: 通过正则表达式从response.text提取实际结果与type_jsonpath任选其一;如果不填则默认获取response.text作为实际结果
```
注意:在进行断言的时候,左侧是预期结果,右侧是实际结果。比如我断言类型是`lt` 那么就是预期结果<实际结果
参考示例:
```
assert_response:
user_id:
message: 断言接口返回的user_id
expect_value: ${user_id}
assert_type: ==
type_jsonpath: $.user_id
```
```
assert_response:
user_id:
expect_value: ${user_id}
assert_type: ==
type_jsonpath: $.user_id
```
### 7. 数据库断言说明
数据库断言的参数说明:
```
断言标识(自定义,不为空即可,没有实际的意义):
message: 断言信息,非必填,可为空
sql: 数据库查询语句,必填
expect_value: 预期结果
assert_type: 断言类型,支持如下:==, lt, le, gt, ge, not_eq, str_eq, len_eq, len_gt, len_ge, len_lt, len_le, contains, contained_by, startswith, endswith
type_jsonpath: 通过jsonpath表达式通从数据库查询结果提取实际结果与type_re任选其一
type_re: 通过正则表达式从数据库查询结果提取实际结果与type_jsonpath任选其一;如果不填则默认SQL直接查询结果作为实际结果
```
注意:在进行断言的时候,左侧是预期结果,右侧是实际结果。比如我断言类型是`lt` 那么就是预期结果<实际结果
参考示例:
```
contains_user:
message: 断言数据库查询tokens表表中存在该登录用户记录预期查询结果的长度为1
sql: select * from tokens where user_id=${user_id};
expect_value: 1
assert_type: len_eq
contains_user2:
message: 断言数据库查询tokens表表中存在该登录用户记录;预期 ${user_id} in 查询结果jsonpath式匹配后的结果
sql: select * from tokens where user_id=${user_id};
type_jsonpath: $..user_id
expect_value: ${user_id}
assert_type: ==
contains_user3:
message: 断言数据库查询tokens表表中存在该登录用户记录预期 ${user_id} in 查询结果(正则表达式匹配后的结果)
sql: select * from tokens;
type_re: "'user_id': (.*?),"
expect_value: ${user_id}
assert_type: contains
```
### 8. Excel用例单独说明
框架支持excel多表单自动生成测试用例每一个表单作为一个测试用例模块。
例如:
excel表格名称是test_demo.xlsx
excel表单1名称是GitLink-登录模块
excel表单2名称是示例模块
生成规则:
- 如果excel表单中存在"-",我们将取"-"后面的部分的首字母拼接excel文件名称作为测试用例模块/测试用例类/测试用例方法名称
- 如果excel表单中不存在"-"我们将直接获取表单名称首字母拼接excel文件名称作为测试用例模块/测试用例类/测试用例方法名称
- 测试用例模块/测试用例类/测试用例方法名称同时也将遵循python语法规则进行适当调整
<br/>
基于上述规则:
- excel第一个表单生成的测试用例
测试用例模块test_demo_dlmk.py
测试用例类TestDemoDlmkAuto
测试用例方法test_demo_dlmk_auto
- excel第二个表单生成的测试用例
测试用例模块test_demo_slmk.py
测试用例类TestDemoSlmkAuto
测试用例方法test_demo_slmk_auto
## 六、运行自动化测试
### 1. 激活已存在的虚拟环境
- 如果不存在会创建一个pipenv shell (必须在项目根目录下执行)
### 2. 运行
```
在pycharm>terminal或者电脑命令窗口进入项目根路径执行如下命令如果依赖包是安装在虚拟环境中需要先启动虚拟环境
> python run.py 默认在test环境运行测试用例, 生成allure测试报告
> python run.py -m demo 在test环境仅运行打了标记demo用例生成allure测试报告
> python run.py -env live 在live环境运行测试用例
> python run.py -env=test 在test环境运行测试用例
> python run.py -report=no 在test环境下允许测试用例不生成allure测试报告
```
注意:
- 如果pycharm.interpreter拥有了框架所需的所有依赖包可以通过pycharm直接在`run.py`中右键运行
## 七、查看测试报告
### Allure测试报告
1. Allure生成的测试报告支持通过pycharm点击`outputs/report/allure_html/index.html`,文件右上角选择浏览器打开查看测试报告
2. 如果不通过pycharm打开直接通过文件夹打开windows系统环境下可以点击`outputs/report/allure_html/双击打开Allure报告.bat`打开查看测试报告
<br/>
注意:
- 通过点击`outputs/report/allure_html/双击打开Allure报告.bat`打开测试报告的方法暂时不支持mac系统
- 如果通过点击`outputs/report/allure_html/双击打开Allure报告.bat`打开测试报告,命令窗口显示乱码,或者打不开,可以把`.bat`的文件名称修改为英文的名称,里面的所有中文注释全部移除,再次尝试
## 八 、详细功能说明
- [如何实现动态数据、随机数据的热加载?](https://www.gitlink.org.cn/zone/tester/newdetail/236)
我们有些特殊的场景,可能会涉及到一些定制化的数据,每次执行数据,需要按照指定规则随机生成,实时加载数据,那么这部分应该如何处理呢?
- [如何处理同一环境存在多域名的情况?](https://www.gitlink.org.cn/zone/tester/newdetail/234)
很多公司,通常一套环境是由多个微服务组成。每一个微服务具备不同的域名。那么针对这种同一环境存在多域名的情况,我们应该如何处理呢?
- [如何处理同一套框架测试多套环境的情况?](https://www.gitlink.org.cn/zone/tester/newdetail/233)
假如我想要我的自动化代码分别在不同环境执行,如何处理呢?
- [如何处理用例中需要依赖登录的token/cookies的情况](https://www.gitlink.org.cn/zone/tester/newdetail/235)
我们进行测试的时候,很多接口都是需要先登录之后再进行操作。但是我们不可能每测试一次接口,都登录一次吧,这样有点冗余了。那么,针对这种情况如何处理呢?
- [如何测试上传文件接口?](https://www.gitlink.org.cn/zone/tester/newdetail/238)
我们通过MultipartEncoder的方式进行文件上传。
- [如何通过用例数据动态配置pytest.mark](https://www.gitlink.org.cn/zone/tester/newdetail/257)
在测试过程中我们经常需要对测试用例进行分类运行时仅执行这一类用例。为了实现这一功能我在测试用例中引入了添加pytest的自定义标记的功能同时扩展支持了pytest.mark.skip以及pytest,mark.usefixtues。
注意目前这一功能仅支持通过YAML格式编写用例。EXCEL用例暂时不支持。
- [如何设置测试用例优先级](https://www.gitlink.org.cn/zone/tester/newdetail/260)
测试用例会分优先级, 我们可以利用allure的特性设置用例优先级以及运行指定优先级的用例。
- [如何提取响应数据作为全局变量并使用?](https://www.gitlink.org.cn/zone/tester/newdetail/237)
在测试过程中,通常下一个接口需要用到上一个接口的响应数据,这个时候就涉及到参数的提取。
- [如何进行响应数据断言?](https://www.gitlink.org.cn/zone/tester/newdetail/239)
目前支持5种响应断言方式eq in gt lt not。
- [如何进行数据库断言?](https://www.gitlink.org.cn/zone/tester/newdetail/240)
目前暂时支持两种数据库断言方式len eq。其他方式待扩展。
- [如何配置邮箱通知?](https://www.gitlink.org.cn/zone/tester/newdetail/242)
我们通过第三方模块yagmail发送邮件。
- [如何配置钉钉通知?](https://www.gitlink.org.cn/zone/tester/newdetail/243)
我们通过封装钉钉机器人发送钉钉通知。
- [如何配置企业微信通知?](https://www.gitlink.org.cn/zone/tester/newdetail/241)
我们通过封装企业微信机器人发送通知。
## 九、初始化项目可能遇到的问题
- [测试机安装的是python3.7但是本框架要求3.9.5,怎么办?](https://www.gitlink.org.cn/zone/tester/newdetail/245)
- [无法安装依赖包或者安装很慢,怎么办?](https://www.gitlink.org.cn/zone/tester/newdetail/244)