Getting different responses from postman vs. python API call - python

I'm trying get the same data from an API call in Postman using Python.
The call is relatively simple. It uses Basic Authorization that only requires the API key being passes as the username, and a dynamic component: csv_key variable that is passed from earlier codes.
I was able to successfully made the request (status code 200), but the response from Python is different from the one in Postman. It's missing all key-value pairs except the firs two: id and description.
I'm getting this response from postman:
response from postman
{
"id": "63c9c0927885bf003ecd3a1b",
"description": "Streaming analytics",
"download_url": "https://storage.googleapis.com/***-static/***.csv?GoogleAccessId=888211540537-r3m40kms2upicdr07e5rl2q67feg9loh%40developer.gserviceaccount.com&Expires=4070908800&Signature=WvuuKdddCFKjSNpst5n8yKFNR5qtC1m1o1mQZFWLHmKomJtc7npa6PbwfRoTj9FhIIqbta98VPOYKMGW89XaqXtITh15V%2Bf9opAD3BnuLjTzWC6X24RC5kMCZATXpp9DWi1Our061%2FdKlpUozi1ir7b8AwBWWf%2Bs8u5J6VoelvtEyiZIO4l%2FQdeJ26GqDLRgWElEMAlBE3TJo7m3UuE8gOQPsYBCwBSfLI1bTIytNOHZMUlWuVtMQxEHzUOujAp%2Fgqn1Q8TGGzy5GoeEmzw%2FD80xs%2BALjhT%2BxdiN9riG6%2BEcObrhPoudxl32jUhVH0EmGJwjgiJFQpz%2FLfKr86LrCQ%3D%3D",
"error": "Cannot read property 'email' of undefined",
"completed_at": "2023-01-19T22:13:39.219Z"
}
But I'm only getting the first two key-value pairs using a Python script of the same API call:
response from Python
csv key: 63c9c0927885bf003ecd3a1b
api url: https://api.eventive.org/temporary_exports/63c9c0927885bf003ecd3a1b
<Response [200]>
response:[{'id': '63c9c0927885bf003ecd3a1b', 'description': 'Streaming analytics'}]
Process finished with exit code 0
My code for the Python script is:
import requests
import json
url_for_key = 'https://api.***.org/reports/streams?event_bucket=63279b48d8f8f1009209694f&start=1674111600000&end=1674198000000&tz=America%2FDenver'
api_key = '*************************'
header = {'content-type': 'application/json'}
r1 = requests.get(url=url_for_key, auth=(api_key, ''))
csv_obj = [r1.json()]
csv_key = csv_obj[0]['temporary_export']
#print(csv_obj)
print(f'csv key: {csv_key}')
url_for_link = 'https://api.***.org/temporary_exports/{}'.format(csv_key)
print(f'api url: {url_for_link}')
r2 = requests.get(url=url_for_link, headers=header, auth=(api_key, ''))
print(r2)
print(f'response:{[r2.json()]}')
csv_key is the same as id. Could anyone help me understand what's going on?
Many thanks,

Related

Mediawiki api returning http response code instead of json

I am following some example code in the mediawiki api (see link at the bottom) to get a response in json format that looks something like the following:
"login": {
"lguserid": 21,
"result": "Success",
"lgusername": "William"
}
Unfortunately, I am not getting anything similar to that and instead just get a response that looks as follows:
<Response [200]>
Below is the example code that I'm almost using verbatim at this point, to no avail.
#!/usr/bin/python3
"""
login.py
MediaWiki API Demos
Demo of `Login` module: Sending post request to login
MIT license
"""
import requests
USERNAME = "my_bot_username"
PASSWORD = "my_bot_password"
S = requests.Session()
URL = "https://www.mediawiki.org/w/api.php"
# Retrieve login token first
PARAMS_0 = {
'action':"query",
'meta':"tokens",
'type':"login",
'format':"json"
}
R = S.get(url=URL, params=PARAMS_0)
Again, R is supposed to be in json format instead it is just a http response code not in json format which causes the very next line of the example script (see link at the bottom) fail.
Is the example code outdated or can anyone spot why the code above is not returning a response in json format?
EDIT: The version of mediawiki I am using is 1.17.0
https://www.mediawiki.org/wiki/API:Login#Python
You have to use response.json() to get a json object :
R = S.get(url=URL, params=PARAMS_0)
DATA = R.json()

Python: requests lib post request not sending proper json format data

I am trying to connect to a very closed source database system via REST API to pull some data. The API so weird that it just gives you status code 400 & nothing much. No information or error pointing to what is wrong with the provided data. I am calling this API using postman & it is giving me proper response but when I use Python's requests lib to call this API I am getting 400 status (Which means there is something wrong with the provided data with the request).
This is my code.
def pull_data():
url = construct_url(configs.get("get_data_path"))
payload = json.dumps([
{
"SampleInterval": 600000,
"GetEnum": False,
"ResampleMethod": "Around",
"MinimumConfidence": 0,
"MaxRows": 100,
"TimeFormat": 6,
"ReductionData": "avg",
"TagName": [
"NC_AI3",
"NC_AI32"
],
"StartTime": "05/16/2022 08:49:26.000",
"EndTime": "05/16/2022 13:03:36.000",
"OutputTimeFormat": 6,
"EventSequence": 0
}
])
headers = {'Content-Type': 'application/json'}
res = requests.post(url, json=payload, verify=False, auth=HTTPBasicAuth(configs.get("user"), configs.get("password")), headers=headers)
print("----------", "Status Code", res.status_code, "-------")
I think somehow the json data sent via the request.post method is not getting recognised by the API. I think it is something to do with the fact that I am sending list of dict as json error not a usual dict as we do or see everywhere.
Can please someone tell if I am sending the json data correctly or not or is there any other way to do it?

Consuming API with graphql queries throwing 401 error on R but working fine on Python

I have a requirement to access some information through an API. I need to do this on R. I tried doing on Python and it worked just fine but facing 401 error while doing the same operation on R.
I have the API key and also know the query to be performed. I have attached both Python and R code below.
Python:
import requests
headers = {
'Content-Type': 'application/json',
'Authorization': 'XXXXXXXXXXXXXXXXXXXXXXXXXXXX',
}
query = """
{
boards (ids: 157244624) {
permissions
}
}
"""
response = requests.get('https://XYZwebsite.com/', headers=headers, json={'query': query})
R:
require(httr)
headers = c(
`Content-Type` = 'application/json',
`Authorization` = 'XXXXXXXXXXXXXXXXXXXXXXXXXXXX'
)
data = '{
boards (ids: 157244624) {
permissions
}
}'
res <- GET(url = 'https://XYZwebsite.com/', add_headers(.headers=headers), body = data)
Am i missing out something in the R code? It looks pretty much the same but i am getting a 401 error on R for some weird reason.
In my case api key was expired... really long journey let me to:
amplify update api
walk through all
choose api key
enter new api key name
enter 365 days no further changes
amplify push will not detect changes, so use amplify push --force
maybe it helps
Perhaps try:
r <- GET("https://XYZwebsite.com/",
add_headers(`Content-Type` = "application/json",
`Authorization` = "XXXXXXXXXXXXXXXXXXXXXXXXXXXX"),
body = data)
Edit:
With the gist you are working off of:
Authenticate first:
token <- GQL(auth_query)$authenticate$jwtToken
Then you can run your queries by passing the token you get in the response:
GQL(current_person_query, .token = token)
Seems like you are trying to do two things at once.
If you already have the token then it looks like you are passing it incorrectly:
auth_header <- paste("bearer", .token)
res <- POST(.url, body = pbody, encode="json", add_headers(Authorization=auth_header), ...)
As it should be passed as "bearer XXXXXXXXXXXXXXXXX".

How to call an API using Python Requests library

I can't figure out how to call this api correctly using python urllib or requests.
Let me give you the code I have now:
import requests
url = "http://api.cortical.io:80/rest/expressions/similar_terms?retina_name=en_associative&start_index=0&max_results=1&sparsity=1.0&get_fingerprint=false"
params = {"positions":[0,6,7,29]}
headers = { "api-key" : key,
"Content-Type" : "application/json"}
# Make a get request with the parameters.
response = requests.get(url, params=params, headers=headers)
# Print the content of the response
print(response.content)
I've even added in the rest of the parameters to the params variable:
url = 'http://api.cortical.io:80/rest/expressions/similar_terms?'
params = {
"retina_name":"en_associative",
"start_index":0,
"max_results":1,
"sparsity":1.0,
"get_fingerprint":False,
"positions":[0,6,7,29]}
I get this message back:
An internal server error has been logged # Sun Apr 01 00:03:02 UTC
2018
So I'm not sure what I'm doing wrong. You can test out their api here, but even with testing I can't figure it out. If I go out to http://api.cortical.io/, click on the Expression tab, click on the POST /expressions/similar_terms option then paste {"positions":[0,6,7,29]} in the body textbox and hit the button, it'll give you a valid response, so nothing is wrong with their API.
I don't know what I'm doing wrong. can you help me?
The problem is that you're mixing query string parameters and post data in your params dictionary.
Instead, you should use the params parameter for your query string data, and the json parameter (since the content type is json) for your post body data.
When using the json parameter, the Content-Type header is set to 'application/json' by default. Also, when the response is json you can use the .json() method to get a dictionary.
An example,
import requests
url = 'http://api.cortical.io:80/rest/expressions/similar_terms?'
params = {
"retina_name":"en_associative",
"start_index":0,
"max_results":1,
"sparsity":1.0,
"get_fingerprint":False
}
data = {"positions":[0,6,7,29]}
r = requests.post(url, params=params, json=data)
print(r.status_code)
print(r.json())
200
[{'term': 'headphones', 'df': 8.991197733061748e-05, 'score': 4.0, 'pos_types': ['NOUN'], 'fingerprint': {'positions': []}}]
So, I can't speak to why there's a server error in a third-party API, but I followed your suggestion to try using the API UI directly, and noticed you're using a totally different endpoint than the one you're trying to call in your code. In your code you GET from http://api.cortical.io:80/rest/expressions/similar_terms but in the UI you POST to http://api.cortical.io/rest/expressions/similar_terms/bulk. It's apples and oranges.
Calling the endpoint you mention in the UI call works for me, using the following variation on your code, which requires using requests.post, and as was also pointed out by t.m. adam, the json parameter for the payload, which also needs to be wrapped in a list:
import requests
url = "http://api.cortical.io/rest/expressions/similar_terms/bulk?retina_name=en_associative&start_index=0&max_results=1&sparsity=1.0&get_fingerprint=false"
params = [{"positions":[0,6,7,29]}]
headers = { "api-key" : key,
"Content-Type" : "application/json"}
# Make a get request with the parameters.
response = requests.post(url, json=params, headers=headers)
# Print the content of the response
print(response.content)
Gives:
b'[[{"term":"headphones","df":8.991197733061748E-5,"score":4.0,"pos_types":["NOUN"],"fingerprint":{"positions":[]}}]]'

Starting a conversation with a chat bot hosted on Microsoft Azure through HTTP request in Python

A Microsoft tutorial shows that in order to set up a conversation with a bot I should issue the following HTTP request:
POST https://directline.botframework.com/api/conversations
Authorization: Bearer SECRET_OR_TOKEN
My question is if I can achieve this with the following Python code:
import requests
r = requests.post('https://directline.botframework.com/api/conversations',
params = {'Authorization':'Bearer ftmhNAqZ2tw.cwA.qIA.Xz2ZWfYJzxd8vJjcK9VmINWNLxlvKiM5jC8F_cbaf0s'})
If I print the response with print(r.content) it says:
{ "error": {
"code": "BadArgument",
"message": "Missing token or secret" } }
HTTP requests have three areas where content can be sent:
URL parameters
Body
Headers
To set these in python's requests package the following can be used (POST method assumed, but all are the same):
URL Parameters:
requests.post('https://myurl.com', params = {'MyParam':'MyValue'})
# equivilient to http://myurl.com?MyParam=MyValue
Body:
requests.post('https://myurl.com', data={"key":"value"})
# or if sending json data
requests.post('https://myurl.com', data=json.dumps(myData))
Headers:
requests.post('https://myurl.com', headers={"headername":"value"})
In your specific case, while the API is not well documented - we can assume they expect the "Authorization" data to be sent in a header, as this is standard. In this case, you need to assign headers as follows:
requests.post('https://directline.botframework.com/api/conversations', headers={'Authorization':'Bearer ftmhNAqZ2tw.cwA.qIA.Xz2ZWfYJzxd8vJjcK9VmINWNLxlvKiM5jC8F_cbaf0s'})
The bearer token needs to be sent as a header, not as a payload or query parameter.
You need to use the headers argument:
auth = {'Authorization': 'Bearer xxxYourBearerTokenHerexxx'}
r = requests.post('https://directline.botframework.com/api/conversations', headers=auth)
print(r) # <Response [200]>

Categories

Resources