138 lines
5.0 KiB
C#
138 lines
5.0 KiB
C#
using MailKit.Net.Smtp;
|
|
using MailKit.Security;
|
|
using Microsoft.AspNetCore.Http;
|
|
using Microsoft.Extensions.Options;
|
|
using MimeKit;
|
|
using NLog;
|
|
using System;
|
|
using System.IO;
|
|
using System.Linq;
|
|
using System.Threading;
|
|
using System.Threading.Tasks;
|
|
|
|
namespace MP.Data.Services
|
|
{
|
|
/// <summary>
|
|
/// Implementazione MailKit come descritto qui https://blog.christian-schou.dk/send-emails-with-asp-net-core-with-mailkit/
|
|
/// </summary>
|
|
public class MailService : IMailService
|
|
{
|
|
#region Public Constructors
|
|
|
|
public MailService(IOptions<MailKitMailSettings> settings)
|
|
{
|
|
_settings = settings.Value;
|
|
}
|
|
|
|
#endregion Public Constructors
|
|
|
|
#region Public Methods
|
|
|
|
public async Task<bool> SendAsync(MailKitMailData mailData, CancellationToken ct = default)
|
|
{
|
|
try
|
|
{
|
|
// Initialize a new instance of the MimeKit.MimeMessage class
|
|
var mail = new MimeMessage();
|
|
|
|
#region Sender / Receiver
|
|
|
|
// Sender
|
|
mail.From.Add(new MailboxAddress(_settings.DisplayName, mailData.From ?? _settings.From));
|
|
mail.Sender = new MailboxAddress(mailData.DisplayName ?? _settings.DisplayName, mailData.From ?? _settings.From);
|
|
|
|
// Receiver
|
|
foreach (string mailAddress in mailData.To)
|
|
mail.To.Add(MailboxAddress.Parse(mailAddress));
|
|
|
|
// Set Reply to if specified in mail data
|
|
if (!string.IsNullOrEmpty(mailData.ReplyTo))
|
|
mail.ReplyTo.Add(new MailboxAddress(mailData.ReplyToName, mailData.ReplyTo));
|
|
|
|
// BCC Check if a BCC was supplied in the request
|
|
if (mailData.Bcc != null)
|
|
{
|
|
// Get only addresses where value is not null or with whitespace. x = value of address
|
|
foreach (string mailAddress in mailData.Bcc.Where(x => !string.IsNullOrWhiteSpace(x)))
|
|
mail.Bcc.Add(MailboxAddress.Parse(mailAddress.Trim()));
|
|
}
|
|
|
|
// CC Check if a CC address was supplied in the request
|
|
if (mailData.Cc != null)
|
|
{
|
|
foreach (string mailAddress in mailData.Cc.Where(x => !string.IsNullOrWhiteSpace(x)))
|
|
mail.Cc.Add(MailboxAddress.Parse(mailAddress.Trim()));
|
|
}
|
|
|
|
#endregion Sender / Receiver
|
|
|
|
#region Content
|
|
|
|
// Add Content to Mime Message
|
|
var body = new BodyBuilder();
|
|
mail.Subject = mailData.Subject;
|
|
body.HtmlBody = mailData.Body;
|
|
mail.Body = body.ToMessageBody();
|
|
|
|
// Check if we got any attachments and add the to the builder for our message
|
|
if (mailData.Attachments != null)
|
|
{
|
|
byte[] attachmentFileByteArray;
|
|
|
|
foreach (IFormFile attachment in mailData.Attachments)
|
|
{
|
|
// Check if length of the file in bytes is larger than 0
|
|
if (attachment.Length > 0)
|
|
{
|
|
// Create a new memory stream and attach attachment to mail body
|
|
using (MemoryStream memoryStream = new MemoryStream())
|
|
{
|
|
// Copy the attachment to the stream
|
|
attachment.CopyTo(memoryStream);
|
|
attachmentFileByteArray = memoryStream.ToArray();
|
|
}
|
|
// Add the attachment from the byte array
|
|
body.Attachments.Add(attachment.FileName, attachmentFileByteArray, ContentType.Parse(attachment.ContentType));
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion Content
|
|
|
|
#region Send Mail
|
|
|
|
using var smtp = new SmtpClient();
|
|
|
|
if (_settings.UseSSL)
|
|
{
|
|
await smtp.ConnectAsync(_settings.Host, _settings.Port, SecureSocketOptions.SslOnConnect, ct);
|
|
}
|
|
else if (_settings.UseStartTls)
|
|
{
|
|
await smtp.ConnectAsync(_settings.Host, _settings.Port, SecureSocketOptions.StartTls, ct);
|
|
}
|
|
await smtp.AuthenticateAsync(_settings.UserName, _settings.Password, ct);
|
|
await smtp.SendAsync(mail, ct);
|
|
await smtp.DisconnectAsync(true, ct);
|
|
|
|
#endregion Send Mail
|
|
|
|
return true;
|
|
}
|
|
catch (Exception exc)
|
|
{
|
|
Log.Error($"Eccezione in SendAsync{Environment.NewLine}{exc}");
|
|
return false;
|
|
}
|
|
}
|
|
|
|
#endregion Public Methods
|
|
|
|
#region Private Fields
|
|
|
|
private static Logger Log = LogManager.GetCurrentClassLogger();
|
|
private readonly MailKitMailSettings _settings;
|
|
|
|
#endregion Private Fields
|
|
}
|
|
} |