Skip to content

Commit a6346f9

Browse files
authored
VED-790-Redis-Schema-Storage (#867)
* validation_rules
1 parent 2792405 commit a6346f9

File tree

8 files changed

+360
-218
lines changed

8 files changed

+360
-218
lines changed

lambdas/redis_sync/poetry.lock

Lines changed: 264 additions & 199 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
11
class RedisCacheKey:
22
PERMISSIONS_CONFIG_FILE_KEY = "permissions_config.json"
33
DISEASE_MAPPING_FILE_KEY = "disease_mapping.json"
4+
VALIDATION_RULES_FILE_KEY = "validation_rules.json"

lambdas/redis_sync/src/redis_cacher.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,10 @@ def upload(bucket_name: str, file_key: str) -> dict:
2424

2525
# Transform
2626
redis_mappings = transform_map(config_file_content, file_key)
27+
if not redis_mappings:
28+
msg = f"No valid Redis mappings found for file '{file_key}'. Nothing uploaded."
29+
logger.warning(msg)
30+
return {"status": "warning", "message": msg}
2731

2832
redis_client = get_redis_client()
2933
for key, mapping in redis_mappings.items():

lambdas/redis_sync/src/transform_configs.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,3 +46,7 @@ def transform_supplier_permissions(mapping):
4646
"supplier_permissions": supplier_permissions,
4747
"ods_code_to_supplier": ods_code_to_supplier
4848
}
49+
50+
51+
def transform_validation_rules(data) -> dict:
52+
return {"validation_rules": data}
Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,22 @@
11
from constants import RedisCacheKey
2-
from transform_configs import transform_vaccine_map, transform_supplier_permissions
2+
from transform_configs import (
3+
transform_vaccine_map, transform_supplier_permissions, transform_validation_rules
4+
)
35
from common.clients import logger
46
'''
57
Transform config file to format required in REDIS cache.
68
'''
79

810

9-
def transform_map(data, file_type):
11+
def transform_map(data, file_type) -> dict:
1012
# Transform the vaccine map data as needed
1113
logger.info("Transforming data for file type: %s", file_type)
1214
if file_type == RedisCacheKey.PERMISSIONS_CONFIG_FILE_KEY:
1315
return transform_supplier_permissions(data)
1416
if file_type == RedisCacheKey.DISEASE_MAPPING_FILE_KEY:
1517
return transform_vaccine_map(data)
18+
if file_type == RedisCacheKey.VALIDATION_RULES_FILE_KEY:
19+
return transform_validation_rules(data)
20+
1621
logger.info("No specific transformation defined for file type: %s", file_type)
1722
return data # Default case, return data as is if no transformation is defined

lambdas/redis_sync/tests/test_redis_cacher.py

Lines changed: 24 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -6,21 +6,14 @@
66
class TestRedisCacher(unittest.TestCase):
77

88
def setUp(self):
9-
# mock s3_reader and transform_map
10-
self.s3_reader_patcher = patch("redis_cacher.S3Reader")
11-
self.mock_s3_reader = self.s3_reader_patcher.start()
12-
self.transform_map_patcher = patch("redis_cacher.transform_map")
13-
self.mock_transform_map = self.transform_map_patcher.start()
14-
self.redis_client_patcher = patch("common.redis_client.redis_client")
15-
self.mock_redis_client = self.redis_client_patcher.start()
16-
self.logger_info_patcher = patch("logging.Logger.info")
17-
self.mock_logger_info = self.logger_info_patcher.start()
9+
self.mock_s3_reader = patch("redis_cacher.S3Reader").start()
10+
self.mock_transform_map = patch("redis_cacher.transform_map").start()
11+
self.mock_redis_client = patch("common.redis_client.redis_client").start()
12+
self.mock_logger_info = patch("logging.Logger.info").start()
13+
self.mock_logger_warning = patch("logging.Logger.warning").start()
1814

1915
def tearDown(self):
20-
self.s3_reader_patcher.stop()
21-
self.transform_map_patcher.stop()
22-
self.redis_client_patcher.stop()
23-
self.logger_info_patcher.stop()
16+
patch.stopall()
2417

2518
def test_upload(self):
2619
mock_data = {"a": "b"}
@@ -75,3 +68,21 @@ def test_deletes_extra_fields(self):
7568
})
7669
self.mock_redis_client.hdel.assert_called_once_with("hash_name", "obsolete_key_1", "obsolete_key_2")
7770
self.assertEqual(result, {"status": "success", "message": f"File {file_key} uploaded to Redis cache."})
71+
72+
def test_unrecognised_format(self):
73+
mock_data = {"a": "b"}
74+
75+
self.mock_s3_reader.read = unittest.mock.Mock()
76+
self.mock_s3_reader.read.return_value = mock_data
77+
self.mock_transform_map.return_value = {}
78+
79+
bucket_name = "bucket"
80+
file_key = "file-key.my_yaml"
81+
result = RedisCacher.upload(bucket_name, file_key)
82+
83+
self.mock_s3_reader.read.assert_called_once_with(bucket_name, file_key)
84+
self.assertEqual(result["status"], "warning")
85+
self.assertEqual(result["message"], f"No valid Redis mappings found for file '{file_key}'. Nothing uploaded.")
86+
self.mock_logger_warning.assert_called_once()
87+
self.mock_redis_client.hmset.assert_not_called()
88+
self.mock_redis_client.hdel.assert_not_called()

lambdas/redis_sync/tests/test_transform_config.py

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,15 @@
22
import unittest
33
import json
44
from unittest.mock import patch
5-
from transform_configs import transform_vaccine_map, transform_supplier_permissions
5+
from transform_configs import (
6+
transform_vaccine_map, transform_supplier_permissions, transform_validation_rules
7+
)
68

79

810
class TestTransformConfigs(unittest.TestCase):
911
def setUp(self):
10-
self.logger_info_patcher = patch("transform_configs.logger.info")
11-
self.mock_logger_info = self.logger_info_patcher.start()
12+
self.mock_logger_info = patch("transform_configs.logger.info").start()
13+
self.mock_logger_warning = patch("transform_configs.logger.warning").start()
1214

1315
with open("./tests/test_data/disease_mapping.json") as mapping_data:
1416
self.sample_map = json.load(mapping_data)
@@ -17,7 +19,7 @@ def setUp(self):
1719
self.supplier_data = json.load(permissions_data)
1820

1921
def tearDown(self):
20-
self.logger_info_patcher.stop()
22+
patch.stopall()
2123

2224
def test_disease_to_vacc(self):
2325
with open("./tests/test_data/expected_disease_to_vacc.json") as f:
@@ -43,6 +45,12 @@ def test_ods_code_to_supplier(self):
4345
result = transform_supplier_permissions(self.supplier_data)
4446
self.assertEqual(result["ods_code_to_supplier"], expected)
4547

48+
def test_validation_rules(self):
49+
# validation schema is simple json returned as is to key "validation_rules"
50+
sample_schema = {"type": "object", "properties": {"name": {"type": "string"}}}
51+
result = transform_validation_rules(sample_schema)
52+
self.assertEqual(result, {"validation_rules": sample_schema})
53+
4654
def test_empty_input(self):
4755
result = transform_supplier_permissions([])
4856
self.assertEqual(result, {
Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
2+
import unittest
3+
from unittest.mock import patch
4+
from transform_map import transform_map
5+
from constants import RedisCacheKey
6+
7+
8+
class TestTransformMap(unittest.TestCase):
9+
def setUp(self):
10+
self.mock_logger_info = patch("transform_map.logger.info").start()
11+
self.mock_logger_warning = patch("transform_map.logger.warning").start()
12+
self.mock_supplier_permissions = patch("transform_map.transform_supplier_permissions",
13+
return_value={"result": "supplier"}).start()
14+
self.mock_vaccine_map = patch("transform_map.transform_vaccine_map", return_value={"result": "vaccine"}).start()
15+
self.mock_validation_rules = patch("transform_map.transform_validation_rules").start()
16+
17+
def tearDown(self):
18+
patch.stopall()
19+
20+
def test_permissions_config_file_key_calls_supplier_permissions(self):
21+
data = {"some": "data"}
22+
result = transform_map(data, RedisCacheKey.PERMISSIONS_CONFIG_FILE_KEY)
23+
self.mock_supplier_permissions.assert_called_once_with(data)
24+
self.assertEqual(result, {"result": "supplier"})
25+
self.mock_logger_info.assert_any_call(
26+
"Transforming data for file type: %s", RedisCacheKey.PERMISSIONS_CONFIG_FILE_KEY)
27+
28+
def test_disease_mapping_file_key_calls_vaccine_map(self):
29+
data = {"other": "data"}
30+
self.mock_validation_rules.return_value = {"validation_rules": data}
31+
result = transform_map(data, RedisCacheKey.DISEASE_MAPPING_FILE_KEY)
32+
self.mock_vaccine_map.assert_called_once_with(data)
33+
self.assertEqual(result, {"result": "vaccine"})
34+
self.mock_logger_info.assert_any_call(
35+
"Transforming data for file type: %s", RedisCacheKey.DISEASE_MAPPING_FILE_KEY)
36+
37+
def test_validation_rules_file_key_calls_validation_rules(self):
38+
data = {"validation": "schema"}
39+
self.mock_validation_rules.return_value = {"validation_rules": data}
40+
result = transform_map(data, RedisCacheKey.VALIDATION_RULES_FILE_KEY)
41+
self.mock_validation_rules.assert_called_once_with(data)
42+
self.assertEqual(result, {"validation_rules": data})
43+
self.mock_logger_info.assert_any_call(
44+
"Transforming data for file type: %s", RedisCacheKey.VALIDATION_RULES_FILE_KEY)

0 commit comments

Comments
 (0)