尧图网站建设 尧图网络
  • 首页
  • 关于我们
  • 服务项目
  • 案例展示
  • 建站流程
  • 资讯中心
  • 联系我们
首页/资讯中心/详情

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

E8-写了一个存储过程,用来更新流程的对应版本
📅 发布时间:2026/7/17 21:43:54

起因

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

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

为了更新这些本该用新版本发起的流程,我写了一个存储过程,输入参数是要更新的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

结果

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

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

相关新闻

  • PyTorch实现MNIST手写数字识别:CNN实战教程
  • 无锡宜兴 2026 年 7 月外墙厨房车库防水 宜兴正规漏水检测维修商家 - 苏易修缮
  • 2026年7月最新济南万国官方售后服务网点地址及客服电话一览 - 万国中国官方服务中心

最新新闻

  • Windows 11 LTSC微软商店安装:企业级稳定与现代化生态的完美融合
  • Ansible Playbook 基础与流程控制 30 例(Nginx 企业级实战)-001篇
  • Hermes 0.13升级指南:Tool Chaining、Memory异步持久化与分级熔断详解
  • 2026年7月最新黄石防水补漏权威指南:卫生间/屋面/外墙/地下室正规施工+透明报价+避坑全攻略 - 吉林同城获客
  • 多模型并行生成 PPT 的产品与技术实践
  • 多模态模型技术演进与工业实践指南

日新闻

  • 佛山青少年训练营推荐:军博营地实力顶尖 - 秋山寄远
  • 如何快速上手PvZ2 Gardendless:免费Web版植物大战僵尸2完整指南
  • jiuwen-deepsearch核心功能详解:规划-检索-反思三合一智能工作流

周新闻

  • IX9104 PCIe5.0 高速交换芯片@ACP#完整规格 + 应用场景总结
  • Unity游戏集成Coze智能体:实现NPC智能对话与知识库联动
  • SAP EPIC 建行回单查询:从标准类CL_EPIC_EXAMPLE_CN_CCB_GHTD到Z类的5处关键修改

月新闻

  • 2026年6月公司网站搭建最新热门渠道测评:四大低成本/零代码平台对比+避坑
  • 【Linux】Linux arm 编译QT程序,出现expected “}“报错
  • 【MATLAB例程】四基站二维AOA定位与距离辅助增强对比仿真。基于角度观测和测距修正的固定目标平面定位精度分析

关于尧图

  • 公司简介
  • 团队介绍
  • 企业文化
  • 荣誉资质

服务项目

  • 定制开发
  • 电商建站
  • UI 设计
  • 运维服务

快速链接

  • 案例展示
  • 建站流程
  • 常见问题
  • 资讯中心

联系方式

  • 📍北京市朝阳区互联网产业园 A 座 10 层
  • 📞400-888-8888
  • ✉️contact@rkmt.cn
  • 🕐周一至周日 9:00-21:00

© 2024 北京尧图网络科技有限公司 版权所有 | 京 ICP 备 XXXXXXXX 号