From 72fe6ab3f412fbfd802c6b8694c880db592e0cea Mon Sep 17 00:00:00 2001 From: Bee Webb Date: Sun, 30 Jun 2024 15:27:31 +0000 Subject: [PATCH] json_input: If `json_dict` is not a dict, return a useful error/warning https://github.com/OpenDataServices/flatten-tool/issues/442 --- CHANGELOG.md | 4 ++++ flattentool/json_input.py | 9 +++++++++ flattentool/tests/test_json_input.py | 21 +++++++++++++++++++++ 3 files changed, 34 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 5cc79d8..cca8036 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -13,6 +13,10 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. - Ignore null characters in the input CSV file when reading configuration from the header rows https://github.com/OpenDataServices/flatten-tool/pull/446 +### Changed + +- If `json_dict` is not a dict, return a useful error/warning https://github.com/OpenDataServices/flatten-tool/issues/442 + ## [0.24.2] - 2024-06-12 ### Fixed diff --git a/flattentool/json_input.py b/flattentool/json_input.py index ab28ec7..8fd8ac9 100644 --- a/flattentool/json_input.py +++ b/flattentool/json_input.py @@ -28,6 +28,7 @@ import zc.zlibstorage import ZODB.FileStorage +from flattentool.exceptions import DataErrorWarning from flattentool.i18n import _ from flattentool.input import path_search from flattentool.schema import make_sub_sheet_name @@ -310,6 +311,14 @@ def parse(self): # This is particularly useful for IATI XML, in order to not # fall over on empty activity, e.g. continue + + if not isinstance(json_dict, dict): + warn( + _(f"The value at index {num} is not a JSON object"), + DataErrorWarning, + ) + continue + self.parse_json_dict(json_dict, sheet=self.main_sheet) # only persist every 2000 objects. peristing more often slows down storing. # 2000 top level objects normally not too much to store in memory. diff --git a/flattentool/tests/test_json_input.py b/flattentool/tests/test_json_input.py index a98186e..b15b3da 100644 --- a/flattentool/tests/test_json_input.py +++ b/flattentool/tests/test_json_input.py @@ -112,6 +112,27 @@ def test_parse_basic_json_dict(): assert parser.sub_sheets == {} +def test_parse_not_json_dict(recwarn): + parser = JSONParser(root_json_dict=[["test"], {"a": "b"}, "test"]) + assert list(parser.main_sheet) == ["a"] + assert list(parser.main_sheet.lines) == [{"a": "b"}] + assert parser.sub_sheets == {} + + assert len(recwarn) == 2 + + w = recwarn.pop(UserWarning) + assert ( + repr(w.message) + == "DataErrorWarning('The value at index 0 is not a JSON object')" + ) + + w = recwarn.pop(UserWarning) + assert ( + repr(w.message) + == "DataErrorWarning('The value at index 2 is not a JSON object')" + ) + + def test_parse_nested_dict_json_dict(): parser = JSONParser( root_json_dict=[