boto3-assist 0.27.0__py3-none-any.whl → 0.28.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- boto3_assist/utilities/serialization_utility.py +81 -0
- boto3_assist/version.py +1 -1
- {boto3_assist-0.27.0.dist-info → boto3_assist-0.28.0.dist-info}/METADATA +1 -1
- {boto3_assist-0.27.0.dist-info → boto3_assist-0.28.0.dist-info}/RECORD +7 -7
- {boto3_assist-0.27.0.dist-info → boto3_assist-0.28.0.dist-info}/WHEEL +0 -0
- {boto3_assist-0.27.0.dist-info → boto3_assist-0.28.0.dist-info}/licenses/LICENSE-EXPLAINED.txt +0 -0
- {boto3_assist-0.27.0.dist-info → boto3_assist-0.28.0.dist-info}/licenses/LICENSE.txt +0 -0
|
@@ -8,6 +8,7 @@ import datetime as dt
|
|
|
8
8
|
import decimal
|
|
9
9
|
import inspect
|
|
10
10
|
import json
|
|
11
|
+
import typing
|
|
11
12
|
import uuid
|
|
12
13
|
from datetime import datetime
|
|
13
14
|
from decimal import Decimal
|
|
@@ -116,6 +117,86 @@ class JsonConversions:
|
|
|
116
117
|
Used for snake_case to camelCase and vice versa
|
|
117
118
|
"""
|
|
118
119
|
|
|
120
|
+
@staticmethod
|
|
121
|
+
def string_to_json_obj(
|
|
122
|
+
value: str | list | dict, raise_on_error: bool = True, retry: int = 0
|
|
123
|
+
) -> typing.Union[dict, typing.Any, None]:
|
|
124
|
+
"""
|
|
125
|
+
Converts a string to a JSON object.
|
|
126
|
+
|
|
127
|
+
Args:
|
|
128
|
+
value: The value to convert (string, list, or dict).
|
|
129
|
+
raise_on_error: Whether to raise an exception on error.
|
|
130
|
+
retry: The number of retry attempts made.
|
|
131
|
+
|
|
132
|
+
Returns:
|
|
133
|
+
The converted JSON object, or the original value if conversion fails.
|
|
134
|
+
"""
|
|
135
|
+
# Handle empty/None values
|
|
136
|
+
if not value:
|
|
137
|
+
return {}
|
|
138
|
+
|
|
139
|
+
# Return dicts unchanged
|
|
140
|
+
if isinstance(value, dict):
|
|
141
|
+
return value
|
|
142
|
+
|
|
143
|
+
# Check retry limit early
|
|
144
|
+
if retry > 5:
|
|
145
|
+
raise RuntimeError("Too many attempts to convert string to JSON")
|
|
146
|
+
|
|
147
|
+
try:
|
|
148
|
+
# Convert to string if needed
|
|
149
|
+
if not isinstance(value, str):
|
|
150
|
+
value = str(value)
|
|
151
|
+
|
|
152
|
+
# Clean up the string
|
|
153
|
+
value = value.replace("\n", "").strip()
|
|
154
|
+
if value.startswith("'") and value.endswith("'"):
|
|
155
|
+
value = value.strip("'").strip()
|
|
156
|
+
|
|
157
|
+
# Parse JSON
|
|
158
|
+
parsed_value = json.loads(value)
|
|
159
|
+
|
|
160
|
+
# Handle nested string JSON (recursive case)
|
|
161
|
+
if isinstance(parsed_value, str):
|
|
162
|
+
return JsonConversions.string_to_json_obj(parsed_value, raise_on_error, retry + 1)
|
|
163
|
+
|
|
164
|
+
return parsed_value
|
|
165
|
+
|
|
166
|
+
except json.JSONDecodeError as e:
|
|
167
|
+
# Try to fix malformed JSON with single quotes
|
|
168
|
+
if "Expecting property name enclosed in double quotes" in str(e) and retry < 5:
|
|
169
|
+
if isinstance(value, str):
|
|
170
|
+
fixed_json = JsonConversions.convert_bad_json_string(value)
|
|
171
|
+
return JsonConversions.string_to_json_obj(fixed_json, raise_on_error, retry + 1)
|
|
172
|
+
|
|
173
|
+
if raise_on_error:
|
|
174
|
+
raise e
|
|
175
|
+
return {}
|
|
176
|
+
|
|
177
|
+
except Exception as e:
|
|
178
|
+
if raise_on_error:
|
|
179
|
+
logger.exception({"source": "string_to_json_obj", "error": str(e), "value": value})
|
|
180
|
+
raise e
|
|
181
|
+
|
|
182
|
+
logger.warning({"source": "string_to_json_obj", "returning_original": True, "value": value})
|
|
183
|
+
return value
|
|
184
|
+
|
|
185
|
+
|
|
186
|
+
@staticmethod
|
|
187
|
+
def convert_bad_json_string(bad_json: str) -> str:
|
|
188
|
+
"""
|
|
189
|
+
Fixes malformed JSON by converting single quotes to double quotes.
|
|
190
|
+
|
|
191
|
+
Args:
|
|
192
|
+
bad_json: Malformed JSON string with single quotes.
|
|
193
|
+
|
|
194
|
+
Returns:
|
|
195
|
+
Fixed JSON string with proper double quotes.
|
|
196
|
+
"""
|
|
197
|
+
# Use a placeholder to safely swap quotes
|
|
198
|
+
return bad_json.replace("'", "§§§").replace('"', "'").replace("§§§", '"')
|
|
199
|
+
|
|
119
200
|
@staticmethod
|
|
120
201
|
def _camel_to_snake(value: str) -> str:
|
|
121
202
|
"""Converts a camelCase to a snake_case"""
|
boto3_assist/version.py
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
__version__ = "0.
|
|
1
|
+
__version__ = "0.28.0"
|
|
@@ -6,7 +6,7 @@ boto3_assist/connection_tracker.py,sha256=UgfR9RlvXf3A4ssMr3gDMpw89ka8mSRvJn4M34
|
|
|
6
6
|
boto3_assist/http_status_codes.py,sha256=G0zRSWenwavYKETvDF9tNVUXQz3Ae2gXdBETYbjvJe8,3284
|
|
7
7
|
boto3_assist/role_assumption_mixin.py,sha256=PMUU5yC2FUBjFD1UokVkRY3CPB5zTw85AhIB5BMtbc8,1031
|
|
8
8
|
boto3_assist/session_setup_mixin.py,sha256=X-JQKyyaWNA8Z8kKgf2V2I5vsiLAH8udLTX_xepnsdQ,3140
|
|
9
|
-
boto3_assist/version.py,sha256=
|
|
9
|
+
boto3_assist/version.py,sha256=MRQGtOXBhcDKeeNOL0LiB-cllo6kfd8_KGJOvaDp0XQ,23
|
|
10
10
|
boto3_assist/aws_lambda/event_info.py,sha256=OkZ4WzuGaHEu_T8sB188KBgShAJhZpWASALKRGBOhMg,14648
|
|
11
11
|
boto3_assist/aws_lambda/mock_context.py,sha256=LPjHP-3YSoY6iPl1kPqJDwSVf1zLNTcukUunDtYcbK0,116
|
|
12
12
|
boto3_assist/cloudwatch/cloudwatch_connection.py,sha256=mnGWaLSQpHh5EeY7Ek_2o9JKHJxOELIYtQVMX1IaHn4,2480
|
|
@@ -57,10 +57,10 @@ boto3_assist/utilities/file_operations.py,sha256=IYhJkh8wUPMvGnyDRRa9yOCDdHN9wR3
|
|
|
57
57
|
boto3_assist/utilities/http_utility.py,sha256=_K39Fq0V4QcgklAWctUktuMjqXDTwgMld77IOUfR2zc,1282
|
|
58
58
|
boto3_assist/utilities/logging_utility.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
59
59
|
boto3_assist/utilities/numbers_utility.py,sha256=wzv9d0uXT_2_ZHHio7LBzibwxPqhGpvbq9HinrVn_4A,10160
|
|
60
|
-
boto3_assist/utilities/serialization_utility.py,sha256=
|
|
60
|
+
boto3_assist/utilities/serialization_utility.py,sha256=m5wRZNeWW9VltQPVNziR27OGKO3MDJm6mFmcDHwN-n4,24479
|
|
61
61
|
boto3_assist/utilities/string_utility.py,sha256=XxUIz19L2LFFTRDAAmdPa8Qhn40u9yO7g4nULFuvg0M,11033
|
|
62
|
-
boto3_assist-0.
|
|
63
|
-
boto3_assist-0.
|
|
64
|
-
boto3_assist-0.
|
|
65
|
-
boto3_assist-0.
|
|
66
|
-
boto3_assist-0.
|
|
62
|
+
boto3_assist-0.28.0.dist-info/METADATA,sha256=XrwSSxvnnUASG0OPp4ulP99LgF8CTTcwExXgXbZG1UE,2879
|
|
63
|
+
boto3_assist-0.28.0.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
|
|
64
|
+
boto3_assist-0.28.0.dist-info/licenses/LICENSE-EXPLAINED.txt,sha256=WFREvTpfTjPjDHpOLADxJpCKpIla3Ht87RUUGii4ODU,606
|
|
65
|
+
boto3_assist-0.28.0.dist-info/licenses/LICENSE.txt,sha256=PXDhFWS5L5aOTkVhNvoitHKbAkgxqMI2uUPQyrnXGiI,1105
|
|
66
|
+
boto3_assist-0.28.0.dist-info/RECORD,,
|
|
File without changes
|
{boto3_assist-0.27.0.dist-info → boto3_assist-0.28.0.dist-info}/licenses/LICENSE-EXPLAINED.txt
RENAMED
|
File without changes
|
|
File without changes
|