import { NFProcess } from "./process"; import { NFNodeCfg, NFNodeType } from "./types"; import { NFEndNode } from "./node/endnode"; import { NFExclusiveNode } from "./node/exclusivenode"; import { NFInclusiveNode } from "./node/inclusivenode"; import { NFModuleNode } from "./node/modulenode"; import { NFNode } from "./node/node"; import { NFParallelNode } from "./node/parallelnode"; import { NFSequenceNode } from "./node/sequencenode"; import { NFStartNode } from "./node/startnode"; import { NFSubProcessNode } from "./node/subprocessnode"; import { NFUserTaskNode } from "./node/usertasknode"; import { NFWaitNode } from "./node/waitnode"; /** * 节点管理器:每个流程实例持有一份节点图。 */ export class NFNodeManager{ /** * 所属引擎 */ private process:NFProcess; /** * 当前节点 */ currentNode:NFNode; /** * 节点列表 */ private nodeList:NFNode[] = []; /** * 根据定义创建全部节点并执行 `init`。 * * @param process - 所属流程实例 * @param nodes - 节点配置数组(不含外层 `name`) */ constructor(process:NFProcess,nodes:NFNodeCfg[]){ this.process = process; // 先挂到 process,供节点 init 使用(否则构造未完成时 process.nodeManager 为空) process.nodeManager = this; this.initNodes(nodes); } /** * 按类型实例化节点并加入列表。 * * @param nodes - 节点配置数组 */ private initNodes(nodes:NFNodeCfg[]){ const rNodes = []; for(let n of nodes){ let node; switch(n.type){ case NFNodeType.START: node = new NFStartNode(n,this.process); break; case NFNodeType.END: node = new NFEndNode(n,this.process); break; case NFNodeType.USERTASK: node = new NFUserTaskNode(n,this.process); break; case NFNodeType.MODULETASK: node = new NFModuleNode(n,this.process); break; case NFNodeType.EXCLUSIVE: node = new NFExclusiveNode(n,this.process); break; case NFNodeType.INCLUSIVE: node = new NFInclusiveNode(n,this.process); break; case NFNodeType.PARALLEL: node = new NFParallelNode(n,this.process); break; case NFNodeType.WAIT: node = new NFWaitNode(n,this.process); break; case NFNodeType.SUBPROCESS: node = new NFSubProcessNode(n,this.process); break; default: //默认顺序流 node = new NFSequenceNode(n,this.process); break; } this.nodeList.push(node); } //执行节点初始化操作 this.doNodeInit(); } /** * 对带 `init` 的节点执行初始化(需全部节点构造完成)。 */ private doNodeInit(){ for(let node of this.nodeList){ if(node['init']){ node['init'].apply(node); } } } /** * 按定义 id 查找节点。 * * @param id - 节点 id * @returns 节点;未找到时为 `undefined` */ public getNodeById(id:string){ return this.nodeList.find(item=>item.id === id); } /** * 按类型查找第一个匹配节点。 * * @param type - 节点类型 * @returns 节点;未找到时为 `undefined` */ public getNodeByType(type:NFNodeType){ return this.nodeList.find(item=>item.type === type); } /** * 按名称查找节点。 * * @param name - 节点名 * @returns 节点;未找到时为 `undefined` */ public getNodeByName(name:string){ return this.nodeList.find(item=>item.name === name); } /** * 获取一条顺序流(默认相对当前节点)。 * * @param id - 源或目标节点 id;缺省为当前节点 * @param isDst - 为 `true` 时按目标节点查找 * @returns 顺序流节点;未找到时为 `null` */ getSequenceNode(id?:string,isDst?:boolean):NFSequenceNode{ if(!id){ id = this.currentNode?.id; } if(!id){ return null; } if(isDst){ return this.nodeList.find(item=>item.type === NFNodeType.SEQUENCE && item['dst'] === id); } return this.nodeList.find(item=>item.type === NFNodeType.SEQUENCE && item['src'] === id); } /** * 获取多条顺序流(网关分叉 / 汇聚用)。 * * @param id - 源或目标节点 id * @param isDst - 为 `true` 时按目标节点查找 * @returns 顺序流节点数组 */ getSequenceNodes(id:string,isDst?:boolean):NFSequenceNode[]{ if(isDst){ return this.nodeList.filter(item=>item.type === NFNodeType.SEQUENCE && item['dst'] === id); } return this.nodeList.filter(item=>item.type === NFNodeType.SEQUENCE && item['src'] === id); } /** * 设置当前节点。 * * @param node - 当前节点 */ setCurrentNode(node:NFNode){ this.currentNode = node; } /** * 获取当前节点。 * * @returns 当前节点 */ getCurrentNode():NFNode{ return this.currentNode; } }