Parsing JSON with Python to retrieve values within a dictionary - python

I am trying to parse JSON and retrieve a certain value (ID) but I am getting the following error:
TypeError: string indices must be integers
The following is my code and JSON:
import json
# JSON string
info_symbol = '{"status":{"timestamp":"2023-01-21T15:18:43.937Z","error_code":0,"error_message":null,"elapsed":21,"credit_count":1,"notice":null},"data":{"BITCOIN":{"id":15907,"name":"HarryPotterObamaSonic10Inu","symbol":"BITCOIN"}}}'
# Convert string to Python dict
test_dict = json.loads(info_symbol)
print(test_dict['data'])
for name in test_dict['data']['BITCOIN']:
print(name['id'])
Id like to grab solely the ID - so: 15907
"id":15907,

You don't need the looping in that case to get only the id. If you need all the key and values from the dictionary then you can iterate like below-
import json
# JSON string
info_symbol = '{
"status": {
"timestamp": "2023-01-21T15:18:43.937Z",
"error_code": 0,
"error_message": null,
"elapsed": 21,
"credit_count": 1,
"notice": null
},
"data": {
"BITCOIN": {
"id": 15907,
"name": "HarryPotterObamaSonic10Inu",
"symbol": "BITCOIN"
}
}
}'
# Convert string to Python dict
test_dict = json.loads(info_symbol)
data = test_dict['data']['BITCOIN']
print(f"only id = {data['id']}")
print("--------")
for key, value in test_dict['data']['BITCOIN'].items():
print(key, value)
Output
only id = 15907
--------
id 15907
name HarryPotterObamaSonic10Inu
symbol BITCOIN

for name in test_dict['data']['BITCOIN']:
print(name)
output
{'BITCOIN': {'id': 15907, 'name': 'HarryPotterObamaSonic10Inu', 'symbol': 'BITCOIN'}}
id
name
symbol
So, if you do name['id'], you will get id in first iteration and in second iteration it will throw error
you can get value of id by:
for key, value in test_dict['data']['BITCOIN'].items():
if key=='id':
print(value)
#15907
with comprehension:
[value for key, value in test_dict['data']['BITCOIN'].items() if key=='id']
[15907]

Keys Error
Fellow, test_dict['data]['BITCOIN'] is represented as:
{
'id': 15907,
'name': 'HarryPotterObamaSonic10Inu',
'symbol': 'BITCOIN'
}
Your are iterating the above dictionary, so when you print(name[id]), name iterator take the key:Value of id, name, and symbol.
Literally tour code is accesing as id.['id'], name.['id'], symbol.['id]'.
SOLUTION
just access to the id adding one more bracket:
print( test_dict['data']['BITCOIN']['id'] )
get rid of for loop.

Related

Is there any way to find a specific data in json, without specifying the category

I'm trying to make a script that grabs the "name" field, without me specifying the id
{
"accounts" : {
"random id" : {
"name" : "random name"
}
}
}
If I wanna take the "name", I have to do something like
a = json.loads(jsondata)
b = a["accounts"]
c = b["random id"]
print(str(c["name"]))
But I don't know the id, how can I make it get the "name" without opening "accounts"....?
The object a that is returned by json.loads is a nested dictionary. You can look through the keys of the dictionary and check if there is a key that matched your searchstring (e.g. "name"). If there is, return the value. If there is no key that matches, you check every value in the dict and check if the value itself is a dict (so this would be the second level dict). If it is, you recursively call the function again.
def find_recursive(dictionary, key):
if key in dictionary:
return dictionary[key]
for value in dictionary.values():
if isinstance(value, dict):
return find_recursive(value, key)
>>> find_recursive(a, 'name')
'random name'
This should work:
import json
json = json.loads('{"accounts" : {"random id" : {"name" : "random name" }}}')
accounts = json["accounts"]
for value in json["accounts"].values():
print(value["name"])

How to automatically parse JSON and get all key value pairs in a variable?

I'm trying to dynamically create a database without hard coding all of the API response values for columns and rows so I want to learn how to automatically parse through JSON and put all the keys/values in a variable so I can sort through and put them in the db.
Lets say I had some JSON like this:
(modified snippet from destiny 2 API response indented by 5)
{
"Response": {
"profile": {
"data": {
"userInfo": {
"crossSaveOverride": 1,
"applicableMembershipTypes": [
3,
1
],
"isPublic": true,
"membershipType": 1,
"membershipId": "123",
"displayName": "Name1",
"bungieGlobalDisplayName": "name again",
"bungieGlobalDisplayNameCode": 0000
},
"dateLastPlayed": "2021-6-18T02:33:01Z",
"versionsOwned": 127,
"characterIds": [
"id1",
"id2",
"id3"
],
"seasonHashes": [
3243434344,
3423434244,
3432342443,
3434243244
],
"currentSeasonHash": 3434243244,
"currentSeasonRewardPowerCap": 1330
},
"privacy": 1
}
},
"ErrorCode": 1,
"ThrottleSeconds": 0,
"ErrorStatus": "Success",
"Message": "Ok",
"MessageData": {}
}
I want to automatically parse through and get all of the key/values minus the error code area so everything under "Response". It would all go into the database for example:
displayName
isPublic
Name1
True
Name2
False
I know how to parse normally or loop through but only to grab values like:
displayName = Response["Response"]["profile"]["data"]["userInfo"]["displayName"]
How does one grab all keys and values and then automatically store in a variable from the lowest level? Also, how would one exclude keys if they are not needed?
EDIT: Adding Clarification
I learned that this JSON response type is a dict and I can use Response.keys() and Response.values() to get the keys and values.
What I am asking is, from Response["Response"], how to get all of the keys and values down to the bottom level and exclude the ones I don't need.
For example if I do:
r = Response["Response"]
for key in r.keys():
print(key)
I'm only going to get profile which is what I don't need.
I would have to do:
r = Response["Response"]["profile"]["data"]["userInfo"]
for key in r.keys():
print(key)
which would return
crossSaveOverride
applicableMembershipTypes
isPublic
membershipType
membershipId
displayName
bungieGlobalDisplayName
bungieGlobalDisplayNameCode
Which is what I need but I do not want to manually define
["Response"]["profile"]["data"]["userInfo"]or similar for every response. I want to grab everything automatically while excluding the items I don't need.
Dmitry Torba over at Get all keys of a nested dictionary posted a function that does what you want.
def recursive_items(dictionary):
for key, value in dictionary.items():
if type(value) is dict:
yield from recursive_items(value)
else:
yield (key, value)
a = {'a': {1: {1: 2, 3: 4}, 2: {5: 6}}}
for key, value in recursive_items(a):
print(key, value)
I have tried this approach, what if there is list type in given dictionary!
CallPretty.py
def JsonPrint(response, response_Keys):
print()
print(response_Keys)
for i in range(len(response_Keys)):
if type(response[response_Keys[i]]) == list:
print()
for j in range(len(response[response_Keys[i]])):
if type(response[response_Keys[i]][j]) == dict:
JsonPrint(response[response_Keys[i]][j], list(response[response_Keys[i]][j].keys()))
elif type(response[response_Keys[i]]) == dict:
JsonPrint(response[response_Keys[i]], list(response[response_Keys[i]].keys()))
else:
print(response_Keys[i], ':')
for j in range(len(response[response_Keys[i]].split('\n'))):
print('\t', response[response_Keys[i]].split('\n')[j])

How to write json in specific format in python

I want to display JSON in specific format and data will be from database.So how to form in specific format in python.Format of JSON is
{
"data":{"Device Id" : value from db,"Date":Current Time},
"Data":
{
"Temperature":
{
value from db
},
"Consumptions":
{
value from db
},
"Error":
[
{
value from db
}
]
}
}
I have tried this:
dict((query.description[i][0], value) for i, value in enumerate(row)) for row in query.fetchall()
But I'm not getting desired output and i'm unable to pass data to json. So how to pass data to json.
Error Im getting is Dictionay update sequence element 0# has length 1; 2 is required
Did you use json module?
import json
print json.dumps(yourStructure, indent=6)

Show certain parameter JSON in python

I have some JSON output, for example:
«somethings»:
{
"id": 1,
"param1": 11,
"param2": 12
},
{
"id": 2,
"param1": 21,
"param2": 22
}
I want to show only param1 for each "id". I can do it for use circle for:
for i in range(0, 50):
print parsed_string["somethings"][i]["param1"]
but I don't now how many ids i can get.
In the JSON it's just an array of objects (and Python list once parsed), so you can iterate over all of them like so:
for obj in parsed_string["somethings"]:
print(obj["param1"])
If you need to display key-value, use following code
import json as json
json_string = '[{"id":"A 0","param1":"SOME DATA 1","param2":"SOME DATA 2"},' \
'{"id":"A 1","param1":"SOME DATA 2","param2":"SOME DATA 2"},' \
'{"id":"A 2","param1":"SOME DATA 2","param2":"SOME DATA 2"}]'
json_data = json.loads(json_string)
for d in json_data:
for key, value in d.iteritems():
if (key in ("param1")): # ("id", "param1")
print key, value

how to parse json where key is variable in python?

i am parsing a log file which is in json format,
and contains data in the form of key : value pair.
i was stuck at place where key itself is variable. please look at the attached code
in this code i am able to access keys like username,event_type,ip etc.
problem for me is to access the values inside the "submission" key where
i4x-IITB-CS101-problem-33e4aac93dc84f368c93b1d08fa984fc_2_1 is a variable key which will change for different users,
how can i access it as a variable ?
{
"username": "batista",
"event_type": "problem_check",
"ip": "127.0.0.1",
"event": {
"submission": {
"i4x-IITB-CS101-problem-33e4aac93dc84f368c93b1d08fa984fc_2_1": {
"input_type": "choicegroup",
"question": "",
"response_type": "multiplechoiceresponse",
"answer": "MenuInflater.inflate()",
"variant": "",
"correct": true
}
},
"success": "correct",
"grade": 1,
"correct_map": {
"i4x-IITB-CS101-problem-33e4aac93dc84f368c93b1d08fa984fc_2_1": {
"hint": "",
"hintmode": null,
"correctness": "correct",
"npoints": null,
"msg": "",
"queuestate": null
}
}
this is my code how i am solving it :
import json
import pprint
with open("log.log") as infile:
# Loop until we have parsed all the lines.
for line in infile:
# Read lines until we find a complete object
while (True):
try:
json_data = json.loads(line)
username = json_data['username']
print "username :- " + username
except ValueError:
line += next(infile)
how can i access i4x-IITB-CS101-problem-33e4aac93dc84f368c93b1d08fa984fc_2_1 key and
data inside this key ??
You don't need to know the key in advance, you can simply iterate over the dictionary:
for k,v in obj['event']['submission'].iteritems():
print(k,v)
Suppose you have a dictionary of type d = {"a":"b"} then d.popitem() would give you a tuple ("a","b") which is (key,value). So using this you can access key-value pairs without knowing the key.
In you case if j is the main dictionary then j["event"]["submission"].popitem() would give you tuple
("i4x-IITB-CS101-problem-33e4aac93dc84f368c93b1d08fa984fc_2_1": {
"input_type": "choicegroup",
"question": "",
"response_type": "multiplechoiceresponse",
"answer": "MenuInflater.inflate()",
"variant": "",
"correct": true
})
Hope this is what you were asking.
using python json module you'll end up with a dictionary of parsed values from the above JSON data
import json
parsed = json.loads(this_sample_data_in_question)
# parsed is a dictionary, so are "correct_map" and "submission" dictionary keys within "event" key
So you could iterate over the key, values of the data as a normal dictionary, say like this:
for k, v in parsed.items():
print k, v
Now you could find the (possible different values) of "i4x-IITB-CS101-problem-33e4aac93dc84f368c93b1d08fa984fc_2_1" key in a quick way like this:
import json
parsed = json.loads(the_data_in_question_as_string)
event = parsed['event']
for key, val in event.items():
if key in ('correct_map', 'submission'):
section = event[key]
for possible_variable_key, its_value in section.items():
print possible_variable_key, its_value
Of course there might be better way of iterating over the dictionary, but that one you could choose based on your coding taste, or performance if you have a fairly larger kind of data than the one posted in here.

Categories

Resources