11 Commits

Author SHA1 Message Date
yubaolee
7a34fa7c51 🐛fix: 修复网关节点查询异常 2026-06-14 22:53:37 +08:00
yubaolee
62babb205c 🐛fix: 修复加签 2026-06-13 23:44:08 +08:00
yubaolee
a222959efe 🔄refactor: 重构驳回的逻辑 2026-06-12 01:50:47 +08:00
yubaolee
0340fb224f ⚠️feat: 增加一个强制退出程序的脚本 2026-06-12 00:25:27 +08:00
yubaolee
1a43adb9a6 🔄refactor: 修复BUG,更新文档 2026-06-12 00:22:55 +08:00
yubaolee
cbb43f0011 🔄refactor: 优化流程 2026-06-11 23:51:17 +08:00
yubaolee
9aac53b3eb 🐛fix: 修复召回 2026-06-11 21:34:53 +08:00
yubaolee
bfe9bf2481 🐛fix: 修复召回流程 2026-06-10 23:44:49 +08:00
yubaolee
ab41783e9f 🐛fix: #IJR8AQ 模板编号和发布时间更改无效 2026-06-10 23:39:24 +08:00
yubaolee
fd4a328a72 * 🐛fix: #IJQXD6 概念容易混淆,建议列表上方撤销改名为召回 2026-06-10 21:25:32 +08:00
yubaolee
17f0e402ac 🐛fix: 修复不同意时异常 2026-06-09 00:57:56 +08:00
17 changed files with 273 additions and 111 deletions

View File

@@ -1,6 +1,6 @@
---
name: dev
description: OpenAuth.Net开发规范
description: OpenAuth.Net后端开发规范
---
## 编码规范

25
CheckAndKillPort52789.bat Normal file
View File

@@ -0,0 +1,25 @@
@echo off
chcp 936
setlocal enabledelayedexpansion
echo <20><><EFBFBD>ڼ<EFBFBD><DABC><EFBFBD>52789<38>˿<EFBFBD>ռ<EFBFBD><D5BC><EFBFBD><EFBFBD><EFBFBD><EFBFBD>...
rem <20><><EFBFBD><EFBFBD>ռ<EFBFBD><D5BC>52789<38>˿ڵĽ<DAB5><C4BD><EFBFBD>
FOR /F "tokens=5" %%i IN ('netstat -ano ^| findstr :52789 ^| findstr LISTENING') DO (
SET pid=%%i
echo <20><><EFBFBD><EFBFBD>ռ<EFBFBD><D5BC>52789<38>˿ڵĽ<DAB5><C4BD>̣<EFBFBD>PID: %%i
echo <20><><EFBFBD>ڲ<EFBFBD>ѯ<EFBFBD><D1AF><EFBFBD><EFBFBD><EFBFBD><EFBFBD>Ϣ...
tasklist | findstr %%i
echo <20><><EFBFBD>ڽ<EFBFBD><DABD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> %%i...
taskkill /F /PID %%i
echo <20><>֤<EFBFBD>˿<EFBFBD><CBBF>Ƿ<EFBFBD><C7B7><EFBFBD><EFBFBD>ͷ<EFBFBD>...
netstat -ano | findstr :52789
goto :END
)
echo δ<><CEB4><EFBFBD><EFBFBD>ռ<EFBFBD><D5BC>52789<38>˿ڵĽ<DAB5><C4BD>̡<EFBFBD>
:END
echo <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ɡ<EFBFBD>
pause

View File

@@ -6,7 +6,7 @@
public struct FlowInstanceStatus
{
/// <summary>
/// 撤销、召回
/// 召回
/// </summary>
public const int Draft = -1;
/// <summary>

View File

@@ -10,6 +10,16 @@
public string name { get; set; }
/// <summary>
/// 节点类型
/// <para>
/// start:开始节点
/// end:结束节点
/// node:普通节点
/// fork:网关开始
/// join:网关结束
/// </para>
/// </summary>
public string type { get; set; }
public int left { get; set; }
@@ -47,10 +57,29 @@
/// </summary>
public string NodeRejectType { get; set; }
/// <summary>
/// 审批标记1通过2不通过3驳回
/// </summary>
public int? Taged { get; set; }
/// <summary>
/// 审批人名称
/// </summary>
public string UserName { get; set; }
/// <summary>
/// 审批人ID
/// </summary>
public string UserId { get; set; }
/// <summary>
/// 审批意见
/// </summary>
public string Description { get; set; }
/// <summary>
/// 审批时间
/// </summary>
public string TagedTime { get; set; }
//网关审批通过的方式,

View File

@@ -267,6 +267,8 @@ namespace OpenAuth.App.Flow
isFirst = false;
break;
}
preNode = GetPreNode(preNode.id);
}
if (isFirst)
@@ -400,13 +402,22 @@ namespace OpenAuth.App.Flow
}
/// <summary>
/// 撤销流程,清空所有节点
/// 召回流程,清空所有节点,返回开始节点并修改为草稿状态
/// </summary>
public void ReCall(RecallFlowInstanceReq request)
{
foreach (var item in Nodes)
{
item.Value.setInfo = null;
if (item.Value.setInfo != null)
{
item.Value.setInfo.Taged = null;
item.Value.setInfo.UserName = null;
item.Value.setInfo.UserId = null;
item.Value.setInfo.Description = null;
item.Value.setInfo.TagedTime = null;
item.Value.setInfo.ConfluenceOk = null;
item.Value.setInfo.ConfluenceNo = null;
}
}
flowInstance.IsFinish = FlowInstanceStatus.Draft;
@@ -414,17 +425,18 @@ namespace OpenAuth.App.Flow
flowInstance.ActivityId = startNodeId;
flowInstance.ActivityName = Nodes[startNodeId].name;
flowInstance.MakerList = GetNodeMarkers(Nodes[startNodeId], flowInstance.CreateUserId);
flowInstance.SchemeContent = JsonHelper.Instance.Serialize(ToSchemeObj());
var sugarClient = AutofacContainerModule.GetService<ISqlSugarClient>();
sugarClient.Updateable(flowInstance).ExecuteCommand();
SaveOperationHis($"【回】备注:{request.Description}");
SaveOperationHis($"【回】备注:{request.Description}");
sugarClient.Ado.CommitTran();
}
///<summary>
/// 标记节点1通过-1不通过,0驳回
/// 标记节点1通过2不通过,3驳回
/// </summary>
/// <param name="nodeId"></param>
public void MakeTagNode(string nodeId, Tag tag)
@@ -448,6 +460,9 @@ namespace OpenAuth.App.Flow
}
}
/// <summary>
/// 转换为流程方案对象
/// </summary>
public object ToSchemeObj()
{
return new
@@ -583,8 +598,11 @@ namespace OpenAuth.App.Flow
#region
/// <summary>
/// 寻找下一步的执行人
/// 一般用于本节点审核完成后,修改流程实例的当前执行人,可以做到通知等功能
/// 计算流程推进到下一步的执行人
/// <para>创建流程实例Add新建流程后计算第一个审批人</para>
/// <para>网关审批完成VerifyGatewayStart网关结束后推进到下一节点</para>
/// <para>普通节点审批通过VerifyNode审批同意后推进到下一节点</para>
/// <para>启动草稿流程Start草稿变为运行状态计算下一执行人</para>
/// </summary>
/// <returns></returns>
public string GetNextMakers(NodeDesignateReq request = null)
@@ -598,11 +616,13 @@ namespace OpenAuth.App.Flow
//如果request为空则应该是草稿状态变为启动或为网关节点使用nextNode的setInfo
if (request == null)
{
request = new NodeDesignateReq
{
NodeDesignateType = nextNode.setInfo.NodeDesignate,
NodeDesignates = nextNode.setInfo.NodeDesignateData.datas
};
request = new NodeDesignateReq();
}
//从url审批过来的request不为空但是这两个属性是空的
if(request.NodeDesignateType == null || request.NodeDesignates == null){
request.NodeDesignateType = nextNode.setInfo.NodeDesignate;
request.NodeDesignates = nextNode.setInfo.NodeDesignateData.datas;
}
if (GetNextNodeType() == Define.NODE_TYPE_FORK) //如果是网关节点
@@ -621,9 +641,7 @@ namespace OpenAuth.App.Flow
throw new Exception("前端提交的节点权限类型异常,请检查流程");
}
var revelanceApp = AutofacContainerModule.GetService<RevelanceManagerApp>();
var users = revelanceApp.Get(Define.USERROLE, false, request.NodeDesignates);
makerList = GenericHelpers.ArrayToString(users, makerList);
makerList = ResolveDesignateUsers(Define.SPECIAL_ROLE, request.NodeDesignates);
}
else if (nextNode.setInfo.NodeDesignate == Define.RUNTIME_SPECIAL_USER)
{
@@ -633,7 +651,7 @@ namespace OpenAuth.App.Flow
throw new Exception("前端提交的节点权限类型异常,请检查流程");
}
makerList = GenericHelpers.ArrayToString(request.NodeDesignates, makerList);
makerList = ResolveDesignateUsers(Define.SPECIAL_USER, request.NodeDesignates);
}
else if (nextNode.setInfo.NodeDesignate == Define.SPECIAL_SQL)
{
@@ -643,10 +661,7 @@ namespace OpenAuth.App.Flow
throw new Exception("前端提交的节点权限类型异常,请检查流程");
}
var sql = ReplaceSql(nextNode.setInfo.NodeDesignateData.datas[0]);
var sugarClient = AutofacContainerModule.GetService<ISqlSugarClient>();
var result = sugarClient.Ado.SqlQuery<string>(sql);
makerList = GenericHelpers.ArrayToString(result, makerList);
makerList = ResolveDesignateUsers(Define.SPECIAL_SQL, nextNode.setInfo.NodeDesignateData.datas);
}
else if (nextNode.setInfo.NodeDesignate == Define.RUNTIME_PARENT
|| nextNode.setInfo.NodeDesignate == Define.RUNTIME_MANY_PARENTS)
@@ -693,6 +708,99 @@ namespace OpenAuth.App.Flow
return makerList;
}
/// <summary>
/// 获取节点审批人
/// <para>回退/查询"场景,回答"这个节点设计时配了谁来审"</para>
/// <para>驳回到指定节点RejectNode流程被驳回时需要重新计算目标节点的审批人</para>
/// <para>召回流程ReCall将流程撤回到开始节点用创建人ID算出审批人</para>
/// <para>撤销审批UndoVerification恢复上一个节点的审批人</para>
/// <para>网关分支中查找可审核节点GetOneForkLineCanCheckNodeId遍历分支判断当前用户是否有权审核</para>
/// <para>网关分支获取审核者GetOneForkLineMakers找到分支线上下一个待审人</para>
/// </summary>
public string GetNodeMarkers(FlowNode node, string flowinstanceCreateUserId = "")
{
string makerList = "";
if (node.type == Define.NODE_TYPE_START && (!string.IsNullOrEmpty(flowinstanceCreateUserId))) //如果是开始节点,通常情况下是驳回到开始了
{
makerList = flowinstanceCreateUserId;
}
else if (node.setInfo != null)
{
if (node.setInfo.NodeDesignate == Define.RUNTIME_SPECIAL_ROLE
|| node.setInfo.NodeDesignate == Define.RUNTIME_SPECIAL_USER)
{
//如果是运行时选定的用户,则暂不处理。由上个节点审批时选定
}
else if (node.setInfo.NodeDesignate == Define.RUNTIME_PARENT
|| node.setInfo.NodeDesignate == Define.RUNTIME_MANY_PARENTS)
{
//驳回/撤销场景:找到目标节点的前一个节点的执行人,以其为基准计算直属上级
var preNode = GetPreNode(node.id);
var preNodeUserId = preNode.setInfo?.UserId;
if (!string.IsNullOrEmpty(preNodeUserId))
{
var userManagerApp = AutofacContainerModule.GetService<UserManagerApp>();
var parentId = userManagerApp.GetParent(preNodeUserId);
if (!StringExtension.IsNullOrEmpty(parentId))
{
makerList = GenericHelpers.ArrayToString(new[] { parentId }, makerList);
}
}
}
else if (node.setInfo.NodeDesignate == Define.RUNTIME_CHAIRMAN)
{
//驳回/撤销场景:获取发起人的部门负责人
var orgManagerApp = AutofacContainerModule.GetService<OrgManagerApp>();
var chairmanIds = orgManagerApp.GetChairmanId(node.setInfo.NodeDesignateData?.datas);
makerList = GenericHelpers.ArrayToString(chairmanIds, makerList);
}
else
{
makerList = ResolveDesignateUsers(node.setInfo.NodeDesignate, node.setInfo.NodeDesignateData?.datas);
}
}
else //如果没有设置节点信息,属于流程设计异常
{
throw new Exception($"节点【{node.name}】未设置审批人信息,请检查流程设计!");
}
return makerList;
}
/// <summary>
/// 根据指定类型和指定数据解析审批人列表(公共辅助方法)
/// </summary>
/// <param name="designateType">节点指定类型</param>
/// <param name="designateData">节点指定数据</param>
/// <returns>审批人列表字符串</returns>
private string ResolveDesignateUsers(string designateType, string[] designateData)
{
string makerList = "";
if (string.IsNullOrEmpty(designateType) || designateType == Define.ALL_USER) //所有成员
{
makerList = "1";
}
else if (designateType == Define.SPECIAL_USER) //指定成员
{
makerList = GenericHelpers.ArrayToString(designateData, makerList);
}
else if (designateType == Define.SPECIAL_ROLE) //指定角色
{
var revelanceApp = AutofacContainerModule.GetService<RevelanceManagerApp>();
var users = revelanceApp.Get(Define.USERROLE, false, designateData);
makerList = GenericHelpers.ArrayToString(users, makerList);
}
else if (designateType == Define.SPECIAL_SQL) //指定SQL
{
var sql = ReplaceSql(designateData[0]);
var sugarClient = AutofacContainerModule.GetService<ISqlSugarClient>();
var result = sugarClient.Ado.SqlQuery<string>(sql);
makerList = GenericHelpers.ArrayToString(result, makerList);
}
return makerList;
}
/// <summary>
/// 计算多实例、会签节点的执行人
/// </summary>
@@ -762,57 +870,6 @@ namespace OpenAuth.App.Flow
return GenericHelpers.ArrayToString(makerList, "");
}
/// <summary>
/// 这里专门处理由前端选择相关的节点执行人
/// </summary>
/// <param name="node"></param>
/// <returns></returns>
public string GetNodeMarkers(FlowNode node, string flowinstanceCreateUserId = "")
{
string makerList = "";
if (node.type == Define.NODE_TYPE_START && (!string.IsNullOrEmpty(flowinstanceCreateUserId))) //如果是开始节点,通常情况下是驳回到开始了
{
makerList = flowinstanceCreateUserId;
}
else if (node.setInfo != null)
{
if (string.IsNullOrEmpty(node.setInfo.NodeDesignate) ||
node.setInfo.NodeDesignate == Define.ALL_USER) //所有成员
{
makerList = "1";
}
else if (node.setInfo.NodeDesignate == Define.SPECIAL_USER) //指定成员
{
makerList = GenericHelpers.ArrayToString(node.setInfo.NodeDesignateData.datas, makerList);
}
else if (node.setInfo.NodeDesignate == Define.SPECIAL_ROLE) //指定角色
{
var revelanceApp = AutofacContainerModule.GetService<RevelanceManagerApp>();
var users = revelanceApp.Get(Define.USERROLE, false, node.setInfo.NodeDesignateData.datas);
makerList = GenericHelpers.ArrayToString(users, makerList);
}
else if (node.setInfo.NodeDesignate == Define.SPECIAL_SQL) //指定SQL
{
//如果是指定SQL则需要执行SQL并返回结果
var sql = ReplaceSql(node.setInfo.NodeDesignateData.datas[0]);
var sugarClient = AutofacContainerModule.GetService<ISqlSugarClient>();
var result = sugarClient.Ado.SqlQuery<string>(sql);
makerList = GenericHelpers.ArrayToString(result, makerList);
}
else if (node.setInfo.NodeDesignate == Define.RUNTIME_SPECIAL_ROLE
|| node.setInfo.NodeDesignate == Define.RUNTIME_SPECIAL_USER)
{
//如果是运行时选定的用户,则暂不处理。由上个节点审批时选定
}
}
else //如果没有设置节点信息,默认所有人都可以审核
{
makerList = "1";
}
return makerList;
}
/// <summary>
/// 替换SQL中的权限占位符
/// <para>如当前用户的全部下属select id from sysuser where parentId = {loginUser}</para>

View File

@@ -103,22 +103,23 @@ namespace OpenAuth.App
/// </summary>
public FlowApprover[] GetApprovers(QueryApproverReq req)
{
var query= Repository.AsQueryable()
// 一次查询,内存中处理,避免 ISugarQueryable 状态污染
var all = Repository.AsQueryable()
.Where(u => u.InstanceId == req.FlowInstanceId
&& u.ActivityId == req.ActivityId && u.Status == 0); //本节点待审批的加签人
if (query.Count() == 0)
&& u.ActivityId == req.ActivityId && u.Status == 0)
.OrderBy(u => u.OrderNo)
.ToArray();
if (all.Length == 0) return null;
// 顺序执行:只返回第一个
if (all[0].ApproveType == Define.APPROVE_TYPE_SEQUENTIAL)
{
return null;
return new[] { all[0] };
}
//如果是顺序执行,取第一个人
if (query.First().ApproveType == Define.APPROVE_TYPE_SEQUENTIAL)
{
var result = query.OrderBy(u => u.OrderNo).First();
return new[] { result };
}
//否则并行且/并行或都是返回所有加签人
return query.ToArray();
// 并行且/并行或:返回全部
return all;
}
/// <summary>

View File

@@ -2,7 +2,7 @@
* @Author: yubaolee <yubaolee@163.com> | ahfu~ <954478625@qq.com>
* @Date: 2024-12-13 16:55:17
* @Description: 工作流实例表操作
* @LastEditTime: 2025-10-18 14:35:01
* @LastEditTime: 2026-06-11 22:35:03
* Copyright (c) 2024 by yubaolee | ahfu~ , All Rights Reserved.
*/
@@ -512,6 +512,7 @@ namespace OpenAuth.App
else //审批结果为不同意
{
flowInstance.IsFinish = FlowInstanceStatus.Disagree;
flowInstance.MakerList = "";
wfruntime.nextNodeId = "-1";
}
@@ -520,7 +521,7 @@ namespace OpenAuth.App
$"结果:{(tag.Taged == 1 ? "" : "")},备注:{tag.Description}";
wfruntime.SaveOperationHis(tag.UserId, tag.UserName, content);
if (flowInstance.IsFinish == 1)
if (flowInstance.IsFinish == FlowInstanceStatus.Finished)
{
//给知会人员发送通知信息
var userids = _userManagerApp.GetNoticeUsers(flowInstance.Id);
@@ -592,20 +593,20 @@ namespace OpenAuth.App
/// </summary>
public void Verification(VerificationReq request)
{
TagState tagState = (TagState)Int32.Parse(request.VerificationFinally);
//如果是同意,需要判断是否为运行时选定下一步执行角色/执行人
if (request.VerificationFinally == "1")
if (tagState == TagState.Ok)
{
CheckNodeDesignate(request);
}
bool isReject = TagState.Reject.Equals((TagState)Int32.Parse(request.VerificationFinally));
if (isReject) //驳回
if (tagState == TagState.Reject)
{
RejectNode(request);
RejectNode(request); // 驳回
}
else
{
NodeVerification(request);
NodeVerification(request); // 审核(同意/不同意)
}
}
@@ -660,7 +661,13 @@ namespace OpenAuth.App
ActivityId = flowinstance.ActivityId
});
if (flowinstance.MakerList != "1" && !flowinstance.MakerList.Contains(user.User.Id) &&
//流程已终止(完成/不同意/撤销等),不允许继续审批
if (flowinstance.IsFinish != FlowInstanceStatus.Running && flowinstance.IsFinish != FlowInstanceStatus.Rejected)
{
resp.CanVerify = false;
}
//当前用户不是当前节点的审批人,不允许继续审批
else if (flowinstance.MakerList != "1" && !flowinstance.MakerList.Contains(user.User.Id) &&
!approvers.Contains(user.User.Id))
{
resp.CanVerify = false;

View File

@@ -48,6 +48,8 @@ namespace OpenAuth.App
FrmUrlTemplate = flowScheme.FrmUrlTemplate,
Disabled = flowScheme.Disabled,
Description = flowScheme.Description,
CreateDate = flowScheme.CreateDate,
SchemeCode = flowScheme.SchemeCode,
OrgId = flowScheme.OrgId
},u => u.Id == flowScheme.Id);
}

View File

@@ -1,7 +1,7 @@
<!--
* @Author: yubaolee <yubaolee@163.com> | ahfu~ <954478625@qq.com>
* @Date: 2024-01-08 17:08:56
* @LastEditTime: 2024-06-21 10:16:05
* @LastEditTime: 2026-06-14 22:50:56
* @Description:
* @
* @Copyright (c) 2024 by yubaolee | ahfu~ , All Rights Reserved.
@@ -304,9 +304,20 @@ export default {
const to = info.targetId
if (from === to) return false
const filter = that.flowData.lines.filter(link => (link.from === from && link.to === to))
const filter = that.flowData.lines.filter(link => (link.from === from && link.to === to)
|| (link.from === to && link.to === from))
if (filter.length > 0) {
that.$message.error('同方向的两节点连线只能有一条!')
that.$message.error('两节点连线只能有一条!')
return false
}
if(from.includes("end")){
that.$message.error('结束节点不能作为起点!')
return false
}
if(to.includes("start")){
that.$message.error('开始节点不能作为终点!')
return false
}
return true

View File

@@ -122,9 +122,13 @@ OpenAuth.Net工作流分为两个大类
* 同意:流程审批通过,流程结束;
* 不同意:流程审批不通过,流程结束;
* **不同意(拒绝 / 反对)**:审批人明确不批准本次申请,属于终结性意见。
* 驳回:可以驳回到指定的步骤,该步骤的人可以重新审批提交;
* 结果:本次申请失败,流程结束,如果重新发起新流程。
* **驳回(退回 / 打回)**:审批人认为资料不全 / 有误,需要修改后重提,属于回退 + 重走动作。
* 结果:流程未终结,可修复后继续。

View File

@@ -30,6 +30,7 @@ SelectUsersCom是一个用于选择用户或角色的组件提供了两种使
| users | Object | - | 初始选中项ID列表或对象列表 |
| inType | String | 'id' | 父级传入的是id列表还是对象列表取值为'id'或'obj' |
| modelValue | Boolean | false | 控制对话框显示 |
| single | Boolean | false | 是否单选true时只能选择一个用户/角色 |
### 事件说明
@@ -87,6 +88,7 @@ const handleSave = () => {
| userNames | String | '' | 用户名称(逗号分隔) |
| placeholder | String | '' | 输入框占位符 |
| ignoreAuth | Boolean | false | 是否忽略权限限制 |
| single | Boolean | false | 是否单选true时只能选择一个用户/角色 |
### 事件说明

View File

@@ -4,27 +4,47 @@ createTime: 2025/04/23 23:43:26
permalink: /pro/start/
---
## 工具准备
#### NodeJs
前端环境为NodeJs下载地址[http://nodejs.cn/download/current/](http://nodejs.cn/download/current/)
#### visual studio code
下载最新版的vs code或Cursor、Windsurf、Trae等工具用来作为OpenAuth.Net Vue3版的开发工具。
## 源码下载
根据授权文件的下载指示下载Vue3源码。注意一定要使用下图中的数据库脚本
![2025-04-08-20-53-49](http://img.openauth.net.cn/2025-04-08-20-53-49.png)
## 创建数据库
* 新建一个空数据库OpenAuthPro。使用上一步下载的【sql脚本】文件夹根据你的数据库类型选择运行你需要的脚本`Sql Server脚本.sql``mysql脚本.sql`
## 启动后端
启动后端请参考:[快速开始](/core/start/)
## 启动前端
使用Vs Code或个人喜欢的工具打开openauthvue3文件夹修改配置文件 `.env.dev`对应的后端接口地址,调整为自己的接口地址:
```javascript
VITE_BASE_API = http://localhost:52789/api
VITE_BASE_IMG_URL = http://localhost:52789
```
::: warning 注意
如果是发布打包,调整的文件为 `.env.production`
:::
使用`npm install`命令安装程序运行所需的第三方包。再用`npm run dev`命令运行。如下图
![2025-04-08-20-57-34](http://img.openauth.net.cn/2025-04-08-20-57-34.png)
启动成功后,使用浏览器访问[http://localhost:1803/](http://localhost:1803/) 即可打开vue3版界面
使用 `npm install`命令安装程序运行所需的第三方包。在安装的过程中如果遇到卡住的情况可能是ssl证书问题可以使用以下命令进行配置
```
npm config set strict-ssl false; npm config set registry https://registry.npmmirror.com
```
再用 `npm run dev`命令运行。如下图:
![2025-04-08-20-57-34](http://img.openauth.net.cn/2025-04-08-20-57-34.png)启动成功后,使用浏览器访问[http://localhost:1803/](http://localhost:1803/) 即可打开vue3版界面
![2025-04-08-21-03-19](http://img.openauth.net.cn/2025-04-08-21-03-19.png)

View File

@@ -145,9 +145,13 @@ OpenAuth.Net工作流分为两个大类
* 同意:流程审批通过,流程结束;
* 不同意:流程审批不通过,流程结束;
* **不同意(拒绝 / 反对)**:审批人明确不批准本次申请,属于终结性意见。
* 驳回:可以驳回到指定的步骤,该步骤的人可以重新审批提交;
* 结果:本次申请失败,流程结束,如果重新发起新流程。
* **驳回(退回 / 打回)**:审批人认为资料不全 / 有误,需要修改后重提,属于回退 + 重走动作。
* 结果:流程未终结,可修复后继续。
* 加签:在已有审批流程上临时添加审批人,协助自己审批;

View File

@@ -1273,7 +1273,7 @@ INSERT INTO "MODULEELEMENT" VALUES ('4fba8ea0-6b0d-426f-8687-b654575ca780', 'btn
INSERT INTO "MODULEELEMENT" VALUES ('4fba8ea0-7c5c-426f-8687-b654575ca780', 'btnExport', '导出', NULL, 'export()', 'bianji-copy', 'info', '导出订单', '10', '98a949e8-8704-40a7-b9a1-c0e8801e4057', NULL, NULL);
INSERT INTO "MODULEELEMENT" VALUES ('4fe5d402-4314-4673-8723-eeed4bfaa2e1', 'btnEdit', '编辑', NULL, NULL, 'xiugai', 'primary', '编辑流程', '1', '9486ff22-b696-4d7f-8093-8a3e53c45453', NULL, NULL);
INSERT INTO "MODULEELEMENT" VALUES ('50c9df24-b233-42cb-9a0d-4ce158c75f86', 'btnAdd', '添加', NULL, 'add()', 'xinzeng', 'success', '添加用戶', '0', 'ef386d5d-cd58-43c0-a4ab-80afd0dbcd6c', NULL, NULL);
INSERT INTO "MODULEELEMENT" VALUES ('52be6f7a-0b32-481e-b8a2-929437eafb2a', 'btnRecall', '撤销', NULL, NULL, 'chexiao_', 'danger', NULL, '5', '9486ff22-b696-4d7f-8093-8a3e53c45453', NULL, NULL);
INSERT INTO "MODULEELEMENT" VALUES ('52be6f7a-0b32-481e-b8a2-929437eafb2a', 'btnRecall', '召回', NULL, NULL, 'chexiao_', 'danger', NULL, '5', '9486ff22-b696-4d7f-8093-8a3e53c45453', NULL, NULL);
INSERT INTO "MODULEELEMENT" VALUES ('57dfb830-6b65-41e0-848e-88aa604f9ad8', 'btnEdit', '编辑', NULL, 'edit()', 'bianji-copy', 'primary', '修改外部数据源管理', '2', 'e11b4ece-b4c6-44f5-b1c1-8f1dadbf037c', NULL, NULL);
INSERT INTO "MODULEELEMENT" VALUES ('584c7a3b-d28a-47b4-8648-7797d05d83d1', 'btnDel', '删除', NULL, 'del()', 'shanchu', 'danger', NULL, '3', '9486ff22-b696-4d7f-8093-8a3e53c45453', NULL, NULL);
INSERT INTO "MODULEELEMENT" VALUES ('44075557-496e-4dde-bb75-7b69f51ab4fe', 'btnEdit', '编辑', NULL, 'edit()', 'bianji-copy', 'primary', '编辑模块', '2', 'bc80478d-0547-4437-9cff-be4b40144bdf', NULL, NULL);

View File

@@ -1055,7 +1055,7 @@ INSERT INTO "public"."moduleelement" VALUES ('4fba8ea0-6b0d-426f-8687-b654575ca7
INSERT INTO "public"."moduleelement" VALUES ('4fba8ea0-7c5c-426f-8687-b654575ca780', 'btnExport', '导出', '', 'export()', 'bianji-copy', 'info', '导出订单', 10, '98a949e8-8704-40a7-b9a1-c0e8801e4057', NULL, NULL);
INSERT INTO "public"."moduleelement" VALUES ('4fe5d402-4314-4673-8723-eeed4bfaa2e1', 'btnEdit', '编辑', '', '', 'xiugai', 'primary', '编辑流程', 1, '9486ff22-b696-4d7f-8093-8a3e53c45453', '', '');
INSERT INTO "public"."moduleelement" VALUES ('50c9df24-b233-42cb-9a0d-4ce158c75f86', 'btnAdd', '添加', '', 'add()', 'xinzeng', 'success', '添加用戶', 0, 'ef386d5d-cd58-43c0-a4ab-80afd0dbcd6c', NULL, NULL);
INSERT INTO "public"."moduleelement" VALUES ('52be6f7a-0b32-481e-b8a2-929437eafb2a', 'btnRecall', '撤销', '', '', 'chexiao_', 'danger', '', 5, '9486ff22-b696-4d7f-8093-8a3e53c45453', '', '');
INSERT INTO "public"."moduleelement" VALUES ('52be6f7a-0b32-481e-b8a2-929437eafb2a', 'btnRecall', '召回', '', '', 'chexiao_', 'danger', '', 5, '9486ff22-b696-4d7f-8093-8a3e53c45453', '', '');
INSERT INTO "public"."moduleelement" VALUES ('57dfb830-6b65-41e0-848e-88aa604f9ad8', 'btnEdit', '编辑', '', 'edit()', 'bianji-copy', 'primary', '修改外部数据源管理', 2, 'e11b4ece-b4c6-44f5-b1c1-8f1dadbf037c', '', '');
INSERT INTO "public"."moduleelement" VALUES ('584c7a3b-d28a-47b4-8648-7797d05d83d1', 'btnDel', '删除', '', 'del()', 'shanchu', 'danger', '', 3, '9486ff22-b696-4d7f-8093-8a3e53c45453', NULL, NULL);
INSERT INTO "public"."moduleelement" VALUES ('5ed1681c-13d2-4c87-8675-a8d95c0b40ae', 'btnAddMenu', '添加菜单', '', 'assignButton()', 'xinzeng', 'success', '为模块分配按钮', 4, 'bc80478d-0547-4437-9cff-be4b40144bdf', NULL, NULL);

View File

@@ -3413,7 +3413,7 @@ GO
INSERT INTO [dbo].[ModuleElement] ([Id], [DomId], [Name], [Attr], [Script], [Icon], [Class], [Remark], [Sort], [ModuleId], [TypeName], [TypeId]) VALUES (N'50c9df24-b233-42cb-9a0d-4ce158c75f86', N'btnAdd', N'添加', N'', N'add()', N'xinzeng', N'success', N'添加用戶', N'0', N'ef386d5d-cd58-43c0-a4ab-80afd0dbcd6c', NULL, NULL)
GO
INSERT INTO [dbo].[ModuleElement] ([Id], [DomId], [Name], [Attr], [Script], [Icon], [Class], [Remark], [Sort], [ModuleId], [TypeName], [TypeId]) VALUES (N'52be6f7a-0b32-481e-b8a2-929437eafb2a', N'btnRecall', N'撤销', N'', N'', N'chexiao_', N'danger', N'', N'5', N'9486ff22-b696-4d7f-8093-8a3e53c45453', N'', N'')
INSERT INTO [dbo].[ModuleElement] ([Id], [DomId], [Name], [Attr], [Script], [Icon], [Class], [Remark], [Sort], [ModuleId], [TypeName], [TypeId]) VALUES (N'52be6f7a-0b32-481e-b8a2-929437eafb2a', N'btnRecall', N'召回', N'', N'', N'chexiao_', N'danger', N'', N'5', N'9486ff22-b696-4d7f-8093-8a3e53c45453', N'', N'')
GO
INSERT INTO [dbo].[ModuleElement] ([Id], [DomId], [Name], [Attr], [Script], [Icon], [Class], [Remark], [Sort], [ModuleId], [TypeName], [TypeId]) VALUES (N'57dfb830-6b65-41e0-848e-88aa604f9ad8', N'btnEdit', N'编辑', N'', N'edit()', N'bianji-copy', N'primary', N'修改外部数据源管理', N'2', N'e11b4ece-b4c6-44f5-b1c1-8f1dadbf037c', N'', N'')

View File

@@ -792,7 +792,7 @@ INSERT INTO `moduleelement` VALUES ('4fba8ea0-6b0d-426f-8687-b654575ca780', 'btn
INSERT INTO `moduleelement` VALUES ('4fba8ea0-7c5c-426f-8687-b654575ca780', 'btnExport', '导出', '', 'export()', 'bianji-copy', 'info', '导出订单', 10, '98a949e8-8704-40a7-b9a1-c0e8801e4057', NULL, NULL);
INSERT INTO `moduleelement` VALUES ('4fe5d402-4314-4673-8723-eeed4bfaa2e1', 'btnEdit', '编辑', '', '', 'xiugai', 'primary', '编辑流程', 1, '9486ff22-b696-4d7f-8093-8a3e53c45453', '', '');
INSERT INTO `moduleelement` VALUES ('50c9df24-b233-42cb-9a0d-4ce158c75f86', 'btnAdd', '添加', '', 'add()', 'xinzeng', 'success', '添加用戶', 0, 'ef386d5d-cd58-43c0-a4ab-80afd0dbcd6c', NULL, NULL);
INSERT INTO `moduleelement` VALUES ('52be6f7a-0b32-481e-b8a2-929437eafb2a', 'btnRecall', '撤销', '', '', 'chexiao_', 'danger', '', 5, '9486ff22-b696-4d7f-8093-8a3e53c45453', '', '');
INSERT INTO `moduleelement` VALUES ('52be6f7a-0b32-481e-b8a2-929437eafb2a', 'btnRecall', '召回', '', '', 'chexiao_', 'danger', '', 5, '9486ff22-b696-4d7f-8093-8a3e53c45453', '', '');
INSERT INTO `moduleelement` VALUES ('57dfb830-6b65-41e0-848e-88aa604f9ad8', 'btnEdit', '编辑', '', 'edit()', 'bianji-copy', 'primary', '修改外部数据源管理', 2, 'e11b4ece-b4c6-44f5-b1c1-8f1dadbf037c', '', '');
INSERT INTO `moduleelement` VALUES ('584c7a3b-d28a-47b4-8648-7797d05d83d1', 'btnDel', '删除', '', 'del()', 'shanchu', 'danger', '', 3, '9486ff22-b696-4d7f-8093-8a3e53c45453', NULL, NULL);
INSERT INTO `moduleelement` VALUES ('5ed1681c-13d2-4c87-8675-a8d95c0b40ae', 'btnAddMenu', '添加菜单', '', 'assignButton()', 'xinzeng', 'success', '为模块分配按钮', 4, 'bc80478d-0547-4437-9cff-be4b40144bdf', NULL, NULL);