EMailServiceImpl.java
/**
* Copyright 2014 Global Crop Diversity Trust
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
**/
package org.genesys.server.service.impl;
import java.nio.file.Files;
import java.nio.file.Path;
import java.time.Instant;
import java.util.Arrays;
import java.util.HashMap;
import java.util.Locale;
import java.util.Map;
import javax.mail.internet.MimeMessage;
import org.apache.commons.lang3.ArrayUtils;
import org.apache.commons.lang3.StringUtils;
import org.genesys.server.exception.NotFoundElement;
import org.genesys.server.model.impl.Article;
import org.genesys.server.service.ArticleService;
import org.genesys.server.service.ArticleTranslationService;
import org.genesys.server.service.ContentService;
import org.genesys.server.service.EMailService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.core.task.TaskExecutor;
import org.springframework.mail.javamail.JavaMailSender;
import org.springframework.mail.javamail.JavaMailSenderImpl;
import org.springframework.mail.javamail.MimeMessageHelper;
import org.springframework.mail.javamail.MimeMessagePreparator;
import org.springframework.stereotype.Service;
@Service
public class EMailServiceImpl implements EMailService, InitializingBean {
private static final Logger LOG = LoggerFactory.getLogger(EMailServiceImpl.class);
private static final String EMAIL_TEMPLATE_PATH = "/email/template.html";
@Autowired
private JavaMailSender mailSender;
@Autowired
private TaskExecutor taskExecutor;
@Autowired
private ArticleService articleService;
@Autowired
private ContentService contentService;
@Value("${mail.async}")
private boolean async;
@Value("${mail.debug.message}")
private String debugMessage;
@Value("${mail.user.from}")
private String emailFrom;
@Value("${mail.disabled:false}")
private boolean emailDisabled;
@Value("${base.url}")
private String baseUrl;
@Value("${frontend.url}")
private String frontendUrl;
@Override
public void afterPropertiesSet() throws Exception {
ArticleTranslationService.TranslatedArticle emailTemplate = null;
try {
emailTemplate = articleService.getGlobalArticle(ContentService.SMTP_EMAIL_TEMPLATE, Locale.ENGLISH);
} catch (NotFoundElement e) {
LOG.warn("{} email template article not found.", ContentService.SMTP_EMAIL_TEMPLATE);
}
if (emailTemplate == null || emailTemplate.entity == null) {
try {
String templateContent = Files.readString(Path.of(getClass().getResource(EMAIL_TEMPLATE_PATH).getPath()));
Article article = new Article();
article.setSlug(ContentService.SMTP_EMAIL_TEMPLATE);
article.setOriginalLanguageTag(Locale.ENGLISH.getLanguage());
article.setTitle("Email Template");
article.setSummary("HTML template that is automatically applied to all emails");
article.setBody(templateContent);
article.setTemplate(true);
article.setPublishDate(Instant.now());
articleService.createFast(article);
} catch (Exception e) {
LOG.warn("An exception occurred while reading " + EMAIL_TEMPLATE_PATH, e);
}
}
}
@Override
public String[] toEmails(String emailAddresses) {
if (StringUtils.isBlank(emailAddresses)) {
return null;
}
String[] res = emailAddresses.split(",|;");
for (int i = 0; i < res.length; i++) {
res[i] = StringUtils.trim(res[i]);
}
return res;
}
@Override
public void sendMail(String mailSubject, String mailBody, String... emailTo) {
sendMail(mailSubject, mailBody, null, emailTo);
}
@Override
public void sendMail(String mailSubject, String mailBody, String[] emailCc, String... emailTo) {
sendSimpleEmail(mailSubject, mailBody, emailFrom, emailCc, emailTo);
}
public void sendSimpleEmail(final String subject, final String text, final String emailFrom, final String[] emailCc, final String... emailTo) {
printDebugInfo(subject, text, emailFrom, emailTo);
final MimeMessagePreparator preparator = new MimeMessagePreparator() { // For debugging
@Override
public void prepare(MimeMessage mimeMessage) throws Exception {
final MimeMessageHelper message = new MimeMessageHelper(mimeMessage, "UTF-8");
message.setFrom(emailFrom);
message.setTo(emailTo);
LOG.info("Email to: {}", ArrayUtils.toString(emailTo, "<NULL>"));
if (emailCc != null && emailCc.length > 0) {
message.setCc(emailCc);
}
message.setSubject(subject);
String messageText = text;
try {
final Map<String, Object> scopes = new HashMap<>();
scopes.put("messageBody", text);
scopes.put("subject", subject);
scopes.put("frontendUrl", frontendUrl);
scopes.put("baseUrl", baseUrl);
scopes.put("serverName", "Genesys");
ArticleTranslationService.TranslatedArticle article = articleService.getGlobalArticle(ContentService.SMTP_EMAIL_TEMPLATE, Locale.ENGLISH);
if (article != null) {
var body = article.getTranslation() != null ? article.getTranslation().getBody() : article.getEntity().getBody();
messageText = contentService.processTemplate(body, scopes);
}
} catch (Exception e) {
LOG.warn("Exception in applying email template", e);
}
message.setText(messageText, true);
}
};
doSend(preparator);
}
protected void doSend(final MimeMessagePreparator preparator) {
if (emailDisabled) {
LOG.warn("Emailing is disabled");
return;
}
// execute sender in separate thread
JavaMailSenderImpl javaMailSender = (JavaMailSenderImpl)mailSender;
if (async) {
LOG.info("Sending email message asynchroniously");
taskExecutor.execute(() -> {
try {
LOG.warn("Sending email now via {}:{}", javaMailSender.getHost(), javaMailSender.getPort());
mailSender.send(preparator);
LOG.warn("Email delivered to {}:{}", javaMailSender.getHost(), javaMailSender.getPort());
} catch (final Throwable e) {
LOG.error("Error sending email: {}", e.getMessage());
}
});
} else {
LOG.warn("Sending email now via {}:{}", javaMailSender.getHost(), javaMailSender.getPort());
mailSender.send(preparator);
}
}
protected void printDebugInfo(String subject, String text, String emailFrom, String[] emailTo) {
LOG.debug(getDebugString(subject, text, emailFrom, emailTo));
}
protected String getDebugString(String subject, String text, String emailFrom, String[] emailTo) {
return String.format(debugMessage, emailFrom, Arrays.toString(emailTo), subject, text);
}
}