camunda 设置全局任务监听和执行监听

在使用camunda的过程中,往往需要给用户任务节点设置审批人,最快的方法就是 使用全局监听来实现。

直接先定义 全局任务监听和执行监听


import lombok.extern.slf4j.Slf4j;
import org.camunda.bpm.engine.delegate.DelegateTask;
import org.camunda.bpm.engine.delegate.TaskListener;
import org.springframework.stereotype.Component;

/**
 * 全局任务监听,用于设置任务处理人逻辑
 *

 */
@Component
@Slf4j
public class GlobalTaskListener implements TaskListener {

	@Override
	public void notify(DelegateTask delegateTask) {
		log.info("用户任务监听");

		// 查询审批配置,设置审批人

		// 设置单个审批人
//		delegateTask.setAssignee();
		// 设置候选用户
//		delegateTask.addCandidateUsers();

	}


}


import lombok.extern.slf4j.Slf4j;
import org.camunda.bpm.engine.delegate.DelegateExecution;
import org.camunda.bpm.engine.delegate.ExecutionListener;
import org.camunda.bpm.model.bpmn.impl.instance.SequenceFlowImpl;
import org.camunda.bpm.model.bpmn.impl.instance.UserTaskImpl;
import org.camunda.bpm.model.bpmn.instance.FlowElement;
import org.camunda.bpm.model.bpmn.instance.FlowNode;
import org.camunda.bpm.model.bpmn.instance.LoopCharacteristics;
import org.camunda.bpm.model.bpmn.instance.MultiInstanceLoopCharacteristics;
import org.camunda.bpm.model.bpmn.instance.UserTask;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.List;
import java.util.Objects;

// 这个执行监听用于 多实例任务节点设置审批人
@Slf4j
@Component
public class GlobalMultiInstanceExecutionListener implements ExecutionListener {

	@Override
	public void notify(DelegateExecution delegateExecution) throws Exception {

		log.info("全局执行监听");
		FlowElement currentElement = delegateExecution.getBpmnModelElementInstance();
		// 是连线
		if ((!(currentElement instanceof SequenceFlowImpl))) {
			return;
		}

		// 是任务节点
		FlowNode targetNode = ((SequenceFlowImpl) currentElement).getTarget();
		if ((!(targetNode instanceof UserTask))) {
			return;
		}

		// 是多实例节点
		LoopCharacteristics loopCharacteristics = ((UserTaskImpl) targetNode).getLoopCharacteristics();
		if (!Objects.nonNull(loopCharacteristics) || !(loopCharacteristics instanceof MultiInstanceLoopCharacteristics)) {
			return;
		}


		// 设置 多实例集合
        // TODO 设置审批逻辑
	}

}

实现的方法是  自定义 BpmnParseListener 解析器 在流程引擎解析xml的时候,把上面两个监听器添加到xml中。继承 ProcessApplicationEventParseListener ,并重写里面的方法。
ProcessApplicationEventParseListener 里面有每个节点类型的解析方法,这里只重写了两个

解析用户任务的方法 parseUserTask 和解析连线节点 parseSequenceFlow 方法,如果有其他需求,可以重写父类里面的其他方法

这里给多实例节点设置审批人比较特殊,不能在执行到这个节点上的时候 使用任务监听或执行监听来设置,必须在执行到这个节点之前就设置好多实例集合,所以这里在多实例节点前的连线上添加 执行监听。



import lombok.extern.slf4j.Slf4j;
import org.camunda.bpm.application.impl.event.ProcessApplicationEventParseListener;
import org.camunda.bpm.engine.delegate.ExecutionListener;
import org.camunda.bpm.engine.delegate.TaskListener;
import org.camunda.bpm.engine.impl.bpmn.behavior.MultiInstanceActivityBehavior;
import org.camunda.bpm.engine.impl.bpmn.behavior.UserTaskActivityBehavior;
import org.camunda.bpm.engine.impl.pvm.PvmActivity;
import org.camunda.bpm.engine.impl.pvm.delegate.ActivityBehavior;
import org.camunda.bpm.engine.impl.pvm.process.ActivityImpl;
import org.camunda.bpm.engine.impl.pvm.process.ScopeImpl;
import org.camunda.bpm.engine.impl.pvm.process.TransitionImpl;
import org.camunda.bpm.engine.impl.task.TaskDefinition;
import org.camunda.bpm.engine.impl.util.xml.Element;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

/**
 * 自定义 解析器
 */
@Slf4j
@Component
public class DyBpmnParseListener extends ProcessApplicationEventParseListener {
	@Autowired
	private GlobalTaskListener globalTaskListener;

	@Autowired
	private GlobalMultiInstanceExecutionListener globalMultiInstanceExecutionListener;


	/**
	 * 自定义流程引擎 在解析用户任务前的逻辑
	 * 给所有任务 添加 create事件 任务监听 GlobalTaskListener
	 */
	@Override
	public void parseUserTask(Element userTaskElement, ScopeImpl scope, ActivityImpl activity) {
		this.addStartEventListener(activity);
		this.addEndEventListener(activity);
		UserTaskActivityBehavior activityBehavior = (UserTaskActivityBehavior) activity.getActivityBehavior();
		TaskDefinition taskDefinition = activityBehavior.getTaskDefinition();
		taskDefinition.addTaskListener(TaskListener.EVENTNAME_CREATE, globalTaskListener);

		this.addTaskCreateListeners(taskDefinition);
		this.addTaskAssignmentListeners(taskDefinition);
		this.addTaskCompleteListeners(taskDefinition);
		this.addTaskUpdateListeners(taskDefinition);
		this.addTaskDeleteListeners(taskDefinition);
	}


	/**
	 * 解析连线
	 * 如果连线的目标节点 是多实例节点,则给当前连线设置 执行监听
	 */
	@Override
	public void parseSequenceFlow(Element sequenceFlowElement, ScopeImpl scopeElement, TransitionImpl transition) {
		PvmActivity destination = transition.getDestination();
		ActivityBehavior activityBehavior = destination.getActivityBehavior();
		// 多实例,默认给当前连线设置执行监听
		if (activityBehavior instanceof MultiInstanceActivityBehavior) {
			transition.addListener(ExecutionListener.EVENTNAME_TAKE, globalMultiInstanceExecutionListener);
		}
		this.addTakeEventListener(transition);
	}

}

然后将自定义解析器添加到 流程引擎插件中



import org.camunda.bpm.engine.ProcessEngine;
import org.camunda.bpm.engine.impl.cfg.ProcessEngineConfigurationImpl;
import org.camunda.bpm.engine.impl.cfg.ProcessEnginePlugin;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;


@Configuration
public class ProcessEngineConfig implements ProcessEnginePlugin {

	@Autowired
	private DyBpmnParseListener dyBpmnParseListener;



	@Override
	public void preInit(ProcessEngineConfigurationImpl processEngineConfiguration) {
		// 关闭历史记录清理,系统需要保留历史记录
		processEngineConfiguration.setHistoryCleanupEnabled(false);
		// 配置自定义解析器
		processEngineConfiguration.getCustomPreBPMNParseListeners().add(dyBpmnParseListener);
	}

	@Override
	public void postInit(ProcessEngineConfigurationImpl processEngineConfiguration) {

	}

	@Override
	public void postProcessEngineBuild(ProcessEngine processEngine) {
	}
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值