Python 玩转接口自动化测试!(实战)
接口自动化测试是验证 API 是否按预期工作的过程,常用 RESTful API,通过 HTTP 方法如 GET、POST、PUT、DELETE 操作资源。Python 的 requests 库是一个流行的 HTTP 客户端库,易于发送请求和处理响应。根据 requests: HTTP for Humans,它支持 cookies、headers 和 JSON 数据,适合测试工程师用于自动化测试。
接口自动化测试是提升测试效率的关键,而Python的requests库因其简洁易用、功能强大,成为测试工程师的“瑞士军刀”。
但你是否还在用requests.get()
和requests.post()
写重复代码?是否遇到过文件上传失败、Cookie管理混乱、响应断言复杂的问题?
本文从零到一拆解requests库的进阶用法,手把手教你打造高可用的接口自动化框架!
一、requests库的“核心六式”
1. 基础请求:GET/POST轻松上手
- 安装 requests 库
- 运行命令 pip install requests 安装库。
- 选择测试框架:unittest 或 pytest,安装 pytest 可运行 pip install pytest。
- 示例:确保环境配置正确,测试前验证 requests 版本。
- 定义 API 基础 URL 和测试结构
-
示例:requests如下:
-
import requests
# GET请求:查询用户列表
response = requests.get(
url="https://api.example.com/users",
params={"page": 1, "size": 10} # 自动拼接URL参数
)
# POST请求:创建新用户
payload = {"name": "哪吒", "role": "tester"}
response = requests.post(
url="https://api.example.com/users",
json=payload # 自动设置Content-Type为application/json
)
print(response.status_code) # 状态码
print(response.json()) # 解析JSON响应
2. 会话管理:保持登录态(Session对象)
痛点:每次请求手动传Cookie/Token太麻烦!
解决:用Session对象自动保持会话!
# 登录并保持会话
with requests.Session() as s:
login_data = {"username": "admin", "password": "test123"}
s.post("https://api.example.com/login", data=login_data)
# 后续请求自动携带Cookie
profile = s.get("https://api.example.com/profile")
print(profile.json())
3. 文件上传:测试文件接口必备
# 上传图片文件
files = {'file': open('test_image.jpg', 'rb')} # 二进制模式打开
response = requests.post(
"https://api.example.com/upload",
files=files,
headers={"Authorization": "Bearer xyz123"}
)
# 多文件上传(如测试批量导入)
multiple_files = [
('files', ('report1.xlsx', open('report1.xlsx', 'rb'))),
('files', ('report2.xlsx', open('report2.xlsx', 'rb')))
]
response = requests.post(url, files=multiple_files)
4. 超时与重试:提升测试稳定性
# 设置超时(连接超时3秒,读取超时10秒)
try:
response = requests.get(
"https://api.example.com/data",
timeout=(3, 10)
)
except requests.exceptions.Timeout:
print("请求超时,请检查网络或服务状态!")
# 自动重试(需安装requests-retry库)
from requests.adapters import HTTPAdapter
from requests.packages.urllib3.util.retry import Retry
retry_strategy = Retry(
total=3, # 最大重试次数
status_forcelist=[500, 502, 503, 504], # 遇到这些状态码重试
backoff_factor=1 # 重试等待时间间隔
)
adapter = HTTPAdapter(max_retries=retry_strategy)
session = requests.Session()
session.mount("https://", adapter)
response = session.get(url)
5. 响应断言:自动化测试的灵魂
# 断言状态码和关键字段
assert response.status_code == 200, f"状态码异常:{response.status_code}"
response_data = response.json()
assert response_data["code"] == 0, "接口返回错误码"
assert "user_id" in response_data["data"], "未返回用户ID"
assert len(response_data["data"]["roles"]) >= 1, "用户角色至少一个"
# 使用JSON Schema验证数据结构(需安装jsonschema库)
schema = {
"type": "object",
"properties": {
"code": {"type": "number"},
"data": {
"type": "object",
"properties": {
"user_id": {"type": "string"},
"roles": {"type": "array"}
},
"required": ["user_id"]
}
},
"required": ["code", "data"]
}
import jsonschema
jsonschema.validate(instance=response_data, schema=schema)
6. 高级配置:代理、SSL验证与Mock
# 设置代理(用于测试环境隔离或抓包调试)
proxies = {
"http": "http://10.10.1.10:3128",
"https": "http://10.10.1.10:1080"
}
requests.get("https://api.example.com", proxies=proxies)
# 禁用SSL证书验证(测试环境临时使用,生产环境慎用!)
response = requests.get(url, verify=False)
# 结合Mock服务(如使用pytest-mock)
def test_api(mocker):
mock_response = mocker.Mock()
mock_response.json.return_value = {"code": 0, "data": "mocked"}
mocker.patch("requests.get", return_value=mock_response)
result = requests.get("https://api.example.com")
assert result.json()["code"] == 0
二、接口自动化框架设计实战
1. 封装工具类:拒绝重复代码
class APIClient:
def __init__(self, base_url):
self.base_url = base_url
self.session = requests.Session()
self.session.headers.update({"User-Agent": "AutoTest/1.0"})
def get(self, path, params=None):
url = f"{self.base_url}{path}"
return self.session.get(url, params=params)
def post_json(self, path, data):
url = f"{self.base_url}{path}"
return self.session.post(url, json=data)
# 使用示例
client = APIClient("https://api.example.com")
response = client.post_json("/users", {"name": "敖丙"})
2. 参数化测试:数据驱动
import pytest
test_data = [
("正常登录", {"username": "admin", "password": "123456"}, 200),
("密码错误", {"username": "admin", "password": "wrong"}, 401),
("用户名为空", {"username": "", "password": "123456"}, 400)
]
@pytest.mark.parametrize("case_name, data, expected_code", test_data)
def test_login(case_name, data, expected_code):
response = requests.post("https://api.example.com/login", json=data)
assert response.status_code == expected_code, f"用例失败:{case_name}"
3. 测试报告生成:Allure集成
import allure
@allure.title("测试创建用户接口")
def test_create_user():
with allure.step("步骤1:准备测试数据"):
payload = {"name": "接口测试用户"}
with allure.step("步骤2:发送POST请求"):
response = requests.post(url, json=payload)
with allure.step("步骤3:验证响应结果"):
assert response.status_code == 201
assert response.json()["id"] is not None
三、常见坑点与解决方案
❌ 坑1:响应内容乱码
-
原因:服务器返回的编码与requests自动检测不一致。
-
解决:手动指定编码:
response.encoding = 'utf-8' # 或 'gbk'
print(response.text)
❌ 坑2:文件上传接口报错
-
排查:检查是否以二进制模式(
'rb'
)打开文件,且服务端要求的字段名是否正确。
❌ 坑3:Cookie失效问题
-
解决:使用Session对象保持会话,或定期刷新Token。
四、拓展:接口性能监控小技巧
import time
start_time = time.time()
response = requests.get("https://api.example.com/heavy-api")
end_time = time.time()
assert end_time - start_time < 2.0, f"接口响应超时:{end_time - start_time}秒"
print(f"接口响应时间:{round(end_time - start_time, 2)}秒")
使用 Python requests 库进行接口自动化测试,需掌握请求发送、响应验证和复杂场景处理。这不仅是技术技能,更是提升软件质量的关键。
“用 Python requests 玩转接口测试,测试工程师的效率从此飞跃!”