Skip to content

Commit 146b105

Browse files
authored
[HOTFIX] [PRMDR-445] (#138)
* [PRMDR-445] Fix incorrect logic in token expiry time comparison, add unit test to verify new logic * [PRMDR-445] add one unit test to verify logic
1 parent 2e19091 commit 146b105

File tree

2 files changed

+177
-5
lines changed

2 files changed

+177
-5
lines changed

lambdas/services/pds_api_service.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,8 @@ def pds_request(self, nhs_number: str, retry_on_expired: bool):
2828
+ int(access_token_response["issued_at"]) / 1000
2929
)
3030
time_safety_margin_seconds = 10
31-
if time.time() - access_token_expiration > time_safety_margin_seconds:
31+
remaining_time_before_expiration = access_token_expiration - time.time()
32+
if remaining_time_before_expiration < time_safety_margin_seconds:
3233
access_token = self.get_new_access_token()
3334

3435
x_request_id = str(uuid.uuid4())

lambdas/tests/unit/services/test_pds_api_service.py

Lines changed: 175 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -169,28 +169,46 @@ def test_get_new_access_token_raise_PdsErrorException(mocker):
169169
mock_update_ssm.assert_not_called()
170170

171171

172+
def mock_pds_token_response_issued_at(timestamp_in_sec: float) -> dict:
173+
response_token = {
174+
"access_token": "Sr5PGv19wTEHJdDr2wx2f7IGd0cw",
175+
"expires_in": "599",
176+
"token_type": "Bearer",
177+
"issued_at": str(int(timestamp_in_sec * 1000)),
178+
}
179+
180+
return response_token
181+
182+
172183
def test_pds_request_valid_token(mocker):
173184
response = Response()
174185
response.status_code = 200
175186
response._content = json.dumps(PDS_PATIENT).encode("utf-8")
176-
mock_api_request_parameters = ("api.test/endpoint/", json.dumps(RESPONSE_TOKEN))
187+
mock_post = mocker.patch("requests.get", return_value=response)
188+
189+
time_now = 1600000000
190+
mocker.patch("time.time", return_value=time_now)
191+
mock_response_token = mock_pds_token_response_issued_at(time_now)
192+
193+
mock_api_request_parameters = (
194+
"api.test/endpoint/",
195+
json.dumps(mock_response_token),
196+
)
177197
nhs_number = "1111111111"
178198
mock_url_endpoint = "api.test/endpoint/Patient/" + nhs_number
179199
mock_authorization_header = {
180-
"Authorization": f"Bearer {RESPONSE_TOKEN['access_token']}",
200+
"Authorization": f"Bearer {mock_response_token['access_token']}",
181201
"X-Request-ID": "123412342",
182202
}
183203

184204
mock_get_parameters = mocker.patch(
185205
"services.pds_api_service.PdsApiService.get_parameters_for_pds_api_request",
186206
return_value=mock_api_request_parameters,
187207
)
188-
mocker.patch("time.time", return_value=1600000000.953031)
189208
mock_new_access_token = mocker.patch(
190209
"services.pds_api_service.PdsApiService.get_new_access_token"
191210
)
192211
mocker.patch("uuid.uuid4", return_value="123412342")
193-
mock_post = mocker.patch("requests.get", return_value=response)
194212

195213
pds_service.pds_request(nhs_number="1111111111", retry_on_expired=True)
196214

@@ -201,6 +219,159 @@ def test_pds_request_valid_token(mocker):
201219
)
202220

203221

222+
def test_pds_request_not_refresh_token_if_more_than_10_seconds_before_expiry(mocker):
223+
response = Response()
224+
response.status_code = 200
225+
response._content = json.dumps(PDS_PATIENT).encode("utf-8")
226+
mocker.patch("requests.get", return_value=response)
227+
228+
time_now = 1600000000
229+
mocker.patch("time.time", return_value=time_now)
230+
mock_response_token = mock_pds_token_response_issued_at(time_now - 599 + 11)
231+
232+
mock_api_request_parameters = (
233+
"api.test/endpoint/",
234+
json.dumps(mock_response_token),
235+
)
236+
237+
mock_get_parameters = mocker.patch(
238+
"services.pds_api_service.PdsApiService.get_parameters_for_pds_api_request",
239+
return_value=mock_api_request_parameters,
240+
)
241+
mock_new_access_token = mocker.patch(
242+
"services.pds_api_service.PdsApiService.get_new_access_token"
243+
)
244+
mocker.patch("uuid.uuid4", return_value="123412342")
245+
246+
pds_service.pds_request(nhs_number="1111111111", retry_on_expired=True)
247+
248+
mock_get_parameters.assert_called_once()
249+
mock_new_access_token.assert_not_called()
250+
251+
252+
def test_pds_request_refresh_token_9_seconds_before_expiration(mocker):
253+
response = Response()
254+
response.status_code = 200
255+
response._content = json.dumps(PDS_PATIENT).encode("utf-8")
256+
257+
time_now = 1600000000
258+
mocker.patch("time.time", return_value=time_now)
259+
mock_response_token = mock_pds_token_response_issued_at(time_now - 599 + 9)
260+
new_mock_access_token = "mock_access_token"
261+
262+
mock_api_request_parameters = (
263+
"api.test/endpoint/",
264+
json.dumps(mock_response_token),
265+
)
266+
nhs_number = "1111111111"
267+
mock_url_endpoint = "api.test/endpoint/Patient/" + nhs_number
268+
mock_authorization_header = {
269+
"Authorization": f"Bearer {new_mock_access_token}",
270+
"X-Request-ID": "123412342",
271+
}
272+
273+
mock_get_parameters = mocker.patch(
274+
"services.pds_api_service.PdsApiService.get_parameters_for_pds_api_request",
275+
return_value=mock_api_request_parameters,
276+
)
277+
mock_new_access_token = mocker.patch(
278+
"services.pds_api_service.PdsApiService.get_new_access_token",
279+
return_value=new_mock_access_token,
280+
)
281+
mocker.patch("uuid.uuid4", return_value="123412342")
282+
mock_post = mocker.patch("requests.get", return_value=response)
283+
284+
pds_service.pds_request(nhs_number="1111111111", retry_on_expired=True)
285+
286+
mock_get_parameters.assert_called_once()
287+
mock_new_access_token.assert_called_once()
288+
mock_post.assert_called_with(
289+
url=mock_url_endpoint, headers=mock_authorization_header
290+
)
291+
292+
293+
def test_pds_request_refresh_token_if_already_expired(mocker):
294+
response = Response()
295+
response.status_code = 200
296+
response._content = json.dumps(PDS_PATIENT).encode("utf-8")
297+
298+
time_now = 1600000000
299+
mocker.patch("time.time", return_value=time_now)
300+
mock_response_token = mock_pds_token_response_issued_at(time_now - 599)
301+
new_mock_access_token = "mock_access_token"
302+
303+
mock_api_request_parameters = (
304+
"api.test/endpoint/",
305+
json.dumps(mock_response_token),
306+
)
307+
nhs_number = "1111111111"
308+
mock_url_endpoint = "api.test/endpoint/Patient/" + nhs_number
309+
mock_authorization_header = {
310+
"Authorization": f"Bearer {new_mock_access_token}",
311+
"X-Request-ID": "123412342",
312+
}
313+
314+
mock_get_parameters = mocker.patch(
315+
"services.pds_api_service.PdsApiService.get_parameters_for_pds_api_request",
316+
return_value=mock_api_request_parameters,
317+
)
318+
mock_new_access_token = mocker.patch(
319+
"services.pds_api_service.PdsApiService.get_new_access_token",
320+
return_value=new_mock_access_token,
321+
)
322+
mocker.patch("uuid.uuid4", return_value="123412342")
323+
mock_post = mocker.patch("requests.get", return_value=response)
324+
325+
pds_service.pds_request(nhs_number="1111111111", retry_on_expired=True)
326+
327+
mock_get_parameters.assert_called_once()
328+
mock_new_access_token.assert_called_once()
329+
mock_post.assert_called_with(
330+
url=mock_url_endpoint, headers=mock_authorization_header
331+
)
332+
333+
334+
def test_pds_request_refresh_token_if_already_expired_11_seconds_ago(mocker):
335+
response = Response()
336+
response.status_code = 200
337+
response._content = json.dumps(PDS_PATIENT).encode("utf-8")
338+
339+
time_now = 1600000000
340+
mocker.patch("time.time", return_value=time_now)
341+
mock_response_token = mock_pds_token_response_issued_at(time_now - 599 - 11)
342+
new_mock_access_token = "mock_access_token"
343+
344+
mock_api_request_parameters = (
345+
"api.test/endpoint/",
346+
json.dumps(mock_response_token),
347+
)
348+
nhs_number = "1111111111"
349+
mock_url_endpoint = "api.test/endpoint/Patient/" + nhs_number
350+
mock_authorization_header = {
351+
"Authorization": f"Bearer {new_mock_access_token}",
352+
"X-Request-ID": "123412342",
353+
}
354+
355+
mock_get_parameters = mocker.patch(
356+
"services.pds_api_service.PdsApiService.get_parameters_for_pds_api_request",
357+
return_value=mock_api_request_parameters,
358+
)
359+
mock_new_access_token = mocker.patch(
360+
"services.pds_api_service.PdsApiService.get_new_access_token",
361+
return_value=new_mock_access_token,
362+
)
363+
mocker.patch("uuid.uuid4", return_value="123412342")
364+
mock_post = mocker.patch("requests.get", return_value=response)
365+
366+
pds_service.pds_request(nhs_number="1111111111", retry_on_expired=True)
367+
368+
mock_get_parameters.assert_called_once()
369+
mock_new_access_token.assert_called_once()
370+
mock_post.assert_called_with(
371+
url=mock_url_endpoint, headers=mock_authorization_header
372+
)
373+
374+
204375
def test_pds_request_expired_token(mocker):
205376
response = Response()
206377
response.status_code = 200

0 commit comments

Comments
 (0)