Skip to content

Commit 9788ca4

Browse files
committed
working on signing requests
1 parent 7d6eafd commit 9788ca4

File tree

4 files changed

+52
-7
lines changed

4 files changed

+52
-7
lines changed

http_client/src/vonage_http_client/auth.py

Lines changed: 16 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -37,10 +37,10 @@ def __init__(
3737
application_id: Optional[str] = None,
3838
private_key: Optional[str] = None,
3939
signature_secret: Optional[str] = None,
40-
signature_method: Optional[Literal['md5', 'sha1', 'sha256', 'sha512']] = None,
40+
signature_method: Optional[Literal['md5', 'sha1', 'sha256', 'sha512']] = 'md5',
4141
) -> None:
4242
self._validate_input_combinations(
43-
api_key, api_secret, application_id, private_key
43+
api_key, api_secret, application_id, private_key, signature_secret
4444
)
4545

4646
self._api_key = api_key
@@ -110,18 +110,27 @@ def sign_params(self, params: dict) -> dict:
110110

111111
if self._signature_method is None:
112112
hasher.update(self._signature_secret.encode())
113-
114113
return hasher.hexdigest()
115114

115+
def check_signature(self, params) -> bool:
116+
params = dict(params)
117+
signature = params.pop('sig', '').lower()
118+
return hmac.compare_digest(signature, self.signature(params))
119+
116120
def _validate_input_combinations(
117-
self, api_key, api_secret, application_id, private_key
121+
self, api_key, api_secret, application_id, private_key, signature_secret
118122
):
119-
if (api_key and not api_secret) or (not api_key and api_secret):
123+
if (api_secret or signature_secret) and not api_key:
124+
raise InvalidAuthError(
125+
'`api_key` must be set when `api_secret` or `signature_secret` is set.'
126+
)
127+
128+
if api_key and not (api_secret or signature_secret):
120129
raise InvalidAuthError(
121-
'Both api_key and api_secret must be set or both must be None.'
130+
'At least one of `api_secret` and `signature_secret` must be set if `api_key` is set.'
122131
)
123132

124133
if (application_id and not private_key) or (not application_id and private_key):
125134
raise InvalidAuthError(
126-
'Both application_id and private_key must be set or both must be None.'
135+
'Both `application_id` and `private_key` must be set or both must be None.'
127136
)

http_client/src/vonage_http_client/http_client.py

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -136,6 +136,10 @@ def make_request(
136136
self._headers['Authorization'] = self._auth.create_basic_auth_string()
137137
elif auth_type == 'signature':
138138
params = self._auth.sign_params(params)
139+
140+
print(params)
141+
print(self._auth.check_signature(params))
142+
139143
with self._session.request(
140144
request_type,
141145
url,
@@ -161,6 +165,7 @@ def _parse_response(self, response: Response) -> Union[dict, None]:
161165
logger.debug(
162166
f'Response received from {response.url} with status code: {response.status_code}; headers: {response.headers}'
163167
)
168+
print(response.request.headers)
164169
content_type = response.headers['Content-Type'].split(';', 1)[0]
165170
if 200 <= response.status_code < 300:
166171
if response.status_code == 204:

http_client/tests/test_auth.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,8 @@ def read_file(path):
1919
api_secret = '1234qwerasdfzxcv'
2020
application_id = 'asdfzxcv'
2121
private_key = read_file('data/dummy_private_key.txt')
22+
signature_secret = 'signature_secret'
23+
signature_method = 'sha256'
2224

2325

2426
def test_create_auth_class_and_get_objects():
@@ -27,6 +29,8 @@ def test_create_auth_class_and_get_objects():
2729
api_secret=api_secret,
2830
application_id=application_id,
2931
private_key=private_key,
32+
signature_secret=signature_secret,
33+
signature_method=signature_method,
3034
)
3135

3236
assert auth.api_key == api_key

http_client/tests/test_http_client.py

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -95,6 +95,33 @@ def test_make_post_request():
9595
assert loads(responses.calls[0].request.body) == params
9696

9797

98+
@responses.activate
99+
def test_make_post_request_with_signature():
100+
build_response(
101+
path, 'POST', 'https://example.com/post_signed_params', 'example_post.json'
102+
)
103+
client = HttpClient(
104+
Auth(
105+
api_key='asdfzxcv', signature_secret='qwerasdfzxcv', signature_method='sha256'
106+
),
107+
http_client_options={'api_host': 'example.com'},
108+
)
109+
params = {
110+
'test': 'post request',
111+
'testing': 'http client',
112+
}
113+
114+
res = client.post(
115+
host='example.com',
116+
request_path='/post_signed_params',
117+
params=params,
118+
auth_type='signature',
119+
)
120+
assert res['hello'] == 'world!'
121+
122+
assert loads(responses.calls[0].request.body) == params
123+
124+
98125
@responses.activate
99126
def test_http_response_general_error():
100127
build_response(path, 'GET', 'https://example.com/get_json', '400.json', 400)

0 commit comments

Comments
 (0)