You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

调用pytest fixture时出现TypeError:'Response'对象不可调用问题

问题分析与解决方案

问题根源

  1. fixture返回的是Response对象而非可调用函数:你定义的get_request fixture在被pytest实例化时,会直接执行内部的GET请求并返回requests.Response对象。测试函数中get_request(test_url + '/endpoint')试图把这个Response对象当作函数调用,必然触发TypeError: 'Response' object is not callable错误。
  2. fixture逻辑存在bug:代码中用了elif params is None,这意味着只有当headers为None时才会检查params。如果headers不为空但params为None,params会保持None值,后续传给requests.get时可能引发异常。

解决方案

根据你的需求,分两种场景处理:

场景1:希望fixture是可复用的请求工具(推荐)

修改conftest.py中的fixture,让它返回一个可调用的内部函数,而不是直接执行请求:

@pytest.fixture()
def get_request():
    def _get_request(url=base_url, headers=None, params=None):
        # 修复逻辑bug:用if替代elif
        if headers is None:
            headers = {}
        if params is None:
            params = {}
        session = requests.Session()
        response = session.get(
            url=url,
            headers=get_token(), 
            params=params,
            verify=False,
        )
        return response
    # 返回内部函数,让测试函数可以调用它传入参数
    return _get_request

测试函数无需修改,此时get_request是一个可调用的函数,执行后返回对应URL的Response对象:

import pytest
import requests

def test_get_request2(get_request):
     response = get_request(test_url + '/endpoint')
     # 后续可以断言response的状态码、响应体等
     assert response.status_code == 200

场景2:希望fixture直接返回指定请求的Response

如果不需要动态传参,而是让fixture直接返回特定请求的结果,可以通过pytest的参数化机制实现:
修改conftest.py:

@pytest.fixture()
def get_request(request):
    # 从request.param中获取测试用例传入的参数
    req_params = request.param or {}
    url = req_params.get('url', base_url)
    headers = req_params.get('headers', {})
    params = req_params.get('params', {})
    
    session = requests.Session()
    response = session.get(
        url=url,
        headers=get_token(), 
        params=params,
        verify=False,
    )
    return response

测试函数通过@pytest.mark.parametrize传参,并设置indirect=True让pytest把参数传给fixture:

import pytest
import requests

@pytest.mark.parametrize(
    'get_request',
    [{'url': test_url + '/endpoint'}],  # 传入请求的URL参数
    indirect=True  # 告诉pytest将参数传递给fixture处理
)
def test_get_request2(get_request):
    # 此时get_request就是目标URL的Response对象,直接使用
    assert get_request.status_code == 200

内容的提问来源于stack exchange,提问作者K Ʌ Z E

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.01 21:55:42