【golang】使用AWS S3生成兼容存储的预签名上传 URL
·
适用场景:前后端分离架构中,前端需要直传文件到存储桶,后端仅负责签发临时上传链接,提升安全性和性能。
本文将基于 AWS SDK for Go v2(兼容 S3 协议)演示生成一个有效的 临时预签名上传链接。
前提条件
- 已部署 MinIO 或其他 S3 兼容服务(单机或集群)
- 已创建 Bucket,并拥有 AccessKey / SecretKey
- 项目中已引入 AWS SDK for Go v2 相关依赖:
go get github.com/aws/aws-sdk-go-v2/config
go get github.com/aws/aws-sdk-go-v2/credentials
go get github.com/aws/aws-sdk-go-v2/service/s3
重要说明
MinIO、Ceph RGW、阿里云 OSS(需开启 S3 兼容模式)、腾讯云 COS 等支持 S3 API 的对象存储服务都可以使用该代码生成预签名 URL,只需正确配置 Endpoint、访问凭证(Credentials)以及按需设置 UsePathStyle 参数即可。
核心代码
ctx := context.Background()
// 使用 AWS 加载默认配置
cfg, err := config.LoadDefaultConfig(ctx,
config.WithCredentialsProvider(
credentials.NewStaticCredentialsProvider(
local_config.AppConfig.Minio.AccessKey, // 替换为自己的Access Key
local_config.AppConfig.Minio.SecretKey, // 替换为自己的Secret Key
"", // Session Token(MinIO 通常不需要,留空)
),
),
config.WithRegion(local_config.AppConfig.Minio.Region), // 指定区域(MinIO 可以任意填写,但必须提供)
config.WithBaseEndpoint(local_config.AppConfig.Minio.Endpoint), // MinIO 服务地址,例如 http://localhost:9000
)
if err != nil {
fmt.Println(err)
}
// 创建 S3 客户端
client := s3.NewFromConfig(cfg, func(o *s3.Options) {
o.UsePathStyle = true // 启用路径风格 URL
})
// 创建预签名客户端
presignClient := s3.NewPresignClient(client)
// 生成用于上传对象(PutObject)的预签名 URL
response, err := presignClient.PresignPutObject(ctx, &s3.PutObjectInput{
Bucket: aws.String(local_config.AppConfig.Minio.BucketName), // 存储桶名称
Key: aws.String(req.FileName), // 对象在桶中的键(即文件路径/名称)
ContentType: aws.String(req.ContentType), // 上传文件的类型(可选)
}, func(opts *s3.PresignOptions) {
// 设置预签名 URL 的有效期
opts.Expires = 300 * time.Second
})
if err != nil {
fmt.Println(err)
}
// 此时 response.URL 就是可以直接用于 PUT 请求的临时上传链接
// 可将其返回给前端使用
关键点
启用 UsePathStyle = true 的原因
MinIO 默认采用路径风格的 URL 格式(例如 http://endpoint/bucket/key),这与 AWS SDK 默认使用的虚拟主机风格不同。若不启用相应配置,可能会导致 404 错误或 URL 解析失败。
因此需要显式设置 UsePathStyle = true,使请求格式变为: http://minio.example.com/mybucket/file.jpg
更多推荐
所有评论(0)