Python 3でリクエストとレスポンスをモックする方法は?

PYTHON3 チュートリアル

Python 3でリクエストとレスポンスをモックする方法

Python 3でHTTPリクエストとレスポンスをモックすることは、テストの際に非常に重要です。これにより、外部のAPIに依存せずに、コードの動作を確認することができます。特に、外部サービスが不安定な場合や、テスト環境でAPIを使用したくない場合に役立ちます。

モックの基本概念

モックとは、実際のオブジェクトの代わりに使用される偽物のオブジェクトです。Pythonでは、`unittest.mock`モジュールを使用してモックを作成します。このモジュールを使うことで、関数の戻り値を指定したり、呼び出し回数を確認したりすることができます。

Pythonでのモックの実装例

以下に、Pythonの`requests`ライブラリをモックする方法をいくつか紹介します。

例1: requests.getをモックする

まず、`requests.get`メソッドをモックして、特定のレスポンスを返す方法を見てみましょう。

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
from unittest.mock import patch
import requests
def get_example():
response = requests.get("https://api.example.com/data")
return response.json()
with patch('requests.get') as mock_get:
mock_get.return_value.json.return_value = {'key': 'value'}
result = get_example()
print(result) # {'key': 'value'}
from unittest.mock import patch import requests def get_example(): response = requests.get("https://api.example.com/data") return response.json() with patch('requests.get') as mock_get: mock_get.return_value.json.return_value = {'key': 'value'} result = get_example() print(result) # {'key': 'value'}
from unittest.mock import patch
import requests

def get_example():
    response = requests.get("https://api.example.com/data")
    return response.json()

with patch('requests.get') as mock_get:
    mock_get.return_value.json.return_value = {'key': 'value'}
    result = get_example()
    print(result)  # {'key': 'value'}

この例では、`requests.get`が呼ばれると、モックされたレスポンスが返されます。`return_value.json.return_value`は、`requests.get().json()`が返す値を指定しています。

例2: requests.postをモックする

次に、`requests.post`メソッドをモックして、特定のステータスコードを返す方法を示します。

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
from unittest.mock import patch
import requests
def post_example(data):
response = requests.post("https://api.example.com/data", json=data)
return response.status_code
with patch('requests.post') as mock_post:
mock_post.return_value.status_code = 201
result = post_example({'key': 'value'})
print(result) # 201
from unittest.mock import patch import requests def post_example(data): response = requests.post("https://api.example.com/data", json=data) return response.status_code with patch('requests.post') as mock_post: mock_post.return_value.status_code = 201 result = post_example({'key': 'value'}) print(result) # 201
from unittest.mock import patch
import requests

def post_example(data):
    response = requests.post("https://api.example.com/data", json=data)
    return response.status_code

with patch('requests.post') as mock_post:
    mock_post.return_value.status_code = 201
    result = post_example({'key': 'value'})
    print(result)  # 201

この例では、`requests.post`が呼ばれると、モックされたステータスコード201が返されます。

例3: 外部APIを完全にモックする

最後に、より複雑な例として、外部API全体をモックする方法を紹介します。これにより、複数のエンドポイントを持つAPIのテストが可能になります。

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
from unittest.mock import patch
import requests
def fetch_data(endpoint):
response = requests.get(f"https://api.example.com/{endpoint}")
return response.json()
api_responses = {
'endpoint1': {'data': 'value1'},
'endpoint2': {'data': 'value2'},
}
def mock_get(url, *args, **kwargs):
endpoint = url.split('/')[-1]
return MockResponse(api_responses.get(endpoint, {}))
class MockResponse:
def __init__(self, json_data):
self.json_data = json_data
def json(self):
return self.json_data
with patch('requests.get', side_effect=mock_get):
print(fetch_data('endpoint1')) # {'data': 'value1'}
print(fetch_data('endpoint2')) # {'data': 'value2'}
from unittest.mock import patch import requests def fetch_data(endpoint): response = requests.get(f"https://api.example.com/{endpoint}") return response.json() api_responses = { 'endpoint1': {'data': 'value1'}, 'endpoint2': {'data': 'value2'}, } def mock_get(url, *args, **kwargs): endpoint = url.split('/')[-1] return MockResponse(api_responses.get(endpoint, {})) class MockResponse: def __init__(self, json_data): self.json_data = json_data def json(self): return self.json_data with patch('requests.get', side_effect=mock_get): print(fetch_data('endpoint1')) # {'data': 'value1'} print(fetch_data('endpoint2')) # {'data': 'value2'}
from unittest.mock import patch
import requests

def fetch_data(endpoint):
    response = requests.get(f"https://api.example.com/{endpoint}")
    return response.json()

api_responses = {
    'endpoint1': {'data': 'value1'},
    'endpoint2': {'data': 'value2'},
}

def mock_get(url, *args, **kwargs):
    endpoint = url.split('/')[-1]
    return MockResponse(api_responses.get(endpoint, {}))

class MockResponse:
    def __init__(self, json_data):
        self.json_data = json_data

    def json(self):
        return self.json_data

with patch('requests.get', side_effect=mock_get):
    print(fetch_data('endpoint1'))  # {'data': 'value1'}
    print(fetch_data('endpoint2'))  # {'data': 'value2'}

この例では、`requests.get`をカスタム関数`mock_get`で置き換えています。この関数はURLを解析し、対応するモックレスポンスを返します。

まとめ

Python 3でリクエストとレスポンスをモックすることは、テストを効率的に行うための強力な手段です。`unittest.mock`を使用することで、外部依存を排除し、コードのテストをより信頼性の高いものにすることができます。これらの例を参考にして、あなたのプロジェクトに適したモックの実装を試してみてください。

Python 3でリクエストとレスポンスをモックする方法は、unittest.mockモジュールを使用することです。このモジュールを使うと、テスト中に外部APIやサーバーとの通信をシミュレートすることができます。

具体的には、unittest.mockモジュールのpatchメソッドを使って、リクエストを送信する関数やクラスをモック化し、テスト中にその振る舞いを制御することができます。また、requestsモジュールを使ってHTTPリクエストを送信する場合は、requestsモジュールをモック化して、テスト中にリクエストとレスポンスを操作することができます。

このようにして、Python 3でリクエストとレスポンスをモックすることで、外部依存性を排除してテストをより効果的に行うことができます。

購読
通知


0 Comments
Inline Feedbacks
View all comments