diff --git a/aws_lambda_powertools/utilities/data_classes/active_mq_event.py b/aws_lambda_powertools/utilities/data_classes/active_mq_event.py index 058a6a6ecf4..09981bdcdd2 100644 --- a/aws_lambda_powertools/utilities/data_classes/active_mq_event.py +++ b/aws_lambda_powertools/utilities/data_classes/active_mq_event.py @@ -27,7 +27,9 @@ def decoded_data(self) -> str: @property def json_data(self) -> Any: """Parses the data as json""" - return json.loads(self.decoded_data) + if self._json_data is None: + self._json_data = json.loads(self.decoded_data) + return self._json_data @property def connection_id(self) -> str: diff --git a/aws_lambda_powertools/utilities/data_classes/code_pipeline_job_event.py b/aws_lambda_powertools/utilities/data_classes/code_pipeline_job_event.py index e13d32fb169..e17bd13807c 100644 --- a/aws_lambda_powertools/utilities/data_classes/code_pipeline_job_event.py +++ b/aws_lambda_powertools/utilities/data_classes/code_pipeline_job_event.py @@ -23,7 +23,9 @@ def user_parameters(self) -> str: @property def decoded_user_parameters(self) -> Dict[str, Any]: """Json Decoded user parameters""" - return json.loads(self.user_parameters) + if self._json_data is None: + self._json_data = json.loads(self.user_parameters) + return self._json_data class CodePipelineActionConfiguration(DictWrapper): diff --git a/aws_lambda_powertools/utilities/data_classes/common.py b/aws_lambda_powertools/utilities/data_classes/common.py index f209fc8c192..88d1f1d9761 100644 --- a/aws_lambda_powertools/utilities/data_classes/common.py +++ b/aws_lambda_powertools/utilities/data_classes/common.py @@ -8,6 +8,7 @@ class DictWrapper: def __init__(self, data: Dict[str, Any]): self._data = data + self._json_data: Optional[Any] = None def __getitem__(self, key: str) -> Any: return self._data[key] @@ -65,7 +66,9 @@ def body(self) -> Optional[str]: @property def json_body(self) -> Any: """Parses the submitted body as json""" - return json.loads(self.decoded_body) + if self._json_data is None: + self._json_data = json.loads(self.decoded_body) + return self._json_data @property def decoded_body(self) -> str: diff --git a/aws_lambda_powertools/utilities/data_classes/rabbit_mq_event.py b/aws_lambda_powertools/utilities/data_classes/rabbit_mq_event.py index 7676e6ff9b5..0822a58da18 100644 --- a/aws_lambda_powertools/utilities/data_classes/rabbit_mq_event.py +++ b/aws_lambda_powertools/utilities/data_classes/rabbit_mq_event.py @@ -88,7 +88,9 @@ def decoded_data(self) -> str: @property def json_data(self) -> Any: """Parses the data as json""" - return json.loads(self.decoded_data) + if self._json_data is None: + self._json_data = json.loads(self.decoded_data) + return self._json_data class RabbitMQEvent(DictWrapper): diff --git a/tests/functional/data_classes/test_amazon_mq.py b/tests/functional/data_classes/test_amazon_mq.py index 0f4f5079565..a88a962c17b 100644 --- a/tests/functional/data_classes/test_amazon_mq.py +++ b/tests/functional/data_classes/test_amazon_mq.py @@ -34,6 +34,7 @@ def test_active_mq_event(): messages = list(event.messages) message = messages[1] assert message.json_data["timeout"] == 0 + assert message.json_data["data"] == "CZrmf0Gw8Ov4bqLQxD4E" def test_rabbit_mq_event(): @@ -47,6 +48,7 @@ def test_rabbit_mq_event(): assert message.data is not None assert message.decoded_data is not None assert message.json_data["timeout"] == 0 + assert message.json_data["data"] == "CZrmf0Gw8Ov4bqLQxD4E" assert isinstance(message, RabbitMessage) properties = message.basic_properties diff --git a/tests/functional/test_data_classes.py b/tests/functional/test_data_classes.py index 7a211ec2e01..86d9344ca4d 100644 --- a/tests/functional/test_data_classes.py +++ b/tests/functional/test_data_classes.py @@ -272,6 +272,8 @@ def test_cognito_pre_token_generation_trigger_event(): claims_override_details.set_group_configuration_groups_to_override(expected_groups) assert claims_override_details.group_configuration.groups_to_override == expected_groups assert event["response"]["claimsOverrideDetails"]["groupOverrideDetails"]["groupsToOverride"] == expected_groups + claims_override_details = event.response.claims_override_details + assert claims_override_details["groupOverrideDetails"]["groupsToOverride"] == expected_groups claims_override_details.set_group_configuration_iam_roles_to_override(["role"]) assert claims_override_details.group_configuration.iam_roles_to_override == ["role"] @@ -1054,6 +1056,7 @@ def test_base_proxy_event_json_body(): data = {"message": "Foo"} event = BaseProxyEvent({"body": json.dumps(data)}) assert event.json_body == data + assert event.json_body["message"] == "Foo" def test_base_proxy_event_decode_body_key_error(): @@ -1084,7 +1087,7 @@ def test_base_proxy_event_json_body_with_base64_encoded_data(): event = BaseProxyEvent({"body": encoded_data, "isBase64Encoded": True}) # WHEN calling json_body - # THEN then base64 decode and json load + # THEN base64 decode and json load assert event.json_body == data @@ -1120,7 +1123,8 @@ def test_kinesis_stream_event_json_data(): json_value = {"test": "value"} data = base64.b64encode(bytes(json.dumps(json_value), "utf-8")).decode("utf-8") event = KinesisStreamEvent({"Records": [{"kinesis": {"data": data}}]}) - assert next(event.records).kinesis.data_as_json() == json_value + record = next(event.records) + assert record.kinesis.data_as_json() == json_value def test_alb_event(): @@ -1392,9 +1396,11 @@ def test_code_pipeline_event_decoded_data(): event = CodePipelineJobEvent(load_event("codePipelineEventData.json")) assert event.data.continuation_token is None - decoded_params = event.data.action_configuration.configuration.decoded_user_parameters + configuration = event.data.action_configuration.configuration + decoded_params = configuration.decoded_user_parameters assert decoded_params == event.decoded_user_parameters - assert "VALUE" == decoded_params["KEY"] + assert decoded_params["KEY"] == "VALUE" + assert configuration.decoded_user_parameters["KEY"] == "VALUE" assert "my-pipeline-SourceArtifact" == event.data.input_artifacts[0].name