在.Net Core中首先引入FluentEmail.Core和FluentEmail.Smtp组件,如图所示.Net Core中对FluentEmail.Smtp进行封装使用_邮件发送

方式一(一个Helper帮助类):

        我们新建一个EmailHelper类,该类具体的封装如下所示:

using FluentEmail.Core;
using FluentEmail.Core.Models;
using FluentEmail.Smtp;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Net.Mail;
using System.Text;
using System.Threading.Tasks;
using Attachment = FluentEmail.Core.Models.Attachment;

namespace Quber.Core.GlKafka.App_Code.CommonHelper
{
/// <summary>
/// 基于FluentEmail.Smtp的邮件发送帮助类
/// </summary>
public class EmailHelper
{
/// <summary>
/// 邮件发送人名称(只有用户名,没有后面的@163.com等)
/// </summary>
private const string EMAILUSERNAME = "qubernet";

/// <summary>
/// 邮件发送人密码(有些邮件服务器可能是对应的授权码,而非邮件的登录密码)
/// </summary>
private const string EMAILUSERPWD = "MJNENWL***";

/// <summary>
/// 邮件发送人邮箱(完整邮箱)
/// </summary>
private const string EMAILUSERNAMESEND = "qubernet@163.com";

public EmailHelper()
{

}

public static async Task<bool> Send(string toUsers, string subject, string content)
{
return await Send(toUsers, subject, content, null, null, null, null);
}

public static async Task<bool> Send(string toUsers, string subject, string content, Action<string, string> succAction)
{
return await Send(toUsers, subject, content, null, succAction, null, null);
}

public static async Task<bool> Send(string toUsers, string subject, string content, Action<string, string> succAction, Action<string, string, string> failAction)
{
return await Send(toUsers, subject, content, null, succAction, failAction, null);
}

public static async Task<bool> Send(string toUsers, string subject, string content, List<Attachment> attachList)
{
return await Send(toUsers, subject, content, attachList, null, null, null);
}

public static async Task<bool> Send(string toUsers, string subject, string content, List<Attachment> attachList, Action<string, string> succAction)
{
return await Send(toUsers, subject, content, attachList, succAction, null, null);
}

public static async Task<bool> Send(string toUsers, string subject, string content, List<Attachment> attachList, Action<string, string> succAction, Action<string, string, string> failAction)
{
return await Send(toUsers, subject, content, attachList, succAction, failAction, null);
}

/// <summary>
/// 设置smtp信息
/// </summary>
private static void SetDefaultSetting()
{
//使用smtp服务发送邮件必须要设置smtp服务信息
var smtp = new SmtpClient
{
Host = "smtp.163.com",//smtp服务器地址
Port = 25,//端口号,默认为25
EnableSsl = false,
UseDefaultCredentials = false,
//DeliveryMethod = SmtpDeliveryMethod.Network,
Credentials = new NetworkCredential(EMAILUSERNAME, EMAILUSERPWD)
};

//设置默认发送信息
Email.DefaultSender = new SmtpSender(smtp);
}

/// <summary>
/// 发送邮件(异步)
/// </summary>
/// <param name="toUsers">接收人(多个人用英文的分号分隔),格式如:qubernet@163.com或qubernet@163.com;757200834@qq.com</param>
/// <param name="subject">主题</param>
/// <param name="content">内容(支持Html)</param>
/// <param name="attachList">附件集合,具体格式如下</param>
/// <param name="succAction">发送成功回调(返回主题和内容参数)</param>
/// <param name="failAction">发送失败回调(返回主题、内容和失败原因参数)</param>
/// <param name="ccUsers">抄送人,格式和接收人参数一致</param>
/// <returns></returns>
public static async Task<bool> Send(
string toUsers,
string subject,
string content,
List<Attachment> attachList,
Action<string, string> succAction,
Action<string, string, string> failAction,
string ccUsers)
{
/*
*
* attachList参数示例:
new List<FluentEmail.Core.Models.Attachment>
{
new FluentEmail.Core.Models.Attachment{
Data = System.IO.File.OpenRead("Quber.Core.Service项目库说明.txt"),
ContentType = "text/plain",
Filename = "Quber.Core.Service项目库说明.txt"
},
new FluentEmail.Core.Models.Attachment{
Data = System.IO.File.OpenRead("003.jpg"),
ContentType = "image/*",
Filename = "003.jpg"
}
})
*
*/

SetDefaultSetting();

var ret = true;

try
{
List<Address> toUserList = null, ccUserList = null;
if (toUsers != null) toUserList = toUsers.Split(';').Select(m => new Address { EmailAddress = m }).ToList();
if (ccUserList != null) ccUserList = ccUsers.Split(';').Select(m => new Address { EmailAddress = m }).ToList();

var email = Email
.From(EMAILUSERNAMESEND) //发送人
.Subject(subject) //邮件标题
.Body(content, true); //邮件内容

if (toUserList != null) email = email.To(toUserList); //收件人
if (ccUserList != null) email = email.CC(ccUserList); //抄送人
if (attachList != null) email = email.Attach(attachList);//添加附件

var result = await email.SendAsync();

if (result.Successful)
{
if (succAction != null) succAction(subject, content);
}
else
{
if (failAction != null)
{
//发送失败的原因
var sendFailMsg = result.ErrorMessages;
failAction(subject, content, string.Join(';', sendFailMsg));
}

ret = false;
}

}
catch (Exception ex)
{
if (failAction != null) failAction(subject, content, ex.Message);

ret = false;
}

return ret;
}
}
}

         以上封装只是针对简单应用的封装,里面有一些变量可根据自己的需求进行调整,如从配置中去读取等。

        使用示例如下所示:

发送主题和文字内容:

var ret = await EmailHelper.Send(
"qubernet@163.com;qubernet1@qq.com;qubernet2@qq.com;qubernet3@qq.com",
"测试的发送主题",
"测试的发送内容");

发送主题、文字内容和附件:

var ret = await EmailHelper.Send(
"qubernet@163.com;qubernet1@qq.com;qubernet2@qq.com;qubernet3@qq.com",
"测试的发送主题",
"测试的发送内容",
new List<FluentEmail.Core.Models.Attachment>
{
new FluentEmail.Core.Models.Attachment{
Data = System.IO.File.OpenRead("Quber.Core.Service项目库说明.txt"),
ContentType = "text/plain",
Filename = "Quber.Core.Service项目库说明.txt"
},
new FluentEmail.Core.Models.Attachment{
Data = System.IO.File.OpenRead("003.jpg"),
ContentType = "image/*",
Filename = "003.jpg"
}
});

 ​方式二(.Net Core依赖注入方式):

        这里我们以.Net Core辅助角色服务为例(Windows服务)。

        首先我们在启动程序Program.cs的ConfigureServices方法中注册FluentEmail相关的配置服务,具体如下所示:

/// <summary>
/// 邮件发送人名称(只有用户名,没有后面的@163.com等)
/// </summary>
private const string EMAILUSERNAME = "qubernet";

/// <summary>
/// 邮件发送人密码(有些邮件服务器可能是对应的授权码,而非邮件的登录密码)
/// </summary>
private const string EMAILUSERPWD = "MJNENWL***";

/// <summary>
/// 邮件发送人邮箱(完整邮箱)
/// </summary>
private const string EMAILUSERNAMESEND = "qubernet@163.com";


//注册FluentEmail相关配置服务
services
//设置默认发送用户
.AddFluentEmail(EMAILUSERNAMESEND)
//配置默认的smtp服务信息
.AddSmtpSender(new SmtpClient
{
Host = "smtp.163.com",//smtp服务器地址
Port = 25,//端口号,默认为25
EnableSsl = false,
UseDefaultCredentials = false,
//DeliveryMethod = SmtpDeliveryMethod.Network,
Credentials = new NetworkCredential(EMAILUSERNAME, EMAILUSERPWD)
});

        然后我们同样新建一个帮助类EmailHelper.cs(其实就是对接口IFluentEmail的方法的实现,​这里需要注意的是:我们封装的方法名称最好不要取为Send和SendAsync,因为IFluentEmail中已经有这2个方法名称的定义,比如我们这里封装的方法名称为SendEmail​),具体代码如下所示:

using FluentEmail.Core;
using FluentEmail.Core.Models;
using FluentEmail.Smtp;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Net.Mail;
using System.Text;
using System.Threading.Tasks;
using Attachment = FluentEmail.Core.Models.Attachment;

namespace Quber.Core.GlKafka.App_Code.CommonHelper
{
/// <summary>
/// 基于FluentEmail.Smtp的邮件发送帮助类
/// </summary>
public static class EmailHelper
{
public static async Task<bool> SendEmail(this IFluentEmail email, string toUsers, string subject, string content)
{
return await SendEmail(email, toUsers, subject, content, null, null, null, null);
}

public static async Task<bool> SendEmail(this IFluentEmail email, string toUsers, string subject, string content, Action<string, string> succAction)
{
return await SendEmail(email, toUsers, subject, content, null, succAction, null, null);
}

public static async Task<bool> SendEmail(this IFluentEmail email, string toUsers, string subject, string content, Action<string, string> succAction, Action<string, string, string> failAction)
{
return await SendEmail(email, toUsers, subject, content, null, succAction, failAction, null);
}

public static async Task<bool> SendEmail(this IFluentEmail email, string toUsers, string subject, string content, List<Attachment> attachList)
{
return await SendEmail(email, toUsers, subject, content, attachList, null, null, null);
}

public static async Task<bool> SendEmail(this IFluentEmail email, string toUsers, string subject, string content, List<Attachment> attachList, Action<string, string> succAction)
{
return await SendEmail(email, toUsers, subject, content, attachList, succAction, null, null);
}

public static async Task<bool> SendEmail(this IFluentEmail email, string toUsers, string subject, string content, List<Attachment> attachList, Action<string, string> succAction, Action<string, string, string> failAction)
{
return await SendEmail(email, toUsers, subject, content, attachList, succAction, failAction, null);
}

/// <summary>
/// 发送邮件(异步)
/// </summary>
/// <param name="toUsers">接收人(多个人用英文的分号分隔),格式如:qubernet@163.com或qubernet@163.com;757200834@qq.com</param>
/// <param name="subject">主题</param>
/// <param name="content">内容(支持Html)</param>
/// <param name="attachList">附件集合,具体格式如下</param>
/// <param name="succAction">发送成功回调(返回主题和内容参数)</param>
/// <param name="failAction">发送失败回调(返回主题、内容和失败原因参数)</param>
/// <param name="ccUsers">抄送人,格式和接收人参数一致</param>
/// <returns></returns>
public static async Task<bool> SendEmail(this IFluentEmail email,
string toUsers,
string subject,
string content,
List<Attachment> attachList,
Action<string, string> succAction,
Action<string, string, string> failAction,
string ccUsers)
{
/*
*
* attachList参数示例:
new List<FluentEmail.Core.Models.Attachment>
{
new FluentEmail.Core.Models.Attachment{
Data = System.IO.File.OpenRead("Quber.Core.Service项目库说明.txt"),
ContentType = "text/plain",
Filename = "Quber.Core.Service项目库说明.txt"
},
new FluentEmail.Core.Models.Attachment{
Data = System.IO.File.OpenRead("003.jpg"),
ContentType = "image/*",
Filename = "003.jpg"
}
})
*
*/

var ret = true;

try
{
List<Address> toUserList = null, ccUserList = null;
if (toUsers != null) toUserList = toUsers.Split(';').Select(m => new Address { EmailAddress = m }).ToList();
if (ccUserList != null) ccUserList = ccUsers.Split(';').Select(m => new Address { EmailAddress = m }).ToList();

email = email
.Subject(subject) //邮件标题
.Body(content, true); //邮件内容

if (toUserList != null) email = email.To(toUserList); //收件人
if (ccUserList != null) email = email.CC(ccUserList); //抄送人
if (attachList != null) email = email.Attach(attachList);//添加附件

var result = await email.SendAsync();

if (result.Successful)
{
if (succAction != null) succAction(subject, content);
}
else
{
if (failAction != null)
{
//发送失败的原因
var sendFailMsg = result.ErrorMessages;
failAction(subject, content, string.Join(';', sendFailMsg));
}

ret = false;
}

}
catch (Exception ex)
{
if (failAction != null) failAction(subject, content, ex.Message);

ret = false;
}

return ret;
}
}
}

调用示例:

        新建一个辅助角色类用于测试,比如名称为TestWorker,具体实现示例如下所示:

using FluentEmail.Core;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading;
using System.Threading.Tasks;

namespace Quber.Core.Test
{
public class TestWorker : BackgroundService
{
private readonly ILogger<KafkaMainWorker> _logger;

/// <summary>
/// 定义IFluentEmail对象
/// </summary>
private IFluentEmail _email;

public TestWorker(ILogger<TestWorker> logger, IFluentEmail email)
{
_logger = logger;

//通过依赖注入初始实例化_email对象
_email = email;
}

protected override async Task ExecuteAsync(CancellationToken stoppingToken)
{
while (!stoppingToken.IsCancellationRequested)
{
//然后调用EmailHelper帮助类中封装的方法SendEmail
var ret1 = await _email.SendEmail("qubernet@163.com;757200834@qq.com", "测试的发送主题", "测试的发送内容!");
var ret2 = await _email.SendEmail(
"qubernet@163.com;qubernet1@qq.com;qubernet2@qq.com;qubernet3@qq.com",
"测试的发送主题",
"测试的发送内容",
new List<FluentEmail.Core.Models.Attachment>
{
new FluentEmail.Core.Models.Attachment{
Data = System.IO.File.OpenRead("Quber.Core.Service项目库说明.txt"),
ContentType = "text/plain",
Filename = "Quber.Core.Service项目库说明.txt"
},
new FluentEmail.Core.Models.Attachment{
Data = System.IO.File.OpenRead("003.jpg"),
ContentType = "image/*",
Filename = "003.jpg"
}
});
}
}
}
}

        完整版的EmailHelper.cs如下所示:

using FluentEmail.Core;
using FluentEmail.Core.Models;
using FluentEmail.Smtp;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Net.Mail;
using System.Text;
using System.Threading.Tasks;
using Attachment = FluentEmail.Core.Models.Attachment;

namespace Quber.Core.GlKafka.App_Code.CommonHelper
{
/// <summary>
/// 基于FluentEmail.Smtp的邮件发送帮助类
/// </summary>
public static class EmailHelper
{
#region Helper帮助类的方式

/// <summary>
/// 邮件发送人名称(只有用户名,没有后面的@163.com等)
/// </summary>
private const string EMAILUSERNAME = "qubernet";

/// <summary>
/// 邮件发送人密码(有些邮件服务器可能是对应的授权码,而非邮件的登录密码)
/// </summary>
private const string EMAILUSERPWD = "MJNENWL***";

/// <summary>
/// 邮件发送人邮箱(完整邮箱)
/// </summary>
private const string EMAILUSERNAMESEND = "qubernet@163.com";

public static async Task<bool> Send(string toUsers, string subject, string content)
{
return await Send(toUsers, subject, content, null, null, null, null);
}

public static async Task<bool> Send(string toUsers, string subject, string content, Action<string, string> succAction)
{
return await Send(toUsers, subject, content, null, succAction, null, null);
}

public static async Task<bool> Send(string toUsers, string subject, string content, Action<string, string> succAction, Action<string, string, string> failAction)
{
return await Send(toUsers, subject, content, null, succAction, failAction, null);
}

public static async Task<bool> Send(string toUsers, string subject, string content, List<Attachment> attachList)
{
return await Send(toUsers, subject, content, attachList, null, null, null);
}

public static async Task<bool> Send(string toUsers, string subject, string content, List<Attachment> attachList, Action<string, string> succAction)
{
return await Send(toUsers, subject, content, attachList, succAction, null, null);
}

public static async Task<bool> Send(string toUsers, string subject, string content, List<Attachment> attachList, Action<string, string> succAction, Action<string, string, string> failAction)
{
return await Send(toUsers, subject, content, attachList, succAction, failAction, null);
}

/// <summary>
/// 设置smtp信息
/// </summary>
private static void SetDefaultSetting()
{
//使用smtp服务发送邮件必须要设置smtp服务信息
var smtp = new SmtpClient
{
Host = "smtp.163.com",//smtp服务器地址
Port = 25,//端口号,默认为25
EnableSsl = false,
UseDefaultCredentials = false,
//DeliveryMethod = SmtpDeliveryMethod.Network,
Credentials = new NetworkCredential(EMAILUSERNAME, EMAILUSERPWD)
};

//设置默认发送信息
Email.DefaultSender = new SmtpSender(smtp);
}

/// <summary>
/// 发送邮件(异步)
/// </summary>
/// <param name="toUsers">接收人(多个人用英文的分号分隔),格式如:qubernet@163.com或qubernet@163.com;757200834@qq.com</param>
/// <param name="subject">主题</param>
/// <param name="content">内容(支持Html)</param>
/// <param name="attachList">附件集合,具体格式如下</param>
/// <param name="succAction">发送成功回调(返回主题和内容参数)</param>
/// <param name="failAction">发送失败回调(返回主题、内容和失败原因参数)</param>
/// <param name="ccUsers">抄送人,格式和接收人参数一致</param>
/// <returns></returns>
public static async Task<bool> Send(
string toUsers,
string subject,
string content,
List<Attachment> attachList,
Action<string, string> succAction,
Action<string, string, string> failAction,
string ccUsers)
{
/*
*
* attachList参数示例:
new List<FluentEmail.Core.Models.Attachment>
{
new FluentEmail.Core.Models.Attachment{
Data = System.IO.File.OpenRead("Quber.Core.Service项目库说明.txt"),
ContentType = "text/plain",
Filename = "Quber.Core.Service项目库说明.txt"
},
new FluentEmail.Core.Models.Attachment{
Data = System.IO.File.OpenRead("003.jpg"),
ContentType = "image/*",
Filename = "003.jpg"
}
})
*
*/

SetDefaultSetting();

var ret = true;

try
{
List<Address> toUserList = null, ccUserList = null;
if (toUsers != null) toUserList = toUsers.Split(';').Select(m => new Address { EmailAddress = m }).ToList();
if (ccUserList != null) ccUserList = ccUsers.Split(';').Select(m => new Address { EmailAddress = m }).ToList();

var email = Email
.From(EMAILUSERNAMESEND) //发送人
.Subject(subject) //邮件标题
.Body(content, true); //邮件内容

if (toUserList != null) email = email.To(toUserList); //收件人
if (ccUserList != null) email = email.CC(ccUserList); //抄送人
if (attachList != null) email = email.Attach(attachList);//添加附件

var result = await email.SendAsync();

if (result.Successful)
{
if (succAction != null) succAction(subject, content);
}
else
{
if (failAction != null)
{
//发送失败的原因
var sendFailMsg = result.ErrorMessages;
failAction(subject, content, string.Join(';', sendFailMsg));
}

ret = false;
}

}
catch (Exception ex)
{
if (failAction != null) failAction(subject, content, ex.Message);

ret = false;
}

return ret;
}

#endregion

#region IFluentEmail接口扩展方式,并结合依赖注入使用

public static async Task<bool> SendEmail(this IFluentEmail email, string toUsers, string subject, string content)
{
return await SendEmail(email, toUsers, subject, content, null, null, null, null);
}

public static async Task<bool> SendEmail(this IFluentEmail email, string toUsers, string subject, string content, Action<string, string> succAction)
{
return await SendEmail(email, toUsers, subject, content, null, succAction, null, null);
}

public static async Task<bool> SendEmail(this IFluentEmail email, string toUsers, string subject, string content, Action<string, string> succAction, Action<string, string, string> failAction)
{
return await SendEmail(email, toUsers, subject, content, null, succAction, failAction, null);
}

public static async Task<bool> SendEmail(this IFluentEmail email, string toUsers, string subject, string content, List<Attachment> attachList)
{
return await SendEmail(email, toUsers, subject, content, attachList, null, null, null);
}

public static async Task<bool> SendEmail(this IFluentEmail email, string toUsers, string subject, string content, List<Attachment> attachList, Action<string, string> succAction)
{
return await SendEmail(email, toUsers, subject, content, attachList, succAction, null, null);
}

public static async Task<bool> SendEmail(this IFluentEmail email, string toUsers, string subject, string content, List<Attachment> attachList, Action<string, string> succAction, Action<string, string, string> failAction)
{
return await SendEmail(email, toUsers, subject, content, attachList, succAction, failAction, null);
}

/// <summary>
/// 发送邮件(异步)
/// </summary>
/// <param name="toUsers">接收人(多个人用英文的分号分隔),格式如:qubernet@163.com或qubernet@163.com;757200834@qq.com</param>
/// <param name="subject">主题</param>
/// <param name="content">内容(支持Html)</param>
/// <param name="attachList">附件集合,具体格式如下</param>
/// <param name="succAction">发送成功回调(返回主题和内容参数)</param>
/// <param name="failAction">发送失败回调(返回主题、内容和失败原因参数)</param>
/// <param name="ccUsers">抄送人,格式和接收人参数一致</param>
/// <returns></returns>
public static async Task<bool> SendEmail(this IFluentEmail email,
string toUsers,
string subject,
string content,
List<Attachment> attachList,
Action<string, string> succAction,
Action<string, string, string> failAction,
string ccUsers)
{
if (email == null) return true;

/*
*
* attachList参数示例:
new List<FluentEmail.Core.Models.Attachment>
{
new FluentEmail.Core.Models.Attachment{
Data = System.IO.File.OpenRead("Quber.Core.Service项目库说明.txt"),
ContentType = "text/plain",
Filename = "Quber.Core.Service项目库说明.txt"
},
new FluentEmail.Core.Models.Attachment{
Data = System.IO.File.OpenRead("003.jpg"),
ContentType = "image/*",
Filename = "003.jpg"
}
})
*
*/

var ret = true;

try
{
List<Address> toUserList = null, ccUserList = null;
if (toUsers != null) toUserList = toUsers.Split(';').Select(m => new Address { EmailAddress = m }).ToList();
if (ccUserList != null) ccUserList = ccUsers.Split(';').Select(m => new Address { EmailAddress = m }).ToList();

email = email
.Subject(subject) //邮件标题
.Body(content, true); //邮件内容

if (toUserList != null) email = email.To(toUserList); //收件人
if (ccUserList != null) email = email.CC(ccUserList); //抄送人
if (attachList != null) email = email.Attach(attachList);//添加附件

var result = await email.SendAsync();

if (result.Successful)
{
if (succAction != null) succAction(subject, content);
}
else
{
if (failAction != null)
{
//发送失败的原因
var sendFailMsg = result.ErrorMessages;
failAction(subject, content, string.Join(';', sendFailMsg));
}

ret = false;
}

}
catch (Exception ex)
{
if (failAction != null) failAction(subject, content, ex.Message);

ret = false;
}

return ret;
}

#endregion
}
}