Get keys from json in python - json

I have an API whose response is json like this:
{
"a":1,
"b":2,
"c":[
{
"d":4,
"e":5,
"f":{
"g":6
}
}
]
}
How can I write a python program which will give me the keys ['d','e','g']. What I tried is:
jsonData = request.json() #request is having all the response which i got from api
c = jsonData['c']
for i in c.keys():
key = key + str(i)
print(key)

Function which return only keys which aren't containing dictionary as their value.
jsonData = {
"a": 1,
"b": 2,
"c": [{
"d": 4,
"e": 5,
"f": {
"g": 6
}
}]
}
def get_simple_keys(data):
result = []
for key in data.keys():
if type(data[key]) != dict:
result.append(key)
else:
result += get_simple_keys(data[key])
return result
print get_simple_keys(jsonData['c'][0])
To avoid using recursion change line result += get_simple_keys(data[key])to result += data[key].keys()

Try this,
dct = {
"a":1,
"b":2,
"c":[
{
"d":4,
"e":5,
"f":{
"g":6
}
}
]
}
k=dct["c"][0]
for key in k.keys():
print key

Related

Filtering a json dictionary by values Python

I am trying to write a piece of code where it filters out the values RSI, MOM, MOM_RSI within the Json file and filters by Status. I want to keep the values that has a Status of ACTIVE and get rid of the one that have a status of PAUSED. I have a working code for it from the issue:link. But I want to make it cleaner but attempting to configure the filters within the filtered_data dictionary but its not working. How would I be able to fix it?
Working:
def reading():
with open('data.json') as f:
data = json.load(f)
result = {}
for filter_key in data.keys():
for d in data[filter_key]:
if d['Status'] == 'ACTIVE':
try:
result[filter_key].append(d)
except KeyError:
result[filter_key] = [d]
Not Working Code:
def reading():
with open('data.json') as f:
data = json.load(f)
required_names = {key for filter_key in data.keys() for key in data[filter_key]}
filtered_data = {
key: value
for key, value in data.keys()
if key['Status'] in required_names
}
return data
reading()
Expected Output:
{
"RSI": [
{
"TradingPair": "BTCUSD",
"Status": "ACTIVE",
}
],
"MOM_RSI":[
{
"TradingPair": "BTCUSDT",
"Status": "ACTIVE",
}
]
}
JSON File:
{
"RSI": [
{
"TradingPair": "BTCUSD",
"Status": "ACTIVE",
}
],
"MOM":[
{
"TradingPair": "BCHUSDT",
"Status": "PAUSED",
}
],
"MOM_RSI":[
{
"TradingPair": "BTCUSDT",
"Status": "ACTIVE",
}
]
}
Using inline loops to filter should do the trick for you
for key in data.keys():
data[key] = [x for x in data[key] if x['Status'] == 'ACTIVE']
# in case of empty data, remove the key
data = {k: v for k, v in data.items() if v != []}

This is json file named as 'abc' . I want to access file after that i want to access values of a,b,c,d,e,f . How can I access in groovy language?

{
"Product": [{
"a": "e3ae148d8bc2c5fe366c38da"
},
{
"b": "d211c6e7ed5bd8b4e9316a74085"
},
{
"c": "74be4f1b3b0fa5af77287780"
},
{
"d": "89856f4f139a84c98fb98b8b39c32e2"
},
{
"e": "7bd784e7d3b8490ed614345989a5"
},
{
"f": "d169f6a4a932841b12bdf8ccded57"
}
]
}
Use JsonSlurper,
File file = new File('abc')
String fileContent = file.text
def slurper = new groovy.json.JsonSlurper()
def result = slurper.parseText(fileContent)
println result.Product[0].a //etc.
...

Appending traverse-tree string to json-object to retrieve json-data in python

Here is my sample json data:
{
"id": "67362003",
"a": {
"b": {
"3": 2,
"43": 30,
"c": "jack",
"d": "trail",
"e": [
{
"f": {
"g": "Father",
"h": "Mother"
}
}
],
"p": [
{
"q": {
"r": "Aunt",
"s": "Uncle"
}
}
]
}
}
}
Wrote a method, objpath which will get the each input from user-config: like [root:id, root:a:b:e[0]] and returns each path as ['id] at first call.. and for second call.. it returns ['a']['b']['e'][0] which I can able to read and print in my code of wrapper.
I am able to print print (obj['a']['b']['e'][0]) this manner.. In that, objpath method will return '['a']['b']['e'][0]' part as string. So, here how can I convert it to obj['a']['b']['e'][0] format.. It may be simple, I tried multiple ways.. But somehow it's breaking with type of string/list/dict... Below is my python-wrapper to do same
file_json = 'config_lib/sample.json'
lf = open(file_json, 'r')
obj = json.loads(lf.read())
skeys = ["root:id", "root:a:b:e[0]"]
for skey in skeys:
returns = JsonParser(obj, skey)
# Its returning string.
print type(returns) # <type 'str'>
print (returns) # *['id']* at first itereation, *['a']['b']['e'][0]* at second iteration
print (obj[returns]) # how to print the obj value here ??? I am not getting
I need to print obj['a']['b']['e'][0] and obj['id']
Can anyone please suggest a solution.
By converting the string to json-object resolved the issue..
print ("Returned value is:", eval('obj' + returns))

how to parse CSV to JSON from 2 CSV Files in Groovy

Please help with parse CSV to JSON from 2 CSV Files in groovy
For example :
CSV1:
testKey,status
Name001,PASS
Name002,PASS
Name003,FAIL
CSV2:
Kt,Pd
PT-01,Name001
PT-02,Name002
PT-03,Name003
PT-04,Name004
I want to input in "testlist" data from CSV2.val[1..-1],CSV1.val[1..-1]
Result should be like :
{
"testExecutionKey": "DEMO-303",
"info": {
"user": "admin"
},
"tests": [
{
"TestKey": "PT-01",
"status": "PASS"
},
{
"TestKey": "PT-02",
"status": "PASS"
},
{
"TestKey": "PT-03",
"status": "FAIL"
}
]
code without this modification (from only 1 csv):
import groovy.json.*
def kindaFile = '''
TestKey;Finished;user;status
Name001;PASS;
Name002;PASS;
'''.trim()
def keys
def testList = []
//parse CSV
kindaFile.splitEachLine( /;/ ){ parts ->
if( !keys )
keys = parts
else{
def test = [:]
parts.eachWithIndex{ val, ix -> test[ keys[ ix ] ] = val }
testList << test
}
}
def builder = new JsonBuilder()
def root = builder {
testExecutionKey 'DEMO-303'
info user: 'admin'
tests testList
}
println JsonOutput.prettyPrint(JsonOutput.toJson(root))
Your sample JSON doesn't match the CSV definition. It looks lile you're using fields [1..-1] from CSV 1, as you stated, but fields [0..-2] from CSV 2. As you only have 2 fields in each CSV that's the equivalent of csv1[1] and csv2[0]. The example below uses [0..-2]. Note that if you always have exactly two fields in your input files then the following code could be simplified a little. I've given a more generic solution that can cope with more fields.
Load both CSV files into lists
File csv1 = new File( 'one.csv')
File csv2 = new File( 'two.csv')
def lines1 = csv1.readLines()
def lines2 = csv2.readLines()
assert lines1.size() <= lines2.size()
Note the assert. That's there as I noticed you have 4 tests in CSV2 but only 3 in CSV1. To allow the code to work with your sample data, it iterates through through CSV1 and adds the matching data from CSV2.
Get the field names
fieldSep = /,[ ]*/
def fieldNames1 = lines1[0].split( fieldSep )
def fieldNames2 = lines1[0].split( fieldSep )
Build the testList collection
def testList = []
lines1[1..-1].eachWithIndex { csv1Line, lineNo ->
def mappedLine = [:]
def fieldsCsv1 = csv1Line.split( fieldSep )
fieldsCsv1[1..-1].eachWithIndex { value, fldNo ->
String name = fieldNames1[ fldNo + 1 ]
mappedLine[ name ] = value
}
def fieldsCsv2 = lines2[lineNo + 1].split( fieldSep )
fieldsCsv2[0..-2].eachWithIndex { value, fldNo ->
String name = fieldNames2[ fldNo ]
mappedLine[ name ] = value
}
testList << mappedLine
}
Parsing
You can now parse the list of maps with your existing code. I've made a change to the way the JSON string is displayed though.
def builder = new JsonBuilder()
def root = builder {
testExecutionKey 'DEMO-303'
info user: 'admin'
tests testList
}
println builder.toPrettyString()
JSON Output
Running the above code, using your CSV1 and CSV 2 data, gives the JSON that you desire.
for CSV1:
testKey,status
Name001,PASS
Name002,PASS
Name003,FAIL
and CSV2:
Kt,Pd
PT-01,Name007
PT-02,Name001
PT-03,Name003
PT-05,Name002
PT-06,Name004
PT-07,Name006
result is:
{
"testExecutionKey": "DEMO-303",
"info": {
"user": "admin"
},
"tests": [
{
"status": "PASS",
"testKey": "PT-01"
},
{
"status": "PASS",
"testKey": "PT-02"
},
{
"status": "FAIL",
"testKey": "PT-03"
}
]
}
but I need exactly the same values for testKey (testKey from CSV1=Kt from CSV2)
{
"testExecutionKey": "DEMO-303",
"info": {
"user": "admin"
},
"tests": [
{
"testKey": "PT-02",
"status": "PASS"
},
{
"testKey": "PT-05",
"status": "PASS"
},
{
"testKey": "PT-03",
"status": "FAIL"
}
]
}

How do I get "keys" from an unkown .json saved in my computer using groovy

My end goal is to parse thru an unknown .json file stored on my laptop and get the key names (not the values only key names) using Groovy in SoapUI.
I want to parse an unknown JSON file stored in my computer and get its keys (name of the keys, not the values). I can do 2 things separately:
I am able to read the local JSON using the following code I found online:
def JSON_URL = "file:///C:/Users/xxx/example.json"
URL url = new URL(JSON_URL)
InputStream urlStream = null
try {
urlStream = url.openStream()
BufferedReader reader = new BufferedReader(new Inpu tStreamReader(urlStream))
JsonSlurper js1 = new JsonSlurper()
Object result = js1.parse(reader)
log.info "==> readJSONfile2 result of read: "+result
} catch (Exception e) {
log.info e
}
And if I have the URL, I am able to parse it and get keys like so:
// getting the response
def resp1 = context.expand('${testStepName#response}')
// parsing the set context
def js1 = new JsonSlurper().parseText(resp1)
def keys = js1.entrySet() as List
log.info "==> runTreatmentPlan keys list is: "+keys
log.info "==> runTreatmentPlan keys size is: "+keys.size()
But I am unable to get the keys if the JSON is local to my machine ie unable to combine both the codes. I get error when I do:
Object result = js1.parseText(reader)
I am new to groovy and SoapUI and json - a total newbie and this is my first question. I am really scared because I have seen that some people are kinda rough towards other newbies if the question is basic. I promise, I did google a lot, and I am sure the experienced people might find my question stupid as well, but I am really stuck. I am unable to combine both pieces of code. I kinda feel that I will some how have to use the response from #1 code, but I don't know how.
Can someone help me please?
==== Updating with the JSON structure:
{
"Key0": [
{
"Key1": "Value1",
"Key2": "Value2",
"Key3": "Value3",
"Key4": {
"subKey1": "subValue1"
},
"Key5": {
"subKey1": "subValue1",
"subKey2": "subValue2",
"subKey3": "subValue3",
"subKey4": "subValue4"
},
"Key6": "2016-07-11T17:52:59.000Z",
"Key7": [
{
"subKey1": "subValue1",
"subKey2": "subValue2"
},
{
"subKey1": "subValue1",
"subKey2": "subValue2"
},
{
"subKey1": "subValue1",
"subKey2": "subValue2"
},
{
"subKey1": "subValue1",
"subKey2": "subValue2"
}
]
},
{
"Key1": "Value1",
"Key2": "Value2",
"Key3": "Value3",
"Key4": {
"subKey1": "subValue1"
},
"Key5": {
"subKey1": "subValue1",
"subKey2": "subValue2",
"subKey3": "subValue3",
"subKey4": "subValue4"
},
"Key6": "2016-07-11T17:52:59.000Z",
"Key7": [
{
"subKey1": "subValue1",
"subKey2": "subValue2"
},
{
"subKey1": "subValue1",
"subKey2": "subValue2"
},
{
"subKey1": "subValue1",
"subKey2": "subValue2"
},
{
"subKey1": "subValue1",
"subKey2": "subValue2"
}
]
}
]
}
Given your input, this code:
import groovy.json.JsonSlurper
def traverse
traverse = { tree, keys = [], prefix = '' ->
switch (tree) {
case Map:
tree.each { k, v ->
def name = prefix ? "${prefix}.${k}" : k
keys << name
traverse(v, keys, name)
}
return keys
case Collection:
tree.eachWithIndex { e, i -> traverse(e, keys, "${prefix}[$i]") }
return keys
default :
return keys
}
}
def content = new JsonSlurper().parse( new File( 'sample.json' ) )
traverse(content).each { println it }
Yields this output:
Key0
Key0[0].Key1
Key0[0].Key2
Key0[0].Key3
Key0[0].Key4
Key0[0].Key4.subKey1
Key0[0].Key5
Key0[0].Key5.subKey1
Key0[0].Key5.subKey2
Key0[0].Key5.subKey3
Key0[0].Key5.subKey4
Key0[0].Key6
Key0[0].Key7
Key0[0].Key7[0].subKey1
Key0[0].Key7[0].subKey2
Key0[0].Key7[1].subKey1
Key0[0].Key7[1].subKey2
Key0[0].Key7[2].subKey1
Key0[0].Key7[2].subKey2
Key0[0].Key7[3].subKey1
Key0[0].Key7[3].subKey2
Key0[1].Key1
Key0[1].Key2
Key0[1].Key3
Key0[1].Key4
Key0[1].Key4.subKey1
Key0[1].Key5
Key0[1].Key5.subKey1
Key0[1].Key5.subKey2
Key0[1].Key5.subKey3
Key0[1].Key5.subKey4
Key0[1].Key6
Key0[1].Key7
Key0[1].Key7[0].subKey1
Key0[1].Key7[0].subKey2
Key0[1].Key7[1].subKey1
Key0[1].Key7[1].subKey2
Key0[1].Key7[2].subKey1
Key0[1].Key7[2].subKey2
Key0[1].Key7[3].subKey1
Key0[1].Key7[3].subKey2
import groovy.json.JsonSlurper
/**
* sample.json present in C:/tools/
* { "foo": "bar", "baz": 123 }
*/
def content = new JsonSlurper().parse( new File( 'C:/tools/sample.json' ) )
assert content.keySet() == ['baz', 'foo'] as Set
UPDATE:
After looking at the actual json structure and the issues with the version of Groovy in SOAPUI, below would be a viable option to get all the keys in a specific format:
import groovy.json.JsonSlurper
def textFromFile = new File('/path/to/example.json').text
def content = new JsonSlurper().parseText(textFromFile)
def getAllKeys(Map item) {
item.collect { k, v ->
v instanceof Map ? convertToString(v).collect { "${k}.$it" } : k
}.flatten()
}
assert getAllKeys(content) == [
'Key1', 'Key2', 'Key3',
'Key4.subKey1', 'Key5.subKey1', 'Key5.subKey2',
'Key5.subKey3', 'Key5.subKey4',
'Key6', 'Key7'
]