When adding jbpm to a project I didn't want to have to configure mail settings in two places and learn a second templating language just to send reminder mails from a business process. The following is how I integrated the Seam mail system into jbpm to get around those issues. The following is sufficient for my purposes but should probably be extended to be more generic/flexible. /** * Copyright Software Factory - 2009 */ package nz.co.softwarefactory.risingstars.jbpm; import java.util.HashMap; import java.util.Map; import java.util.Set; import nz.co.softwarefactory.risingstars.util.EmailEventListener; import org.jboss.seam.core.Events; import org.jbpm.graph.exe.ExecutionContext; import org.jbpm.taskmgmt.exe.PooledActor; import org.jbpm.taskmgmt.exe.TaskInstance; /** * Overrides the jBPM mail service to use the seam mail system instead. * * @author craig */ @SuppressWarnings("serial") public class Mail extends org.jbpm.mail.Mail { private static final String TEMPLATE_PATH = "/WEB-INF/pages/occurrence/"; private static final String EMAIL_TASK_ASSIGNMENT = "taskAssignmentEmailWrapper.xhtml"; private static final String EMAIL_TASK_CREATE = "taskCreateEmailWrapper.xhtml"; private static final String EMAIL_TASK_REMINDER = "taskReminderEmailWrapper.xhtml"; private static final String TEMPLATE_TASK_ASSIGNMENT = "task-assign"; private static final String TEMPLATE_TASK_CREATE = "task-create"; private static final String TEMPLATE_TASK_REMINDER = "task-reminder"; public String template = null; public String actors = null; private ExecutionContext executionContext; /** * @see org.jbpm.mail.Mail#execute(org.jbpm.graph.exe.ExecutionContext) */ @Override public void execute(final ExecutionContext executionContext) { this.executionContext = executionContext; super.execute(executionContext); } @Override public void send() { final TaskInstance task = executionContext.getTaskInstance(); final Map<String, Object> parameters = new HashMap<String, Object>(); setActors(task); parameters.put("task", task); // TODO this probably isn't as flexible as it could be as does not all // use of "to" field and will not evaluate // expressions before attempting to resolve addresses. Was using // getRecipients but am not able get it to use // the actor Ids I wanted it to as actors is private and cannot be set. parameters.put("addresses", resolveAddresses(tokenize(actors))); if (Mail.TEMPLATE_TASK_ASSIGNMENT.equals(template)) { Events.instance().raiseAsynchronousEvent(EmailEventListener.EVENT_SEND_ASYNCHRONOUS_JBPM_EMAIL, Mail.TEMPLATE_PATH + Mail.EMAIL_TASK_ASSIGNMENT, parameters); } else if (Mail.TEMPLATE_TASK_REMINDER.equals(template)) { Events.instance().raiseAsynchronousEvent(EmailEventListener.EVENT_SEND_ASYNCHRONOUS_JBPM_EMAIL, Mail.TEMPLATE_PATH + Mail.EMAIL_TASK_REMINDER, parameters); } else if (Mail.TEMPLATE_TASK_CREATE.equals(template)) { Events.instance().raiseAsynchronousEvent(EmailEventListener.EVENT_SEND_ASYNCHRONOUS_JBPM_EMAIL, Mail.TEMPLATE_PATH + Mail.EMAIL_TASK_CREATE, parameters); } } private void setActors(final TaskInstance task) { if (actors == null || actors.isEmpty()) { final String actorId = task.getActorId(); if (actorId != null && !actorId.isEmpty()) { actors = actorId; } else { final Set<PooledActor> pooledActors = task.getPooledActors(); final StringBuilder sb = new StringBuilder(); for (final PooledActor pooledActor : pooledActors) { if (sb.length() > 0) { sb.append(";"); } sb.append(pooledActor.getActorId()); } actors = sb.toString(); } } } } jbpm.cfg.xml <string name='mail.class.name' value='nz.co.softwarefactory.risingstars.jbpm.Mail' /> |
Pageflow and jBPM >