【问题标题】:FastAPI/Mangum JSON decode error when uploading multiple files上传多个文件时 FastAPI/Mangum JSON 解码错误
【发布时间】:2023-01-05 02:46:27
【问题描述】:

我正在尝试使用 FastAPI/Mangum 创建一个无服务器文件上传 API,并且在尝试按照文档中的示例进行操作时遇到了一个奇怪的 JSON 解码问题。这是我的代码

# main.py
import os

from typing import List
from fastapi import FastAPI, File, UploadFile
from fastapi.responses import HTMLResponse
from mangum import Mangum

app = FastAPI()

@app.get("/")
async def main():
    content = """
    <body>
     <form action="/registration/create" enctype="multipart/form-data" method="post">
      <input name="files" type="file" multiple>
      <input type="submit">
     </form>
    </body>
    """
    return HTMLResponse(content=content)

@app.post("/registration/create")
async def create_registration(files: List[UploadFile]):
    return {"file_len": len(files)}

handler = Mangum(app)
# test_main.py
from urllib import response
from fastapi.testclient import TestClient
from main import app

client = TestClient(app)

def test_registration():
    files = [('files', ('example.txt', open('example.txt', 'rb'), 'text/plain'))]
    response = client.post("/registration/create", files=files)
    assert response.status_code == 200

当我运行测试或尝试使用网页示例发布文件时,我收到 JSON 解码错误并且请求失败并返回 422:

{
 "detail":
   [{"loc":["body",0],
     "msg":"Expecting value: line 1 column 1 (char 0)",
     "type":"value_error.jsondecode",
     "ctx": {
       "msg": "Expecting value",
       "doc": "\nContent-Disposition: form-data; name=\\"files\\"; filename=\\"example.txt\\"\\r\\nContent-Type: text/plain\\r\\n\\r\\nexample text in the file\n",
     "pos":0,
     "lineno":1,
     "colno":1
  }
 }]
}

这是我引用的文档页面:https://fastapi.tiangolo.com/tutorial/request-files/#multiple-file-uploads

【问题讨论】:

标签: python python-requests fastapi


【解决方案1】:

您得到的错误只是表明您的 FastAPI 端点按照定义的方式需要 JSON 数据,这是因为您没有使用 File 类型为参数指定默认值,例如 = File(...) .因此,FastAPI 将 List[UploadFile] 解释为 JSON 主体。

您的端点应该如下所示:

from fastapi import File

@app.post("/registration/create")
async def create_registration(files: List[UploadFile] = File(...)):
    return {"file_len": len(files)}

请查看this answer,以及thisthis 答案了解更多详情。

更新

在最新版本的FastAPI中,可以define a file parameter with a type of UploadFile没有必须在参数的默认值中使用 = File()= File(...)。因此,以下内容也应该按预期工作:

@app.post("/registration/create")
async def create_registration(files: List[UploadFile]):
    return {"file_len": len(files)}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-07-24
    • 1970-01-01
    • 2021-04-19
    • 2014-06-25
    • 1970-01-01
    相关资源
    最近更新 更多