Last updated by 4 years ago

Page: Sending SMTP Authenticated Email, Html content with GroovyTemplates and Spring integration, Version:2

Sending SMTP Authenticated, Html E-mail with GroovyTemplates, EmailService and Spring integration

// THIS IS NOT WORKING -- SANTHOSH This tutorial provides some code for a Grails Service that receives an Html content generated by GroovyTemplates, which allows you to send emails from your Grails applications using an Authenticated SMTP server. This example is easily adapted to send non-authenticated e-mails. This flexibility is configured with Grails` Spring integration. This tutorial was inspired in another tutorial for sending e-mails: A simple EmailerService.

First we will have an Html template that will generate the content of our e-mail. The example is from an online store sending an Order confirmation e-mail.

<body>
Order Number: <strong>${order.number}</strong>
<div style="float:left">Client Name: <strong>${order.clientName}</strong></div>
<div style="float:right">Order Date: <strong>${order.ordered}</strong></div>
<div>
	<strong>Order Details</strong>
	<table width="100%" border="1" cellspacing="0" cellpadding="0" bordercolor="#FBC8A2">
		<tr>
			<td><strong>Produto</strong></td>
			<td><strong>Quantidade</strong></td>
			<td><strong>Pre&ccedil;o Unit&aacute;rio</strong></td>
			<td><strong>Pre&ccedil;o Total</strong></td>
		</tr>
		<% order.orderItems.each { %>
			<tr>
				<td>${it.name}</td>
				<td>${it.quantity}</td>
				<td>${it.price}</td>
				<td>${it.price * it.quantity}</td>
			</tr>
		<% } %>
	</table>
	<p>
		<strong>Sub-total:</strong> ${order.subTotal}<br />
		<strong>Shipping:</strong> ${order.shippingCost}<br />
		<strong>Total:</strong> ${order.subTotal + order.shippingCost}
	</p>
</div>
</body>

Second we will have a Controller that will start all the process:

import groovy.text.Template
import groovy.text.SimpleTemplateEngine
import org.springframework.mail.MailException

class StoreController { def processOrder = { if(session.cart){ session.cart.client = session.client def order = mainService.processOrder(session.cart, params) if(order){ flash.message = 'Order processed succesfully.' if(sendNotificationEmail(order)) flash.mailSent = true else flash.mailSent = false } chain(action:orderProcessed, model:[order:order]) } else sessionExpired() }

private sendNotificationEmail(Orderr order){ File tplFile = grailsAttributes.getApplicationContext().getResource( File.separator + "WEB-INF" + File.separator + "orderNotification.gtpl").getFile(); def binding = ["order": order] def engine = new SimpleTemplateEngine() def template = engine.createTemplate(tplFile).make(binding) def body = template.toString()

def email = [ to: [order.clientEmail], // "to" expects a List subject: "Your Order #${order.number}", text: body ]

try { emailerService.sendEmail(email) } catch (MailException ex) { log.error("Failed to send emails", ex) return false } return true } }


Then we have the EmailerService:

import org.apache.log4j.Logger;

import org.springframework.mail.MailException import org.springframework.mail.MailSender import org.springframework.mail.javamail.MimeMessageHelper

import javax.mail.internet.MimeMessage import javax.mail.internet.InternetAddress;

import br.com.interatus.mail.MailPropertiesBean;

/** * Service for sending emails. */ class EmailerService { boolean transactional = false MailSender mailSender MailPropertiesBean mailPropertiesBean

// If next line is commented in, this service fails to be loaded by grails, as every grails-artefact already has a 'log' property // Logger log = Logger.getLogger(this.class.name)

def sendEmail(mail) throws MailException {

MimeMessage mimeMessage = mailSender.createMimeMessage()

MimeMessageHelper helper = new MimeMessageHelper(mimeMessage, true, "ISO-8859-1"); helper.setFrom(mailPropertiesBean.getFrom()); helper.setTo(getInternetAddresses(mail.to)); helper.setSubject(mail.subject); helper.setText(mail.text, true); if(mail.bcc) helper.setBcc(getInternetAddresses(mail.bcc)); if(mail.cc) helper.setCc(getInternetAddresses(mail.cc));

mailSender.send(mimeMessage) }

private InternetAddress[] getInternetAddresses(List emails){ InternetAddress[] mailAddresses = new InternetAddress[emails.size()]; emails.eachWithIndex {mail, i -> mailAddresses[i] = new InternetAddress(mail) } return mailAddresses; } }


Note that so far our EmailerService does not know anything about SMTP Authentication. We used here a small Java helper class: br.com.interatus.mail.MailPropertiesBean . Lets see it:

package br.com.interatus.mail;

/** * Helper bean for setting From address and easy config with Spring. */ public class MailPropertiesBean { private String from;

public String getFrom() { return from; }

public void setFrom(String from) { this.from = from; }

}


Last but not least, we have the Spring wiring:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
	<bean id="smtpAuthenticator" class="br.com.interatus.mail.SmtpAuthenticator">
		<constructor-arg value="your@username.com" />
		<constructor-arg value="your.passwd" />
	</bean>

<bean id="mailPropertiesBean" class="br.com.interatus.mail.MailPropertiesBean"> <property name="from" value="your@username.com" /> </bean>

<bean id="mailSession" class="javax.mail.Session" factory-method="getInstance"> <constructor-arg> <props> <prop key="mail.smtp.auth">true</prop> <!-- If SSL needed… <prop key="mail.smtp.socketFactory.port">465</prop> <prop key="mail.smtp.socketFactory.class"> javax.net.ssl.SSLSocketFactory </prop> <prop key="mail.smtp.socketFactory.fallback"> false </prop> --> </props> </constructor-arg> <constructor-arg ref="smtpAuthenticator" /> </bean>

<bean id="mailSender" class="org.springframework.mail.javamail.JavaMailSenderImpl"> <property name="host" value="your.smtp.server.com" /> <property name="session" ref="mailSession" /> </bean>

</beans>

The last thing is the SmtpAuthenticator class:
public class SmtpAuthenticator extends Authenticator {
    private String username;
    private String password;

public SmtpAuthenticator(String username, String password) { super(); this.username = username; this.password = password; }

public PasswordAuthentication getPasswordAuthentication() { return new PasswordAuthentication(username, password); } }


Have fun with Grails and Java Platform! Great Stuff!