在Django中,我有一个向外部API发出请求的视图。该视图位于my_app中。
class ExternalAPIView(View):
def get(self, request, *args, **kwargs):
...
external_api_response = requests.get(settings.EXTERNAL_API_URL)
...
对于其单元测试,我对@patch装饰器的side_effect参数使用以下函数。
def mocked_requests_get_for_external_api(*args, **kwargs):
class MockResponse:
def __init__(self, content, status_code):
self.content = content
self.status_code = status_code
if args[0] == settings.EXTERNAL_API_URL:
return MockResponse(json.dumps('{"value": 1}'), 200)
return MockResponse(None, 404)
...并且单元测试像这样没有问题:
@patch("my_app.views.requests.get", side_effect= mocked_requests_get_for_external_api)
def test_external_api(self, mock_get):
response = self.client.get(settings.EXTERNAL_API_VIEW_URL)
assert response.status_code == 200
data = json.loads(response.content)
assert data["value"] == 1
但是,我在同一项目中有另一个视图,该视图按如下方式调用此ExternalAPIView:
class MainView(View):
def get(self, request, *args, **kwargs):
...
response = requests.get(request.build_absolute_uri(settings.EXTERNAL_API_VIEW_URL))
...
我想为此MainView创建一个单元测试,它将通过settings.EXTERNAL_API_VIEW_URL进行对ExternalAPIView的调用,但是要在ExternalAPIView内部模拟外部API调用。
首先有可能吗?如果是这样,我该怎么办?
答案 0 :(得分:0)
这可以通过仅模拟对requests.get
的第二次调用并保留第一次调用来实现,例如:
import requests
@patch("my_app.views.requests.get", side_effect=[requests.get, mocked_requests_get_for_external_api])
def test_main_view_api(self, mock_get):
response = self.client.get(MAIN_VIEW_URL)
assert response.status_code == 200
data = json.loads(response.content)
assert data["value"] == 1