You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

FastAPI+Lambda+API Gateway部署后上传Excel文件损坏问题

解决FastAPI+Mangum部署Lambda/API Gateway后Excel文件损坏问题

核心问题根源

API Gateway默认会对非文本类型的请求/响应做字符编码转换或Base64处理,而.xlsx本质是ZIP压缩包,二进制数据一旦被篡改就会触发zipfile.BadZipFile错误。结合Mangum的适配逻辑,需要从配置和代码层面同步调整。


分步解决方案

1. 配置API Gateway二进制媒体类型

  • 登录API Gateway控制台,进入目标API的Settings页面,在Binary Media Types中添加以下两种类型:
    • multipart/form-data(处理文件上传的表单类型)
    • application/vnd.openxmlformats-officedocument.spreadsheetml.sheet(xlsx文件的MIME类型)
  • 若用SAM/CloudFormation部署,需在AWS::ApiGateway::RestApi资源中显式配置:
    Resources:
      MyApi:
        Type: AWS::ApiGateway::RestApi
        Properties:
          Name: MyExcelUploadApi
          BinaryMediaTypes:
            - "multipart/form-data"
            - "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet"
    

2. 调整Mangum初始化配置

Mangum需要明确告知API Gateway的Base64编码逻辑,避免二进制数据被错误转码:

from mangum import Mangum

# 初始化时开启Base64编码支持
handler = Mangum(app, api_gateway_base64_encoded=True)

3. 确保文件上传时读取原始二进制数据

在FastAPI的上传接口中,直接读取文件的二进制内容,不要进行字符串解码:

from fastapi import FastAPI, UploadFile, File
import boto3

app = FastAPI()
s3 = boto3.client("s3")

@app.post("/upload-excel")
async def upload_excel(file: UploadFile = File(...)):
    # 直接读取二进制字节流,跳过字符串解码步骤
    file_bytes = await file.read()
    # 上传到S3时指定正确的Content-Type
    s3.put_object(
        Bucket="your-bucket-name",
        Key=f"uploads/{file.filename}",
        Body=file_bytes,
        ContentType=file.content_type
    )
    return {"status": "success"}

4. 验证文件完整性

  • 上传完成后,从S3控制台下载文件,对比本地原文件的大小:若大小不一致,说明传输过程中数据被篡改。
  • 用终端命令验证文件是否为有效ZIP包:
    unzip -t your-uploaded-file.xlsx
    
    若输出"No errors detected",则文件正常;否则需检查编码链路。

5. 排查API Gateway阶段配置

部分场景下,全局Binary Media Types设置不会自动同步到部署阶段:

  • 进入API的Stages页面,选择目标阶段,进入Settings,确认Binary Media Types已包含所需类型。

内容的提问来源于stack exchange,提问作者frenchytheasian

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.25 05:47:21