流程引擎BPM设计之:流程消息
# .流程引擎BPM设计之:流程消息
| 项目 | 内容 |
|------|------|
| **文档名称** | .流程引擎BPM设计之:流程消息 |
| **文档编号** | ZTE-CCBPM-FLOW-MSG-2026-001 |
| **版本号** | V1.0 |
| **密级** | 内部公开 |
| **编制日期** | 2026-07-20 |
| **编制依据** | `PushMsg`、`SMS`、`ExecEvent`、`Dev2Interface.Port_SendMessage`、`Node.HisPushMsgs`、`Flow.PushMsgs`、管理端 `NodeMsg` / `FlowExt` |
| **适用范围** | 流程消息体系宣讲、消息通道选型、项目交付规范、团队技术路线评估 |
---
## 修订记录
| 版本 | 日期 | 修订人 | 说明 |
|------|------|--------|------|
| V1.0 | 2026-07-20 | — | 初版:流程消息定义、设备通道、内容类型、设计主张与设计记录、CCFlow/JFlow 实证 |
---
## 摘要
驰骋 BPM 主张:**事件负责「发生了什么」,消息负责「告诉谁、用什么说、从哪打开」。**
在事件执行过程中,需要把执行内容与结果,传递给该流程实例上相关人员——这一能力,我们称为**流程消息**。
事件分流程事件与节点事件;消息同样分**流程消息**与**节点消息**。二者共用事件时钟(如 `SendSuccess`、`WorkArrive`、`FlowOverAfter`),但配置独立、职责清晰:事件跑业务,消息做触达。
本文说明驰骋 BPM 对「流程消息」的设计思想与主张,重点记录关键设计决策,并以 **驰骋 BPM(CCFlow / JFlow)** 为实现对照。
---
## 一、什么是流程消息
### 1.1 定义
> **流程消息** = 在事件执行过程中,把执行的内容与结果,传递给该流程实例上相关人员的过程。
典型场景:发送成功时,把提醒推给当事人(下一节点接收人)、其他节点人员(如申请人)、以及表单字段上的人员。
| 对比项 | 只跑事件、不推消息 | 流程消息体系 |
|--------|-------------------|--------------|
| 用户感知 | 业务已变,人不知晓 | 人在合适通道被触达 |
| 配置位置 | 外挂 / 事件脚本里硬编码通知 | 独立消息配置,按事件挂接 |
| 通道扩展 | 每加一种 IM 就改业务代码 | 设备可插拔,内容模板复用 |
| 打开工作 | 手工拼 URL、难鉴权 | 统一超链接 + Token 校验 |
### 1.2 驰骋的主张
> **主张一:消息是事件的一等产出,不是售后补丁。**
> 发送成功、工作到达、退回、移交、流程结束——这些时钟点上,消息与业务脚本并列配置。
> **主张二:事件管逻辑,消息管触达。**
> 不要在二开里到处 `Port_SendMsg` 散落;优先用消息模板绑定事件,二开只补例外。
> **主张三:人、内容、设备三分离。**
> 「发给谁」「说什么」「用哪类设备接」各自可配,组合而不是绑死。
> **主张四:能打开,才算送达。**
> 消息不是纯文本广播;内容里应有可点开的超链接,且链接必须经 Token 校验合法性。
---
## 二、流程消息总览
### 2.1 与事件对称
| 维度 | 事件 | 消息 |
|------|------|------|
| 分类 | 流程事件 / 节点事件 | 流程消息 / 节点消息 |
| 挂接点 | `SendWhen`、`SendSuccess`、`FlowOverAfter`… | 同一套事件标记(`EventNo`) |
| 职责 | 校验、改数据、调外部系统 | 选人、组文案、推设备 |
| 配置入口 | 节点/流程事件、外挂 | 节点消息、流程消息 |
### 2.2 发送成功时的典型触达
```
用户点击发送 → 引擎流转成功(SendSuccess / WorkArrive)
│
├─ 当事人:下一节点接收人(待办提醒)
├─ 相关人:申请人、指定节点处理人、抄送人等
└─ 字段人:表单上「经办人」「抄送对象」等字段人员
│
└─ 按消息设备分发(站内信 / IM / 短信 / 邮件 / 企微 / 钉钉 / 飞书 / App…)
```
### 2.3 谁该收到消息
| 推送对象思路 | 含义 | 典型用途 |
|--------------|------|----------|
| 当前待办人 | 下一节点(或当前)应处理的人 | 工作到达、发送成功 |
| 指定节点工作人员 | 历史上在某节点办过的人 | 知会申请人上级节点 |
| 指定人员 / 角色 / 部门 | 配置名单或组织范围 | 合规抄送、监察 |
| 按 SQL / 数据源 | 动态算出接收人 | 复杂组织规则 |
| 表单字段 | 字段值即人员编号 | 业务自选抄送人 |
| 流程发起人 | Starter | 「办完了通知申请人」 |
---
## 三、消息设备:接受消息的载体
> **消息设备** = 用于接受消息的载体。
| 设备类型 | 适合内容形态 | 说明 |
|----------|--------------|------|
| 站内信 | 邮件格式(标题 + 正文) | 系统内提醒中心、可回看 |
| 即时通讯(IM) | 短消息 | 企业内部 IM、会话提醒 |
| 手机短信 | 短消息 | 强触达、内容宜短 |
| 邮件 | 邮件格式 | 标题 + 富文本正文 + 链接 |
| 企业微信 | 短消息为主 | 组织内工作通知 |
| 钉钉 | 短消息为主 | 组织内工作通知 |
| 飞书 | 短消息为主 | 组织内工作通知 |
| App 推送 | 短消息为主 | 移动端角标 / 推送栏 |
**设计要点**:设备是通道,不是业务。同一条消息配置,可勾选多种设备;全局开关与节点级勾选可并存,便于「公司默认策略 + 流程个性策略」。
---
## 四、事件内容类型:短消息与邮件格式
根据场景不同,内容分为两类:
| 类型 | 结构 | 适合设备 |
|------|------|----------|
| **短消息** | 一段内容输出 | 短信、IM、企微 / 钉钉 / 飞书、App |
| **邮件格式** | 标题 + 主体内容 | 站内信、邮件 |
> **设计记录 R1:内容类型按「设备消费能力」划分,不按「业务事件」划分。**
> 同一 `SendSuccess` 事件,可同时启用短消息模板与邮件模板;不是为每个事件发明第三种格式。
| 字段语义(抽象) | 短消息 | 邮件格式 |
|------------------|--------|----------|
| 标题 | 可有可无(部分设备用摘要) | **必需** |
| 正文 | 一段文本 | 主体内容(可较长) |
| 超链接 | 内嵌或附后 | 正文中的 `{Url}` |
---
## 五、事件内容定义与打开超链接
### 5.1 内容定义
事件消息内容需要支持**个性化设置**,通常包含:
1. **标题**(邮件格式必备)——可用 `{Title}`、`@WebUser.Name` 等变量
2. **内容**——可用流程名、节点名、单号、退回意见等变量
3. **连接**——用户点击后打开工作页面
示例(语义示意):
- 短消息:`有新工作{{Title}}需要您处理,发送人:@WebUser.Name,打开{Url}`
- 邮件标题:`新工作{{Title}},发送人@WebUser.Name`
- 邮件正文:`您好,有新工作需要处理,点击这里打开 {Url}`
### 5.2 打开超链接与 Token
> **打开超链接**:消息设备上的链接,必须能安全打开目标页面——需要带 **Token(加密字符串)**,用于身份与合法性校验。
设计要求:
| 要求 | 说明 |
|------|------|
| 可点开 | 邮件 / 站内信 / IM 卡片都能落到同一「打开工作」语义 |
| 可校验 | Token 与人员、WorkID、节点等信息绑定,拒绝伪造链接 |
| 可替换 | URL 中可含接收人占位(如按人替换 Emp),一人一链 |
| 可跨端 | PC、移动、第三方 App WebView 共用打开协议 |
**没有 Token 的链接,不应被视为合格的流程消息出口。**
---
## 六、设计记录(重点)
### R1. 消息与事件同时钟、分配置
事件执行完后,按 `EventNo` 匹配消息条目再推送。
业务二开与消息推送都挂在 `SendSuccess` 等点上,但**存储与配置界面分离**,避免「改通知必须改代码」。
### R2. 流程消息 / 节点消息对称于流程事件 / 节点事件
- 节点消息:绑定节点,适合「本节点发送成功通知下家」
- 流程消息:绑定流程,适合「流程结束通知发起人」等跨节点语义
同一产品能力,两级挂接,实施时按粒度选型。
### R3. 人、文案、设备三轴正交
| 轴 | 配置什么 | 为何独立 |
|----|----------|----------|
| 人 | PushWay:待办人 / 字段 / SQL / 指定人… | 组织规则变化频繁 |
| 文案 | SMSDoc / MailTitle / MailDoc | 话术与合规文案常改 |
| 设备 | 站内信、邮件、钉钉、企微… | 企业 IT 通道各不相同 |
### R4. 短消息与邮件格式双轨,而不是「万能正文」
IM/短信吃不了长 HTML;邮件/站内信又需要标题与主体。
双轨模板是故意的产品决策,降低「一条内容适配所有设备」的失败率。
### R5. 默认模板保底,个性化可覆盖
每个事件类型提供默认标题/正文模板;未配置时仍可提醒。
配置了则覆盖默认——保证「开箱能用」,也保证「项目可定制」。
### R6. 先入库、再分发;消息可消噪
消息先写入统一消息表(带 MsgFlag / MsgType / WorkID),再按设备发送。
流程结束、删除等节点可清理过期待办提醒,避免「流程已结束,站内信还在催」。
### R7. 超链接必须可鉴权
打开 URL 携带 Token(或等价安全串)。
从消息点进系统 = 受控登录/打开工作,而不是裸露 WorkID 的公开地址。
### R8. 机器节点默认可不推人
纯机器执行的节点(无人待办)在到达/发送成功时,可不推送人工消息——消息是给人的,不是给自动机的。
---
## 七、设计思想小结(宣传要点)
1. **流程消息是正式产品能力**:事件发生后,相关人必须被系统化触达。
2. **与事件对称分类**:流程消息 / 节点消息,跟流程事件 / 节点事件同构。
3. **设备可插拔**:站内信、短信、邮件、企微、钉钉、飞书、App 都是消息设备。
4. **内容分型**:短消息一段话;邮件格式要标题 + 主体。
5. **内容可个性化**:变量替换 + 超链接,点开即办。
6. **链接必鉴权**:Token 校验合法性,安全与体验一体设计。
7. **消息与二开解耦**:同一事件点,脚本跑业务,消息做通知。
---
## 八、以驰骋 BPM(CCFlow / JFlow)为例
以下用驰骋 BPM 开源引擎 **CCFlow(.NET)** 与 **JFlow(Java)** 说明上述思想如何落地。二者消息模型同源:事件名、`PushMsg` 配置、`Sys_SMS` 落库、设备分发思想一致,差异主要在语言与宿主集成。
### 8.1 统一调度:事件之后推消息
服务端 `ExecEvent` 在执行节点/流程事件后,进入「处理消息推送」:
1. 仅对有消息意义的事件放行(如 `WorkArrive`、`SendSuccess`、`ReturnAfter`、`ShitAfter`、`FlowOverAfter` 等)
2. 读取节点的 `HisPushMsgs`(或流程的 `PushMsgs`)
3. 按 `EventNo == doType` 匹配条目
4. 调用 `PushMsg.DoSendMessage(...)` 生成文案并分发
这直接对应本文「事件与消息同时钟、分配置」。
### 8.2 配置实体:`WF_PushMsg` / `PushMsg`
| 能力 | 落点 |
|------|------|
| 挂接事件 | `EventNo`(与节点/流程事件列表一致) |
| 推给谁 | `PushWayNo`:`TodoEmps` / `Field` / `NodeWorker` / `BySQL` / `SpecEmpNo` / `Starter` 等 |
| 短消息 | `IsEnableSMS` + `SMSDoc` |
| 邮件格式 | `IsEnableEmail` + `MailTitle` + `MailDoc` |
| 设备勾选 | `Msg`(站内)、`DD`(钉钉)、`WeChat`(企微)、邮件/短信等 |
| 打开链接 | `DoSendMessage` 生成 `OpenUrl`,经 `Port_SendMessage` 写入 |
管理端:
- 节点属性 → **节点消息**(`NodeExt` → `PushMsgs`)
- 流程属性 → **流程消息**(`FlowExt` → `PushMsgs`)
- 编辑界面可见「短消息推送」「邮件」分组(如 `NMGener`)
### 8.3 内容模板:默认值 + 变量
CCFlow 中 `PushMsg.MailTitle` / `MailDoc` / `SMSDoc` 在空配置时按事件给出默认模板,例如发送成功:
- 短消息:`有新工作{{Title}}需要您处理, 发送人:@WebUser.No, @WebUser.Name,打开{Url}`
- 邮件标题:`新工作{{Title}},发送人@WebUser.No,@WebUser.Name`
- 邮件正文:含标题、单号、`{Url}` 等
运行时替换 `{Title}`、`{FlowName}`、`{NodeName}`、`@WebUser.*`,并支持表单字段表达式继续替换。
### 8.4 消息落库与设备发送:`Sys_SMS` / `SMS`
`Dev2Interface.Port_SendMessage` 写入 `SMS` 实体:
- 邮件侧:`Title`、`DocOfEmail`
- 短消息侧:`MobileInfo`
- 扩展:`OpenUrl`、`PushModel`、提醒规则等
实际发往邮件 / 钉钉 / 企业微信等时,由 `SMS.SendMessage` 结合**全局开关**与消息上的 **PushType** 决定走哪些设备;亦可经 `OverrideEvent.SendToEmail` / `SendToDingDing` / `SendToWeiXin` 做企业定制。
### 8.5 超链接与 Token
`PushMsg.DoSendMessage` 生成打开地址(示意):
```text
HostVue3URL + "#/WF/Port?DoWhat=OF&Token=" + GUID_WorkID_{EmpStr}_NodeID
```
要点:
- `Token`(此处为安全串 `sid`)绑定工作与接收人占位
- 按接收人替换 `{EmpStr}`,一人一链
- 消息设备上点击后走统一 Port 打开协议,再校验合法性
这对应本文主张四:「能打开,且打开可鉴权」。
### 8.6 一句话对照
| 思想 | 在 CCFlow / JFlow 中的落点 |
|------|----------------------------|
| 流程消息定义 | 事件后的 `PushMsg` 推送 |
| 流程消息 / 节点消息 | `Flow.PushMsgs` / `Node.HisPushMsgs` |
| 消息设备 | 站内信、邮件、钉钉、企微等 + `OverrideEvent` 扩展 |
| 短消息 / 邮件格式 | `SMSDoc` vs `MailTitle`+`MailDoc` |
| 内容个性化 | 默认模板 + 变量替换 |
| 打开超链接 | `OpenUrl` + Token/`sid` 校验语义 |
| 统一出口 | `Port_SendMessage` → `Sys_SMS` |
### 8.7 与「流程二开」的关系
同一事件点上:
| 能力 | 做什么 |
|------|--------|
| 前端/后端外挂、事件配置 | 业务校验、改接收人、调 ERP |
| 流程/节点消息 | 通知人、选设备、组文案、给链接 |
二者并列,不互相替代。需要个性化通知时优先配 `PushMsg`;只有通道或文案规则引擎覆盖不了时,再在二开里调用 `Port_SendMsg` / `Port_SendMessage`。
---
## 结语
驰骋 BPM 对流程消息的态度很明确:
> **事件发生了,相关人就该被通知到;通知要分人、分文案、分设备,并且点开链接必须能安全打开工作——消息不是日志,而是流程体验的一部分。**
以 CCFlow / JFlow 为证:流程消息与节点消息、短消息与邮件格式、多消息设备、Token 打开链路,都是源码里可配置、可运行、可交付的工程现实。
---
## 附录:关键源码索引(便于二次开发)
| 主题 | CCFlow / Vue3 路径(示例) |
|------|----------------------------|
| 消息推送实体 | `CCFlow/Components/BP.WF/Template/PushMsg.cs` |
| 消息落库与设备发送 | `CCFlow/Components/BP.WF/SMS.cs` |
| 发送 API | `CCFlow/Components/BP.WF/Dev2Interface.cs`(`Port_SendMessage` / `Port_SendMsg`) |
| 事件后推消息 | `CCFlow/Components/BP.WF/WF/ExecEvent.cs` |
| 节点默认消息 | `CCFlow/Components/BP.WF/WF/Node.cs`(`HisPushMsgs`) |
| 流程消息集合 | `CCFlow/Components/BP.WF/WF/Flow.cs`(`PushMsgs`) |
| 管理端-节点消息 | `Vue3/src/WF/Admin/AttrNode/NodeMsg/` |
| 管理端-流程消息 | `Vue3/src/WF/Admin/AttrFlow/FlowExt.ts` |
| 设备扩展点 | `OverrideEvent.SendToEmail` / `SendToDingDing` / `SendToWeiXin` |
---
*本文档属于「.流程引擎BPM设计之」系列,侧重设计思想与主张;具体 API 与设备开关以当期产品帮助与源码为准。*

浙公网安备 33010602011771号