NecroNetToolkit Mail API

In a lot of web projects, you need to send out emails. It may be to
notify user that his registration has been successful, his order has
been received etc. as well as notify site administrator about various
events. There are some mail toolkits out there, but none are really what
I would like for my MVC oriented toolkit. What I mean is that I like to
create partial views as templates for my emails. Other than that, the
mail api will be able to send text mails (optionally formatted), mainly
as a last resort, because I like sending emails in html much better.
So I started with this interface:

Notice the event handler – you’ve probably guessed by now that all mails
will be sent asynchronously. It takes very long time to send an email,
and if you were to send it synchronously, it would block until the email
is sent, preventing the user from viewing content until that mail is
sent. This is very bothersome, so I would not suggest sending emails
synchronously if you really don’t have a good reason to. In the handler
event args, there are these properties:

Success (bool, whether or not the email was sent without error),

To (IEnumerable of MailAddress)

Subject (string)

Body (string)

Exception (Exception, if any occurred during sending mail (null
on success))

You might be wondering how I render the view into string. Well, I found
this handy method on the internet some time ago:

Some restrictions apply for this obviously, for example there is no
HttpContext, so you have to do all that stuff (like generating urls) in
your controller, and pass it into the view in model. But for emails it’s
not that big of a deal.

For asynchronous sending, I’m using TPL (Task Parallel Library), because
I can manage it easier, and I also found that SmtpClient’s SendAsync
methods are weird (read: I tried them and the email didn’t get sent at
all). So with TPL I have more control over it. You may have noticed that
IMailBot is also IDisposable, because I want to dispose SmtpClient when
I’m done with it (that sends QUIT message to SMTP server). Here is how I
implemented this:

Notice that the SmtpClient is disposed after Dispose is called and all
mail is sent.

You can imagine other methods from the IMailBot interface just create a
MailMessage and pass it to SendAsync method.

Another matter is to configure the mail bot. You can configure the
SmtpClient the same way you are used to, in system.net section of
web.config. I wanted to add a little more, so I took a look at some open
source mail toolkit some Czech MVP guy did a while back, called
Altairis Mail Toolkit and
basically used the very same code for my configuration section. You can
configure from, sender and reply to address; body and subject encoding;
and I added section where you can enable SSL.

In my opinion, keys to a good mailer component are two things: interface
and asynchronous mail sending. On top of that you can add things like
globalization and other stuff like that. You can very easily hook this
up with your favorite dependency injection framework. I use ninject as
an example:

I didn’t have time to finish this yesterday; I didn’t even realize I
should put in some example of usage to be honest. Well, here we go. I’m
not going to explain the SendTextMail methods, these are pretty much
self-explanatory. Instead, I will give you an example about how to use
the SendHtmlMail methods. First, create a view model like you would in
any other view. Note that you have to supply all urls for action links
and other stuff that uses HttpContext from the controller.