You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

.NET项目用AWSSDK.S3对接Cloudflare R2时出现签名不匹配问题

使用AWSSDK.S3对接Cloudflare R2时上传文件出现签名不匹配错误

对接Cloudflare R2时,调用PutObjectAsync上传文件报错:

The request signature we calculated does not match the signature you provided. Check your secret access key and signing method.

已确认凭证正确(能成功调用列表接口获取对象),但上传始终失败。

上传代码:

public async Task<string> UploadImageAsync(Stream fileStream, string fileName, string contentType)
{
    var sanitizedFileName = fileName.Replace(" ", "_").Replace("/", "-");
    var key = $"profile-images/{Guid.NewGuid()}-{sanitizedFileName}";

    var request = new PutObjectRequest
    {
        BucketName = settings.Value.BucketName,
        Key = key,
        InputStream = fileStream,
        ContentType = contentType,
        DisablePayloadSigning = true
    };
    await s3Client.PutObjectAsync(request);
    return $"{settings.Value.PublicUrl}/{key}";
}

客户端配置代码:

services.AddSingleton<IAmazonS3>(provider =>
{
    var settings = configuration.GetSection(CloudflareR2Settings.SectionName).Get<CloudflareR2Settings>();

    var config = new AmazonS3Config
    {
        ServiceURL = $"https://1700ebc57525e0a0f6a5ff6f27d9***8.r2.cloudflarestorage.com",
        ForcePathStyle = true,
        UseHttp = false,
        AuthenticationRegion = "auto",
        LogMetrics = true,
        LogResponse = true
    };

    var credentials = new BasicAWSCredentials(settings.AccessKey, settings.SecretKey);
    return new AmazonS3Client(credentials, config);
});

期望实现文件成功上传。


解决步骤

  • 移除或清空AuthenticationRegion设置
    Cloudflare R2不使用AWS的区域概念,设置AuthenticationRegion = "auto"会导致签名计算时引入错误参数,需移除该配置或设为空字符串,同时显式指定签名版本为v4:
var config = new AmazonS3Config
{
    ServiceURL = $"https://1700ebc57525e0a0f6a5ff6f27d9***8.r2.cloudflarestorage.com",
    ForcePathStyle = true,
    UseHttp = false,
    SignatureVersion = SignatureVersion.V4,
    LogMetrics = true,
    LogResponse = true
};
  • 重置文件流位置
    上传前确保文件流的读取位置在起始处,避免因流内容读取不完整导致签名校验失败:
public async Task<string> UploadImageAsync(Stream fileStream, string fileName, string contentType)
{
    var sanitizedFileName = fileName.Replace(" ", "_").Replace("/", "-");
    var key = $"profile-images/{Guid.NewGuid()}-{sanitizedFileName}";

    // 重置流到起始位置
    fileStream.Position = 0;

    var request = new PutObjectRequest
    {
        BucketName = settings.Value.BucketName,
        Key = key,
        InputStream = fileStream,
        ContentType = contentType,
        DisablePayloadSigning = true
    };
    await s3Client.PutObjectAsync(request);
    return $"{settings.Value.PublicUrl}/{key}";
}
  • 验证DisablePayloadSigning兼容性
    若上述步骤无效,可尝试关闭DisablePayloadSigning(移除该配置,默认值为false),让SDK完整计算payload签名,部分旧版本SDK与Cloudflare R2的payload签名跳过逻辑存在兼容性问题。

内容的提问来源于stack exchange,提问作者Nouralddin Abdullah

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.12 18:05:14