【问题标题】:Create a functioning Response object创建一个正常工作的响应对象
【发布时间】:2016-11-01 13:43:33
【问题描述】:

出于测试目的,我尝试在 python 中创建一个 Response() 对象,但事实证明它比听起来更难。

我试过这个:

from requests.models import Response

the_response = Response()
the_response.code = "expired"
the_response.error_type = "expired"
the_response.status_code = 400

但是当我尝试the_response.json() 时出现错误,因为该函数试图获取len(self.content)a.content 为空。 所以我设置了a._content = "{}",然后我得到一个编码错误,所以我必须更改a.encoding,但是它无法解码内容...... 这种情况一直在继续。有没有一种简单的方法来创建一个具有功能且具有任意 status_code 和内容的 Response 对象?

【问题讨论】:

  • 你有没有考虑过使用responses之类的东西?或者,创建一个mock 而不是尝试重新创建真实对象

标签: python python-requests


【解决方案1】:

这是因为 Response 对象(在 python3 上)的 _content 属性必须是字节而不是 unicode。

这是怎么做的:

from requests.models import Response

the_response = Response()
the_response.code = "expired"
the_response.error_type = "expired"
the_response.status_code = 400
the_response._content = b'{ "key" : "a" }'

print(the_response.json())

【讨论】:

  • 这将起作用,但如果requests 更改Response 的实现会中断;前导下划线表示不应依赖的内部细节。也就是说,它已经有一段时间没有改变了(这样的改变也可能会影响responses 的工作方式,除非它也模拟公共接口)。
  • 100% 同意,但至于 OP 问题 - 这是正确的解决方案。还赞成您的模拟解决方案(比第 3 方库好得多),但 OP 再次要求提供特定用例并想知道为什么他的代码不起作用。
【解决方案2】:

创建一个mock 对象,而不是尝试构建一个真实的对象:

from unittest.mock import Mock

from requests.models import Response

the_response = Mock(spec=Response)

the_response.json.return_value = {}
the_response.status_code = 400

提供spec 可确保当您尝试访问真正的Response 所没有的方法和属性时,mock 会报错。

【讨论】:

    【解决方案3】:

    只需使用responses 库为您完成:

    import responses
    
    @responses.activate
    def test_my_api():
        responses.add(responses.GET, 'http://whatever.org',
                      json={}, status=400)
    
        ...
    

    这样做的好处是它可以拦截真正的请求,而不必在某处注入响应。

    【讨论】:

      【解决方案4】:

      使用requests_mock 库的另一种方法,这里使用提供的夹具:

      import requests
      
      
      def test_response(requests_mock):
          requests_mock.register_uri('POST', 'http://test.com/', text='data', headers={
              'X-Something': '1',
          })
          response = requests.request('POST', 'http://test.com/', data='helloworld')
      
          ...
      

      【讨论】:

        猜你喜欢
        • 2015-10-26
        • 1970-01-01
        • 1970-01-01
        • 2018-06-25
        • 1970-01-01
        • 1970-01-01
        • 2014-12-10
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多