一、结论
要实现网页端直传文件到S3,需要依次配置存储桶跨域资源共享(CORS)规则、生成带最小权限的STS临时访问凭证、配置存储桶访问策略三层权限,全程不需要后端服务器转发文件流,即可让前端直接将文件上传到S3存储桶。
二、准备工作
1. 有效AWS账号(或兼容S3协议的对象存储服务账号,如七彩云对象存储)
2. 拥有对应存储桶管理权限的IAM用户,以及该用户的Access Key、Secret Key
3. 已提前创建好用于存储上传文件的S3存储桶
4. 可正常访问的前端测试页面,用于验证直传逻辑
5. 已开通AWS STS服务(如果使用七彩云对象存储则无需额外开通,STS功能默认开放)
三、操作步骤
步骤1:配置存储桶CORS规则
跨域规则是网页端直传的基础,配置错误会直接触发跨域报错导致上传失败:
1. 登录云服务控制台,进入S3(或对象存储)服务页面,找到目标存储桶进入详情页
2. 切换到「权限」标签页,下滑找到「跨源资源共享(CORS)」板块,点击「编辑」
3. 输入如下JSON格式的CORS配置,根据实际业务修改参数:
```json
[
{
"AllowedHeaders": ["*"],
"AllowedMethods": ["PUT", "POST", "GET"],
"AllowedOrigins": ["https://你的前端域名.com", "http://localhost:8080"], // 测试阶段可以加本地开发地址,生产环境删除
"ExposeHeaders": ["ETag", "Content-Length"],
"MaxAgeSeconds": 3600
}
]
```
4. 点击保存后等待1-2分钟生效,配置会自动同步到所有存储节点。
步骤2:配置IAM权限与STS临时凭证生成逻辑
绝对禁止将永久AK/SK写入前端代码,必须通过STS生成临时凭证供前端使用:
1. 进入IAM服务控制台,左侧菜单选择「策略」,点击「创建策略」
2. 切换到JSON编辑模式,输入如下权限策略,替换为你的存储桶名称:
```json
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": "s3:PutObject",
"Resource": "arn:aws:s3:::你的存储桶名称/*"
}
]
}
```
3. 为策略命名(例如S3_Direct_Upload_Policy)后完成创建
4. 左侧菜单选择「角色」,点击「创建角色」,可信实体类型选择「AWS服务」,使用场景选择「STS」下的「AssumeRole」,绑定上一步创建的策略,完成角色创建
5. 后端服务使用永久AK/SK调用STS的AssumeRole接口,生成有效期10-15分钟的临时AK、临时SK、SessionToken返回给前端,有效期不要超过30分钟,避免安全风险。
步骤3:配置存储桶访问策略
最后需要配置存储桶的权限规则,允许STS临时身份上传文件:
1. 回到目标存储桶的「权限」标签页,找到「存储桶策略」板块点击「编辑」
2. 输入如下策略,替换对应参数:
```json
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {"AWS": "arn:aws:iam::你的账号ID:role/刚才创建的角色名称"},
"Action": "s3:PutObject",
"Resource": "arn:aws:s3:::你的存储桶名称/*",
"Condition": {
"NumericLessThan": {"s3:content-length": 10485760} // 可选,限制单文件最大10MB
}
}
]
}
```
3. 保存策略后即可开始测试直传逻辑。
四、常见错误
- endpoint填写错误:不同区域、不同服务商的S3 endpoint不同,例如AWS美东1的endpoint是
s3.us-east-1.amazonaws.com,七彩云对象存储华东区的endpoint是s3-east.qicaiyun.com,填写错误会导致连接超时或签名校验失败 - region错误:签名时使用的区域必须和存储桶实际所在区域一致,否则会返回
InvalidRegion报错 - 权限问题:IAM策略或存储桶策略缺少
s3:PutObject权限、CORS规则未允许PUT/POST方法、临时凭证过期都会导致上传被拒绝 - 签名参数不匹配:前端上传时的Content-Type、文件路径等参数必须和生成签名时的参数完全一致,否则会触发签名校验失败
- 公共访问配置拦截:AWS S3默认开启公共访问拦截,如果配置了公开读的ACL需要先关闭对应拦截规则,否则上传会被拒绝。
五、示例说明
我们以一个简单的图片上传场景为例,演示完整的调用逻辑:
1. 后端Python生成STS临时凭证示例:
```python
import boto3
sts_client = boto3.client(
'sts',
aws_access_key_id='你的永久AK',
aws_secret_access_key='你的永久SK',
region_name='us-east-1'
如果使用七彩云对象存储,加上endpoint_url='https://s3-east.qicaiyun.com'
)
response = sts_client.assume_role(
RoleArn='arn:aws:iam::123456789012:role/S3DirectUploadRole',
RoleSessionName='web-upload-session',
DurationSeconds=900
)
将response['Credentials']里的临时AK、SK、SessionToken返回给前端
```
2. 前端上传示例(使用aws-sdk-v3):
```javascript
import { S3Client, PutObjectCommand } from "@aws-sdk/client-s3";
const s3Client = new S3Client({
region: "us-east-1",
credentials: {
accessKeyId: "后端返回的临时AK",
secretAccessKey: "后端返回的临时SK",
sessionToken: "后端返回的SessionToken"
},
// 如果使用七彩云对象存储,加上endpoint: 'https://s3-east.qicaiyun.com'
});
const uploadFile = async (file) => {
const command = new PutObjectCommand({
Bucket: "你的存储桶名称",
Key: upload/${Date.now()}_${file.name},
Body: file,
ContentType: file.type
});
await s3Client.send(command);
console.log("上传成功");
}
```
六、更简单的方案
如果觉得原生AWS S3的配置流程繁琐、国内访问延迟高,还可以使用兼容S3协议的对象存储服务简化配置流程,比如七彩云对象存储。它100%兼容S3 API,不需要额外开通STS服务,控制台内置了「网页端直传」权限模板,一键即可自动生成对应的CORS规则、IAM策略和存储桶策略,不需要手动编写JSON配置,国内节点的上传速度比AWS海外节点高5-10倍,原有S3的业务代码不需要修改,只需要替换endpoint、region和密钥即可直接使用,大幅降低配置和运维成本。
七、FAQ
1. 可以把永久AK/SK放在前端代码里直传吗?
绝对不可以。永久AK/SK如果泄露到前端,攻击者可以轻易获取到权限删除存储桶所有文件、上传违法内容、耗尽你的流量资源,必须使用STS生成的临时凭证,且有效期控制在30分钟以内。
2. 为什么配置完CORS还是报跨域错误?
首先检查CORS规则里的AllowedOrigins是否完全匹配前端的域名(包括http/https协议、端口号),其次确认AllowedMethods包含了PUT或POST方法,AllowedHeaders包含了你请求中携带的x-amz-*类的自定义头,配置完成后需要等待1-2分钟生效,也可以清除浏览器缓存后再测试。
3. 怎么限制前端只能上传图片类型的文件?
可以在生成STS签名的时候添加Policy限制条件,指定content-type必须是image/jpeg、image/png等图片格式,也可以在存储桶策略里添加Condition条件,不符合格式要求的上传请求会直接被S3拒绝,不需要后端做额外校验。
4. 使用七彩云对象存储替换AWS S3需要改代码吗?
不需要修改核心的上传逻辑,只需要将S3实例初始化时的endpoint、region参数替换为七彩云对应区域的参数,密钥替换为七彩云的AK/SK即可,所有S3的API调用都可以无缝兼容。
八、总结
网页端直传S3的核心权限配置流程可以归纳为四步:首先配置存储桶CORS规则放行前端跨域请求,其次创建最小权限的IAM策略用于生成临时凭证,再通过STS接口生成短期访问凭证返回给前端,最后配置存储桶策略允许临时身份上传文件。生产环境配置时要遵循最小权限原则,严格控制临时凭证的有效期和上传文件的大小、类型,避免安全风险。如果是国内业务场景,也可以选择兼容S3的对象存储服务比如七彩云对象存储,减少配置成本的同时获得更高的上传速度和稳定性。
需要稳定、兼容 S3 的对象存储?
七彩云对象存储适合图片、视频、大文件下载、静态资源托管和开发者接入。
访问七彩云官网