Java结合AWS SES发送含非ASCII字符邮件失败问题排查
解决AWS SES发送含非ASCII字符邮箱的问题
你的问题核心是错误地对整个邮箱地址使用了IDN.toASCII转换——IDN仅用于处理国际化域名(@后面的部分),而邮箱的本地部分(@前面含中文、俄文的内容)不需要转IDN,直接用UTF-8编码即可。
修正步骤
- 拆分邮箱地址为「本地部分」和「域名部分」,仅对域名部分执行IDN转换(如果域名包含非ASCII字符)
- 用
InternetAddress类按EAI(国际化邮箱)标准构造正确的地址格式,确保SES能识别非ASCII的本地部分 - 检查SES控制台的投递日志,确认是否有其他投递障碍
修正后的代码
import jakarta.mail.internet.InternetAddress import software.amazon.awssdk.regions.Region import software.amazon.awssdk.services.ses.SesClient import software.amazon.awssdk.services.ses.model.SendEmailRequest import java.net.IDN import java.nio.charset.StandardCharsets.UTF_8 // 专门处理邮箱地址:仅转域名,保留本地部分的UTF-8字符 fun processEmailAddress(email: String): String { val splitIndex = email.lastIndexOf('@') require(splitIndex != -1) { "邮箱格式无效" } val localPart = email.substring(0, splitIndex) val domainPart = email.substring(splitIndex + 1) // 仅对域名做IDN转换(比如把中文域名转成punycode) val punycodeDomain = IDN.toASCII(domainPart, IDN.ALLOW_UNASSIGNED) // 用InternetAddress生成符合标准的EAI邮箱地址 return InternetAddress(localPart, punycodeDomain, UTF_8.name()).toString() } fun main() { val ses = SesClient.builder() .region(Region.US_EAST_1) .build() val email1 = processEmailAddress("myemail@gmail.com") val email2 = processEmailAddress("myemail+早上@gmail.com") val email3 = processEmailAddress("myemail+й@gmail.com") val sendRequest = SendEmailRequest.builder() .destination { it.toAddresses(email1, email2, email3) } .message { messageBuilder -> messageBuilder .subject { it.data("Test").charset(UTF_8.name()) } .body { bodyBuilder -> bodyBuilder .html { it.data("<h1>Hello</h1>").charset(UTF_8.name()) } .text { it.data("Hello").charset(UTF_8.name()) } } } .source(InternetAddress("myemail@gmail.com", "My Email", UTF_8.name()).toString()) .build() ses.sendEmail(sendRequest) }
额外说明
- 如果域名本身是纯ASCII(比如gmail.com),IDN转换不会改变它的内容,不影响正常使用
- 若问题仍存在,登录AWS SES控制台查看「已发送邮件」列表,检查投递状态和错误信息——比如部分收件人邮箱可能不支持EAI格式,导致邮件被退回
内容的提问来源于stack exchange,提问作者Cedric Thiebault
相关产品推荐
相关产品推荐

