Please wait. This can take some minutes ...
Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance.
Project price only 1 $
You can buy this project and download/modify it how often you want.
com.day.cq.dam.core.process.SendDownloadAssetEmailProcess Maven / Gradle / Ivy
package com.day.cq.dam.core.process;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.StringWriter;
import java.io.UnsupportedEncodingException;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.jcr.Node;
import javax.jcr.Session;
import javax.jcr.SimpleCredentials;
import javax.mail.Header;
import javax.mail.internet.AddressException;
import javax.mail.internet.InternetAddress;
import javax.mail.internet.InternetHeaders;
import org.apache.commons.io.IOUtils;
import org.apache.commons.lang.StringUtils;
import org.apache.commons.lang.text.StrSubstitutor;
import org.apache.commons.mail.EmailException;
import org.apache.commons.mail.HtmlEmail;
import org.apache.felix.scr.annotations.Component;
import org.apache.felix.scr.annotations.Properties;
import org.apache.felix.scr.annotations.Property;
import org.apache.felix.scr.annotations.Reference;
import org.apache.felix.scr.annotations.ReferencePolicy;
import org.apache.felix.scr.annotations.ReferencePolicyOption;
import org.apache.felix.scr.annotations.Service;
import org.apache.sling.api.resource.Resource;
import org.apache.sling.api.resource.ResourceResolver;
import org.apache.sling.caconfig.resource.ConfigurationResourceResolver;
import org.apache.sling.jcr.api.SlingRepository;
import org.apache.tika.io.CountingInputStream;
import org.osgi.framework.Constants;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import com.day.cq.commons.Externalizer;
import com.day.cq.commons.jcr.JcrConstants;
import com.day.cq.dam.api.DamConstants;
import com.day.cq.dam.commons.process.AbstractAssetWorkflowProcess;
import com.day.cq.dam.commons.util.DamUtil;
import com.day.cq.mailer.MessageGatewayService;
import com.day.cq.workflow.WorkflowException;
import com.day.cq.workflow.WorkflowSession;
import com.day.cq.workflow.exec.WorkItem;
import com.day.cq.workflow.metadata.MetaDataMap;
/**
* The SendDownloadAssetEmailProcess
will send download asset email.
*/
@Component(metatype = false)
@Service
@Properties({
@Property(name = Constants.SERVICE_DESCRIPTION, value = "Send download asset email notification."),
@Property(name = "process.label", value = "Send Download Asset Email Notification")
})
public class SendDownloadAssetEmailProcess extends AbstractAssetWorkflowProcess{
private static final Logger log = LoggerFactory.getLogger(SendDownloadAssetEmailProcess.class);
private static final String DEFAULT_CHARSET = "utf-8";
private static final String EMAIL_TEMPLATE_LEGACY_BUCKET = "/etc";
private static final String EMAIL_TEMPLATE_CACONFIG_BUCKET = "settings";
private static final String SERVICE_USER_ID = "assetidhelper";
@Reference(policy=ReferencePolicy.STATIC)
private MessageGatewayService messageGatewayService;
@Reference(policyOption = ReferencePolicyOption.GREEDY)
private Externalizer externalizer;
@Reference
private ConfigurationResourceResolver configResolver;
@Reference
private SlingRepository repository;
public void execute(WorkItem workItem, WorkflowSession session, MetaDataMap metaData)
throws WorkflowException {
MetaDataMap workflowMetaDataMap = workItem.getWorkflowData().getMetaDataMap();
ResourceResolver resolver = getResourceResolver(session.getSession());
// do not execute upon missing mail service. osgi component still needs to be available for UI
// selection in workflow step configuration.
if (messageGatewayService != null && (messageGatewayService.getGateway(HtmlEmail.class) != null)) {
try{
ArrayList emailRecipients = getEmailRecipients(workflowMetaDataMap);
if (workflowMetaDataMap != null) {
String downloadUrl = (workflowMetaDataMap.containsKey(DamConstants.DOWNLOAD_URL) ? workflowMetaDataMap.get(DamConstants.DOWNLOAD_URL).toString() : null);
if (emailRecipients != null && emailRecipients.size() != 0 && downloadUrl != null) {
String template = getEmailTemplate(metaData, resolver);
if (template != null) {
// get the string substitutors
String zipFileName = downloadUrl.substring(downloadUrl.lastIndexOf('/')+1);
Map valuesMap = new HashMap();
String hostPrefix = getHostPrefix(workItem, resolver);
valuesMap.put("host.prefix", hostPrefix);
valuesMap.put("zipFileName", zipFileName);
String encodedFileName = null;
try {
encodedFileName = URLEncoder.encode(zipFileName, "UTF-8");
} catch (UnsupportedEncodingException e) {
log.error( "Encode the file name failed before sending email in workflow", e);
}
valuesMap.put("downloadurl", downloadUrl.substring(0, downloadUrl.lastIndexOf('/')+1) + encodedFileName);
StrSubstitutor substitutor = new StrSubstitutor(valuesMap);
final HtmlEmail email = createEmail(template, substitutor);
email.setTo( emailRecipients );
messageGatewayService.getGateway(HtmlEmail.class).send(email);
log.info("Email was sent.");
} else {
log.warn("Did not send email. No email template defined");
}
} else {
log.warn("Did not send email. No recipient addresses or assets download URL available.");
}
} else {
log.warn("Did not send email. No workflow metadata is null.");
}
}
catch (EmailException e) {
e.printStackTrace();
log.error( "Fatal error while sending email in workflow", e);
}
} else {
log.warn("cannot send email, mail service unavailable. Please configure Gateway in OSGi Console");
}
}
private ArrayList getEmailRecipients(MetaDataMap workflowMetaDataMap) {
ArrayList emailRecipients = null;
String recipients = workflowMetaDataMap.get("emailTo", new String());
try {
recipients = URLDecoder.decode(recipients, "UTF-8");
List recipientList = Arrays.asList(recipients.split(","));
emailRecipients = new ArrayList();
for (String recipient: recipientList) {
if (!StringUtils.isEmpty(recipient))
emailRecipients.add(new InternetAddress(recipient));
}
} catch (UnsupportedEncodingException e){
log.error("Cannot decode the recipient email address: " + e.getMessage());
} catch (AddressException e){
log.error("Cannot get the recipient email address: " + e.getMessage());
}
return emailRecipients;
}
private String getEmailTemplate(MetaDataMap workflowMetaDataMap, ResourceResolver resolver) {
String template = workflowMetaDataMap.get("template", String.class);
if (template == null) {
// load mail template
String templatePath = workflowMetaDataMap.get("templatePath", String.class);
if (templatePath.startsWith("/")) {
// absolute path specified, resolve using JCR session
template = loadTemplate(resolver.adaptTo(Session.class), templatePath);
} else {
template = loadTemplate(resolver, templatePath);
}
}
log.debug("Loaded template: {}", template);
return template;
}
private HtmlEmail createEmail(final String template, final StrSubstitutor substitutor) {
final HtmlEmail email = new HtmlEmail();
try {
// Note that substitutions must be called, because they are expected to be
// US-ASCII only or specially encoded using MimeUtils class, but substitutions might introduce other chars,
// like e.g. Japanese characters.
// Further the CountingInputStream class does not seem to properly count when reading Japanese characters.
final CountingInputStream in = new CountingInputStream(new ByteArrayInputStream(template.getBytes(DEFAULT_CHARSET)));
final InternetHeaders iHdrs = new InternetHeaders(in);
final Map hdrs = new HashMap();
final Enumeration e = iHdrs.getAllHeaders();
while (e.hasMoreElements()) {
final Header hdr = (Header) e.nextElement();
final String name = hdr.getName();
log.debug("Header: {} = {}", name, hdr.getValue());
hdrs.put(name, iHdrs.getHeader(name));
}
// use the counting stream reader to read the mail body
String templateBody = template.substring(in.getCount());
// create email
email.setCharset(DEFAULT_CHARSET);
// set subject
final String[] ret = hdrs.remove("subject");
final String subject = (ret == null ? "" : ret[0]);
log.info("Email subject: " + subject);
if (!StringUtils.isEmpty(subject)) {
email.setSubject(substitutor.replace(subject));
}
// set message body
templateBody = substitutor.replace(templateBody);
log.debug("Substituted mail body: {}", templateBody);
email.setMsg(templateBody);
IOUtils.closeQuietly(in);
} catch (Exception e){
log.error("Create email: ", e.getMessage());
}
return email;
}
/**
* Loads the mail templates from the repository.
* @deprecated since 6.4. Reading content of email-templates given template-absolute-paths is
* not supported.
* @param path mail templates root path
* @param session session
* @return a reader to the template or null
if not valid.
*/
@Deprecated
public String loadTemplate(final Session session, final String path) {
InputStream is = null;
try {
log.warn("Reading content of email-templates given template-absolute-paths is deprecated");
final Node content = session.getNode(path + "/" + JcrConstants.JCR_CONTENT);
is = content.getProperty(JcrConstants.JCR_DATA).getBinary().getStream();
final InputStreamReader r = new InputStreamReader(is, DEFAULT_CHARSET);
final StringWriter w = new StringWriter();
IOUtils.copy(r, w);
return w.toString();
} catch (final Exception e) {
log.error("Error while loading mail template {}:{}", path, e.toString());
} finally {
IOUtils.closeQuietly(is);
}
return null;
}
private String loadTemplate(final ResourceResolver resolver, final String path) {
InputStream is = null;
try {
// locate legacy templates first
Resource resource = resolver.getResource(EMAIL_TEMPLATE_LEGACY_BUCKET + "/" + path);
if (null == resource) { // no legacy
Resource tenantAssetRootResource = resolver.getResource(DamUtil.getTenantAssetsRoot(resolver));
resource = configResolver.getResource(tenantAssetRootResource, EMAIL_TEMPLATE_CACONFIG_BUCKET, path);
}
final Node content = resource.adaptTo(Node.class).getNode(JcrConstants.JCR_CONTENT);
is = content.getProperty(JcrConstants.JCR_DATA).getBinary().getStream();
final InputStreamReader r = new InputStreamReader(is, DEFAULT_CHARSET);
final StringWriter w = new StringWriter();
IOUtils.copy(r, w);
return w.toString();
} catch (final Exception e) {
log.error("Error while loading mail template {}:{}", path, e.toString());
} finally {
IOUtils.closeQuietly(is);
}
return null;
}
private String getHostPrefix(WorkItem workItem, ResourceResolver resolver) {
ResourceResolver resolverForExternalizer = getResolverForExternalizer(workItem, resolver);
String externalizerHost = externalizer.externalLink(resolverForExternalizer, Externalizer.LOCAL, "");
if (externalizerHost != null && externalizerHost.endsWith("/")) {
return externalizerHost.substring(0, externalizerHost.length() - 1);
} else {
return externalizerHost;
}
}
private ResourceResolver getResolverForExternalizer(WorkItem workItem, ResourceResolver workFlowResourceResolver) {
final String initiator = workItem.getWorkflow().getInitiator();
Session initiatorSession = getUserSession(initiator);
ResourceResolver initiatorResolver = getResourceResolver(initiatorSession);
if (initiatorResolver != null) {
return initiatorResolver;
}
return workFlowResourceResolver;
}
private Session getUserSession(String userId) {
final SimpleCredentials credentials = new SimpleCredentials(userId, new char[0]);
try {
return repository.impersonateFromService(SERVICE_USER_ID, credentials, null);
} catch (Exception e) {
log.info("Impersonation of user '{}' failed", userId, e);
return null;
}
}
}