Getting Deeper Key Value Pairs from a Dictionary in Python - python

I'm trying to get particular values out of a large dictionary and I'm having trouble doing so. I'm parsing through data from an API and attempting to get just the name attribute from my response. This is the format of the response I'm getting back:
{'data':
[{'id': '5555', 'type': 'proj-pha', 'links': {'self': '{sensitive_url}'}, 'attributes':
{'active': True, 'name': 'Plan', 'language': 'plan_l', 'position': 1},
'relationships': {'account': {'links': {'self': '{sensitive_url}', 'related':
'{sensitive_url}'}}, 'pro-exp': {'links': {'self':
'{sensitive_url}', 'related': '{sensitive_url}'}}}}
To clarify, I'm printing out the API response as a dictionary using:
print(response.json())
Here is some general code from my script for context:
params = {
"client_id": CLIENT_ID,
"client_secret": CLIENT_SECRET,
"redirect_uri": REDIRECT_URI,
"response_type": RESPONSE_TYPE
}
token = '{sensitive}'
print("Bearer Token: " + token)
session = requests.session()
session.headers = {"authorization": f"Bearer {token}"}
base_api_endpoint = "{sensitive}"
response = session.get(base_api_endpoint)
print(response.json())
What I want is just the 'name': 'Plan' attribute and that's all. The data provided repeats itself to the next "id" and so on until all the iterations have been posted. I'm trying to query out a list of all of these. I'm not looking for a particular answer on how to loop through these to get all of them though that would be helpful, I'm more focused on being able to just pick out the "name" value by itself.
Thanks!

To get all the names, just use list comprenhension, like this:
[item['attributes']['name'] for item in response['data']]
If you only want the name of the i-th item, just do:
response['data'][i]['attributes']['name']
And the last, if you want the name for a specific id:
def name_by_id(response, id):
for item in response['data']:
if item['id'] == id:
return item['attributes']['name']
return None

Related

Trello - Updating a cards position and color at the same time

I'm trying to have my board update based on some results and having a hard time finding the best way to update both a card's position and the color. The idea is to have a card update based on a result, red and to the top to catch my attention; but if everything is working correctly, then green and to the bottom.
So far I have:
def updateCard():
url = f"https://api.trello.com/1/cards/{CARD_ID}/cover"
headers = {
"Accept": "application/json"
}
query = {
'key': API_KEY,
'token': OAUTH_TOKEN,
'name': 'New Title',
'desc': 'New Description',
'pos': 'bottom',
'value': {'color': 'green'}
}
response = requests.request(
"PUT",
url,
headers=headers,
json=query
)
print(json.dumps(json.loads(response.text), sort_keys=True, indent=4, separators=(",", ": ")))
The pseudo code is from: https://developer.atlassian.com/cloud/trello/rest/api-group-cards/#api-cards-id-put and added my own variables.
I noticed that for changing the color, I need to pass the json variable in the response, and have the URL end with '/cover'. However, this does not work when trying to update the position. If I take the /cover out of the URL, then the position gets updated. Is there a way to have both update at the same time.
Thanks in advance!
I don't know Trello's API, and I can't test it without setting up a developer account, but my instinct is that you might be able to change your query like so:
. . .
url = f"https://api.trello.com/1/cards/{CARD_ID}"
. . .
query = {
'key': API_KEY,
'token': OAUTH_TOKEN,
'value': {
'name': 'New Title',
'desc': 'New Description',
'pos': 'bottom',
'cover': {'color': 'green'}
}
}
It looks like "cover" is a nested object under the "card" object, so you can just put an object in that field. When you're updating the card's position, you should be going for the card object directly, not the /cover field. You would use the /cover endpoint if you intended your request only to be scoped to the cover of the card.
EDIT: Trying a new request format
The workaround to this issue so far (and if anyone has a better syntax, feel free to add a comment):
url = f"https://api.trello.com/1/cards/{CARD_ID}"
url_cover = f"https://api.trello.com/1/cards/{CARD_ID}/cover"
headers = {
"Accept": "application/json"
}
query = {
'key': API_KEY,
'token': OAUTH_TOKEN,
'name': 'New Title 3',
'desc': 'New Description',
'pos': 'top'
}
json = {
'key': API_KEY,
'token': OAUTH_TOKEN,
'value': {
'brightness': 'dark',
'color': card_color,
'size': 'full'}}
response = requests.request(
"PUT",
url,
headers=headers,
params=query
)
response = requests.request(
"PUT",
url_cover,
headers=headers,
json=json
)

How not to hardcode the value of some correlation_id within headers to get required response?

I'm trying to grab different product names from this webpage. The product names, as in 0041-5053-005 generate dynamically. I can however scrape them using xhr with appropriate parameters.
It is necessary to use this following key and value within the headers to get the required data.
headers = {
'client_secret': '',
'client_id': '',
'correlation_id': '0196e1f2-fb29-0modod-6125-fcbb6c2c69c1',
}
This is how I scraped the titles:
import requests
link = "https://es-be-ux-search.cloudhub.io/api/ux/v2/search?"
payload = {
'queryText': '*:*',
'role': 'rockwell-search',
'spellingCorrect': 'true',
'spellcheckPremium': '10',
'segments': 'Productsv4',
'startIndex': 0,
'numResults': 10,
'facets': '',
'languages': 'en',
'locales': 'en_GLOBAL,en-US',
'sort': 'cat_a',
'collections': 'Literature,Web,Sample_Code',
'site': 'RA'
}
with requests.Session() as s:
r = s.get(link,params=payload,headers=headers)
for item in r.json()['response']['docs']:
print(item['catalogNumber'])
I've noticed that the value of client_secret and client_id are static but the value of correlation_id changes.
How can I use the value of correlation_id within the headers without hardcoding?
The correlation ID is used to correlate HTTP requests between a client and server. See this article for details on how that works. It seems as though this API requires the correlation ID to be present in the HTTP headers, but doesn't change the response based on its value. The response is the same if you give an empty string:
headers = {
'client_secret': '...',
'client_id': '...',
'correlation_id': '',
}

Massage data in a dict with array of json objects (nested data/data in a tree structure) in Python 3.0

I need to store the value of 'Address' in a variable for later use. The 'address' value is deep inside an output from a json.dump.
From what I've gathered over looking through some similar issues is that I need to iterate between each value in order access the ScriptPubKey (dict). Since I am only a few hours in to Python, without much prior knowledge about programming, I'm sure that I'm missing something simple - or completely misunderstand the task at hand.
for x in response['result']['vout']:
for y in x:
print(y)
So this is the part of the program I am having issues with:
###Function
def gettranshash(transhashen):
payload = {
"method": "getrawtransaction",
"params": [transhashen],
}
response = requests.post(url, data=json.dumps(payload), headers=headers).json()
response = response['result']
payload = {
"method": "decoderawtransaction",
"params": [response],
}
response = requests.post(url, data=json.dumps(payload), headers=headers).json()
return response
###How I access the function in my program
transaktionshash = input("write transactionhash for a block: ")
response = gettranshash(transaktionshash)
print("Blocket: ", response['result']['hash'])
###Missing the address output :(
print("Blocket: ", response['result']['vout'])
Result from response:
{'result': {'txid':
'4d879b24d65dd418a8e806ed69df7f170022e89666590a7b08e0095009865a5b',
'hash':
'4d879b24d65dd418a8e806ed69df7f170022e89666590a7b08e0095009865a5b',
'version': 1, 'size': 87, 'vsize': 87, 'locktime': 0, 'vin':
[{'coinbase': '0163', 'sequence': 4294967295}], 'vout': [{'value': 50.0,
'n': 0, 'scriptPubKey': {'asm': 'OP_DUP OP_HASH160
071e31b8289aa9d80b970230cb1b8b76466f2ec4 OP_EQUALVERIFY OP_CHECKSIG',
'hex': '76a914071e31b8289aa9d80b970230cb1b8b76466f2ec488ac', 'reqSigs':
1, 'type': 'pubkeyhash', 'addresses':
['1eduGsrvBJcfyTMij2rYXk9viiVV78PNq']}}]}, 'error': None, 'id': None}
This is the result from response['result']['vout']:
[{'value': 50.0, 'n': 0, 'scriptPubKey': {'asm': 'OP_DUP OP_HASH160
071e31b8289aa9d80b970230cb1b8b76466f2ec4 OP_EQUALVERIFY OP_CHECKSIG',
'hex': '76a914071e31b8289aa9d80b970230cb1b8b76466f2ec488ac', 'reqSigs':
1,
'type': 'pubkeyhash', 'addresses':
['1eduGsrvBJcfyTMij2rYXk9viiVV78PNq']}}]
this is from the documentation:
"vout" : [ (array of json objects)
{
"value" : x.xxx, (numeric) The value in BTC
"n" : n, (numeric) index
"scriptPubKey" : { (json object)
"asm" : "asm", (string) the asm
"hex" : "hex", (string) the hex
"reqSigs" : n, (numeric) The required sigs
"type" : "pubkeyhash", (string) The type, eg
'pubkeyhash'
"addresses" : [ (json array of string)
"address" (string) bitcoin address
,...
]
}
}
,...
],
So basically; I need to access the 'address' value in order to use it as input in an iteration for a different function.
Many thanks for any potential tips and let me know if I need to add additional information or clarify anything:)

Trying to parse some json but i am getting a key error - Django

I have a request that I am sending to an API and i am getting a json format response. I want to grab items from the response that is being sent back but not getting anything out of it. I am getting an error with the keys that I am putting in to grab.
From the response below, I want to grab values for specific keys within the response and save them in variables to eventually save them within my database.
Here is the code that I have:
def createUserSynapse(request):
argss = {
'email': 'hello#synapsepay.com',
'phone_number': '555-555-5555',
'legal_name': 'Hello McHello',
'note': ':)', # optional
'supp_id': '123abc', # optional
'is_business': True,
'cip_tag': 1
}
user = SynapseUser.create(clients, **argss)
print(user.json)
response = json.loads(user)
if response:
_id = response['_id']
name = response.client['name']
link = response._links.self['href']
cip = response.extra['cip_tag']
supp = response.extra['supp_id']
print(name)
print(_id)
print(link)
print(cip)
print(supp)
here is a sample of the reply:
{
'_id':'..4e57',
'_links':{
'self':{
'href':'https://uat-api.synapsefi.com/v3.1/users/..54e57'
}
},
'client':{
'id':'..26a34',
'name':'Charlie Brown LLC'
},
'doc_status':{
'physical_doc':'MISSING|INVALID',
'virtual_doc':'MISSING|INVALID'
},
'documents':[
],
'emails':[
],
'extra':{
'cip_tag':1,
'date_joined':1504774195147,
'extra_security':False,
'is_business':True,
'last_updated':1504774195147,
'public_note':None,
'supp_id':'123abc'
},
'is_hidden':False,
'legal_names':[
'Hello McHello'
],
'logins':[
{
'email':'hello#synapsepay.com',
'scope':'READ_AND_WRITE'
}
],
'permission':'UNVERIFIED',
'phone_numbers':[
'555-555-5555'
],
'photos':[
],
'refresh_token':'refresh_..G8LPqF6'
}
And here is the error that I am getting from the browser:
TypeError at /setup_profile/
the JSON object must be str, bytes or bytearray, not 'User'
Request Method: POST
Request URL: http://127.0.0.1:8000/setup_profile/
Django Version: 1.8.6
Exception Type: TypeError
Exception Value:
the JSON object must be str, bytes or bytearray, not 'User'
** UPDATE **
the following is the response when i just print user:
<class 'synapse_pay_rest.models.users.user.User'>({'client': <class 'synapse_pay_rest.client.Client'>(base_url=https://uat-api.synapsefi.com/v3.1), 'json': {'_id': '..920e6', '_links': {'self': {'href': 'https://uat-api.synapsefi.com/v3.1/users/..920e6'}}, 'client': {'id': '..026a34', 'name': 'Charlie Brown LLC'}, 'doc_status': {'physical_doc': 'MISSING|INVALID', 'virtual_doc': 'MISSING|INVALID'}, 'documents': [], 'emails': [], 'extra': {'cip_tag': 1, 'date_joined': 1505093840940, 'extra_security': False, 'is_business': True, 'last_updated': 1505093840940, 'public_note': None, 'supp_id': '123abc'}, 'is_hidden': False, 'legal_names': ['Hello McHello'], 'logins': [{'email': 'hello#synapsepay.com', 'scope': 'READ_AND_WRITE'}], 'permission': 'UNVERIFIED', 'phone_numbers': ['555-555-5555'], 'photos': [], 'refresh_token': 'refresh_..cYbeIrNA3P'}, 'id': '..920e6', 'refresh_token': 'refresh_..eIrNA3P', 'logins': [{'email': 'hello#synapsepay.com', 'scope': 'READ_AND_WRITE'}], 'phone_numbers': ['555-555-5555'], 'legal_names': ['Hello McHello'], 'permission': 'UNVERIFIED', 'note': None, 'supp_id': '123abc', 'is_business': True, 'cip_tag': 1, 'base_documents': 0, 'oauth_key': 'oauth_..dQZUJ', 'expires_in': '7200'})
Here is what comes from the type user and type user.json:
type(user) returns
<class 'synapse_pay_rest.models.users.user.User'>
type(user.json)
<class 'dict'>
The error is coming from the json loads line
response = json.loads(user)
This is because json.loads expects a string object that can be converted to a json dictionary, but it is being passed a user object, and consequently throwing a TypeError.
In your case, since the type of user.json is a dictionary, we can simply replace the response line with this:
response = user.json

Python JSON nested key value pair parsing

I am trying to make api call which has json as value to one of the keys. It is failing because of extra double quotes in inner json formed.
variable = request.GET.get('name', '{}')
This value of variable is json that is passed from webpage.
Sample data in variable will be like:-
variable= {'name': 'ABC', 'Id': '1'}
Now when I try to form my payload to be sent in post call,
payload = {
'var1': var1,
'variable': variable,
}
Now this "variable" which is added to payload is treated as String and append with double quotes, like this:-
{'var1': '130', 'variable': "{'name': 'ABC', 'Id': '1'}"}
But I want it to be like this:-
{'var1': '130', 'variable': {'name': 'ABC', 'Id': '1'}}
Any suggestions how to make it possible?
this is the code to make the post call with data:-
r = requests.post("URL",data= json.dumps(payload),headers={'Authorization': obj.header, 'Content-type': 'application/json'}, proxies=getProxyDict())
When you get variable from the request it isn't just 'treated' as a string... is is a string.
So you need to:
json.loads(variable)
before adding it to the dict which is later serialized to json.
i.e.
variable = json.loads(request.GET.get('name', '{}'))
payload = {
'var1': var1,
'variable': variable,
}
r = requests.post("URL",data= json.dumps(payload),headers={'Authorization': obj.header, 'Content-type': 'application/json'}, proxies=getProxyDict())
You have presumably already dumped variable to a JSON string. Don't do that; leave it as a dict, and dump the whole thing in one go.
import json
variable = {'name': 'ABC', 'Id': '1'}
payload = {
'var1': 'foo',
'variable': variable,
}
print json.dumps(payload, indent=4)
results to
{
"variable": {
"name": "ABC",
"Id": "1"
},
"var1": "foo"
}
which is perfectly json. But, you may need to set your headers according to the API you're talking to.
request = requests.get('myurl', headers={'accept': 'application/json'})
json_data = request.json()
# manipulate json_data
request = requests.post('myurl', headers={'content-type': 'application/json'}, json=json_data)
Few things I would like to point here.
variable= "{'name': 'ABC', 'Id': '1'}"
This is NOT a valid json string.
variable= '{"name": "ABC", "Id": "1"}'
This is a valid json string.
So first before attaching this variable to payload dict you need to convert it to a python dict like this.
variable = json.loads(variable)
This will create variable something like this.
{u'name': u'ABC', u'Id': u'1'}
Now you can go ahead and add this to your payload dict and continue what you are doing.

Categories