Skip to content

Commit

Permalink
Allow raw parameter to accept callable like body elements
Browse files Browse the repository at this point in the history
  • Loading branch information
ramast authored and jamielennox committed Jan 22, 2024
1 parent b3f7080 commit 3acc5e4
Show file tree
Hide file tree
Showing 6 changed files with 44 additions and 11 deletions.
3 changes: 3 additions & 0 deletions doc/source/response.rst
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,9 @@ Dynamic Response
================

A callback can be provided in place of any of the body elements.
raw attribute also accepts callable that returns HTTPResponse.
The HTTPResponse should have `preload_content=False` or it may not work properly.

Callbacks must be a function in the form of

.. code:: python
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
features:
- |
When using dynamic responses, you can now use a callback function for the
raw HTTPResponse object. This aligns it with all the other parameters that
can be mocked.
2 changes: 1 addition & 1 deletion requests_mock/adapter.pyi
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@ class Adapter(BaseAdapter, _RequestHistoryTracker):
text: Union[str, Callback[str]] = ...,
content: Union[bytes, Callback[bytes]] = ...,
body: Union[IOBase, Callback[IOBase]] = ...,
raw: HTTPResponse = ...,
raw: Union[HTTPResponse, Callback[HTTPResponse]] = ...,
exc: Union[Exception, Type[Exception]] = ...,
additional_matcher: AdditionalMatcher = ...,
**kwargs: Any
Expand Down
18 changes: 9 additions & 9 deletions requests_mock/mocker.pyi
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,7 @@ class MockerCore:
text: Union[str, Callback[str]] = ...,
content: Union[bytes, Callback[bytes]] = ...,
body: Union[IOBase, Callback[IOBase]] = ...,
raw: HTTPResponse = ...,
raw: Union[HTTPResponse, Callback[HTTPResponse]] = ...,
exc: Union[Exception, Type[Exception]] = ...,
additional_matcher: AdditionalMatcher = ...,
json_encoder: Optional[Type[JSONEncoder]] = ...,
Expand All @@ -77,7 +77,7 @@ class MockerCore:
text: Union[str, Callback[str]] = ...,
content: Union[bytes, Callback[bytes]] = ...,
body: Union[IOBase, Callback[IOBase]] = ...,
raw: HTTPResponse = ...,
raw: Union[HTTPResponse, Callback[HTTPResponse]] = ...,
exc: Union[Exception, Type[Exception]] = ...,
additional_matcher: AdditionalMatcher = ...,
json_encoder: Optional[Type[JSONEncoder]] = ...,
Expand All @@ -99,7 +99,7 @@ class MockerCore:
text: Union[str, Callback[str]] = ...,
content: Union[bytes, Callback[bytes]] = ...,
body: Union[IOBase, Callback[IOBase]] = ...,
raw: HTTPResponse = ...,
raw: Union[HTTPResponse, Callback[HTTPResponse]] = ...,
exc: Union[Exception, Type[Exception]] = ...,
additional_matcher: AdditionalMatcher = ...,
json_encoder: Optional[Type[JSONEncoder]] = ...,
Expand All @@ -121,7 +121,7 @@ class MockerCore:
text: Union[str, Callback[str]] = ...,
content: Union[bytes, Callback[bytes]] = ...,
body: Union[IOBase, Callback[IOBase]] = ...,
raw: HTTPResponse = ...,
raw: Union[HTTPResponse, Callback[HTTPResponse]] = ...,
exc: Union[Exception, Type[Exception]] = ...,
additional_matcher: AdditionalMatcher = ...,
json_encoder: Optional[Type[JSONEncoder]] = ...,
Expand All @@ -143,7 +143,7 @@ class MockerCore:
text: Union[str, Callback[str]] = ...,
content: Union[bytes, Callback[bytes]] = ...,
body: Union[IOBase, Callback[IOBase]] = ...,
raw: HTTPResponse = ...,
raw: Union[HTTPResponse, Callback[HTTPResponse]] = ...,
exc: Union[Exception, Type[Exception]] = ...,
additional_matcher: AdditionalMatcher = ...,
json_encoder: Optional[Type[JSONEncoder]] = ...,
Expand All @@ -165,7 +165,7 @@ class MockerCore:
text: Union[str, Callback[str]] = ...,
content: Union[bytes, Callback[bytes]] = ...,
body: Union[IOBase, Callback[IOBase]] = ...,
raw: HTTPResponse = ...,
raw: Union[HTTPResponse, Callback[HTTPResponse]] = ...,
exc: Union[Exception, Type[Exception]] = ...,
additional_matcher: AdditionalMatcher = ...,
json_encoder: Optional[Type[JSONEncoder]] = ...,
Expand All @@ -187,7 +187,7 @@ class MockerCore:
text: Union[str, Callback[str]] = ...,
content: Union[bytes, Callback[bytes]] = ...,
body: Union[IOBase, Callback[IOBase]] = ...,
raw: HTTPResponse = ...,
raw: Union[HTTPResponse, Callback[HTTPResponse]] = ...,
exc: Union[Exception, Type[Exception]] = ...,
additional_matcher: AdditionalMatcher = ...,
json_encoder: Optional[Type[JSONEncoder]] = ...,
Expand All @@ -209,7 +209,7 @@ class MockerCore:
text: Union[str, Callback[str]] = ...,
content: Union[bytes, Callback[bytes]] = ...,
body: Union[IOBase, Callback[IOBase]] = ...,
raw: HTTPResponse = ...,
raw: Union[HTTPResponse, Callback[HTTPResponse]] = ...,
exc: Union[Exception, Type[Exception]] = ...,
additional_matcher: AdditionalMatcher = ...,
json_encoder: Optional[Type[JSONEncoder]] = ...,
Expand All @@ -231,7 +231,7 @@ class MockerCore:
text: Union[str, Callback[str]] = ...,
content: Union[bytes, Callback[bytes]] = ...,
body: Union[IOBase, Callback[IOBase]] = ...,
raw: HTTPResponse = ...,
raw: Union[HTTPResponse, Callback[HTTPResponse]] = ...,
exc: Union[Exception, Type[Exception]] = ...,
additional_matcher: AdditionalMatcher = ...,
json_encoder: Optional[Type[JSONEncoder]] = ...,
Expand Down
2 changes: 1 addition & 1 deletion requests_mock/response.py
Original file line number Diff line number Diff line change
Expand Up @@ -270,7 +270,7 @@ def _call(f, *args, **kwargs):
text=_call(self._params.get('text')),
content=_call(self._params.get('content')),
body=_call(self._params.get('body')),
raw=self._params.get('raw'),
raw=_call(self._params.get('raw')),
json_encoder=self._params.get('json_encoder'),
status_code=context.status_code,
reason=context.reason,
Expand Down
24 changes: 24 additions & 0 deletions tests/test_adapter.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,12 +10,15 @@
# License for the specific language governing permissions and limitations
# under the License.

import http.client
import io
import json
import re
import urllib.parse

import purl
import requests
from urllib3 import HTTPResponse

import requests_mock
from . import base
Expand Down Expand Up @@ -119,6 +122,27 @@ def _text_cb(request, context):
self.assertHeaders(resp)
self.assertLastRequest()

def test_raw_callback(self):
status_code = 401
data = 'testdata'

def _raw_cb(request, context):
return HTTPResponse(
status=status_code,
headers=self.headers,
body=io.BytesIO(data.encode('utf-8')),
preload_content=False,
reason=http.client.responses.get(status_code),
)

self.adapter.register_uri('GET', self.url, raw=_raw_cb)
resp = self.session.get(self.url)
self.assertEqual(status_code, resp.status_code)
self.assertEqual(data, resp.text)
self.assertEqual(data.encode('utf-8'), resp.content)
self.assertHeaders(resp)
self.assertLastRequest()

def test_json(self):
json_data = {'hello': 'world'}
self.adapter.register_uri('GET',
Expand Down

0 comments on commit 3acc5e4

Please sign in to comment.