276 lines
15 KiB
Transact-SQL
276 lines
15 KiB
Transact-SQL
/* ============================================================================
|
||
FMS 工作流模拟数据 —— 费用报销审批(expense_approval)
|
||
|
||
用途:给流程设计器 / 流程管理页造一份「够复杂」的样本,用来测试编辑体验。
|
||
不是业务模板,也不代表任何一家公司的真实审批制度。
|
||
|
||
刻意覆盖到的能力(对照《FMS工作流与审批设计》):
|
||
- 7 种节点类型全用到:start / user_task / cc_task / exclusive_gateway
|
||
/ parallel_gateway / service_task / end(§4.4)
|
||
- 6 种审批方式全用到:single / any / all / serial / n_of_m / percentage(§6.4)
|
||
- 条件分支(两条显式条件左右分开、再汇合到中间,合起来覆盖全部取值)、并行分支与汇合、抄送节点(§9.9)
|
||
- 8 种审批人解析类型中的 5 种:dept_manager / position / org_role / user(§6.6)
|
||
- 节点扩展配置:requiredCount(n_of_m)、requiredRatio(percentage)、
|
||
formPolicy(只读/必填字段)、dueHours、allowClaim、commentRequired
|
||
|
||
前置条件:wf_* 表已由 fms_workflow.sql 建好。
|
||
使用说明:
|
||
1. 执行前先切换到目标数据库(USE FMS)。
|
||
2. 本脚本可重复执行:先按流程编码清理本流程的版本/节点/连线/规则,再重建。
|
||
3. 只写 wf_definition / wf_version / wf_node / wf_edge / wf_actor_rule;
|
||
不写 wf_binding(绑哪个模块是实施决定),也不写任何运行表。
|
||
|
||
流程走向(两条条件分支都是左右分开、再汇合到中间):
|
||
开始 → 部门负责人审批(或签) → 金额判断
|
||
├─ 金额 > 10000 → 总经理审批(单人) ┐
|
||
└─ 金额 <= 10000 → 财务复核(会签) ┴→ 并行分支
|
||
├→ 法务串行会签(串行) ┐
|
||
├→ 抄送财务总监(抄送) ├→ 并行汇合 → 是否超阈值
|
||
└→ 风控按比例通过(0.6)┘ ├─ 金额 >= 50000 → 董事长审批(N 人通过,2 人) ┐
|
||
└─ 金额 < 50000 → 归档 ────────────────────┴→ 结束
|
||
============================================================================ */
|
||
|
||
SET NOCOUNT ON;
|
||
|
||
declare @def varchar(50) = 'expense_approval';
|
||
declare @ver varchar(50) = 'expense_approval_v1';
|
||
declare @by varchar(50) = 'g3soft';
|
||
declare @now datetime2 = sysutcdatetime();
|
||
|
||
/* ----------------------------------------------------------------------------
|
||
1. 清理(脚本可重复执行):只动本流程自己的行
|
||
---------------------------------------------------------------------------- */
|
||
|
||
delete from dbo.wf_actor_rule
|
||
where b_version_id in (select b_id from dbo.wf_version where b_definition_id = @def);
|
||
|
||
delete from dbo.wf_edge
|
||
where b_version_id in (select b_id from dbo.wf_version where b_definition_id = @def);
|
||
|
||
delete from dbo.wf_node
|
||
where b_version_id in (select b_id from dbo.wf_version where b_definition_id = @def);
|
||
|
||
delete from dbo.wf_binding
|
||
where b_version_id in (select b_id from dbo.wf_version where b_definition_id = @def);
|
||
|
||
delete from dbo.wf_version where b_definition_id = @def;
|
||
delete from dbo.wf_definition where b_id = @def;
|
||
|
||
/* ----------------------------------------------------------------------------
|
||
2. 流程定义 + 版本
|
||
|
||
b_canvas_json 只放界面布局(节点坐标),不参与执行(§6.2)。
|
||
格式与设计器 domain 层约定一致:{ schemaVersion, nodes: { <nodeKey>: {x,y} } }
|
||
坐标是纵向(TB)排布:主干在 x=520 的中线上,两个条件分支的两条支线分别落在中线
|
||
左右(x=240 / x=800),到汇合节点再回到中线。
|
||
---------------------------------------------------------------------------- */
|
||
|
||
insert into dbo.wf_definition (b_id, b_name, b_i18n, b_canuse, b_bz,
|
||
b_created_by, b_created_at, b_updated_by, b_updated_at)
|
||
values (@def, N'费用报销审批', 'workflow.expense_approval', 1,
|
||
N'模拟数据:覆盖条件分支、并行、会签、串行会签、N 人通过、按比例通过与抄送',
|
||
@by, @now, @by, @now);
|
||
|
||
insert into dbo.wf_version (b_id, b_definition_id, b_version_no, b_status, b_schema_version,
|
||
b_canvas_json, b_checksum, b_published_by, b_published_at, b_bz,
|
||
b_created_by, b_created_at, b_updated_by, b_updated_at)
|
||
values (@ver, @def, 1, 'published', 1,
|
||
N'{
|
||
"schemaVersion": 1,
|
||
"nodes": {
|
||
"start": { "x": 520, "y": 60 },
|
||
"dept_manager": { "x": 520, "y": 170 },
|
||
"amount_gateway": { "x": 520, "y": 280 },
|
||
"gm_approve": { "x": 240, "y": 400 },
|
||
"finance_review": { "x": 800, "y": 400 },
|
||
"parallel_split": { "x": 520, "y": 520 },
|
||
"legal_countersign": { "x": 200, "y": 640 },
|
||
"cc_cfo": { "x": 520, "y": 640 },
|
||
"risk_review": { "x": 840, "y": 640 },
|
||
"parallel_join": { "x": 520, "y": 760 },
|
||
"big_amount_gateway":{ "x": 520, "y": 870 },
|
||
"chairman_approve": { "x": 240, "y": 990 },
|
||
"archive": { "x": 800, "y": 990 },
|
||
"end": { "x": 520, "y": 1110 }
|
||
}
|
||
}',
|
||
'mock-checksum-expense_approval_v1', @by, @now, N'模拟数据:已发布版本',
|
||
@by, @now, @by, @now);
|
||
|
||
/* ----------------------------------------------------------------------------
|
||
3. 节点(14 个)
|
||
|
||
b_approval_mode / b_reject_mode / b_due_hours 是常用列;
|
||
requiredCount、requiredRatio、formPolicy 等低频配置进 b_config_json(§6.4)。
|
||
---------------------------------------------------------------------------- */
|
||
|
||
insert into dbo.wf_node (b_id, b_version_id, b_node_key, b_name, b_node_type,
|
||
b_approval_mode, b_reject_mode, b_due_hours, b_config_json, b_xh, b_canuse)
|
||
values
|
||
-- 开始
|
||
('n_exp_start', @ver, 'start', N'开始', 'start',
|
||
null, null, null, null, 10, 1),
|
||
|
||
-- 部门负责人审批:或签(部门负责人 或 分管副总 任一人通过即可)
|
||
('n_exp_dept_manager', @ver, 'dept_manager', N'部门负责人审批', 'user_task',
|
||
'any', 'return_initiator', 24,
|
||
N'{"schemaVersion":1,"allowInitiator":false,"excludePreviousActors":true,"allowClaim":true,"commentRequired":false,"formPolicy":{"readonly":[],"required":["b_reason"]}}',
|
||
20, 1),
|
||
|
||
-- 条件分支:金额判断
|
||
('n_exp_amount_gateway', @ver, 'amount_gateway', N'金额判断', 'exclusive_gateway',
|
||
null, null, null, null, 30, 1),
|
||
|
||
-- 总经理审批:单人
|
||
('n_exp_gm_approve', @ver, 'gm_approve', N'总经理审批', 'user_task',
|
||
'single', 'terminate', 48,
|
||
N'{"schemaVersion":1,"allowInitiator":false,"excludePreviousActors":true,"allowClaim":false,"commentRequired":true,"formPolicy":{"readonly":["b_amount","b_dept_id"],"required":[]}}',
|
||
40, 1),
|
||
|
||
-- 财务复核:会签(全部通过)
|
||
('n_exp_finance_review', @ver, 'finance_review', N'财务复核', 'user_task',
|
||
'all', 'terminate', 24,
|
||
N'{"schemaVersion":1,"allowInitiator":false,"excludePreviousActors":true,"allowClaim":false,"commentRequired":false,"formPolicy":{"readonly":["b_amount"],"required":[]}}',
|
||
50, 1),
|
||
|
||
-- 并行分支
|
||
('n_exp_parallel_split', @ver, 'parallel_split', N'并行分支', 'parallel_gateway',
|
||
null, null, null, null, 60, 1),
|
||
|
||
-- 法务串行会签:按 wf_actor_rule.b_priority 逐个激活
|
||
('n_exp_legal_countersign', @ver, 'legal_countersign', N'法务串行会签', 'user_task',
|
||
'serial', 'return_previous', 72,
|
||
N'{"schemaVersion":1,"allowInitiator":false,"excludePreviousActors":true,"allowClaim":false,"commentRequired":true,"formPolicy":{"readonly":[],"required":[]}}',
|
||
70, 1),
|
||
|
||
-- 抄送财务总监:不产生待办,节点激活即完成
|
||
('n_exp_cc_cfo', @ver, 'cc_cfo', N'抄送财务总监', 'cc_task',
|
||
null, null, null,
|
||
N'{"schemaVersion":1,"commentRequired":false}', 80, 1),
|
||
|
||
-- 风控按比例通过:requiredRatio 在节点激活时换算成应签人数
|
||
('n_exp_risk_review', @ver, 'risk_review', N'风控按比例通过', 'user_task',
|
||
'percentage', 'terminate', 48,
|
||
N'{"schemaVersion":1,"allowInitiator":false,"excludePreviousActors":true,"allowClaim":false,"commentRequired":false,"requiredRatio":0.6,"formPolicy":{"readonly":[],"required":[]}}',
|
||
90, 1),
|
||
|
||
-- 并行汇合
|
||
('n_exp_parallel_join', @ver, 'parallel_join', N'并行汇合', 'parallel_gateway',
|
||
null, null, null, null, 100, 1),
|
||
|
||
-- 条件分支:是否超阈值
|
||
('n_exp_big_amount_gateway', @ver, 'big_amount_gateway', N'是否超阈值', 'exclusive_gateway',
|
||
null, null, null, null, 110, 1),
|
||
|
||
-- 董事长审批:N 人通过(3 个候选人里 2 人通过即完成)
|
||
('n_exp_chairman_approve', @ver, 'chairman_approve', N'董事长审批', 'user_task',
|
||
'n_of_m', 'terminate', 72,
|
||
N'{"schemaVersion":1,"allowInitiator":false,"excludePreviousActors":true,"allowClaim":false,"commentRequired":true,"requiredCount":2,"formPolicy":{"readonly":[],"required":[]}}',
|
||
120, 1),
|
||
|
||
-- 服务节点:归档(第一阶段只占位,不执行)
|
||
('n_exp_archive', @ver, 'archive', N'归档', 'service_task',
|
||
null, null, null,
|
||
N'{"schemaVersion":1,"serviceKey":"expense_archive"}', 130, 1),
|
||
|
||
-- 结束
|
||
('n_exp_end', @ver, 'end', N'结束', 'end',
|
||
null, null, null, null, 140, 1);
|
||
|
||
/* ----------------------------------------------------------------------------
|
||
4. 连线(17 条)
|
||
|
||
b_condition_json 为 null 表示无条件的兜底分支。本样本两条条件分支都写成显式条件,
|
||
两条合起来覆盖全部取值,不依赖兜底(§6.5)。
|
||
b_priority 小的先判断。
|
||
---------------------------------------------------------------------------- */
|
||
|
||
insert into dbo.wf_edge (b_id, b_version_id, b_from_node_key, b_to_node_key, b_name,
|
||
b_condition_json, b_priority, b_canuse, b_bz)
|
||
values
|
||
('e_exp_01', @ver, 'start', 'dept_manager', null, null, 10, 1, null),
|
||
('e_exp_02', @ver, 'dept_manager', 'amount_gateway', null, null, 10, 1, null),
|
||
|
||
-- 金额判断:> 10000 走总经理,<= 10000 走财务复核。两条都是显式条件,合起来覆盖全部金额
|
||
('e_exp_03', @ver, 'amount_gateway', 'gm_approve', N'金额大于 1 万',
|
||
N'{"field":"b_amount","operator":"gt","value":10000}', 10, 1, null),
|
||
('e_exp_04', @ver, 'amount_gateway', 'finance_review', N'金额不大于 1 万',
|
||
N'{"field":"b_amount","operator":"le","value":10000}', 20, 1, null),
|
||
-- 总经理审批 → 并行分支:与「财务复核」并列,两条支线在并行分支汇合
|
||
('e_exp_05', @ver, 'gm_approve', 'parallel_split', null, null, 10, 1, null),
|
||
('e_exp_06', @ver, 'finance_review', 'parallel_split', null, null, 10, 1, null),
|
||
|
||
-- 并行分支:三条出线同时激活
|
||
('e_exp_07', @ver, 'parallel_split', 'legal_countersign', null, null, 10, 1, null),
|
||
('e_exp_08', @ver, 'parallel_split', 'cc_cfo', null, null, 20, 1, null),
|
||
('e_exp_09', @ver, 'parallel_split', 'risk_review', null, null, 30, 1, null),
|
||
|
||
-- 并行汇合:三条支线全部到达后才继续
|
||
('e_exp_10', @ver, 'legal_countersign', 'parallel_join', null, null, 10, 1, null),
|
||
('e_exp_11', @ver, 'cc_cfo', 'parallel_join', null, null, 10, 1, null),
|
||
('e_exp_12', @ver, 'risk_review', 'parallel_join', null, null, 10, 1, null),
|
||
('e_exp_13', @ver, 'parallel_join', 'big_amount_gateway',null, null, 10, 1, null),
|
||
|
||
-- 是否超阈值:>= 50000 走董事长审批,< 50000 走归档。两条都是显式条件,合起来覆盖全部金额
|
||
('e_exp_14', @ver, 'big_amount_gateway','chairman_approve', N'金额大于等于 5 万',
|
||
N'{"field":"b_amount","operator":"ge","value":50000}', 10, 1, null),
|
||
('e_exp_15', @ver, 'big_amount_gateway','archive', N'金额小于 5 万',
|
||
N'{"field":"b_amount","operator":"lt","value":50000}', 20, 1, null),
|
||
-- 董事长审批 → 结束:与「归档」并列,两条支线在结束汇合
|
||
('e_exp_16', @ver, 'chairman_approve', 'end', null, null, 10, 1, null),
|
||
('e_exp_17', @ver, 'archive', 'end', null, null, 10, 1, null);
|
||
|
||
/* ----------------------------------------------------------------------------
|
||
5. 审批人 / 抄送人规则
|
||
|
||
解析规则执行后必须把规则快照写进运行表(§6.6);这里只配规则本身。
|
||
b_priority 既是串行会签的顺序来源,也是同类型规则的判断顺序。
|
||
---------------------------------------------------------------------------- */
|
||
|
||
insert into dbo.wf_actor_rule (b_id, b_version_id, b_node_key, b_actor_type, b_actor_ref,
|
||
b_resolve_json, b_condition_json, b_fallback_type, b_fallback_ref,
|
||
b_priority, b_canuse, b_bz)
|
||
values
|
||
-- 部门负责人审批(或签):发起人所属部门负责人 或 分管副总
|
||
('r_exp_dm_1', @ver, 'dept_manager', 'dept_manager', null, null, null, 'admin', null, 10, 1, N'发起人或业务归属部门负责人'),
|
||
('r_exp_dm_2', @ver, 'dept_manager', 'position', 'vice_president', null, null, 'admin', null, 20, 1, N'分管副总'),
|
||
|
||
-- 总经理审批(单人)
|
||
('r_exp_gm_1', @ver, 'gm_approve', 'position', 'gm', null, null, 'admin', null, 10, 1, N'总经理岗'),
|
||
|
||
-- 财务复核(会签):两条规则 → 两名审批人都必须通过
|
||
('r_exp_fr_1', @ver, 'finance_review', 'org_role', 'finance', null, null, 'admin', null, 10, 1, N'财务组织角色'),
|
||
('r_exp_fr_2', @ver, 'finance_review', 'position', 'finance_manager', null, null, 'admin', null, 20, 1, N'财务经理岗'),
|
||
|
||
-- 法务串行会签(串行):按 priority 10 → 20 → 30 逐个激活
|
||
('r_exp_lc_1', @ver, 'legal_countersign', 'org_role', 'legal_lead', null, null, 'admin', null, 10, 1, N'法务负责人(第一个签)'),
|
||
('r_exp_lc_2', @ver, 'legal_countersign', 'user', 'U001', null, null, 'admin', null, 20, 1, N'指定用户(第二个签)'),
|
||
('r_exp_lc_3', @ver, 'legal_countersign', 'position', 'legal_staff', null, null, 'admin', null, 30, 1, N'法务专员(第三个签)'),
|
||
|
||
-- 抄送财务总监(抄送):不产生待办
|
||
('r_exp_cc_1', @ver, 'cc_cfo', 'org_role', 'cfo', null, null, 'none', null, 10, 1, N'财务总监'),
|
||
|
||
-- 风控按比例通过(3 名候选人里过 60% → 2 人)
|
||
('r_exp_rr_1', @ver, 'risk_review', 'org_role', 'risk', null, null, 'admin', null, 10, 1, N'风控组织角色'),
|
||
('r_exp_rr_2', @ver, 'risk_review', 'position', 'risk_manager', null, null, 'admin', null, 20, 1, N'风控经理岗'),
|
||
('r_exp_rr_3', @ver, 'risk_review', 'user', 'U002', null, null, 'admin', null, 30, 1, N'指定用户'),
|
||
|
||
-- 董事长审批(N 人通过,requiredCount = 2)
|
||
('r_exp_ca_1', @ver, 'chairman_approve', 'user', 'U001', null, null, 'admin', null, 10, 1, N'候选人一'),
|
||
('r_exp_ca_2', @ver, 'chairman_approve', 'user', 'U002', null, null, 'admin', null, 20, 1, N'候选人二'),
|
||
('r_exp_ca_3', @ver, 'chairman_approve', 'user', 'U003', null, null, 'admin', null, 30, 1, N'候选人三');
|
||
|
||
/* ----------------------------------------------------------------------------
|
||
6. 自检
|
||
---------------------------------------------------------------------------- */
|
||
|
||
select N'流程定义' as 项, count(*) as 行数 from dbo.wf_definition where b_id = @def
|
||
union all
|
||
select N'流程版本', count(*) from dbo.wf_version where b_definition_id = @def
|
||
union all
|
||
select N'节点', count(*) from dbo.wf_node where b_version_id = @ver
|
||
union all
|
||
select N'连线', count(*) from dbo.wf_edge where b_version_id = @ver
|
||
union all
|
||
select N'审批人规则', count(*) from dbo.wf_actor_rule where b_version_id = @ver;
|