.NET 4.5.2集成SendGrid遇连接强制关闭错误求助
.NET 4.5.2集成SendGrid发送邮件报错排查方案
问题场景
基于.NET 4.5.2的旧项目,集成SendGrid发送邮件时触发以下错误:
System.Net.Http.HttpRequestException: 发送请求时发生错误。
SocketException: 现有连接被远程主机强制关闭
触发错误的代码:
public void Email_ALL() { try { ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12; ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls11; var sendclient = new SendGridClient("api-key"); var from = new EmailAddress("hello@test.com", "Test"); var subject = "Sending with Twilio SendGrid is Fun"; var to = new EmailAddress("Test@gmail.com", "Example User"); var plainTextContent = "and easy to do anywhere, even with C#"; var htmlContent = "<strong>and easy to do anywhere, even with C#</strong>"; var msg = MailHelper.CreateSingleEmail(from, to, subject, plainTextContent, htmlContent); var result = Task.Run(() => sendclient.SendEmailAsync(msg)).GetAwaiter().GetResult(); } catch (Exception ex) { throw ex; } }
错误原因分析
- TLS版本被错误覆盖:代码中先设置
Tls12后又设置Tls11,后者直接覆盖了前者。而SendGrid已弃用TLS 1.1,强制要求使用TLS 1.2或更高版本,导致TLS握手失败,远程主机主动断开连接。 - 异步调用阻塞方式存在风险:用
Task.Run(...).GetAwaiter().GetResult()同步阻塞异步方法,在部分上下文环境中可能引发死锁,间接导致连接异常。
修复方案
1. 修正TLS版本配置
将TLS版本统一设置为TLS 1.2(.NET 4.5.2原生支持该协议):
// 仅启用TLS 1.2,符合SendGrid的要求 ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;
2. 优化异步调用逻辑
优先将方法改为异步模式,避免同步阻塞:
public async Task Email_ALL() { try { ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12; var sendclient = new SendGridClient("api-key"); var from = new EmailAddress("hello@test.com", "Test"); var subject = "Sending with Twilio SendGrid is Fun"; var to = new EmailAddress("Test@gmail.com", "Example User"); var plainTextContent = "and easy to do anywhere, even with C#"; var htmlContent = "<strong>and easy to do anywhere, even with C#</strong>"; var msg = MailHelper.CreateSingleEmail(from, to, subject, plainTextContent, htmlContent); var result = await sendclient.SendEmailAsync(msg); } catch (Exception ex) { // 建议添加日志记录后再抛出,便于排查问题 throw; } }
如果必须保持同步调用,可通过ConfigureAwait(false)降低死锁风险:
var result = Task.Run(() => sendclient.SendEmailAsync(msg).ConfigureAwait(false)).GetAwaiter().GetResult();
3. 额外检查项
- 确认SendGrid API密钥有效,且已在控制台完成发件人域名验证。
- 检查服务器防火墙/代理是否允许出站请求到
https://api.sendgrid.com。 - 确保.NET 4.5.2安装了最新补丁,部分旧补丁存在TLS 1.2支持缺陷。
内容的提问来源于stack exchange,提问作者Vasu V
相关产品推荐
相关产品推荐

