A modern, flexible email delivery library for .NET that simplifies sending emails through various providers like SendGrid and Amazon SES. MailFusion offers robust template support, comprehensive error handling, and a clean, strongly-typed API.
- 📧 Multiple Email Provider Support
- SendGrid
- Amazon SES
- Development (console output for testing)
- Custom Email provider support
- 📝 Template Support
- Scriban template engine integration
- HTML and plain text support
- Template caching for performance
- Strong typing for template models
- Custom template engine support
- Custom template loader support
- ⚡ Modern .NET Features
- Async/await throughout
- Nullable reference types
- Record types for immutable data
- Modern C# features
- Builder pattern configuration
- 🛡️ Robust Error Handling
- Detailed error information
- Provider-specific error mapping
- Strongly-typed error codes
- Comprehensive logging
- 🧪 Development-Friendly
- Development provider for testing
- Detailed debugging information
- Comprehensive XML documentation
- Rich logging support
- Sensible defaults
Install MailFusion via NuGet:
dotnet add package MailFusion
The simplest way to get started is with the basic configuration in your appsettings.json
:
{
"Email": {
"Provider": "SendGrid",
"SendGrid": {
"ApiKey": "your-api-key"
}
}
}
And in your Program.cs
or Startup.cs
:
services.AddMailFusion(Configuration, Environment);
MailFusion supports extensive customization through the builder pattern:
services.AddMailFusion(Configuration, Environment, builder =>
{
builder
.UseCustomEmailProvider<MyEmailProvider>()
.UseCustomTemplateEngine<MyTemplateEngine>()
.UseCustomTemplateLoader<MyTemplateLoader>();
});
public class WelcomeEmailModel : IEmailTemplateModel
{
public string Subject => "Welcome to Our Service!";
public string Email { get; init; }
public string UserName { get; init; }
}
public class EmailService
{
private readonly IEmailService _emailService;
public EmailService(IEmailService emailService)
{
_emailService = emailService;
}
public async Task SendWelcomeEmailAsync(string userEmail, string userName)
{
var model = new WelcomeEmailModel
{
Email = userEmail,
UserName = userName
};
var sender = new EmailSender
{
Name = "My Service",
Email = "[email protected]",
ReplyEmail = "[email protected]"
};
var recipients = new[]
{
new EmailRecipient { Email = userEmail, Name = userName }
};
var result = await _emailService.SendFromTemplateAsync(
"welcome-email",
model,
sender,
recipients);
if (result.IsFailure)
{
// Handle error
}
}
}
{
"Email": {
"Provider": "SendGrid",
"SendGrid": {
"ApiKey": "your-api-key"
}
}
}
{
"Email": {
"Provider": "AmazonSes",
"AmazonSes": {
"AccessKey": "your-access-key",
"SecretKey": "your-secret-key",
"Region": "us-east-1"
}
}
}
{
"Email": {
"Provider": "Development",
"Development": {
"UseColors": true,
"ShowHtmlBody": true,
"ShowPlainTextBody": false
}
}
}
Template configuration is optional. If not specified, MailFusion will use these defaults:
- File-based template provider
- Templates directory at
{BaseDirectory}/Templates/Email
To customize template settings:
{
"EmailTemplates": {
"Provider": "File",
"File": {
"TemplatesPath": "path/to/templates"
}
}
}
public class MyEmailProvider : IEmailProvider
{
public async Task<IResult<Unit>> SendEmailAsync(EmailMessage message, CancellationToken cancellationToken = default)
{
// Custom implementation
}
}
// Registration
services.AddMailFusion(Configuration, Environment, builder =>
{
builder.UseCustomEmailProvider<MyEmailProvider>();
});
public class MyTemplateEngine : IEmailTemplateEngine
{
public async Task<IResult<IEmailTemplate>> LoadTemplateAsync<TModel>(
string templateName, TModel model) where TModel : IEmailTemplateModel
{
// Custom implementation
}
}
// Registration
services.AddMailFusion(Configuration, Environment, builder =>
{
builder.UseCustomTemplateEngine<MyTemplateEngine>();
});
public class MyTemplateLoader : IEmailTemplateLoader
{
public async Task<IResult<(string html, string text)>> LoadTemplateAsync(string templateName)
{
// Custom implementation
}
}
// Registration
services.AddMailFusion(Configuration, Environment, builder =>
{
builder.UseCustomTemplateLoader<MyTemplateLoader>();
});
When using the default file-based template system, organize your templates as follows:
Templates/
└── Email/
├── welcome/
│ ├── welcome.html
│ └── welcome.txt
└── order-confirmation/
├── order-confirmation.html
└── order-confirmation.txt
HTML template (welcome.html
):
<h1>Welcome {{ UserName }}!</h1>
<p>Thank you for joining our service.</p>
Text template (welcome.txt
):
Welcome {{ UserName }}!
Thank you for joining our service.
MailFusion uses the Result pattern for error handling:
var result = await _emailService.SendFromTemplateAsync(...);
if (result.IsFailure)
{
var error = result.Error;
logger.LogError("Failed to send email: {ErrorCode} - {ErrorMessage}",
error.Code,
error.Message);
}
For development and testing, use the Development provider:
{
"Email": {
"Provider": "Development"
}
}
This will output emails to the console instead of sending them.
MailFusion integrates with Microsoft.Extensions.Logging:
services.AddLogging(builder =>
{
builder.AddConsole();
// Add other logging providers as needed
});
- Fork the repository
- Create a feature branch:
git checkout -b my-new-feature
- Commit your changes:
git commit -am 'Add some feature'
- Push to the branch:
git push origin my-new-feature
- Submit a pull request
This project is licensed under the MIT License - see the LICENSE file for details.
- SendGrid - Email service provider
- Amazon SES - Email service provider
- Scriban - Template engine
For support, please open an issue in the GitHub repository.
Made with ❤️ by Ahmed Kamal