C# 如何将 Await 添加到此函数 - SendEmailAsync - Dot Net Core 中的 MailKit
C# how to add Await to this function - SendEmailAsync - MailKit in Dot Net Core
我有基于 MailKit 的代码。在哪里添加 await 关键字?
public async Task SendEmailAsync(string email, string subject, string mess)
{
var message = new MimeMessage();
message.From.Add(new MailboxAddress("Joey Tribbiani", "joey@friends.com"));
message.To.Add(new MailboxAddress("Mrs. Chanandler Bong", "chandler@friends.com"));
message.Subject = "How you doin'?";
message.Body = new TextPart("plain")
{
Text = @"Hey Chandler"
};
using (var client = new SmtpClient())
{
// For demo-purposes, accept all SSL certificates (in case the server supports STARTTLS)
client.ServerCertificateValidationCallback = (s, c, h, e) => true;
client.Connect("smtp.friends.com", 587, false);
// Note: since we don't have an OAuth2 token, disable
// the XOAUTH2 authentication mechanism.
client.AuthenticationMechanisms.Remove("XOAUTH2");
// Note: only needed if the SMTP server requires authentication
client.Authenticate("joey", "password");
client.Send(message);
client.Disconnect(true);
}
}
这是一个类似的实现(但我找不到使它工作的凭据)所以我改为上面的
public async Task SendEmailAsync(string email, string subject, string message)
{
using (var client = new HttpClient { BaseAddress = new Uri("smtp.gmail.com") })
{
client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Basic",
Convert.ToBase64String(Encoding.ASCII.GetBytes("api:key-*")));
var content = new FormUrlEncodedContent(new[]
{
new KeyValuePair<string, string>("from", "postmaster@sandbox*.mailgun.org"),
new KeyValuePair<string, string>("to", email),
new KeyValuePair<string, string>("subject", subject),
new KeyValuePair<string, string>("text", message)
});
await client.PostAsync("sandbox*.mailgun.org/messages", content).ConfigureAwait(false);
}
}
如果您使用的是 .Net 核心和 MailKit,您应该引用 MailKit 库并通过它们发送。我用于发送电子邮件的 MailKit class 如下:
using System;
using System.Threading;
using MailKit.Security;
using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Options;
using MimeKit;
using SmtpClient = MailKit.Net.Smtp.SmtpClient;
namespace App.Email
{
public class MailKit : IMailKit
{
private readonly ILogger<MailKit> _logger;
private readonly Settings _settings;
public MailKit(ILogger<MailKit> logger, IOptions<Settings> settings)
{
_logger = logger;
_settings = settings.Value;
}
/// <summary>
/// Sends an email asynchronously using SMTP
/// </summary>
/// <param name="toEmailAddress"></param>
/// <param name="subject"></param>
/// <param name="bodyHtml"></param>
/// <param name="bodyText"></param>
/// <param name="retryCount"></param>
/// <param name="toName"></param>
public async void Send(string toName, string toEmailAddress, string subject, string bodyHtml, string bodyText, int retryCount = 4)
{
var message = new MimeMessage();
message.From.Add(new MailboxAddress(_settings.MailKitFromName, _settings.MailKitFromAddress));
message.To.Add(new MailboxAddress(toName, toEmailAddress));
message.Subject = subject;
var builder = new BodyBuilder
{
TextBody = bodyText,
HtmlBody = bodyHtml
};
message.Body = builder.ToMessageBody();
for (var count = 1; count <= retryCount; count++)
{
try
{
using (var client = new SmtpClient())
{
client.LocalDomain = _settings.MailKitLocalDomain;
client.Authenticate(_settings.MailKitUsername, _settings.MailKitPassword);
SecureSocketOptions secureSocketOptions;
if (!Enum.TryParse(_settings.MailKitSecureSocketOption, out secureSocketOptions))
{
secureSocketOptions = SecureSocketOptions.Auto;
}
await client.ConnectAsync(_settings.MailKitHost, _settings.MailKitPort, secureSocketOptions).ConfigureAwait(false);
await client.SendAsync(message).ConfigureAwait(false);
await client.DisconnectAsync(true).ConfigureAwait(false);
return;
}
}
catch (Exception exception)
{
_logger.LogError(0, exception, "MailKit.Send failed attempt {0}", count);
if (retryCount >= 0)
{
throw;
}
await Task.Delay(count * 1000);
}
}
}
}
}
界面
namespace App.Email
{
public interface IMailKit
{
void Send(string toName, string toEmailAddress, string subject, string bodyHtml, string bodyText, int retryCount = 4);
}
}
您可以这样使用 async functions:
public class Notification
{
public Notification() { }
private string emailSubject,receiverEmail,emailBody;
public string EmailSubject { get => emailSubject; set => emailSubject = value; }
public string ReceiverEmail { get => receiverEmail; set => receiverEmail = value; }
public string EmailBody { get => emailBody; set => emailBody = value; }
public async Task<bool> sendEmail(){
try
{
var message = new MimeMessage();
message.From.Add(new MailboxAddress("Smart Living", "smartliving321@gmail.com"));
message.To.Add(new MailboxAddress("Person", receiverEmail));
message.Subject = emailSubject;
message.Body = new TextPart("plain")
{
Text = emailBody
};
using (var client = new SmtpClient())
{
await client.ConnectAsync("smtp.gmail.com", 587, false);
await client.AuthenticateAsync("smartliving321@gmail.com", "living@smart1122");
await client.SendAsync(message);
await client.DisconnectAsync(true);
// client.ServerCertificateValidationCallback=();
};
return true;
}
catch (Exception ex) {
return false;
}
}
}
这是我的简单解决方案,现在我可以在 asp 核心项目中使用 IdentityServer 使用 MailKit 发送电子邮件。
public class EmailSender : Microsoft.AspNetCore.Identity.UI.Services.IEmailSender
{
private readonly EmailConfiguration _emailConfig;
public EmailSender(EmailConfiguration emailConfig)
{
_emailConfig = emailConfig;
}
public Task SendEmailAsync(string email, string subject, string htmlMessage)
{
var message = new MimeMessage();
message.From.Add(new MailboxAddress(_emailConfig.FromName, _emailConfig.FromEmail));
message.To.Add(new MailboxAddress(email.Trim().ToLower(), email.Trim().ToLower()));
message.Subject = subject;
message.Body = new TextPart("html") { Text = htmlMessage };
using (var client = new SmtpClient())
{
try
{
client.Connect(_emailConfig.SmtpServer, _emailConfig.Port, MailKit.Security.SecureSocketOptions.SslOnConnect);
client.Authenticate(_emailConfig.UserName, _emailConfig.Password);
client.Send(message);
client.Disconnect(true);
return Task.FromResult(true);
}
catch (Exception)
{
throw;
}
finally
{
}
}
}
并在 startup.cs -> ConfigureServices
var emailConfig = Configuration.GetSection("EmailConfiguration")
.Get<EmailService.EmailConfiguration>();
services.AddSingleton(emailConfig);
services.AddScoped<IEmailSender, EmailService.EmailSender>();
我有基于 MailKit 的代码。在哪里添加 await 关键字?
public async Task SendEmailAsync(string email, string subject, string mess)
{
var message = new MimeMessage();
message.From.Add(new MailboxAddress("Joey Tribbiani", "joey@friends.com"));
message.To.Add(new MailboxAddress("Mrs. Chanandler Bong", "chandler@friends.com"));
message.Subject = "How you doin'?";
message.Body = new TextPart("plain")
{
Text = @"Hey Chandler"
};
using (var client = new SmtpClient())
{
// For demo-purposes, accept all SSL certificates (in case the server supports STARTTLS)
client.ServerCertificateValidationCallback = (s, c, h, e) => true;
client.Connect("smtp.friends.com", 587, false);
// Note: since we don't have an OAuth2 token, disable
// the XOAUTH2 authentication mechanism.
client.AuthenticationMechanisms.Remove("XOAUTH2");
// Note: only needed if the SMTP server requires authentication
client.Authenticate("joey", "password");
client.Send(message);
client.Disconnect(true);
}
}
这是一个类似的实现(但我找不到使它工作的凭据)所以我改为上面的
public async Task SendEmailAsync(string email, string subject, string message)
{
using (var client = new HttpClient { BaseAddress = new Uri("smtp.gmail.com") })
{
client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Basic",
Convert.ToBase64String(Encoding.ASCII.GetBytes("api:key-*")));
var content = new FormUrlEncodedContent(new[]
{
new KeyValuePair<string, string>("from", "postmaster@sandbox*.mailgun.org"),
new KeyValuePair<string, string>("to", email),
new KeyValuePair<string, string>("subject", subject),
new KeyValuePair<string, string>("text", message)
});
await client.PostAsync("sandbox*.mailgun.org/messages", content).ConfigureAwait(false);
}
}
如果您使用的是 .Net 核心和 MailKit,您应该引用 MailKit 库并通过它们发送。我用于发送电子邮件的 MailKit class 如下:
using System;
using System.Threading;
using MailKit.Security;
using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Options;
using MimeKit;
using SmtpClient = MailKit.Net.Smtp.SmtpClient;
namespace App.Email
{
public class MailKit : IMailKit
{
private readonly ILogger<MailKit> _logger;
private readonly Settings _settings;
public MailKit(ILogger<MailKit> logger, IOptions<Settings> settings)
{
_logger = logger;
_settings = settings.Value;
}
/// <summary>
/// Sends an email asynchronously using SMTP
/// </summary>
/// <param name="toEmailAddress"></param>
/// <param name="subject"></param>
/// <param name="bodyHtml"></param>
/// <param name="bodyText"></param>
/// <param name="retryCount"></param>
/// <param name="toName"></param>
public async void Send(string toName, string toEmailAddress, string subject, string bodyHtml, string bodyText, int retryCount = 4)
{
var message = new MimeMessage();
message.From.Add(new MailboxAddress(_settings.MailKitFromName, _settings.MailKitFromAddress));
message.To.Add(new MailboxAddress(toName, toEmailAddress));
message.Subject = subject;
var builder = new BodyBuilder
{
TextBody = bodyText,
HtmlBody = bodyHtml
};
message.Body = builder.ToMessageBody();
for (var count = 1; count <= retryCount; count++)
{
try
{
using (var client = new SmtpClient())
{
client.LocalDomain = _settings.MailKitLocalDomain;
client.Authenticate(_settings.MailKitUsername, _settings.MailKitPassword);
SecureSocketOptions secureSocketOptions;
if (!Enum.TryParse(_settings.MailKitSecureSocketOption, out secureSocketOptions))
{
secureSocketOptions = SecureSocketOptions.Auto;
}
await client.ConnectAsync(_settings.MailKitHost, _settings.MailKitPort, secureSocketOptions).ConfigureAwait(false);
await client.SendAsync(message).ConfigureAwait(false);
await client.DisconnectAsync(true).ConfigureAwait(false);
return;
}
}
catch (Exception exception)
{
_logger.LogError(0, exception, "MailKit.Send failed attempt {0}", count);
if (retryCount >= 0)
{
throw;
}
await Task.Delay(count * 1000);
}
}
}
}
}
界面
namespace App.Email
{
public interface IMailKit
{
void Send(string toName, string toEmailAddress, string subject, string bodyHtml, string bodyText, int retryCount = 4);
}
}
您可以这样使用 async functions:
public class Notification
{
public Notification() { }
private string emailSubject,receiverEmail,emailBody;
public string EmailSubject { get => emailSubject; set => emailSubject = value; }
public string ReceiverEmail { get => receiverEmail; set => receiverEmail = value; }
public string EmailBody { get => emailBody; set => emailBody = value; }
public async Task<bool> sendEmail(){
try
{
var message = new MimeMessage();
message.From.Add(new MailboxAddress("Smart Living", "smartliving321@gmail.com"));
message.To.Add(new MailboxAddress("Person", receiverEmail));
message.Subject = emailSubject;
message.Body = new TextPart("plain")
{
Text = emailBody
};
using (var client = new SmtpClient())
{
await client.ConnectAsync("smtp.gmail.com", 587, false);
await client.AuthenticateAsync("smartliving321@gmail.com", "living@smart1122");
await client.SendAsync(message);
await client.DisconnectAsync(true);
// client.ServerCertificateValidationCallback=();
};
return true;
}
catch (Exception ex) {
return false;
}
}
}
这是我的简单解决方案,现在我可以在 asp 核心项目中使用 IdentityServer 使用 MailKit 发送电子邮件。
public class EmailSender : Microsoft.AspNetCore.Identity.UI.Services.IEmailSender
{
private readonly EmailConfiguration _emailConfig;
public EmailSender(EmailConfiguration emailConfig)
{
_emailConfig = emailConfig;
}
public Task SendEmailAsync(string email, string subject, string htmlMessage)
{
var message = new MimeMessage();
message.From.Add(new MailboxAddress(_emailConfig.FromName, _emailConfig.FromEmail));
message.To.Add(new MailboxAddress(email.Trim().ToLower(), email.Trim().ToLower()));
message.Subject = subject;
message.Body = new TextPart("html") { Text = htmlMessage };
using (var client = new SmtpClient())
{
try
{
client.Connect(_emailConfig.SmtpServer, _emailConfig.Port, MailKit.Security.SecureSocketOptions.SslOnConnect);
client.Authenticate(_emailConfig.UserName, _emailConfig.Password);
client.Send(message);
client.Disconnect(true);
return Task.FromResult(true);
}
catch (Exception)
{
throw;
}
finally
{
}
}
}
并在 startup.cs -> ConfigureServices
var emailConfig = Configuration.GetSection("EmailConfiguration")
.Get<EmailService.EmailConfiguration>();
services.AddSingleton(emailConfig);
services.AddScoped<IEmailSender, EmailService.EmailSender>();