diff --git a/benedict/serializers/ini.py b/benedict/serializers/ini.py index 2903c9c..5b7fc41 100644 --- a/benedict/serializers/ini.py +++ b/benedict/serializers/ini.py @@ -1,8 +1,10 @@ from configparser import DEFAULTSECT as default_section from configparser import RawConfigParser from io import StringIO +from json.decoder import JSONDecodeError from benedict.serializers.abstract import AbstractSerializer +from benedict.serializers.json import JSONSerializer from benedict.utils import type_util @@ -17,6 +19,7 @@ class INISerializer(AbstractSerializer): "ini", ], ) + self._json = JSONSerializer() @staticmethod def _get_parser(options): @@ -49,9 +52,14 @@ class INISerializer(AbstractSerializer): for section in parser.sections(): data[section] = {} for option, _ in parser.items(section): - data[section][option] = self._get_section_option_value( - parser, section, option - ) + value = self._get_section_option_value(parser, section, option) + if type_util.is_string(value): + try: + value_decoded = self._json.decode(value) + value = value_decoded + except JSONDecodeError: + pass + data[section][option] = value return data def encode(self, d, **kwargs): @@ -63,7 +71,10 @@ class INISerializer(AbstractSerializer): section = key parser.add_section(section) for option_key, option_value in value.items(): - parser.set(section, option_key, f"{option_value}") + if type_util.is_collection(option_value): + parser.set(section, option_key, self._json.encode(option_value)) + else: + parser.set(section, option_key, option_value) str_data = StringIO() parser.write(str_data) return str_data.getvalue() diff --git a/tests/github/test_issue_0284.py b/tests/github/test_issue_0284.py new file mode 100644 index 0000000..15de7b6 --- /dev/null +++ b/tests/github/test_issue_0284.py @@ -0,0 +1,36 @@ +import unittest + +from benedict import benedict + + +class github_issue_0284_test_case(unittest.TestCase): + """ + This class describes a github issue 0284 test case. + https://github.com/fabiocaccamo/python-benedict/issues/284 + + To run this specific test: + - Run python -m unittest tests.github.test_issue_0284 + """ + + def test_from_ini_returns_str_instead_of_dict(self): + original = benedict( + { + "section1": { + "key1": "value1", + }, + "sectionA": { + "keyA": "valueA", + "keyB": "valueB", + "keyC": { + "subkeyC": "subvalueC", + }, + }, + } + ) + readback = benedict.from_ini(original.to_ini()) + keypath = "sectionA.keyC" + # print("original vs readback") + # print(original.get(keypath), type(original.get(keypath))) + # print("-- vs --") + # print(readback.get(keypath), type(readback.get(keypath))) + self.assertEqual(original.get(keypath), readback.get(keypath))