I would like to know the best practice for accessing the underlying file object when uploading a file with fastAPI.
When uploading a file with fastapi, the object we get is a starlette.datastructures.UploadFile.
We can access the underlying file attribute which is a tempfile.SpooledTemporaryFile.
We can then access the underlying private _file attribute, and pass it to libraries that expect a file-like object.
Below is an example of two routes with python-docx and pdftotext:
@router.post("/open-docx")
async def open_docx(upload_file: UploadFile = File(...)):
mydoc = docx.Document(upload_file.file._file) #
# do something
@router.post("/open-pdf")
async def open_pdf(upload_file: UploadFile = File(...)):
mypdf = pdftotext.PDF(upload_file.file._file)
# do something
However, I don't like the idea of accessing the private _file attribute. Is there a better way to pass the file object without saving it first?
Note: to reproduce the example above, put the following code in launch.py and run uvicorn launch:app --reload:
import docx
import pdftotext
from fastapi import FastAPI, File, UploadFile
app = FastAPI()
@app.post("/open-docx")
async def open_docx(upload_file: UploadFile = File(...)):
mydoc = docx.Document(upload_file.file._file)
# do something
return {"firstparagraph": mydoc.paragraphs[0].text}
@app.post("/open-pdf")
async def open_pdf(upload_file: UploadFile = File(...)):
mypdf = pdftotext.PDF(upload_file.file._file)
# do something
return {"firstpage": mypdf[0]}