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

C# MVC应用使用AWS SES发邮件遇IAM凭证及签名错误求助

AWS SES在C# MVC应用中发送邮件的凭证配置与签名错误排查

问题描述

我在C# MVC应用中使用AWS SES官方模板代码发送邮件,EmailSender.cs代码如下:

using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using Amazon;
using Amazon.Runtime;
using Amazon.SimpleEmail;
using Amazon.SimpleEmail.Model;
using Microsoft.AspNetCore.Identity.UI.Services;
using Microsoft.Extensions.Options;

namespace amaranth.Helpers
{
    public class EmailSender : IEmailSender
    {
        private ApiEndpoints _endpoints;

        public EmailSender(IOptions<ApiEndpoints> _options)
        {
            _endpoints = _options.Value;
        }

        public async Task SendEmailAsync(string email, string subject, string htmlMessage)
        {
            using (var client = new AmazonSimpleEmailServiceClient(RegionEndpoint.USEast1))
            {
                var sendRequest = new SendEmailRequest
                {
                    Source = "<A DOMAIN THAT I DO OWN>",
                    Destination = new Destination
                    {
                        ToAddresses =
                        new List<string> { email }
                    },
                    Message = new Message
                    {
                        Subject = new Content(subject),
                        Body = new Body
                        {
                            Html = new Content
                            {
                                Charset = "UTF-8",
                                Data = htmlMessage
                            }
                        }
                    }
                };
                try
                {
                    Console.WriteLine("Sending email using Amazon SES...");
                    var response = await client.SendEmailAsync(sendRequest);
                    Console.WriteLine("The email was sent successfully.");
                }
                catch (Exception ex)
                {
                    Console.WriteLine("The email was not sent.");
                    Console.WriteLine("Error message: " + ex.Message);
                }
            }
        }
    }
}

已确认:

  • 收件人邮箱、主题、HTML内容格式正确
  • Source对应的域名已验证,且AWS SES已脱离沙箱
  • 已创建用于邮件操作的IAM用户

初始错误

运行应用时无法发送邮件,报错:
Error message: Unable to get IAM security credentials from EC2 Instance Metadata Service.

更新后错误

添加BasicAWSCredentials传入IAM用户的Access Key ID和Secret Access Key后,新报错:
Error message: The request signature we calculated does not match the signature you provided. Check your AWS Secret Access Key and signing method. Consult the service documentation for details.

排查步骤与解决方案

1. 验证IAM用户凭证与权限

  • 核对凭证准确性:确认Access Key ID和Secret Access Key无空格、大小写错误(Secret Key严格区分大小写),可临时在代码中打印值(注意不要泄露到日志)验证配置读取是否正确。
  • 检查IAM权限:确保IAM用户拥有SES发送邮件的权限,可附加AmazonSESFullAccess策略(生产环境建议使用最小权限策略,仅允许ses:SendEmail、ses:SendRawEmail操作)。

2. 选择正确的凭证配置方式(推荐优先级)

AWS SDK会自动按以下顺序读取凭证,推荐优先使用非硬编码方式:

  • 本地凭证文件:在用户目录下创建.aws/credentials文件(Windows路径:C:\Users\<用户名>\.aws\credentials;Linux/macOS路径:~/.aws/credentials),格式如下:
[default]
aws_access_key_id = YOUR_ACCESS_KEY
aws_secret_access_key = YOUR_SECRET_KEY

此时代码无需显式传入凭证,SDK会自动读取:

using (var client = new AmazonSimpleEmailServiceClient(RegionEndpoint.USEast1))
  • 系统环境变量:设置AWS_ACCESS_KEY_ID和AWS_SECRET_ACCESS_KEY环境变量,SDK会自动识别。
  • 代码显式传入(仅测试用):若必须在代码中传递,确保配置值未被转义或篡改,比如检查_endpoints.EmailUsername和_endpoints.EmailPassword是否正确绑定配置文件值。

3. 签名错误的额外排查点

  • 区域匹配:代码中使用的RegionEndpoint.USEast1必须与SES服务所在区域一致(例如SES在美西2区则改为RegionEndpoint.USWest2)。
  • 时间同步:服务器系统时间与AWS时间偏差超过5分钟会导致签名验证失败,检查并同步服务器时间。
  • 内容编码:若主题或HTML内容包含特殊字符,确认UTF-8编码生效(代码中已设置Charset = "UTF-8",可尝试简化内容测试)。

4. 代码优化建议

将AWS配置移至appsettings.json避免硬编码:

"AWSSettings": {
  "AccessKey": "YOUR_ACCESS_KEY",
  "SecretKey": "YOUR_SECRET_KEY",
  "Region": "us-east-1"
}

创建配置类:

public class AWSSettings
{
    public string AccessKey { get; set; }
    public string SecretKey { get; set; }
    public string Region { get; set; }
}

在Program.cs中注册配置:

builder.Services.Configure<AWSSettings>(builder.Configuration.GetSection("AWSSettings"));

修改EmailSender注入并使用配置:

private readonly AWSSettings _awsSettings;

public EmailSender(IOptions<AWSSettings> awsSettings)
{
    _awsSettings = awsSettings.Value;
}

public async Task SendEmailAsync(string email, string subject, string htmlMessage)
{
    var region = RegionEndpoint.GetBySystemName(_awsSettings.Region);
    using (var client = new AmazonSimpleEmailServiceClient(
        new BasicAWSCredentials(_awsSettings.AccessKey, _awsSettings.SecretKey), 
        region))
    {
        // 原有sendRequest逻辑不变
    }
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.18 06:25:23