Flutter通过ApiGateway调用Lambda托管FastAPI上传S3图片损坏问题
故障根因定位与修复方案
核心原因
该问题100%由ApiGateway的二进制媒体类型配置不匹配导致,因为你本地调试、Postman调用均正常,说明业务代码逻辑无问题,只有流量经过ApiGateway到Lambda的链路出现了二进制数据篡改:
ApiGateway默认会将未纳入「二进制媒体类型」列表的请求内容当作纯文本处理,会对二进制的图片数据做Base64编码后再透传给Lambda,而你的FastAPI运行在Lambda环境下时,没有对这层Base64编码做自动解码,最终上传到S3的文件是Base64编码后的文本,不是原始图片二进制,因此出现损坏。
具体修复步骤
- 第一步:配置ApiGateway二进制媒体类型
进入AWS ApiGateway控制台对应实例的「设置」页面,在二进制媒体类型配置项中添加如下值:multipart/form-data
也可以直接添加*/*全局覆盖所有二进制类型,避免后续其他类型文件上传出现同类问题,配置完成后需要重新部署ApiGateway的阶段生效。 - 第二步:适配Lambda侧的Base64自动解码
如果你使用Mangum作为FastAPI对接Lambda的适配器,需要在初始化时开启二进制解码能力,示例代码:from mangum import Mangum from fastapi import FastAPI app = FastAPI() # 配置适配器自动处理Base64编码的二进制请求 handler = Mangum( app, binary_media_types=["multipart/form-data", "image/png", "image/jpeg", "image/*"] ) - 第三步(可选):检查ApiGateway集成配置
确认你使用的是Lambda代理集成模式,不要使用自定义集成带请求转换模板的配置,转换模板会主动修改multipart/form-data的请求体结构,导致二进制数据被篡改。
验证方法
在Lambda函数入口处打印原始请求事件的isBase64Encoded字段和请求体前100个字符:
- 如果
isBase64Encoded为true,说明ApiGateway已经将请求做了Base64编码,确认适配器配置正确即可 - 对比正常上传和异常上传的文件头字节,异常文件的头会是Base64编码的文本(比如png正常头是
89 50 4E 47,编码后会是iVBORw0KGgo这样的文本),即可确认根因。
内容的提问来源于stack exchange,提问作者Devon Ray
相关产品推荐
相关产品推荐

