Skip to content

Commit 5edb323

Browse files
committed
feat: add RPC matchers
1 parent 58f6a75 commit 5edb323

File tree

5 files changed

+80
-10
lines changed

5 files changed

+80
-10
lines changed

.pre-commit-config.yaml

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,3 @@ repos:
99
rev: 'v2.3.2'
1010
hooks:
1111
- id: autopep8
12-
13-
- repo: https://github.com/pre-commit/mirrors-mypy
14-
rev: 'v1.17.1'
15-
hooks:
16-
- id: mypy
17-
args: ['--strict']
18-
additional_dependencies:
19-
- types-setuptools
20-
- typing_extensions

pyproject.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
44

55
[project]
66
name = "sipgate_e2e_test_utils"
7-
version = "0.1.0"
7+
version = "0.2.0"
88
authors = []
99
description = "A library for common utils used in E2E testing (XML-, JSON-RPC, awaiting assertions, JobD helpers)"
1010
readme = "README.md"

requirements.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,2 @@
1+
http_request_recorder @ git+https://github.com/sipgate/http-request-recorder.git@main
12
pre-commit
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
import json
2+
from typing import Callable
3+
4+
from http_request_recorder import RecordedRequest
5+
6+
7+
def json_rpc(method: str) -> Callable[[RecordedRequest], bool]:
8+
def matcher(request: RecordedRequest) -> bool:
9+
if request.method != 'POST' or '/jsonrpc' != request.path.lower():
10+
return False
11+
12+
try:
13+
parsed = json.loads(request.body)
14+
except json.decoder.JSONDecodeError:
15+
return False
16+
17+
return 'method' in parsed and method == parsed['method']
18+
19+
return matcher
20+
21+
22+
def xml_rpc(method: str) -> Callable[[RecordedRequest], bool]:
23+
def matcher(request: RecordedRequest) -> bool:
24+
return (
25+
'POST' == request.method and
26+
'/rpc2' == request.path.lower() and
27+
b'<methodName>' + method.encode() + b'</methodName>' in request.body)
28+
29+
return matcher

tests/test_rpc_matchers.py

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
import json
2+
3+
from http_request_recorder import RecordedRequest
4+
5+
6+
from unittest import TestCase
7+
from sipgate_e2e_test_utils.rpc_matchers import xml_rpc, json_rpc
8+
9+
10+
class TestSipgateRpcMatchers(TestCase):
11+
def test_xml_rpc(self) -> None:
12+
assertions = [
13+
(False, ('POST', '/jsonrpc', json.dumps({'method': 'test_method', 'version': '1.1', 'params': [], 'id': 42}).encode())),
14+
(False, ('POST', '/jsonrpc', b'<?xml version="1.0"?><methodCall><methodName>test_method</methodName><params><param><value></value></param></params></methodCall>')),
15+
(False, ('GET', '/rpc2', b'<?xml version="1.0"?><methodCall><methodName>test_method</methodName><params><param><value></value></param></params></methodCall>')),
16+
(False, ('POST', '/rpc2', b'anydata')),
17+
(False, ('POST', '/rpc2', b'<?xml version="1.0"?><methodCall><methodName>another_method</methodName><params><param><value></value></param></params></methodCall>')),
18+
(True, ('POST', '/rpc2', b'<?xml version="1.0"?><methodCall><methodName>test_method</methodName><params><param><value></value></param></params></methodCall>')),
19+
(True, ('POST', '/RPC2', b'<?xml version="1.0"?><methodCall><methodName>test_method</methodName><params><param><value></value></param></params></methodCall>')),
20+
]
21+
22+
for (expected, (method, path, body)) in assertions:
23+
with self.subTest(f'expect {expected} for method={method} path={path} body={body.decode()}'):
24+
request = RecordedRequest()
25+
request.method = method
26+
request.path = path
27+
request.body = body
28+
29+
self.assertEqual(expected, xml_rpc('test_method')(request))
30+
31+
def test_json_rpc(self) -> None:
32+
assertions = [
33+
(False, ('POST', '/rpc2', b'<?xml version="1.0"?><methodCall><methodName>test_method</methodName><params><param><value></value></param></params></methodCall>')),
34+
(False, ('POST', '/rpc2', json.dumps({'method': 'test_method', 'version': '1.1', 'params': [], 'id': 42}).encode())),
35+
(False, ('GET', '/jsonrpc', json.dumps({'method': 'test_method', 'version': '1.1', 'params': [], 'id': 42}).encode())),
36+
(False, ('POST', '/jsonrpc', b'anydata')),
37+
(False, ('POST', '/jsonrpc', json.dumps({'method': 'another_method', 'version': '1.1', 'params': [], 'id': 42}).encode())),
38+
(True, ('POST', '/jsonrpc', json.dumps({'method': 'test_method', 'version': '1.1', 'params': [], 'id': 42}).encode())),
39+
(True, ('POST', '/JSONRPC', json.dumps({'method': 'test_method', 'version': '1.1', 'params': [], 'id': 42}).encode())),
40+
]
41+
42+
for (expected, (method, path, body)) in assertions:
43+
with self.subTest(f'expect {expected} for method={method} path={path} body={body.decode()}'):
44+
request = RecordedRequest()
45+
request.method = method
46+
request.path = path
47+
request.body = body
48+
49+
self.assertEqual(expected, json_rpc('test_method')(request))

0 commit comments

Comments
 (0)