0

I have a JSON string in the following format that i get from an API and need to reformat it, so that I can check the difference between two lookups (which settings are different in the different modules):

{ "modules": [
        {
            "name": "A1",
            "bar" : "AA",
            "settings" :[
                {
                    "name" : "set1",
                    "value" : "1"
                },
                {
                    "name" : "set2",
                    "value" : "2"
                }
            ]
        },
        {
            "name": "A2",
            "bar" : "DD",
            "settings" :[
                {
                    "name" : "set1",
                    "value" : "A21"
                }
            ]
        },
        {
            "name": "A1",
            "settings" :[
                {
                    "name" : "set3",
                    "value" : "1"
                }
            ]
        }
    ]
}

and need to get it into a dictionary of the format

'A1' : {
    'bar' : 'AA',
    'settings': {
        'set1' : '1',
        'set2' : '2',
        'set3' : '1'
    }....

is there any nicer, easier way to do this than, assuming I have read the string from above in a dictionary json_dict

modules_a = { module['name'] : { 'bar' : module['bar'], 'settings' : {}} for module in json_dict['modules']

for module in json_dict['modules']:
    modules_a[module['name']]['settings'].update( s['name']: s['value'] for s in module['settings'] )
0

2 Answers 2

1

you have some errors in the input, you missed a comma after bar. Here is a more readable version:

# First, merge together the modules with the same names
concatenated_json = {'modules': []}
reference_dict = dict()

for module in json["modules"]:
    # Check whether module has a 'bar' and whether it has already been mentioned
    if module.get("bar") is not None and reference_dict.get(module["bar"]) is None:
        # Module has not been mentioned yet, add it to the fixed dict and note its reference
        concatenated_json['modules'].append(module)
        reference_dict[module["name"]] = module
    else:
        # Append to settings of a previously mentioned module
        reference_dict[module["name"]]["settings"] += module["settings"]

json = concatenated_json

# Format dict in a required way
modules_a = {
    module["name"]:{
        "bar": module["bar"],
        "settings": {
            setting["name"]: setting["value"] for setting in module["settings"]
        }
    }
    for module in json["modules"]
}
Sign up to request clarification or add additional context in comments.

Comments

0

Here's a way to do it, although I'm not sure what you meant about "resorting".

# Preallocate result.
modules_a = {module['name']: {'settings': []} for module in json_dict['modules']}

for module in json_dict['modules']:
    obj = modules_a[module['name']]
    obj.update({k: v for k, v in module.items() if k != 'settings'})
    # Accumulate 'settings' in a list.
    obj['settings'].extend([{setting['name']: setting['value']}
                                for setting in module['settings'] ])

import json
print(json.dumps(modules_a, indent=4))

Result:

{
    "A1": {
        "settings": [
            {
                "set1": "1"
            },
            {
                "set2": "2"
            },
            {
                "set3": "1"
            }
        ],
        "bar": "AA",
        "name": "A1"
    },
    "A2": {
        "settings": [
            {
                "set1": "A21"
            }
        ],
        "bar": "DD",
        "name": "A2"
    }
}

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.