File upload using FastAPI returns error 422

Question:

I am using the example from the official documentation: https://fastapi.tiangolo.com/tutorial/request-files/#import-file

Server code:

@app.post("/uploadfile")
async def create_upload_file(data: UploadFile = File(...)):
    print("> uploaded file:",data.filename)
    return {"filename": data.filename}

Client code:

files = {'upload_file': open('config.txt', 'rb')}
resp = requests.post(
        url = URL,
        files = files)
print(resp.json())

The problem is that the server always responds with error 422:

{'detail': [{'loc': ['body', 'data'], 'msg': 'field required', 'type': 'value_error.missing'}]}

I am using Python 3 on both server and client and the python-multipart package is already installed.

Can someone please tell me what I am doing wrong, what am I missing, how should I fix the code?

Any hints are much appreciated.

Asked By: stev

||

Answers:

Well, I just realized my error (which is not immediately obvious for newbies like me :))

The parameter you pass on client side ('upload_file')

files = {'upload_file': open('config.txt', 'rb')}

must match the parameter on the server side ('data'):

async def create_upload_file(data: UploadFile = File(...)):

So in order to work I had to rename on client side ‘upload_file‘ to ‘data‘:

files = {'data': open('config.txt', 'rb')} # renamed 'upload_file' to 'data'

That’s it. Hopefully this helps some others as well.

Answered By: stev

On client side you should use the same name given for the parameter on server side, when adding the file. In your case, that parameter is called data, as shown below:

@app.post('/uploadfile')
async def create_upload_file(data: UploadFile = File(...)):
                             ^^^^

Hence, you should replace upload_file with data on client side, as shown below:

url = 'http://127.0.0.1:8000/uploadfile'
files = {'data': open('config.txt', 'rb')}
r = requests.post(url=url, files=files)

More details and examples on how to upload file(s) using Python requests and FastAPI can be found in this answer, as well as here, here and here.

Answered By: Chris