Search code examples
c#htmlasp.netsmtpclient

How to preserve newline wrapping via SMTP where the email body needs to support HTML


So I'm building an auto-emailing script that will send out receipts to employees once they log an issue, the email needs to allow HTML.

However, when I pull the description out of the database and display it on the front end (asp:textbox) of the .aspx page it displays with new line characters, formatted properly but when I send the description via SMTP to recipients the line breaks (newline characters) don't wrap the text to the new line.

E.g: Example string: "Bob is a human,\n and he likes basketball" In asp:textbox controls it renders properly but when sent via the email it doesn't.

What's the crack with that? Do I need to replace the \n with HTML breaks as they come through or can you preserve them?

Here's the basic idea of what the script is:

SmtpClient client = new SmtpClient();
client.Port = 587;
client.Host = "smtp.outlook.com";
client.EnableSsl = true;
client.Timeout = 10000;
client.DeliveryMethod = SmtpDeliveryMethod.Network;
client.UseDefaultCredentials = false;
client.Credentials = new System.Net.NetworkCredential(serverEmail, serverEmailAuthToken);

MailMessage mm = new MailMessage(serverEmail, recipient, "Tasket Report Number: "
                                 + tasketTitle + " has been received.",
                                 "Tasket Report Number: " + tasketTitle + "<br/>"
                                 + "Problem Domain: " + domain + "<br/>"
                                 + "Report Type: " + type + "<br/>"
                                 + "Report Area: " + area + "<br/>"
                                 + "Description: " + description
                                 + "<br/>");
mm.IsBodyHtml = true;
mm.BodyEncoding = UTF8Encoding.UTF8;
mm.DeliveryNotificationOptions = DeliveryNotificationOptions.OnFailure;
client.Send(mm);

Solution

  • \n is whitespace to HTML renderers.

    You need to convert the newlines to <br /> tags, or paragraphs, in order to render as newlines in an HTML mail body.

    And you should make sure that the actual text is HtmlEncoded. If you don't, user input could be used to inject markup into the mail.

    Time-tested set of utility functions, I hereby declare thee open source:

    public string enc(string s)
    {
        return System.Web.HttpUtility.HtmlEncode(s);
    }
    
    /// <summary>
    /// HTML-encodes a string after replacing its newlines with br tags
    /// </summary>
    public string enc_br(string s)
    {
        if (String.IsNullOrWhiteSpace(s))
            return s;
        var lines = s.Split(new string[] { Environment.NewLine }, StringSplitOptions.None);
        if (lines.Length == 1)
            return enc(lines[0]);
        else
        {
            for (var i = 0; i < lines.Length; ++i)
            {
                lines[i] = enc(lines[i]);
            }
            return String.Join("<br />", lines);
        }
    }
    

    Sample usage:

    ...  + "Problem Domain: " + enc_br(domain) + "<br/>"
    

    Consider using String.Format, or, if you are on a sufficiently recent .NET version, string interpolation: it will improve readability of your composition greatly.