如何让第三方通过Curl免签名上传任意文件至AWS S3存储桶?
AWS没有直接提供和Azure容器级预签名URL完全一致的桶级预签名功能,但有两个实用方案可以满足你「第三方仅用Curl、无需手动计算签名、可上传任意文件到桶」的需求:
方案1:S3预签名POST表单(支持任意文件上传)
这是最接近Azure容器预签名的方案,你可以生成一个预签名POST表单,第三方只需用Curl提交文件到该表单,无需计算签名,且支持上传任意名称的文件(可配置前缀限制)。
你这边生成预签名POST表单
用AWS CLI生成表单配置(以允许上传整个桶为例,如需限制前缀可修改--key-prefix参数):
aws s3 presign-post --bucket your-bucket-name --key-prefix "" --expires-in 86400
执行后会得到包含url(S3上传地址)和fields(表单必填字段)的JSON结果。
第三方用Curl上传(无需签名计算)
第三方直接使用你提供的表单字段,用Curl提交文件即可:
curl -X POST \ -F "key=${filename}" \ -F "AWSAccessKeyId=xxx" \ -F "policy=xxx" \ -F "signature=xxx" \ -F "file=@/path/to/local/file" \ https://your-bucket-name.s3.amazonaws.com/
注:${filename}替换为第三方要上传的文件名,其他fields字段直接复用你生成的内容即可,有效期可通过--expires-in设置(示例为24小时)。
方案2:STS短期临时凭证(无需每日计算签名)
给第三方生成短期IAM凭证(包含Access Key、Secret Key、Session Token),有效期可设1-36小时,第三方用这些凭证通过Curl上传时,可借助Curl的--aws-sigv4参数自动处理签名,无需手动计算当日签名。
你这边生成短期凭证
先创建一个仅拥有S3上传权限(s3:PutObject)的IAM角色,再用AWS CLI调用STS生成凭证:
aws sts assume-role --role-arn arn:aws:iam::123456789012:role/ThirdPartyUploadRole --role-session-name upload-session --duration-seconds 3600
执行后会得到Credentials字段,里面包含第三方需要的三个凭证值。
第三方用Curl上传(无需手动算签名)
第三方设置环境变量后,用Curl直接上传任意文件:
export AWS_ACCESS_KEY_ID="xxx" export AWS_SECRET_ACCESS_KEY="xxx" export AWS_SESSION_TOKEN="xxx" curl --aws-sigv4 "aws:amz:us-east-1:s3" \ -X PUT \ -T "/path/to/local/file" \ https://your-bucket-name.s3.us-east-1.amazonaws.com/目标文件名
注:替换为你的S3桶所在区域,这个方案的优势是第三方可在凭证有效期内重复上传任意数量的文件,无需每次重新获取表单。
方案3:S3 Access Points + 上述方案(权限隔离优化)
如果需要更精细的权限控制(比如仅允许上传到桶内某个前缀),可以创建S3 Access Point,给Access Point单独配置上传权限,再结合预签名POST或STS凭证使用,进一步隔离桶的全局权限。
核心对比Azure容器预签名
AWS没有直接的「桶级预签名URL」,但上述方案可实现等价效果:
- 预签名POST适合一次性批量上传场景,无需第三方保存凭证;
- STS短期凭证适合几小时到一天的持续上传需求,第三方可重复使用凭证。
内容的提问来源于stack exchange,提问作者ilymid

