Sunday, September 3, 2017

Spring Boot - Example Email with Thymeleaf HTML Templates

I have a Spring Boot backend application that needed to send emails.

Java application email libraries include: Java mail native, Spring, and apache email (and others).  Lots of articles say apache email API is more intuitive, but others say if you are already using a Java/Spring application, then to go ahead and use the Spring one.   I decided to try the Spring Boot one first, since we have a Java/Spring application.

The Spring boot library satisfied the three criteria below, and seems to work great on my local environment:
  1. the ability to send simple text email 
  2. the ability to send HTML email (support for HTML emails already had the Thymeleaf HTML templating library provided with Spring Boot)
  3. the ability to attach a file(s) to the email
The application is using the "Starters" spring boot jars (i.e. spring-boot-starter-web, spring-boot-starter-data-jpa, spring-boot-starter-security, etc), so I just needed to make the application aware of the spring-boot-starter-thymeleaf jar file for the application to use it.

Windows 7
Oracle Java 1.8.0_66
Spring Boot 1.3.1.RELEASE
Sprint Boot 1.3.1.RELEASE spring-boot-starter-thymeleaf

The example below supports criteria number 2 to send HTML emails using Thymeleaf email templates.  I've also included unescaped HTML, passing multiple variables to HTML template, and inline image in the example below as well.

src/main/resources/templates/logo_cherryshoe.png: cherryshoe logo to put as inline image in HTML email

src/main/resources/  add applicable properties
# Email<email smtp host>
spring.mail.port=<email smtp port>
# must match thyme html template name under templates resource folder

src/main/resources/templates/email.html: Thyme HTML Email template, used as the default email template
<!DOCTYPE html>
<html lang="en" xmlns="" xmlns:th="">
<head><title>CherryShoe Html Email Example</title>
body {
    background-color: white;

/* White space is preserved with \n\n\n\n and css class a, span, tr { white-space: pre; } */
a, span, tr { white-space: pre; }

body {
 color: black;
 font-family: 'Arial', sans-serif;
 font-weight: normal;
 font-style: normal;
 font-size: x-small;

table {
    border-collapse: collapse;
    width: 100%;

table, th, td {
    border: 1px solid black;

.ten {
 width: 10%;
.forty {
 width: 40%;

.twenty-five {
 width: 25%;

th {
    background-color: #C6DEFF;
    color: black;
    vertical-align: middle;

th, td {
    padding: 1px;
    text-align: left;
    vertical-align: middle;

.cherryshoe-font-bold {
 color: black;
 font-family: 'Arial', sans-serif;
 font-weight: bold;
 font-style: normal;
 font-size: x-small;

Hi <span th:text="${name}"></span>, <br></br><br></br>

<!-- Need br formatted this way for SAX Parser to parse with no errors -->
<span class="cherryshoe-font-bold">Example Table Data generated from backend service</span>
<th class="twenty-five">Column 1</th>
<th class="ten">Column 2</th>
<th class="twenty-five">Column 3</th>
<th class="forty">Column 4</th>
<!-- Use th:utext to show unescaped html -->
<span th:utext="${table1}"></span>

Thank you
<img src="logo_cherryshoe.png" th:src="'cid:' + ${imageResourceName}" alt="CherryShoe Logo"/>




public interface SendEmailService {

  * Send html emails.
  * @throws IOException
 public void sendHtmlEmail() throws IOException;


import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;

import javax.mail.MessagingException;
import javax.mail.internet.MimeMessage;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.mail.javamail.JavaMailSender;
import org.springframework.mail.javamail.MimeMessageHelper;
import org.springframework.stereotype.Service;
import org.thymeleaf.TemplateEngine;
import org.thymeleaf.context.Context;

 * White space is preserved in text email with \n. It is also preserved in HTML
 * email with the css in the html template
public class SendEmailServiceSpringBootImpl implements SendEmailService {

 // JavaMailSenderImpl is thread safe after it's constructed
 private JavaMailSender mailSender;

 // needed for HTML email templating
 private TemplateEngine templateEngine;

 private String defaultFrom;

 // The default configuration of Thymeleaf expects that all HTML files are
 // placed under resources/templates directory and ends with the .html
 // extension.
 // Can also externalize the templates/*.html files
 private String defaultMailTemplate;

 private Logger log = LoggerFactory.getLogger(getClass());

 private final ThreadLocal<DateFormat> threadLocalDf = new ThreadLocal<DateFormat>() {
  protected DateFormat initialValue() {
   return new SimpleDateFormat("MM/dd/yyyy");

 public void sendHtmlEmail() throws IOException {
  MimeMessage mail = mailSender.createMimeMessage();
  InputStream imageIs = null;
  try {

   // set multiple context variables key/value pairs for email template
   String templateMailBodyNameKey = "name";
   String templateMailBodyNameVal = "[Name]";
   String templateMailBodyTable1Key = "table1";
   StringBuffer templateMailBodyTable1Val = new StringBuffer();
   String templateMailBodyImageKey = "imageResourceName";
   String templateMailBodyImageVal = "logo_cherryshoe.png";

   // table 1 get data
   for (int i = 0; i < 5; i++) {
    templateMailBodyTable1Val.append("<tr><td class=\"twenty-five\">Column 1 Data - ");
    templateMailBodyTable1Val.append("<td class=\"ten\">Column 2 Data -  ");
    templateMailBodyTable1Val.append("<td class=\"twenty-five\">Column 3 Data - ");
    templateMailBodyTable1Val.append("<td class=\"forty\">Column 4 Data - ");

   Map<String, Object> variables = new HashMap<String, Object>();
   variables.put(templateMailBodyNameKey, templateMailBodyNameVal);
   variables.put(templateMailBodyTable1Key, templateMailBodyTable1Val.toString());
   variables.put(templateMailBodyImageKey, templateMailBodyImageVal);

   Context context = new Context();
   variables.forEach((name, value) -> context.setVariable(name, value));

   String content = templateEngine.process(defaultMailTemplate, context);

   MimeMessageHelper helper = new MimeMessageHelper(mail, true);
   helper.setSubject("CherryShoe Example Html Email - " + threadLocalDf.get().format(new Date()));
   helper.setText(content, true); // make html email

   // Add the inline image, must go after setText. Referenced from the
   // mail template as "cid:${imageResourceName}"
   imageIs = this.getClass().getClassLoader().getResourceAsStream("templates/" + templateMailBodyImageVal);
   byte[] imageByteArray = IOUtils.toByteArray(imageIs);

   final InputStreamSource imageSource = new ByteArrayResource(imageByteArray);
   helper.addInline(templateMailBodyImageVal, imageSource, "image/png");

  } catch (MessagingException e) {
  } finally {
   if (imageIs != null)



import javax.inject.Named;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.SpringApplicationConfiguration;
import org.springframework.test.context.TestExecutionListeners;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import org.springframework.test.context.transaction.TransactionalTestExecutionListener;
import org.springframework.test.context.web.WebAppConfiguration;
import org.springframework.transaction.annotation.Transactional;
import com.cherryshoe.CherryShoeAppApplication;

@SpringApplicationConfiguration(classes = CherryShoeAppApplication.class)
@TestExecutionListeners({ DependencyInjectionTestExecutionListener.class, TransactionalTestExecutionListener.class })
public class SendEmailServiceITTest {

 private SendEmailService emailServiceSpringBoot;

 public void sendHtmlEmailTest() throws Exception {
  try {
  } catch (Exception e) {


  1. Thanks for sharing! You know, Mozilla Thunderbird is one of the major alternatives to Microsoft’s email applications and PIM tools. Completely free and open source, it is available to users on various platforms, including Windows, Mac OS X and Linux. Transfer emails from Thunderbird to Outlook software url is an efficient and extremely fast data migration solution that will help you transfer all types of matching data from Thunderbird to Outlook in no time.

  2. Thanks for this post, really useful. There's one more tool to find contact information: It helps me to find personal emails and phone numbers.find email chrome extension

  3. Some template providers like ‘’ offer template related services irrespective of where you actually purchased the template from.

  4. Thanks for sharing such a useful and amazing blog, Nice to read this.I thank you for this.Explore 24x7ServerSupport to get the most comprehensive cloud computing services.

  5. Awesome and interesting article. Great things you've always shared with us. Thanks. Just continue composing this kind of post. hotmail sign in

  6. So, if anyone misses the email sign up a pop-up then they can easily get back to your offer. So, create some offer banners or call-to-action & email sign up on your homepage, blog.
    Email List for Marketing

  7. The article looks magnificent, but it would be beneficial if you can share more about the suchlike subjects in the future. Keep posting. sign in to Hotmail

  8. Its a great pleasure reading your post.Its full of information I am looking for and I love to post a comment that "The content of your post is awesome" Great work. ActiveCampaign limits

  9. Great Information sharing .. I am very happy to read this article .. thanks for giving us go through info.Fantastic nice. I appreciate this post.
    email hunter

  10. Thank you for some other informative blog. Where else could I get that type of information written in such an ideal means? I have a mission that I’m just now working on, and I have been at the look out for such information. email lookup

  11. It is the kind of information I have been trying to find. Thank you for writing this information. It has proved utmost beneficial for me. visit this site

  12. If you are looking for a professional developers of magneto, then this blog is for you. You can opt for quality Magento Development Services USA for a wide range of information.

  13. Very informative article that you have shared here about the dedicated servers. Your article is very useful for us and I couldn't find any knowledge on this matter prior to. You can opt for quality SEO marketing services Minneapolis for a wide range of information.

  14. Backing up critical data is done quickly and effectively because your company can effortlessly create a replication site. You can buy office 2019 key UK at a great price. Most enterprise virtualization platforms contain software that helps automate the failover during a disaster.

  15. Nice blog, thanks for sharing the useful information. Swissmailbox also provides the
    mailing address Switzerland service, visit our website.

  16. You there, this is really good post here. Thanks for taking the time to post such valuable information. Quality content is what always gets the visitors coming.


I appreciate your time in leaving a comment!