应安装官方 aws.sdk.s3 包(非旧版 awssdk.s3),.net 6+ 必用新版;初始化推荐默认凭据链,区域须匹配桶;小文件用 putobjectasync,大文件慎用 transferutility;key 中 / 仅为分隔符,中文需统一 utf-8 编码。

AWSSDK.S3 NuGet 包怎么选
.NET 项目里用 AWS S3,必须安装 AWS.SDK.S3,但要注意:它不是独立包,而是由 AWS.SDK.Core + AWS.SDK.S3 组成。NuGet 搜索时别只输 “AWS S3”,直接搜 AWS.SDK.S3,选官方 Amazon Web Services 发布的那一个(ID 确实就是 AWS.SDK.S3)。旧版 AWSSDK(无点号、大版本 2.x)已弃用,不支持 .NET 6+ 的默认 TLS 1.2+ 要求,会静默失败。
- 安装命令:
dotnet add package AWS.SDK.S3 - 若项目是 .NET Framework 4.7.2+,也推荐用新版 SDK,旧版
AWSSDK.S3(v3.3.x)在上传大文件时容易因分块重试逻辑缺陷卡住 - 不要手动引用
AWS.SDK.Core单独包——AWS.SDK.S3已声明依赖,重复引用可能引发AssemblyLoadException
初始化 S3Client 的三种常见方式
AmazonS3Client 是操作入口,初始化方式决定凭证来源和区域行为:
- 用默认凭据链(推荐开发/测试):
var client = new AmazonS3Client(),它会按顺序查:环境变量 →~/.aws/credentials→ EC2 实例角色。注意 Windows 上路径是%USERPROFILE%.aws\credentials - 显式传入凭证和区域:
var client = new AmazonS3Client(new BasicAWSCredentials("AKIA...", "xxx"), RegionEndpoint.USEast1);但密钥硬编码进代码是严重安全风险,仅限临时调试 - 使用配置对象(适合多环境):
var config = new AmazonS3Config { RegionEndpoint = RegionEndpoint.USEast2 }; var client = new AmazonS3Client(config);此时仍走默认凭据链,只是强制指定区域——S3 桶所在区域必须匹配,否则报AmazonS3Exception: The bucket you are attempting to access must be addressed using the specified endpoint
上传小文件用 PutObjectAsync,别用 UploadAsync
PutObjectAsync 是最直接的方式,适合 ≤5 MB 的文件:
它把整个流一次性发到 S3,无分块、无进度回调、无自动重试(SDK 内部有基础重试,但不可配置)
-
示例:
using var stream = File.OpenRead(@"C:\data\report.pdf"); await client.PutObjectAsync(new PutObjectRequest { BucketName = "my-bucket", Key = "uploads/report.pdf", InputStream = stream, ContentType = "application/pdf" }); 别误用
TransferUtility.UploadAsync:它是为大文件(>5 MB)设计的,内部做分块上传(Multipart Upload),但需要额外初始化TransferUtility实例,且默认启用 MD5 校验——若网络不稳定或文件内容动态生成,MD5 计算可能失败并抛AmazonS3Exception: Unable to compute MD5 hash如果真要传大文件,用
TransferUtility前务必设UseMD5 = false,或改用底层InitiateMultipartUpload+ 分块UploadPart手动控制
Key 中的路径分隔符和中文处理
S3 本身没有“文件夹”概念,Key 是纯字符串,/ 只是约定俗成的分隔符:
-
Key = "logs/2024/06/app.log"是合法的,控制台会显示为嵌套目录,但本质还是单个对象 - 中文或 Unicode 字符在
Key中可以,但必须确保编码一致:.NET 默认 UTF-8,S3 接收时也按 UTF-8 解析,一般没问题;但如果前端 JavaScript 用encodeURIComponent编码后再传 Key,后端 C# 就得先Uri.UnescapeDataString,否则出现乱码 Key 导致 404 - 避免 Key 以
/开头(如/images/logo.png),部分 SDK 版本会静默截断,最终存成images/logo.png;也不要用..\或空格开头,虽不报错但易引发权限或签名异常
S3 上传看着简单,真正上线时最容易栽在凭据加载顺序、区域错配、Key 编码不一致这三处——它们都不报编译错误,但运行时要么 403,要么 400,要么对象“消失”。










