当前位置: 首页 > news >正文

E8-写了一个存储过程,用来更新流程的对应版本

起因

需求的来源是这样式儿的,我们公司某个部门,原来由副总分管,本月做了组织架构调整,副总和部门经理之间增加了总监,导致不得不大量的修改涉及到的路径,给路径创建一个新版本,增加总监节点,再修各节点的表单。整个调整周期会很长,甚至有调漏掉了的路径。而且还发生了在我发布新版本之前,已经有同事已经发起了流程。

归纳一下其实就是路径的版本切换不及时,有按旧版本发起的流程需要调整成新版本。局限是新版本相比旧版本变化不大,仅是新增了节点。这种问题可以按下面的方法处理。

为了更新这些本该用新版本发起的流程,我写了一个存储过程,输入参数是要更新的requestid,输出参数状态标识@returnFlg、状态文本@returnMsg。

经过

数据结构并不复杂,最大的困难在找节点之间的关系,在泛微其自身的数据结构里是没有记录不同版本的节点之间的关系的。在这存储过程里我先后 了节点的名称和节点的位置作为线索去做判定的,如果两个版本中存在同名的节点,认为是同一个节点。如果根据节点名称没有找到相同节点的话,那就看两个版本中存在不存在位置相近的节点,如果存在,认为是同一个节点。

CREATE procedure workflow_RequestVersion_Update
@requestid int,
@returnFlg nvarchar(1) output,
@returnMsg nvarchar(1000) output

as


-- 0.1 定义需要用取的变量
declare @workflowidOld int, -- 工作流id(当前的)
@workflowidNew int, -- 工作流id(新的)
@workflowname varchar(1000), -- 工作流名称
@currentnodeidOld int, -- 当前节点id(当前的)
@currentnodeidNew int, -- 当前节点id(新的)
@lastnodeidOld int, --
@lastnodeidNew int,

@nodeidOld int, -- 节点id(当前的)
@nodeidNew int, -- 节点id(新的)
@nodename varchar(1000), -- 当前节点名称(现在的)
@drawxpos int, -- 节点图形显示横坐标
@drawypos int, -- 节点图形显示纵坐标
@currentoperatorid int, -- 工作流请求节点操作人信息ID
@tolerancex int, -- 横坐标容差
@tolerancey int -- 纵坐标容差

-- 0.2 设置坐标位置容差,虽然不知道是按节点的什么位置记录的坐标位置,但能肯定的是坐标的单位是像素。
select @tolerancex = 5,
@tolerancey = 5

IF OBJECT_ID('tempdb..#workflow_currentoperator_v') IS NOT NULL
DROP TABLE #workflow_currentoperator_v;

-- 0,3 创建临时表,存储当前流程实例的节点信息
create table #workflow_currentoperator_v (
id int,
requestid int,
nodeidold int,
nodeidnew int,
workflowidold int,
workflowidnew int
)

-- 1、 用传入的参数@requestid找到对应的workflowid等表头里的信息。
select @workflowidOld = workflowid, -- 工作流id(当前的)
@currentnodeidOld = currentnodeid, -- 当前节点id(当前的)
@lastnodeidOld = lastnodeid -- 最后操作节点id(当前的)
from workflow_requestbase -- 工作流请求基本信息表
where requestid = @requestid

-- 2、 用获得的@workflowid找对应的workflowname和activeVersionID,
-- 测试过,发现一旦修改了路径名称,所有版本会同时修改,具备用workflowname作为主键的条件。
select @workflowname = workflowname, -- 工作流名称
@workflowidNew = activeVersionID -- 当前流程所属活动版本ID, 这里记录的是活动的那个版本的workflowbase.id
from workflow_base -- 工作流基本信息表
where id = @workflowidOld

-- 找每个节点的新的nodeid,给它们都先存到临时表里
insert into #workflow_currentoperator_v
(id, requestid, nodeidold, workflowidold )
select id, requestid, nodeid, workflowid
from workflow_currentoperator
where requestid = @requestid

declare workflowidold_Cursor CURSOR for
SELECT id, nodeidold
FROM #workflow_currentoperator_v

open workflowidold_Cursor
FETCH NEXT FROM workflowidold_Cursor into @currentoperatorid, @nodeidOld

while @@FETCH_STATUS = 0
begin

-- 3、 有了新版本的ID,找对应的节点的ID
-- “是同一个节点”的判断原则:要么名称相同,要么位置相同。

select @nodename = nodename -- 节点名称
from workflow_nodebase
where id = @nodeidOld --当前节点id(现在的)

-- 3.1.1 找“名称相同”的节点

select @nodeidnew = id
from workflow_nodebase
where id in ( select nodeid
from workflow_nodehtmllayout
where workflowid = @workflowidNew) and
nodename = @nodename

-- 3.1.2 如果按名称没有找到对应的节点,
if isnull(@nodeidNew ,0) = 0
begin
-- 这里应该是个存储过程,因为坐标可能存在误差。
-- 坐标是以像素为单位记的。
-- 取当前节点的坐标
select @drawxpos = drawxpos,
@drawypos = drawypos
from workflow_nodebase
where id = @nodeidOld --当前节点id(现在的)

-- 3.1.2 如果没有“名称相同”的节点,再去根据位置找节点。
select @nodeidNew = id
from workflow_nodebase
where id in ( select nodeid
from workflow_nodehtmllayout
where workflowid = @workflowidNew) and
drawxpos between @drawxpos - @tolerancex and @drawxpos + @tolerancex and
drawypos between @drawypos - @tolerancey and @drawypos + @tolerancey
end

-- 3.1.4 根据@currentnodeidnew,判断是报异常并退出,还是更新临时表。
if isnull(@nodeidNew ,0) = 0
begin
-- 没找到的话,报错退出
select @returnFlg = 'E',
@returnMsg = '更新失败!流程ID:' + CAST(@requestid AS NVARCHAR(10)) + ',节点:' + @nodename + ',没找到对应节点。'

-- 退出整个存储过程
CLOSE workflowidold_Cursor
DEALLOCATE workflowidold_Cursor
IF OBJECT_ID('tempdb..#workflow_currentoperator_v') IS NOT NULL
begin
DROP TABLE #workflow_currentoperator_v
end
RETURN

end
else
begin
-- 找到的话,更新临时表
update #workflow_currentoperator_v
set nodeidnew = @nodeidNew,
workflowidnew = @workflowidNew
where id = @currentoperatorid

-- 3.1.5 比对表头里的当前节点ID、操作节点ID,是不是和现在正处理的节点ID相同,如果是,取新ID
if @currentnodeidOld = @nodeidOld
begin
select @currentnodeidNew = @nodeidNew
end

if @lastnodeIdOld = @nodeidOld
begin
select @lastnodeIdNew = @nodeidNew
end

end

FETCH NEXT FROM workflowidold_Cursor into @currentoperatorid, @nodeidOld
end

-- 4. 关闭并释放游标
CLOSE workflowidold_Cursor
DEALLOCATE workflowidold_Cursor

-- 5、更新表头workflow_requestbase,更新wrokflowid、lastnodeid、currentnodeid
begin tran
BEGIN TRY

update workflow_requestbase
set workflowid = @workflowidNew,
lastnodeid = isnull(@lastnodeidNew, lastnodeid),
currentnodeid = isnull(@currentnodeidNew, currentnodeid)
where requestid = @requestid

update a
set a.nodeid = b.nodeidNew,
a.workflowid = b.workflowidNew
from workflow_currentoperator a
inner join
#workflow_currentoperator_v b
on a.id = b.id
where a.requestid = @requestid

select @returnFlg = 'S',
@returnMsg = '更新成功!流程ID:' + CAST(@requestid AS NVARCHAR(10)) + ',更新完毕。'

COMMIT tran;
END TRY
BEGIN CATCH
-- 3. 如果发生任何错误,回滚事务
ROLLBACK TRANSACTION;
-- 可以在此处记录错误信息
select @returnFlg = 'E',
@returnMsg = '更新失败!流程ID:' + CAST(@requestid AS NVARCHAR(10)) + ',更新失败。'

END CATCH;

GO

结果

写到这里基本可以满足我自己的要求,并且测试通过了。不得不承认它有一定的局限性,如果工作流的活动版本比当前流程对应的工作流版本少节点的话,缺少的那个节点就更新不到了。

写到这里呢,这次想分享的知识点就全部分享结束了。用那句老掉牙的话收个尾吧,希望这篇文章对已经看到这儿的小伙伴们有所帮助。还是那句话,喜欢的小伙伴们请关注、点赞、评论。大家的鼓励是我持续创作的动力。感谢!

http://www.cnnetsun.cn/news/3464837.html

相关文章:

  • Arm Ethos-U65 介绍(1) 架构、数据格式与算子
  • 2026答辩翻车真相!论文满分也过不了|90%人栽在临场细节问答盲区,一键补救
  • 【ChatGPT儿童故事创作黄金法则】:20年教育科技专家亲授——3步生成高互动、零说教、符合发展心理学的AI故事
  • 5分钟学会HashCalculator:免费文件完整性校验终极指南
  • CW32开发板与DFPlayer Mini的MP3播放系统实现
  • Ubuntu软件管理全指南:从APT到Snap安装与卸载
  • Ubuntu 24.04下NVIDIA驱动与CUDA安装优化指南
  • Next操作工程实践:从Python迭代器到SQL分页的稳定性设计
  • Mac mini服务器改造:定时开关机与电源管理全攻略
  • 2026国内主流热计量表生产厂家盘点 供热工程靠谱品牌推荐
  • 自制语言(压缩包)
  • 小白安装ubuntu desktop是否需要断网安装
  • 软件设计师①
  • LLM应用安全防护实战:从威胁模型到部署LLM-Guard防火墙
  • Mediapipe实时人像分割:30FPS毫秒级抠图技术解析
  • OpenClaw+阿里云轻量服务器+飞书集成实战指南
  • 不止是LOGO!读懂无线充电的核心通用标准——Qi认证
  • Qwen3-ASR音乐语音识别工作流:多语言高鲁棒性离线推理实战
  • sqlserver 链接 MYSQL数据库 (无废话 百分100%可用)
  • Windows虚拟机安装macOS全攻略:开发iOS应用必备
  • 0714|美股重挫、大众裁员、AI劲敌、专家联署、长鑫IPO
  • 镀银碳带结构优化提升打印质量与耐用性
  • 从微信支付文档学习系统设计:接口文档如何揭示架构核心
  • Cadence 小知识(26)---设置铜皮连接方式
  • 信号线串联电阻的设计原理与应用场景
  • 【毕设分享】springboot智能推荐农产品团购系统21315
  • 全志T113-i评估板开发实战与异构核通信解析
  • SSRF漏洞原理、漏洞点、利用与防御
  • 笔记本KVM显卡直通技术实战指南
  • 计算机毕业设计之玩具租赁管理系统