Skip to content

Commit 6c8fcaf

Browse files
committed
resolve wider issues
1 parent 007b4dd commit 6c8fcaf

File tree

5 files changed

+33
-41
lines changed

5 files changed

+33
-41
lines changed

lambdas/filenameprocessor/src/file_validation.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ def is_valid_datetime(timestamp: str) -> bool:
3737
return True
3838

3939

40-
def validate_extended_attributes_file_key(file_key: str) -> str:
40+
def validate_extended_attributes_file_key(file_key: str) -> tuple[str, str]:
4141
"""
4242
Checks that all elements of the file key are valid, raises an exception otherwise.
4343
Returns a string containing the organization code.

lambdas/filenameprocessor/src/supplier_permissions.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ def validate_vaccine_type_permissions(vaccine_type: str, supplier: str) -> list:
2222
return supplier_permissions
2323

2424

25-
def validate_permissions_for_extended_attributes_files(vaccine_type: str, supplier: str) -> tuple[str]:
25+
def validate_permissions_for_extended_attributes_files(vaccine_type: str, supplier: str) -> str:
2626
"""
2727
Checks that the supplier has COVID vaccine type and its CUD permissions.
2828
Raises an exception if the supplier does not have at least one permission for the vaccine type.

lambdas/filenameprocessor/tests/test_file_key_validation.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -135,7 +135,7 @@ def test_validate_extended_attributes_file_key(self, mock_get_redis_client):
135135
mock_redis.hget.side_effect = create_mock_hget(MOCK_ODS_CODE_TO_SUPPLIER, {})
136136
mock_redis.hkeys.return_value = ["COVID"]
137137
mock_get_redis_client.return_value = mock_redis
138-
vaccine_type, supplier = validate_extended_attributes_file_key(file_key)
138+
_, supplier = validate_extended_attributes_file_key(file_key)
139139
self.assertEqual(
140140
supplier,
141141
expected_result,

lambdas/filenameprocessor/tests/test_lambda_handler.py

Lines changed: 29 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -427,37 +427,40 @@ def raise_connection_error(*args, **kwargs):
427427
@patch("elasticache.get_redis_client")
428428
def test_lambda_handler_extended_attributes_invalid_timestamp(self, mock_get_redis_client):
429429
"""
430-
Invalid timestamps (too short or non-parseable) should fail validation and move to archive.
430+
Invalid timestamps (too short or non-parseable) should fail validation
431+
and move to extended-attributes-archive/.
431432
"""
432-
# Valid Redis
433+
# Set up valid Redis responses
433434
mock_redis = fakeredis.FakeStrictRedis()
434435
mock_redis.hget = Mock(side_effect=create_mock_hget({"X8E5B": "RAVS"}, {}))
435436
mock_redis.hkeys = Mock(return_value=["COVID", *all_vaccine_types_in_this_test_file])
436437
mock_get_redis_client.return_value = mock_redis
437438

438-
# Case 1: too short timestamp
439-
invalid_timestamp_key = "Vaccination_Extended_Attributes_v1_5_X8E5B_20000101T0000.csv"
440-
s3_client.put_object(
441-
Bucket=BucketNames.SOURCE, Key=invalid_timestamp_key, Body=MOCK_EXTENDED_ATTRIBUTES_FILE_CONTENT
442-
)
443-
with patch("file_name_processor.uuid4", return_value="invalid_timestamp_id"):
444-
lambda_handler(self.make_event([self.make_record(invalid_timestamp_key)]), None)
445-
# Failed audit and archive
446-
item1 = self.get_audit_table_items()[0]
447-
self.assertEqual(item1[AuditTableKeys.STATUS]["S"], "Failed")
448-
s3_client.get_object(Bucket=BucketNames.SOURCE, Key=f"extended-attributes-archive/{invalid_timestamp_key}")
449-
450-
# Case 2: non-parseable timestamp
451-
invalid_timestamp_key2 = "Vaccination_Extended_Attributes_v1_5_X8E5B_20XX0101T00000001.csv"
452-
s3_client.put_object(
453-
Bucket=BucketNames.SOURCE, Key=invalid_timestamp_key2, Body=MOCK_EXTENDED_ATTRIBUTES_FILE_CONTENT
454-
)
455-
with patch("file_name_processor.uuid4", return_value="invalid_timestamp_id2"):
456-
lambda_handler(self.make_event([self.make_record(invalid_timestamp_key2)]), None)
457-
# Failed audit and archive
458-
item2 = self.get_audit_table_items()[-1]
459-
self.assertEqual(item2[AuditTableKeys.STATUS]["S"], "Failed")
460-
s3_client.get_object(Bucket=BucketNames.SOURCE, Key=f"extended-attributes-archive/{invalid_timestamp_key2}")
439+
invalid_cases = [
440+
("Vaccination_Extended_Attributes_v1_5_X8E5B_20000101T0000.csv", "invalid_timestamp_id"),
441+
("Vaccination_Extended_Attributes_v1_5_X8E5B_20XX0101T00000001.csv", "invalid_timestamp_id2"),
442+
]
443+
444+
for file_key, fake_msg_id in invalid_cases:
445+
with self.subTest(f"Invalid timestamp test for: {file_key}"):
446+
# Upload the invalid file
447+
s3_client.put_object(
448+
Bucket=BucketNames.SOURCE,
449+
Key=file_key,
450+
Body=MOCK_EXTENDED_ATTRIBUTES_FILE_CONTENT,
451+
)
452+
453+
with patch("file_name_processor.uuid4", return_value=fake_msg_id):
454+
lambda_handler(self.make_event([self.make_record(file_key)]), None)
455+
456+
# Validate audit entry
457+
audit_items = self.get_audit_table_items()
458+
last_item = audit_items[-1] # always get the most recent write
459+
self.assertEqual(last_item[AuditTableKeys.STATUS]["S"], "Failed")
460+
461+
archived_key = f"extended-attributes-archive/{file_key}"
462+
retrieved = s3_client.get_object(Bucket=BucketNames.SOURCE, Key=archived_key)
463+
self.assertIsNotNone(retrieved)
461464

462465
@patch("elasticache.get_redis_client")
463466
def test_lambda_handler_extended_attributes_extension_checks(self, mock_get_redis_client):
@@ -569,16 +572,11 @@ def test_lambda_handler_extended_attributes_extension_checks(self, mock_get_redi
569572
patch("file_name_processor.uuid4", return_value=test_cases[0].message_id),
570573
patch(
571574
"file_name_processor.copy_file_to_external_bucket",
572-
side_effect=lambda src_bucket, key, dst_bucket, dst_key, exp_owner, exp_src_owner: (
573-
# effectively do nothing
574-
None,
575-
),
575+
side_effect=lambda src_bucket, key, dst_bucket, dst_key, exp_owner, exp_src_owner: (None,),
576576
),
577577
):
578578
lambda_handler(self.make_event([self.make_record(invalid_file_key)]), None)
579579

580-
# Assert audit table entry captured with Failed and queue_name set to the identifier.
581-
# Assert that the ClientError message is an InvalidFileKeyError.
582580
table_items = self.get_audit_table_items()
583581
# Removed brittle assertion on total audit count; subsequent checks below verify the expected audit content
584582
item = table_items[-1]
@@ -594,7 +592,6 @@ def test_lambda_handler_extended_attributes_extension_checks(self, mock_get_redi
594592
self.assertEqual(item[AuditTableKeys.EXPIRES_AT]["N"], str(test_cases[0].expires_at))
595593
# File should be moved to source under archive/
596594
dest_key = f"extended-attributes-archive/{invalid_file_key}"
597-
print(f" destination file is at {s3_client.list_objects(Bucket=BucketNames.SOURCE)}")
598595
retrieved = s3_client.get_object(Bucket=BucketNames.SOURCE, Key=dest_key)
599596
self.assertIsNotNone(retrieved)
600597

lambdas/filenameprocessor/tests/test_supplier_permissions.py

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -91,17 +91,14 @@ def test_validate_permissions_for_extended_attributes_files_fail_no_covid(self):
9191

9292
def test_validate_permissions_for_extended_attributes_files_fail_partial_ops(self):
9393
"""Supplier with only partial COVID permissions (e.g., C only) should raise error as CUD required."""
94-
# Note: Implementation checks only the first matching COVID entry's operation string.
95-
# Therefore, entries like COVID.CRUD (which includes C, U, D letters) will pass.
96-
# The following cases should fail because the first COVID entry lacks at least one of C/U/D.
9794
partial_permission_cases = [
9895
["COVID.C"],
9996
["COVID.U"],
10097
["COVID.D"],
10198
["COVID.CU"],
10299
["COVID.UD"],
103100
["COVID.CD"],
104-
["COVID.S"], # status only
101+
["COVID.S"],
105102
]
106103

107104
for permissions in partial_permission_cases:
@@ -119,15 +116,13 @@ def test_validate_permissions_for_extended_attributes_files_fail_partial_ops(sel
119116

120117
def test_validate_permissions_for_extended_attributes_files_multiple_entries(self):
121118
"""Multiple COVID permission entries should pass only if the first matching COVID entry contains CUD."""
122-
# Case: First entry has CUDS -> success
123119
with patch(
124120
"supplier_permissions.get_supplier_permissions_from_cache",
125121
return_value=["COVID.CUDS", "COVID.C"],
126122
):
127123
result = validate_permissions_for_extended_attributes_files("COVID", "RAVS")
128124
self.assertEqual(result, "RAVS_COVID")
129125

130-
# Case: First entry lacks CUD (even if later one has CUDS) -> fail
131126
with patch(
132127
"supplier_permissions.get_supplier_permissions_from_cache",
133128
return_value=["COVID.C", "COVID.CUDS"],

0 commit comments

Comments
 (0)