Python Requests: Post JSON and file in single request

oznu picture oznu · Oct 18, 2013 · Viewed 52.7k times · Source

I need to do a API call to upload a file along with a JSON string with details about the file.

I am trying to use the python requests lib to do this:

import requests

info = {
    'var1' : 'this',
    'var2'  : 'that',
}

data = json.dumps({
    'token' : auth_token,
    'info'  : info,
})

headers = {'Content-type': 'multipart/form-data'}

files = {'document': open('file_name.pdf', 'rb')}

r = requests.post(url, files=files, data=data, headers=headers)

This throws the following error:

    raise ValueError("Data must not be a string.")
 ValueError: Data must not be a string

If I remove the 'files' from the request, it works.
If I remove the 'data' from the request, it works.
If I do not encode data as JSON it works.

For this reason I think the error is to do with sending JSON data and files in the same request.

Any ideas on how to get this working?

Answer

ralf htp picture ralf htp · Mar 11, 2016

See this thread How to send JSON as part of multipart POST-request

Do not set the Content-type header yourself, leave that to pyrequests to generate

def send_request():
    payload = {"param_1": "value_1", "param_2": "value_2"}
    files = {
        'json': (None, json.dumps(payload), 'application/json'),
        'file': (os.path.basename(file), open(file, 'rb'), 'application/octet-stream')
    }

    r = requests.post(url, files=files)
    print(r.content)