如何在Tavern+Pytest的YAML测试用例中调用外部函数?
在Tavern + pytest中通过YAML调用外部函数并跨用例传递变量
你已经搞定了基础POST用例的运行,现在要解决的核心问题是调用外部函数处理响应,并把变量传递到另一个YAML的GET请求,我来一步步帮你落地:
1. 先修正YAML中$ext的配置位置
你当前把$ext嵌套在response.body下,但Tavern的$ext用于响应处理/变量提取时,应该直接挂载在response节点下(或对应验证字段)。调整后的POST用例YAML结构如下:
test_name: POST请求调用外部函数并保存变量 stages: - name: 发送POST请求并处理响应 request: url: path_to_my_mock_endpoint method: POST headers: content-type: application/json response: status_code: 202 # 用$ext调用外部函数,处理响应并完成变量传递 $ext: function: utils:post_function extra_kwargs: responseText: "Great job!" responseCode: 202 tavernVerification: 1001
2. 修改外部函数,实现变量会话存储
你的utils.py里的post_function目前仅打印参数,现在需要让它从响应中提取目标变量,并保存到Tavern的全局会话上下文——这样其他YAML用例就能直接引用这个变量。Tavern会自动把response(响应对象)和session(会话上下文对象)传给函数,直接用就行:
def post_function(response, session, **kwargs): # 先确认参数接收正常(调试用,上线可删) print("传入的额外参数:", kwargs) print("POST响应内容:", response.json()) # 从响应中提取你需要传递的变量,比如假设响应里有个`resource_id`字段 target_id = response.json().get("resource_id") # 把变量存入Tavern会话,其他用例可通过`!tavern.extract`引用 session["saved_resource_id"] = target_id # 如果需要做响应验证,返回布尔值表示验证结果(True=通过,False=失败) return response.status_code == kwargs.get("responseCode", 200)
3. 在GET请求YAML中引用会话变量
假设你的GET用例是get.tavern.yaml,可以通过!tavern.extract语法从会话中获取之前保存的变量:
test_name: 使用POST保存的变量发送GET请求 stages: - name: 携带变量发送GET请求 request: url: path_to_my_get_endpoint/{!tavern.extract saved_resource_id} method: GET headers: content-type: application/json response: status_code: 200
4. 关键注意事项
- 确保utils.py在pytest搜索路径:把它放在项目根目录,或者运行pytest时设置
PYTHONPATH环境变量,让pytest能找到utils模块。 - 用例运行顺序:要先跑POST用例再跑GET用例,才能保证变量已存入会话。可以通过指定文件顺序运行:
pytest.exe post.tavern.yaml get.tavern.yaml --junit-xml=./pass.xml - $ext函数返回值:如果用于响应验证,必须返回布尔值;如果仅处理变量,返回任意值都可以,但建议返回
True避免用例误判失败。
内容的提问来源于stack exchange,提问作者Will Black
相关产品推荐
相关产品推荐

