Activiti基础的使用笔记

理解了工作流的大概过程可以尝试编辑一个工作流页面bpmn文件,然后可以对其进行基本的使用,理解代码对工作流的处理流程。

 文件修改为.xml文件后可由后端读取解析,其解析的内容为:

<?xml version="1.0" encoding="UTF-8"?>
<definitions xmlns="http://www.omg.org/spec/BPMN/20100524/MODEL" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:activiti="http://activiti.org/bpmn" xmlns:bpmndi="http://www.omg.org/spec/BPMN/20100524/DI" xmlns:omgdc="http://www.omg.org/spec/DD/20100524/DC" xmlns:omgdi="http://www.omg.org/spec/DD/20100524/DI" typeLanguage="http://www.w3.org/2001/XMLSchema" expressionLanguage="http://www.w3.org/1999/XPath" targetNamespace="http://www.activiti.org/test">
  <process id="second_approve" name="二级审批流程" isExecutable="true">
    <startEvent id="startEvent" name="开始"></startEvent>
    <userTask id="submitForm" name="填写审批信息">
      <extensionElements>
        <activiti:formProperty id="message" name="申请信息" type="string" required="true"></activiti:formProperty>
        <activiti:formProperty id="name" name="申请人名称" type="string" required="true"></activiti:formProperty>
        <activiti:formProperty id="submitTime" name="提交时间" type="date" datePattern="yyyy-MM-dd" required="true"></activiti:formProperty>
        <activiti:formProperty id="submitType" name="确认申请" type="string" required="true"></activiti:formProperty>
      </extensionElements>
    </userTask>
    <sequenceFlow id="flow1" sourceRef="startEvent" targetRef="submitForm"></sequenceFlow>
    <exclusiveGateway id="decideSubmit" name="提交或取消"></exclusiveGateway>
    <sequenceFlow id="flow2" sourceRef="submitForm" targetRef="decideSubmit"></sequenceFlow>
    <userTask id="tl_approve" name="主管审批">
      <extensionElements>
        <activiti:formProperty id="tlApprove" name="主管审批结果" type="string" required="true"></activiti:formProperty>
        <activiti:formProperty id="tlMessage" name="主管审批备注" type="string" required="true"></activiti:formProperty>
      </extensionElements>
    </userTask>
    <sequenceFlow id="flow3" sourceRef="decideSubmit" targetRef="tl_approve">
      <conditionExpression xsi:type="tFormalExpression"><![CDATA[${ submitType == "y" || submitType == "Y" }]]></conditionExpression>
    </sequenceFlow>
    <exclusiveGateway id="decideTLApprove" name="主管审批校验"></exclusiveGateway>
    <sequenceFlow id="flow4" sourceRef="tl_approve" targetRef="decideTLApprove"></sequenceFlow>
    <userTask id="hr_approve" name="人事审批">
      <extensionElements>
        <activiti:formProperty id="hrApprove" name="人事审批结果" type="string" required="true"></activiti:formProperty>
        <activiti:formProperty id="hrMessage" name="人事审批备注" type="string" required="true"></activiti:formProperty>
      </extensionElements>
    </userTask>
    <sequenceFlow id="flow5" sourceRef="decideTLApprove" targetRef="hr_approve">
      <conditionExpression xsi:type="tFormalExpression"><![CDATA[${ tlApprove == "y" || tlApprove == "Y" }]]></conditionExpression>
    </sequenceFlow>
    <endEvent id="endEventCancel" name="取消"></endEvent>
    <sequenceFlow id="flow7" sourceRef="decideSubmit" targetRef="endEventCancel">
      <conditionExpression xsi:type="tFormalExpression"><![CDATA[${ submitType == "n" || submitType == "N" }]]></conditionExpression>
    </sequenceFlow>
    <sequenceFlow id="flow8" sourceRef="decideTLApprove" targetRef="submitForm">
      <conditionExpression xsi:type="tFormalExpression"><![CDATA[${ tlApprove == "n" || tlApprove == "N" }]]></conditionExpression>
    </sequenceFlow>
    <exclusiveGateway id="decideHRApprove" name="人事审批校验"></exclusiveGateway>
    <sequenceFlow id="flow9" sourceRef="hr_approve" targetRef="decideHRApprove"></sequenceFlow>
    <endEvent id="endEvent" name="结束"></endEvent>
    <sequenceFlow id="flow10" sourceRef="decideHRApprove" targetRef="endEvent">
      <conditionExpression xsi:type="tFormalExpression"><![CDATA[${ tlApprove == "y" || tlApprove == "Y" }]]></conditionExpression>
    </sequenceFlow>
    <sequenceFlow id="flow11" sourceRef="decideHRApprove" targetRef="submitForm">
      <conditionExpression xsi:type="tFormalExpression"><![CDATA[${ hrApprove == "n" || hrApprove == "N" }]]></conditionExpression>
    </sequenceFlow>
  </process>
  <bpmndi:BPMNDiagram id="BPMNDiagram_second_approve">
    <bpmndi:BPMNPlane bpmnElement="second_approve" id="BPMNPlane_second_approve">
      <bpmndi:BPMNShape bpmnElement="startEvent" id="BPMNShape_startEvent">
        <omgdc:Bounds height="35.0" width="35.0" x="150.0" y="290.0"></omgdc:Bounds>
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape bpmnElement="submitForm" id="BPMNShape_submitForm">
        <omgdc:Bounds height="55.0" width="105.0" x="230.0" y="280.0"></omgdc:Bounds>
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape bpmnElement="decideSubmit" id="BPMNShape_decideSubmit">
        <omgdc:Bounds height="40.0" width="40.0" x="380.0" y="288.0"></omgdc:Bounds>
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape bpmnElement="tl_approve" id="BPMNShape_tl_approve">
        <omgdc:Bounds height="55.0" width="105.0" x="465.0" y="281.0"></omgdc:Bounds>
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape bpmnElement="decideTLApprove" id="BPMNShape_decideTLApprove">
        <omgdc:Bounds height="40.0" width="40.0" x="614.0" y="288.0"></omgdc:Bounds>
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape bpmnElement="hr_approve" id="BPMNShape_hr_approve">
        <omgdc:Bounds height="55.0" width="105.0" x="701.0" y="280.0"></omgdc:Bounds>
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape bpmnElement="endEventCancel" id="BPMNShape_endEventCancel">
        <omgdc:Bounds height="35.0" width="35.0" x="500.0" y="390.0"></omgdc:Bounds>
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape bpmnElement="decideHRApprove" id="BPMNShape_decideHRApprove">
        <omgdc:Bounds height="40.0" width="40.0" x="869.0" y="287.0"></omgdc:Bounds>
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape bpmnElement="endEvent" id="BPMNShape_endEvent">
        <omgdc:Bounds height="35.0" width="35.0" x="960.0" y="290.0"></omgdc:Bounds>
      </bpmndi:BPMNShape>
      <bpmndi:BPMNEdge bpmnElement="flow1" id="BPMNEdge_flow1">
        <omgdi:waypoint x="185.0" y="307.0"></omgdi:waypoint>
        <omgdi:waypoint x="230.0" y="307.0"></omgdi:waypoint>
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge bpmnElement="flow2" id="BPMNEdge_flow2">
        <omgdi:waypoint x="335.0" y="307.0"></omgdi:waypoint>
        <omgdi:waypoint x="380.0" y="308.0"></omgdi:waypoint>
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge bpmnElement="flow3" id="BPMNEdge_flow3">
        <omgdi:waypoint x="420.0" y="308.0"></omgdi:waypoint>
        <omgdi:waypoint x="465.0" y="308.0"></omgdi:waypoint>
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge bpmnElement="flow4" id="BPMNEdge_flow4">
        <omgdi:waypoint x="570.0" y="308.0"></omgdi:waypoint>
        <omgdi:waypoint x="614.0" y="308.0"></omgdi:waypoint>
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge bpmnElement="flow5" id="BPMNEdge_flow5">
        <omgdi:waypoint x="654.0" y="308.0"></omgdi:waypoint>
        <omgdi:waypoint x="701.0" y="307.0"></omgdi:waypoint>
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge bpmnElement="flow7" id="BPMNEdge_flow7">
        <omgdi:waypoint x="400.0" y="328.0"></omgdi:waypoint>
        <omgdi:waypoint x="400.0" y="407.0"></omgdi:waypoint>
        <omgdi:waypoint x="500.0" y="407.0"></omgdi:waypoint>
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge bpmnElement="flow8" id="BPMNEdge_flow8">
        <omgdi:waypoint x="634.0" y="288.0"></omgdi:waypoint>
        <omgdi:waypoint x="634.0" y="241.0"></omgdi:waypoint>
        <omgdi:waypoint x="282.0" y="241.0"></omgdi:waypoint>
        <omgdi:waypoint x="282.0" y="280.0"></omgdi:waypoint>
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge bpmnElement="flow9" id="BPMNEdge_flow9">
        <omgdi:waypoint x="806.0" y="307.0"></omgdi:waypoint>
        <omgdi:waypoint x="869.0" y="307.0"></omgdi:waypoint>
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge bpmnElement="flow10" id="BPMNEdge_flow10">
        <omgdi:waypoint x="909.0" y="307.0"></omgdi:waypoint>
        <omgdi:waypoint x="960.0" y="307.0"></omgdi:waypoint>
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge bpmnElement="flow11" id="BPMNEdge_flow11">
        <omgdi:waypoint x="889.0" y="287.0"></omgdi:waypoint>
        <omgdi:waypoint x="889.0" y="196.0"></omgdi:waypoint>
        <omgdi:waypoint x="282.0" y="196.0"></omgdi:waypoint>
        <omgdi:waypoint x="282.0" y="280.0"></omgdi:waypoint>
      </bpmndi:BPMNEdge>
    </bpmndi:BPMNPlane>
  </bpmndi:BPMNDiagram>
</definitions>

用代码对流程进行开发使用。

package com.gjp.activiti.helloworld;

import com.google.common.collect.Maps;
import com.sun.org.apache.xpath.internal.operations.Or;
import org.activiti.engine.*;
import org.activiti.engine.form.FormProperty;
import org.activiti.engine.form.TaskFormData;
import org.activiti.engine.impl.form.DateFormType;
import org.activiti.engine.impl.form.StringFormType;
import org.activiti.engine.repository.Deployment;
import org.activiti.engine.repository.DeploymentBuilder;
import org.activiti.engine.repository.ProcessDefinition;
import org.activiti.engine.runtime.ProcessInstance;
import org.activiti.engine.task.Task;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.*;

public class DemoActiviti {
    private static final Logger logger = LoggerFactory.getLogger(DemoActiviti.class);

    public static void main(String[] args) throws ParseException {
        System.out.println("我启动了!");
        //创建流程引擎
        ProcessEngine processEngine = getProcessEngine();

        //部署流程定义文件
        ProcessDefinition processDefinition = getDeploymentBuilder(processEngine);

        //启动流程
        ProcessInstance processInstance = getProcessInstance(processEngine, processDefinition);

        //处理流程任务
        processInstanceDuelWith(processInstance, processEngine);

        System.out.println("我结束了!");
    }

    /**
     * 创建流程引擎
     * @return
     */
    private static ProcessEngine getProcessEngine(){
        ProcessEngineConfiguration cfg = ProcessEngineConfiguration.createStandaloneInMemProcessEngineConfiguration();
        ProcessEngine processEngine = cfg.buildProcessEngine();
        String name = processEngine.getName();
        String version = ProcessEngine.VERSION;
        // logger.info("我的引擎名称为{},版本为{}",name,version);
        System.out.println(String.format("流程引擎名称{ %s },版本{ %s }", name, version));
        return processEngine;
    }

    /**
     * 部署流程定义文件
     * @param processEngine  获取创建的流程空间
     * @return
     */
    private static ProcessDefinition getDeploymentBuilder(ProcessEngine processEngine){
        RepositoryService repositoryService = processEngine.getRepositoryService();
        DeploymentBuilder deploymentBuilder = repositoryService.createDeployment();
        //deploymentBuilder.addClasspathResource("secound_approve.bpmn.xml");
        Deployment deployment = deploymentBuilder.
                addClasspathResource("secound_approve.bpmn.xml").deploy();;
        String deploymentId = deployment.getId();
        ProcessDefinition processDefinition = repositoryService.createProcessDefinitionQuery()
                .deploymentId(deploymentId)
                .singleResult();//根据id获取流程定义对象
        // logger.info("流程定义文件{},流程ID{}",processDefinition.getName(),processDefinition.getId());
        System.out.println(String.format("流程定义文件{ %s },流程id{ %s }", processDefinition.getName(), processDefinition.getId()));
        return processDefinition;
    }

    /**
     * 启动流程
     * @param processEngine 获取创建的流程空间
     * @param processDefinition 获取部署的流程
     * @return 返回启动的流程实例
     */
    private  static ProcessInstance getProcessInstance(ProcessEngine processEngine, ProcessDefinition processDefinition){
        RuntimeService runtimeService = processEngine.getRuntimeService();
        ProcessInstance processInstance = runtimeService.startProcessInstanceById(processDefinition.getId());
        System.out.println(String.format("启动流程{%s}", processInstance.getProcessDefinitionKey()));
        return processInstance;
    }

    /**
     *  处理工作任务
     * @param processInstance 获取流程实例
     * @param processEngine 获取流程引擎模板
     * @throws ParseException 日期转化时异常输出
     */
    private static void processInstanceDuelWith(ProcessInstance processInstance, ProcessEngine processEngine ) throws ParseException {
        Scanner scanner = new Scanner(System.in);
        while (processInstance!=null && !processInstance.isEnded()) {
            //当流程没有结束的时候,继续获取流程信息
            TaskService taskService = processEngine.getTaskService();//获取工作流服务
            List<Task> processEngineList = taskService.createTaskQuery().list();
            System.out.println(String.format("任务总数为:{%s}", processEngineList.size()));
            for (Task task : processEngineList) {
                System.out.println(String.format("待处理的任务为:{%s}", task.getName()));
                //初始化表单服务类并初始化工作流程数据
                FormService formService = processEngine.getFormService();
                TaskFormData taskFormData = formService.getTaskFormData(task.getId());
                //获取bpmn文件中的表单内容
                List<FormProperty> formPropertyList = taskFormData.getFormProperties();
                for (FormProperty formProperty :formPropertyList){
                    System.out.println(String.format("流程id:%s ,流程值:%s", formProperty.getId(), formProperty.getValue()));
                }
                //这里的内容是不允许key为空
                Map<String , Object> variables = new Hashtable<String, Object>();
                //获取了流程表单内容进行处理
                //根据表单的行类型,获取输入类型
                for (FormProperty formProperty : formPropertyList ){
                    String inLine = "";
                    if ((StringFormType.class).isInstance(formProperty.getType())){
                        System.out.println(String.format("请输入%s:", formProperty.getName()));
                        inLine = scanner.nextLine();
                        variables.put( formProperty.getId() , inLine);
                    }else if ((DateFormType.class).isInstance(formProperty.getType())){
                        System.out.println(String.format("输入%s,格式为:yyyy-MM-dd:", formProperty.getName()));
                        inLine = scanner.nextLine();
                        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
                        Date date = sdf.parse(inLine);
                        variables.put(formProperty.getId(), date);
                    } else {
                        logger.info("其他类型不支持");
                    }
                    logger.info("你输入的内容为" + inLine);
                }
                //提交流程
                taskService.complete( task.getId() , variables);
            }
            //获取流程实例最新状态
            processInstance = processEngine.getRuntimeService()
                    .createProcessInstanceQuery()
                    .processInstanceId(processInstance.getId())
                    .singleResult();
        }
    }
}

其结果如下:

我启动了!
流程引擎名称{ default },版本{ 6.0.0.4 }
流程定义文件{ 二级审批流程 },流程id{ second_approve:1:4 }
启动流程{second_approve}
任务总数为:{1}
待处理的任务为:{填写审批信息}
流程id:message ,流程值:null
流程id:name ,流程值:null
流程id:submitTime ,流程值:null
流程id:submitType ,流程值:null
请输入申请信息:
---我想请假--
请输入申请人名称:
--小麦麸--
输入提交时间,格式为:yyyy-MM-dd:
2018-09-17
请输入确认申请:
y
任务总数为:{1}
待处理的任务为:{主管审批}
流程id:tlApprove ,流程值:null
流程id:tlMessage ,流程值:null
请输入主管审批结果:
y
请输入主管审批备注:
--2018-09-17 这个人的请假我不想给--
任务总数为:{1}
待处理的任务为:{人事审批}
流程id:hrApprove ,流程值:null
流程id:hrMessage ,流程值:null
请输入人事审批结果:
y
请输入人事审批备注:
--2018-09-11 这个人的请假我不想给--
我结束了!

Process finished with exit code 0

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值