Curl Post Json data not being read in Python Django - python

Am using curl exe in windows, to communicate with my Django backend.
Following is the command am using.
curl --dump-header - -H "Accept: application/json" -H "Content-Type: application/json" -X POST --data "{\"uid\":12,\"token\":\"asdert\"}" http://localhost:8000/restapi/v1/foo/
Now this give the data in wrong format. i.e. in the view the post is showing this data
print request.POST
{"{\"uid\":12,\"access_token\":\"asdert\"}": [""]}
What is the correct way to post json data ?
Edit:
I have tried several other methods for e.g.
I am trying to communiate with my rest api using http://slumber.in/.
Even here am getting the same result as above.
import slumber
api = slumber.API("http://localhost/restapi/v1/"
api.foo.post({"uid":"100"})
Excerpts from the view
print request.POST
{u'{"uid": "100"}': [u'']}
P.S. - curl --dump-header - -H "Accept: application/json" -H "Content-Type: application/json" -X POST --data "uid=12&token=asdert" http://localhost:8000/restapi/v1/foo/
This works. But this is not Json format.

I tried your command with http://httpbin.org/post and it worked fine.
Now, your problem is that you should access the incoming JSON data from
request.raw_post_data
instead of request.POST.
(Or if you are using Django 1.4+, use request.body instead as request.raw_post_data is being deprecated)
Detailed code should be something like this:
import json
if request.method == "POST":
data = json.loads(request.raw_post_data)
print data

Related

Submitting Python file in batch mode in Livy(without Hadoop installed)

i have made a simple python file which want to submit in Livy.Livy is currently running in local mode.Also I have mentioned following property in livy.conf file.
Property name: livy.file.local-dir-whitelist,
value "/usr/local/livy/scripts"
My file is kept in following path "/usr/local/livy/scripts"
import json, pprint, requests, textwrap
host = 'http://localhost:8998'
data = {'kind': 'spark'}
headers = {'Content-Type': 'application/json'}
r = requests.post(host + '/sessions', data=json.dumps(data), headers=headers)
r.json()
I am submitting it using curl as follows:
curl -X POST --data '{"file": "/usr/local/livy/scripts/pi.py"}' -H "Content-Type: application/json" 10.140.178.24:8999/batches
It is giving me following error:
requirement failed: Local path /usr/local/livy/scripts/pi.py cannot be added to user sessions.
My Ubuntu system only have following things:
a)Spark
b)Livy
c)Java
What am I doing wrong here?
For people using incubating mode of livy for first time,kindly check that the template file is renamed with stripping off .template in livy.conf.template.Then make sure that the following configurations are present in it.
livy.spark.master = local
livy.file.local-dir-whitelist = /path/to/script/folder/
Kindly make sure that forward slash is present in end of path
Then write url in following manner for
Python:
curl -v -X POST --data '{"file": "/path/to/script/folder/name-of-python-file.py"}' -H "Content-Type: application/json" localhost:8998/batches
Note:It will not accept relative path,whole absolute path needs to be defined in it.
curl -X POST --data '{"file": "/usr/local/livy/scripts/pi.py"}' -H "Content-Type: application/json" 10.140.178.24:8999/batches
{"id":2,"state":"starting","log":[]}

Get raw POST payload in Flask

I am sending text by cUrl
curl -X POST -d "Separate account charge and opdeducted fr" http://192.168.50.8/text
and try to get
#application.route("/text",methods=['POST'])
def clausIE():
content = request.data
text = str(content, encoding="utf-8")
But get empty string, what I am doing wrong?
Note: I use Python3.6
This is not really a Flask problem, you are using the wrong curl options.
The -d switch should only be used for form data. curl automatically will set the Content-Type header to application/x-www-form-urlencoded, which means that Flask will load the raw body content and parse it as a form. You'll have to set a different Content-Type header manually, using -H 'Content-Type: application/octet-stream' or another mime-type more appropriate to your data.
You also want to use --data-binary, not -d (--data), as the latter also tries to parse the content into key-value fields and will remove newlines:
curl -X POST -H 'Content-Type: application/octet-stream' \
--data-binary "Separate account charge and opdeducted fr" \
http://192.168.50.8/text
The complete answer seems to be scattered around some comments and the accepted reply. So to summarize this, the Python Flask code should look like
#application.route("/text",methods=['POST'])
def clausIE():
content = request.get_data()
text = str(content, encoding="utf-8")
return text
and this is what you should have at your terminal
curl -X POST --data-binary "Hello World!" http://192.168.50.8/text
At my own setup (OS X) I am allowed to drop -X POST and to wrap the URL around quotes, so that gives
curl --data-binary "Hello World!" "http://192.168.50.8/text"

How to make curl post request from python

I am trying to make a post request using curl in python but the below script throws error
import os
first_name1 = "raj"
last_name1 = "kiran"
full_name = "raj kiran"
headline = "astd"
location1 = "USA"
current_company1 = "ss"
curl_req = 'curl -X POST -H "Content-Type: application/json" -d '{"first_name":"{0}","last_name":"{1}","current_company":"{2}","title":"{3}","campus":"","location":"{4}","display_name":"{5}","find_personal_email":"true"}' http://localhost:8090'.format(first_name1,last_name1,current_company1,headline,location1,full_name)
os.popen(curl_req)
Error:
SyntaxError: invalid syntax
How to make above program work?
The problem in your code is the quotes. Change it to:
curl_req = '''curl -X POST -H "Content-Type: application/json" -d '{"first_name":"{0}","last_name":"{1}","current_company":"{2}","title":"{3}","campus":"","location":"{4}","display_name":"{5}","find_personal_email":"true"}' http://localhost:8090'''.format(first_name1,last_name1,current_company1,headline,location1,full_name)
But, as mentioned in the comments, requests will always be a better choice.
Requests syntax:
import requests
post_data = {
# all the data you want to send
}
response = requests.post('http://localhost:8090', data=post_data)
print response.text
One good resource I've used for converting a cURL request to Python requests is curlconverter. You can enter your cURL request and it will format it for Python requests.
As a side note, it can also convert for PHP and Node.js.
Hope that helps!

Using DictField with html post

I have some code that used to work before the Drf 3.3 / Django 1.8 combo:
I'd have a serializer like this:
class MySerializer(...):
dict_field = serializers.DictField(child=serializers.CharField())
.....
The following used to work previously, but now dict field is empty:
curl http://server.com/api/endpoint -H "Authorization: Token <XXX>" -d other_field=ABC -d dict_field.key1=val1 -d dict_field.key2=val2
The code for DictField seems like it expects the data in this format, but it's not working. Other non dict fields work, and using json works, but for separate reasons, I must use HTTP POST. Is this a bug with the latest versions?
you can post dictionary data like :
curl -H "Content-Type: application/json" -H "Authorization: Token <XXX>" -X POST http://server.com/api/endpoint -d '{"other_field": "ABC","dict_field": {"key1":"val1","key2":"val2"}}'

Flask multidict mapping causing error

I'm sending a POST request via terminal to my flask backend server by doing the following:
curl -v -H "Accept: application/json" -H "Content-type: application/json" -X POST -d '{“Email”:”email#email.com”,”Password”:”testpass”}' http://127.0.0.1:5000/auth/login
I can print out the request data in flask by doing the following:
print(request.data)
However, when I try to input the data into a form to validate the information, the process comes to a halt and fails.
I'm pretty sure the issue is caused by this code, since nothing gets executed after this line:
data = MultiDict(mapping=request.json)
Any idea why?
I'm not sure that your quotes are all the same in your curl command. I tried adapting that to one of my apis and it returned an error. Are you using the right quotes in your json? Are those smart quotes? I was able to replace them and it worked.
curl -v -H "Accept: application/json" -H "Content-type: application/json" -X POST -d '{"email":"email#email.com","password":"testpass"}' http://127.0.0.1:5000/auth/login
If you are then taking the dictionary and then loading them into a form (form = LoginForm(**data)) you also need to make sure your keys match the naming of your form. I see in your json you have Email with E uppercase. Make sure that is the name of the form field in your form. If it is email = StringField(...) it won't map.

Categories

Resources