Camunda ScriptTask SendTask ReceiveTask操作

文章目录

  • 开始
  • 脚本任务(ScriptTask)
  • 发送任务(SendTask)
  • 接收任务(ReceiveTask)
  • 流程图xml

开始

前面我们已经介绍了Camunda最基本的操作和常见的监听器,如果不熟悉Camunda,可以先看一下,方便搭建环境,亲手测试。

Camunda组件与服务与基本操作

Camunda中强大的监听服务

本篇将简单介绍Camunda的Script Task、Send Task、Receive Task。

熟悉这些Task,可以帮我们更好理解Camunda流程。

脚本任务(ScriptTask)

脚本任务

Format:JavaScript

Type:Inline script

execution.setVariable("pa", "javascript");

如果启动流程发现:Can’t find scripting engine for ‘javascript’: scriptEngine is null

可以加入下面的依赖:

<dependency>
    <groupId>org.graalvm.js</groupId>
    <artifactId>js</artifactId>
    <version>23.0.3</version>
</dependency>
<dependency>
    <groupId>org.graalvm.js</groupId>
    <artifactId>js-scriptengine</artifactId>
    <version>23.0.3</version>
</dependency>

除了JavaScript,还可以使用Python、Groovy、Ruby等,得添加相关的依赖。

尽量不要在脚本中实现复杂的逻辑,调试起来比较麻烦,排查问题也痛苦。

发送任务(SendTask)

发送任务

发送任务Send Task和我们之前介绍的Service Task差不多。

可以配置为Java Class然后实现JavaDelegate类。

在实现类中可以获取相关信息,例如:上一个脚本节点设置的参数。

import org.camunda.bpm.engine.delegate.DelegateExecution;
import org.camunda.bpm.engine.delegate.JavaDelegate;

public class SendTaskJavaDelegate implements JavaDelegate {

    @Override
    public void execute(DelegateExecution delegateExecution) {
        System.out.println(SendTaskJavaDelegate.class.getName() + "--start");

        System.out.println("获取参数:" + delegateExecution.getVariable("pa"));
        System.out.println("getId:" + delegateExecution.getId());
        System.out.println("getProcessInstanceId:" + delegateExecution.getProcessInstanceId());
        System.out.println("getActivityInstanceId:" + delegateExecution.getActivityInstanceId());
        System.out.println("getCurrentActivityId:" + delegateExecution.getCurrentActivityId());
        System.out.println("getCurrentActivityName:" + delegateExecution.getCurrentActivityName());
        System.out.println("getProcessBusinessKey:" + delegateExecution.getProcessBusinessKey());
        System.out.println("getProcessDefinitionId:" + delegateExecution.getProcessDefinitionId());
        System.out.println("getBusinessKey:" + delegateExecution.getBusinessKey());
        System.out.println("getEventName:" + delegateExecution.getEventName());
        System.out.println(SendTaskJavaDelegate.class.getName() + "--end");
    }
}
com.example.workflow.delegate.SendTaskJavaDelegate--start
获取参数:javascript
getId:1fbafcb1-c0ac-11ee-b7bf-00ffe7687986
getProcessInstanceId:1fbafcb1-c0ac-11ee-b7bf-00ffe7687986
getActivityInstanceId:Activity_0xcgnyl:2053ba46-c0ac-11ee-b7bf-00ffe7687986
getCurrentActivityId:Activity_0xcgnyl
getCurrentActivityName:发送任务
getProcessBusinessKey:task0002
getProcessDefinitionId:Process_0btcu4b:2:ca1b15a6-c0aa-11ee-8ced-00ffe7687986
getBusinessKey:task0002
getEventName:null
com.example.workflow.delegate.SendTaskJavaDelegate--end

接收任务(ReceiveTask)

接收任务节点可以用来阻塞节点往下执行,比如等一个外部任务完成。

有例如,一个节点必须依赖另一个节点完成,就可以在节点前添加一个接收任务节点,等其他节点完成之后,通过接收任务节点继续往下走。

接收任务

可以根据activityId来查询任务executionId

@Test
public void queryExecutionId() {
    String activityId = "Activity_1nu3d7a";
    Execution execution = runtimeService.createExecutionQuery()
            .activityId(activityId).singleResult();
    System.out.println(execution);
}
select * from act_hi_actinst where ACT_ID_ ='Activity_1nu3d7a';

然后通过executionId来通知接收消息的节点,不用等了,可以到下一个节点了。

@Test
public void signal() {
    String executionId = "2054cbb7-c0ac-11ee-b7bf-00ffe7687986";
    runtimeService.signal(executionId);
}

除了signal,还可以correlateMessage来通知Receive Task完成:

@Test
public void correlateMessage() {
    String messageName = "Message_0ud6hg1";
    runtimeService.correlateMessage(messageName);
}

消息也可以是中文:

@Test
public void correlate() {
    String messageName = "消息2";
    MessageCorrelationBuilder messageCorrelation =
            runtimeService.createMessageCorrelation(messageName);
    messageCorrelation.correlate();
}

完整的测试用例:

import jakarta.annotation.Resource;
import org.camunda.bpm.engine.RuntimeService;
import org.camunda.bpm.engine.runtime.Execution;
import org.camunda.bpm.engine.runtime.MessageCorrelationBuilder;
import org.junit.jupiter.api.Test;
import org.springframework.boot.test.context.SpringBootTest;


@SpringBootTest
class ApplicationTest {

    @Resource
    private RuntimeService runtimeService;

    @Test
    public void queryExecutionId() {
        String activityId = "Activity_1nu3d7a";
        Execution execution = runtimeService.createExecutionQuery()
                .activityId(activityId).singleResult();
        System.out.println(execution);
    }

    @Test
    public void signal() {
        String executionId = "2054cbb7-c0ac-11ee-b7bf-00ffe7687986";
        runtimeService.signal(executionId);
    }

    @Test
    public void correlateMessage() {
        String messageName = "Message_0ud6hg1";
        runtimeService.correlateMessage(messageName);
    }

    @Test
    public void correlate() {
        String messageName = "消息2";
        MessageCorrelationBuilder messageCorrelation =
                runtimeService.createMessageCorrelation(messageName);
        messageCorrelation.correlate();
    }
}

记得添加依赖,不要加错了,不然执行不了。

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-test</artifactId>
</dependency>

流程图xml

<?xml version="1.0" encoding="UTF-8"?>
<bpmn:definitions xmlns:bpmn="http://www.omg.org/spec/BPMN/20100524/MODEL" xmlns:bpmndi="http://www.omg.org/spec/BPMN/20100524/DI" xmlns:dc="http://www.omg.org/spec/DD/20100524/DC" xmlns:camunda="http://camunda.org/schema/1.0/bpmn" xmlns:di="http://www.omg.org/spec/DD/20100524/DI" xmlns:modeler="http://camunda.org/schema/modeler/1.0" id="Definitions_18zyppt" targetNamespace="http://bpmn.io/schema/bpmn" exporter="Camunda Modeler" exporterVersion="5.19.0" modeler:executionPlatform="Camunda Platform" modeler:executionPlatformVersion="7.20.0">
  <bpmn:process id="Process_0btcu4b" name="任务测试" isExecutable="true" camunda:historyTimeToLive="180">
    <bpmn:startEvent id="StartEvent_1">
      <bpmn:outgoing>Flow_0x6f2m3</bpmn:outgoing>
    </bpmn:startEvent>
    <bpmn:sequenceFlow id="Flow_0x6f2m3" sourceRef="StartEvent_1" targetRef="Activity_08nl9jt" />
    <bpmn:scriptTask id="Activity_08nl9jt" name="脚本任务" scriptFormat="JavaScript">
      <bpmn:incoming>Flow_0x6f2m3</bpmn:incoming>
      <bpmn:outgoing>Flow_1kkp455</bpmn:outgoing>
      <bpmn:script>execution.setVariable("pa", "javascript");</bpmn:script>
    </bpmn:scriptTask>
    <bpmn:sequenceFlow id="Flow_1kkp455" sourceRef="Activity_08nl9jt" targetRef="Activity_0xcgnyl" />
    <bpmn:sendTask id="Activity_0xcgnyl" name="发送任务" camunda:class="com.example.workflow.delegate.SendTaskJavaDelegate">
      <bpmn:incoming>Flow_1kkp455</bpmn:incoming>
      <bpmn:outgoing>Flow_0gw8gq5</bpmn:outgoing>
    </bpmn:sendTask>
    <bpmn:sequenceFlow id="Flow_0gw8gq5" sourceRef="Activity_0xcgnyl" targetRef="Activity_1nu3d7a" />
    <bpmn:receiveTask id="Activity_1nu3d7a" name="接收任务" messageRef="Message_13j3si4">
      <bpmn:incoming>Flow_0gw8gq5</bpmn:incoming>
      <bpmn:outgoing>Flow_09l62nk</bpmn:outgoing>
    </bpmn:receiveTask>
    <bpmn:sequenceFlow id="Flow_09l62nk" sourceRef="Activity_1nu3d7a" targetRef="Activity_1oedt3n" />
    <bpmn:userTask id="Activity_1oedt3n" name="用户任务">
      <bpmn:incoming>Flow_09l62nk</bpmn:incoming>
      <bpmn:outgoing>Flow_1yorrvs</bpmn:outgoing>
    </bpmn:userTask>
    <bpmn:endEvent id="Event_1o1zu4l">
      <bpmn:incoming>Flow_1yorrvs</bpmn:incoming>
    </bpmn:endEvent>
    <bpmn:sequenceFlow id="Flow_1yorrvs" sourceRef="Activity_1oedt3n" targetRef="Event_1o1zu4l" />
  </bpmn:process>
  <bpmn:message id="Message_3n3k1s8" name="消息1" />
  <bpmn:message id="Message_13j3si4" name="消息2" />
  <bpmn:message id="Message_0ud6hg1" name="Message_0ud6hg1" />
  <bpmndi:BPMNDiagram id="BPMNDiagram_1">
    <bpmndi:BPMNPlane id="BPMNPlane_1" bpmnElement="Process_0btcu4b">
      <bpmndi:BPMNShape id="_BPMNShape_StartEvent_2" bpmnElement="StartEvent_1">
        <dc:Bounds x="149" y="99" width="36" height="36" />
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape id="Activity_0slvat5_di" bpmnElement="Activity_08nl9jt">
        <dc:Bounds x="220" y="77" width="100" height="80" />
        <bpmndi:BPMNLabel />
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape id="Activity_1obj6uy_di" bpmnElement="Activity_0xcgnyl">
        <dc:Bounds x="360" y="77" width="100" height="80" />
        <bpmndi:BPMNLabel />
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape id="Activity_1gz5v9p_di" bpmnElement="Activity_1nu3d7a">
        <dc:Bounds x="250" y="210" width="100" height="80" />
        <bpmndi:BPMNLabel />
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape id="Activity_0k177dl_di" bpmnElement="Activity_1oedt3n">
        <dc:Bounds x="410" y="210" width="100" height="80" />
        <bpmndi:BPMNLabel />
      </bpmndi:BPMNShape>
      <bpmndi:BPMNShape id="Event_1o1zu4l_di" bpmnElement="Event_1o1zu4l">
        <dc:Bounds x="572" y="232" width="36" height="36" />
      </bpmndi:BPMNShape>
      <bpmndi:BPMNEdge id="Flow_0x6f2m3_di" bpmnElement="Flow_0x6f2m3">
        <di:waypoint x="185" y="117" />
        <di:waypoint x="220" y="117" />
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge id="Flow_1kkp455_di" bpmnElement="Flow_1kkp455">
        <di:waypoint x="320" y="117" />
        <di:waypoint x="360" y="117" />
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge id="Flow_0gw8gq5_di" bpmnElement="Flow_0gw8gq5">
        <di:waypoint x="410" y="157" />
        <di:waypoint x="410" y="184" />
        <di:waypoint x="300" y="184" />
        <di:waypoint x="300" y="210" />
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge id="Flow_09l62nk_di" bpmnElement="Flow_09l62nk">
        <di:waypoint x="350" y="250" />
        <di:waypoint x="410" y="250" />
      </bpmndi:BPMNEdge>
      <bpmndi:BPMNEdge id="Flow_1yorrvs_di" bpmnElement="Flow_1yorrvs">
        <di:waypoint x="510" y="250" />
        <di:waypoint x="572" y="250" />
      </bpmndi:BPMNEdge>
    </bpmndi:BPMNPlane>
  </bpmndi:BPMNDiagram>
</bpmn:definitions>

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/364558.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

编程实例源代码,知识库管理软件源码文件下载及代码说明

编程实例源代码&#xff0c;知识库管理软件源码文件下载及代码说明 一、前言 知识库管理软件是一款图片集查询软件&#xff0c;软件可以使用中文编程工具免费自由版开发完成。 编程工具下载及源码文件下载路径 编程入门视频教程链接 https://edu.csdn.net/course/detail/3…

C++之平衡二叉搜索树查找

个人主页&#xff1a;[PingdiGuo_guo] 收录专栏&#xff1a;[C干货专栏] 大家好&#xff0c;我是PingdiGuo&#xff0c;今天我们来学习平衡二叉搜索树查找。 目录 1.什么是二叉树 2.什么是二叉搜索树 3.什么是平衡二叉搜索树查找 4.如何使用平衡二叉搜索树查找 5.平衡二叉…

EBC金融英国CEO:高波动性周期下,如何寻找市场的稳定性?

利率主导的市场&#xff0c;将在2024年延续。目前&#xff0c;固收市场对于降息的定价&#xff0c;正通过利率传导至不同资产中。尽管市场迫切利用通胀去佐证降息&#xff0c;但各国央行仍囿于通胀目标的政策桎梏。政策和市场预期的博弈将继续牵动市场脉搏&#xff0c;引发价格…

英码科技携手昇腾共建算力底座:推出EA500I超强AI处理能力边缘计算盒子!

在数字经济浪潮中&#xff0c;算力已成为不可或缺的驱动力&#xff0c;为各行各业的数字化转型提供了强大的推动力。面对多元化和供需不平衡的挑战&#xff0c;需要实现从理论架构到软硬件实现的质的飞跃&#xff0c;以满足持续增长的算力需求&#xff0c;华为昇腾在这一方面展…

2024PMP考试新考纲-【业务环境领域】典型真题和很详细解析(2)

华研荟继续分享【业务环境Business Environment领域】在新考纲下的真题&#xff0c;帮助大家体会和理解新考纲下PMP的考试特点和如何应用所学的知识和常识&#xff08;经验&#xff09;来解题&#xff0c;并且举一反三&#xff0c;一次性3A通过2024年PMP考试。 2024年PMP考试新…

【每日一题】7.LeetCode——合并两个有序链表

&#x1f4da;博客主页&#xff1a;爱敲代码的小杨. ✨专栏&#xff1a;《Java SE语法》|《数据结构与算法》 ❤️感谢大家点赞&#x1f44d;&#x1f3fb;收藏⭐评论✍&#x1f3fb;&#xff0c;您的三连就是我持续更新的动力❤️ &#x1f64f;小杨水平有限&#xff0c;欢…

网络协议 UDP协议

网络协议 UDP协议 在之前的文章中有对UDP协议套接字的使用进行讲解&#xff0c;本文主要对UDP协议进行一些理论补充。 文章目录 网络协议 UDP协议1. 概念2. UDP协议格式2.1 数据报长度2.2 校验和/检验和2.2.1 CRC校验2.2.2 MD5算法 1. 概念 UDP&#xff0c;即User Datagram P…

使用阿里云的IDaaS实现知行之桥EDI系统的单点登录

&#xff0c;在开始测试之前&#xff0c;需要确定用哪个信息作为“登陆用户的ID字段”。 这个字段用来在完成SSO登陆之后&#xff0c;用哪个信息将阿里云IDaaS的用户和知行之桥EDI系统的用户做对应。这里我们使用了 phonenumber 这个自定义属性。需要在阿里云做如下配置&#x…

[力扣 Hot100]Day20 旋转图像

题目描述 给定一个 n n 的二维矩阵 matrix 表示一个图像。请你将图像顺时针旋转 90 度。 你必须在原地旋转图像&#xff0c;这意味着你需要直接修改输入的二维矩阵。请不要 使用另一个矩阵来旋转图像。 出处 思路 旋转时每四个位置为一组进行swap操作&#xff0c;找好对…

暴搜,回溯,剪枝

力扣77.组合 class Solution {List<List<Integer>>retnew ArrayList<>();List<Integer>pathnew ArrayList<>();int n; int k;public List<List<Integer>> combine(int _n, int _k) {n_n;k_k;dfs(1);return ret;}public void dfs(int…

MSVC++远程调试

1. 介绍 MSVC的调试功能非常强大&#xff0c;可以下断点&#xff0c;单步调试&#xff0c;查看堆栈变量信息等。实际用于生产的电脑环境复杂&#xff0c;更容易发生Bug。生产电脑&#xff0c;由于各种原因有些可能无法安装MSVC用来现场调试。基于打印日志&#xff0c;查看日志…

【DDD】学习笔记-限界上下文对架构的影响

通信边界对架构的影响 限界上下文的通信边界会对系统的架构产生直接的影响&#xff0c;在此之前&#xff0c;我们需要理清几个和边界有关的概念。如前所述&#xff0c;我提出了限界上下文的通信边界的概念&#xff0c;并将其分为进程内通信与进程间通信两种方式。在 Toby Clem…

grafana安装DevOpsProdigy KubeGraf 1.5.2

安装DevOpsProdigy KubeGraf需要安装kube-state-metrics 官方地址&#xff1a;https://github.com/kubernetes/kube-state-metrics/tree/release-2.10/examples/standard 查看k8s版本和kube-state-metrics对应版本&#xff1a; [rootmaster1 kube-state-metrics]# ll 总用量 …

C++ Web 编程

什么是 CGI&#xff1f; 公共网关接口&#xff08;CGI&#xff09;&#xff0c;是一套标准&#xff0c;定义了信息是如何在 Web 服务器和客户端脚本之间进行交换的。CGI 规范目前是由 NCSA 维护的&#xff0c;NCSA 定义 CGI 如下&#xff1a;公共网关接口&#xff08;CGI&…

人工智能福利站,初识人工智能,机器学习,第四课

&#x1f3c6;作者简介&#xff0c;普修罗双战士&#xff0c;一直追求不断学习和成长&#xff0c;在技术的道路上持续探索和实践。 &#x1f3c6;多年互联网行业从业经验&#xff0c;历任核心研发工程师&#xff0c;项目技术负责人。 &#x1f389;欢迎 &#x1f44d;点赞✍评论…

重写Sylar基于协程的服务器(3、协程模块的设计)

重写Sylar基于协程的服务器&#xff08;3、协程模块的设计&#xff09; 重写Sylar基于协程的服务器系列&#xff1a; 重写Sylar基于协程的服务器&#xff08;0、搭建开发环境以及项目框架 || 下载编译简化版Sylar&#xff09; 重写Sylar基于协程的服务器&#xff08;1、日志模…

一站式在线协作开源办公软件ONLYOFFICE,协作更安全更便捷

1、ONLYOFFICE是什么&#xff1f; ONLYOFFICE是一款功能强大的在线协作办公软件&#xff0c;可以创建编辑Word文档、Excel电子表格&#xff0c;PowerPoint&#xff08;PPT&#xff09;演示文稿、Forms表单等多种文件。ONLYOFFICE支持多个平台&#xff0c;无论使用的是 Windows、…

深入了解c语言字符串 2

深入了解c语言字符串 2 一 使用 scanf进行字符串的输入&#xff1a;1.1输入单词&#xff08;不包含空格&#xff09;&#xff1a;1.2 输入带空格的整行文本&#xff1a;1.3 处理输入缓冲区&#xff1a;1.4 注意安全性&#xff1a; 二 使用 printf 字符串的输出&#xff1a;三 输…

2024美赛C题全网最早思路 网球运动(持续更新)

2024美赛已经于今天早上6点准时公布题目。本次美赛将全程跟大家一起战斗冲刺O奖&#xff01;思路持续更新。 2024 MCM Problem C: Momentum in Tennis &#xff08;网球运动的势头&#xff09; 注&#xff1a;在网球运动中&#xff0c;"势头"通常指的是比赛中因一系…

Jmeter学习系列之五:线程组(Thread Group)

前言 线程组是一系列线程的集合,每一个线程代表着一个正在使用应用程序的用户。在 jmeter 中,每个线程意味着模拟一个真实用户向服务器发起请求。 在 jmeter 中,线程组组件运行用户设置线程数量、初始化方式等等配置。 例如,如果你设置线程数为 100,那么 jmeter 将创建…