feat(REQ-4418) - 调整JSON 转 BPMN 协议的逻辑,适配企业多层级的配置

This commit is contained in:
wangli 2025-08-15 18:48:07 +08:00
parent 791ee00e5f
commit 7815149d4c
14 changed files with 280 additions and 68 deletions

View File

@ -20,6 +20,7 @@ public enum FlowableEngineRespCode implements IModuleRespCode {
ENGINE_NOTICE_CUSTOM_FLOW_ELEMENT_ERROR("005", "查询通知目标用户前参数发生异常,未获取到 WorkspaceType"),
ENGINE_ASYNC_COMMAND_EXECUTION_ERROR("006", "引擎出现 SQL 相关异常, 异常信息:【{}】"),
ENGINE_ASYNC_COMMAND_EXECUTION_RETRY_GIVE_UP("007", "命令重试尝试【{}】次仍然失败,并出现异常, 将放弃, 错误信息:{}"),
ENGINE_POSITION_V2_CONFIG_INVALID("008", "新版本岗位配置不合法, 缺少【{}】, nodeId【{}】"),
;
private final String code;

View File

@ -65,6 +65,7 @@ public interface BpmnConstants {
String FLOW_SERVER_VERSION_130 = "1.3.0";
// 1.4.2 开始启用新版本日志
String FLOW_SERVER_VERSION_142 = "1.4.2";
String FLOW_CATEGORY_VERSION = "categoryVersion";
String CONFIG_SIGN = "signConfig";
String CONFIG_NOTICE = "noticeConfig";
String CONFIG_APPROVE = "approveConfig";

View File

@ -9,6 +9,11 @@ package cn.axzo.workflow.common.enums;
public enum ApproverSpecifyRangeUnitEnum {
in_project("in_project", "项目内"),
in_ent("in_ent", "企业内"),
in_group_lv_1("in_group_lv_1", "集团岗位,上一级"),
in_group_lv_2("in_group_lv_2", "集团岗位,上二级"),
in_group_lv_3("in_group_lv_3", "集团岗位,上三级"),
in_group_lv_4("in_group_lv_4", "集团岗位,上四级"),
in_group_lv_top("in_group_lv_top", "集团岗位,总公司"),
;
private final String type;
private final String desc;

View File

@ -39,4 +39,5 @@ public enum CooperateShipTypeEnum {
public String getDesc() {
return desc;
}
}

View File

@ -17,6 +17,7 @@ public enum SignApproverOrgLimitEnum {
LV_4("LV_4", "上4级组织", 4),
LV_5("LV_5", "上5级组织", 5),
LV_ALL("LV_ALL", "所有组织", -1),
LV_TOP("LV_TOP", "顶层组织", Integer.MAX_VALUE)
;
private final String type;

View File

@ -1,6 +1,9 @@
package cn.axzo.workflow.core.common.utils;
import cn.axzo.workflow.common.enums.ApprovalMethodEnum;
import cn.axzo.workflow.common.enums.ApproverSpecifyRangeEnum;
import cn.axzo.workflow.common.enums.ApproverSpecifyRangeUnitEnum;
import cn.axzo.workflow.common.enums.CooperateShipTypeEnum;
import cn.axzo.workflow.common.enums.InitiatorSpecifiedRangeEnum;
import cn.axzo.workflow.common.enums.ModelBizTypeEnum;
import cn.axzo.workflow.common.exception.WorkflowEngineException;
@ -11,9 +14,7 @@ import cn.axzo.workflow.common.model.request.bpmn.BpmnFieldConf;
import cn.axzo.workflow.common.model.request.bpmn.BpmnJsonModel;
import cn.axzo.workflow.common.model.request.bpmn.BpmnJsonNode;
import cn.axzo.workflow.common.model.request.bpmn.BpmnNoticeConf;
import cn.axzo.workflow.common.model.request.bpmn.BpmnSignApproverLimit;
import cn.axzo.workflow.common.model.request.bpmn.BpmnSignConf;
import cn.axzo.workflow.common.model.request.bpmn.BpmnUpgradeApprovalConf;
import cn.axzo.workflow.common.model.request.bpmn.model.BpmnModelCreateDTO;
import cn.axzo.workflow.core.converter.json.AbstractBpmnJsonConverter;
import cn.axzo.workflow.core.converter.json.BoundaryEventJsonConverter;
@ -101,6 +102,7 @@ import static cn.axzo.workflow.common.constant.BpmnConstants.ELEMENT_ATTRIBUTE_O
import static cn.axzo.workflow.common.constant.BpmnConstants.ELEMENT_ATTRIBUTE_TYPE;
import static cn.axzo.workflow.common.constant.BpmnConstants.ELEMENT_ATTRIBUTE_VALUE;
import static cn.axzo.workflow.common.constant.BpmnConstants.END_EVENT_ID;
import static cn.axzo.workflow.common.constant.BpmnConstants.FLOW_CATEGORY_VERSION;
import static cn.axzo.workflow.common.constant.BpmnConstants.FLOW_MODEL_BIZ_TYPE;
import static cn.axzo.workflow.common.constant.BpmnConstants.FLOW_NODE_JSON;
import static cn.axzo.workflow.common.constant.BpmnConstants.FLOW_SERVER_VERSION;
@ -121,7 +123,13 @@ import static cn.axzo.workflow.common.constant.BpmnConstants.TEMPLATE_SMS_MESSAG
import static cn.axzo.workflow.common.enums.BpmnFlowNodeType.NODE_CONDITION;
import static cn.axzo.workflow.common.enums.BpmnFlowNodeType.NODE_EMPTY;
import static cn.axzo.workflow.common.enums.BpmnFlowNodeType.NODE_EXCLUSIVE_GATEWAY;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getApproverSpecifyRange;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getApproverSpecifyRangeUnit;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getApproverSpecifyValue;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getApproverSpecifyValueV2;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getButtonConfig;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getCategoryVersion;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getCooperateShipType;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getExcludeCooperateShipTypes;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getExcludeIdentityTypes;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getFieldConfig;
@ -129,9 +137,7 @@ import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getInitiat
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getInitiatorSpecifyRange;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getNoticeConfig;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getProcessApproveConf;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getSignApproverLimit;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getSignConfig;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getUpgradeApprovalConf;
/**
* BPMN json 格式转换工具
@ -187,11 +193,12 @@ public final class BpmnJsonConverterUtil {
/**
* json 格式数据转的 BpmnJsonNode 对象,转换成 Flowable 标准的模型 {@link BpmnModel}
*
* @param bpmnJsonNode json 格式对象,可以直接解析
* @param approveConf 流程高审批相关高级配置
* @param bpmnJsonNode json 格式对象,可以直接解析
* @param approveConf 流程高审批相关高级配置
* @param noticeConf
* @param buttonConf
* @param fieldConf
* @param categoryVersion 用于区分新老版本配置
* @return {@link BpmnModel}
*/
public static BpmnModel convertToBpmn(BpmnJsonNode bpmnJsonNode, ModelBizTypeEnum modelBizType,
@ -202,7 +209,8 @@ public final class BpmnJsonConverterUtil {
BpmnNoticeConf noticeConf,
BpmnButtonConf buttonConf,
List<BpmnFieldConf> fieldConf,
String serverVersionStr) {
String serverVersionStr,
Integer categoryVersion) {
if (Objects.isNull(bpmnJsonNode)) {
throw new WorkflowEngineException(CONVERTOR_COMMON_ERROR, "JSON 数据为空");
}
@ -214,16 +222,21 @@ public final class BpmnJsonConverterUtil {
ExtensionAttribute serverVersion = new ExtensionAttribute();
serverVersion.setName(FLOW_SERVER_VERSION);
serverVersion.setValue(serverVersionStr);
ExtensionAttribute categoryVersionAttr = new ExtensionAttribute();
categoryVersionAttr.setName(FLOW_CATEGORY_VERSION);
categoryVersionAttr.setValue(String.valueOf(categoryVersion));
ExtensionAttribute jsonMetaValue = new ExtensionAttribute();
jsonMetaValue.setName(FLOW_NODE_JSON);
jsonMetaValue.setValue(JSONUtil.toJsonStr(bpmnJsonNode));
Process mainProcess = new Process();
mainProcess.setId(id);
mainProcess.setName(name);
mainProcess.setDocumentation(documentation);
mainProcess.addAttribute(modelType);
mainProcess.addAttribute(serverVersion);
mainProcess.addAttribute(categoryVersionAttr);
mainProcess.addAttribute(jsonMetaValue);
//设置流程审批相关高级配置
@ -773,7 +786,7 @@ public final class BpmnJsonConverterUtil {
}
private static FlowElement convertJsonToElement(Class<? extends BaseElement> clz, BpmnJsonNode bpmnJsonNode,
Process process, String formKey) {
Process process, String formKey) {
AbstractBpmnJsonConverter converter = CONVERTERS.getOrDefault(clz, new NotSupportConverter());
FlowElement flowElement = converter.convertJsonToElement(bpmnJsonNode, process, formKey);
if (Objects.nonNull(bpmnJsonNode)) {
@ -822,7 +835,8 @@ public final class BpmnJsonConverterUtil {
model.getJsonModel().getSignConf(),
model.getJsonModel().getNoticeConf(),
model.getJsonModel().getButtonConf(), model.getJsonModel().getFieldConf(),
"1.3.1-SNAPSHOT");
"1.3.1-SNAPSHOT",
2);
getNoticeConfig(bpmnModel.getMainProcess());
getSignConfig(bpmnModel.getMainProcess());
@ -833,6 +847,12 @@ public final class BpmnJsonConverterUtil {
Optional<Boolean> initiatorSpecifiedFilter = getInitiatorSpecifiedFilter(flowElement);
Optional<List<String>> excludeIdentityTypes = getExcludeIdentityTypes(flowElement);
Optional<List<String>> excludeCooperateShipTypes = getExcludeCooperateShipTypes(flowElement);
Optional<Integer> categoryVersion = getCategoryVersion(bpmnModel.getMainProcess());
Optional<ApproverSpecifyRangeEnum> approverSpecifyRange = getApproverSpecifyRange(flowElement);
Optional<String> approverSpecifyValue = getApproverSpecifyValue(flowElement);
Optional<String> approverSpecifyValueV2 = getApproverSpecifyValueV2(flowElement);
Optional<CooperateShipTypeEnum> cooperateShipType = getCooperateShipType(flowElement);
Optional<ApproverSpecifyRangeUnitEnum> approverSpecifyRangeUnit = getApproverSpecifyRangeUnit(flowElement);
// generateImage(bpmnModel);
byte[] xml = transformBytes(bpmnModel);

View File

@ -4,11 +4,14 @@ import cn.axzo.workflow.common.enums.ApprovalMethodEnum;
import cn.axzo.workflow.common.enums.ApproverEmptyHandleTypeEnum;
import cn.axzo.workflow.common.enums.ApproverScopeEnum;
import cn.axzo.workflow.common.enums.ApproverSpecifyEnum;
import cn.axzo.workflow.common.enums.ApproverSpecifyRangeEnum;
import cn.axzo.workflow.common.enums.ApproverSpecifyRangeUnitEnum;
import cn.axzo.workflow.common.enums.AutoApprovalTypeEnum;
import cn.axzo.workflow.common.enums.BpmnFlowNodeType;
import cn.axzo.workflow.common.enums.BpmnProcessInstanceResultEnum;
import cn.axzo.workflow.common.enums.BpmnSignType;
import cn.axzo.workflow.common.enums.CarbonCopyObjectType;
import cn.axzo.workflow.common.enums.CooperateShipTypeEnum;
import cn.axzo.workflow.common.enums.InitiatorSpecifiedRangeEnum;
import cn.axzo.workflow.common.enums.SignApproverOrgLimitEnum;
import cn.axzo.workflow.common.enums.SignApproverRoleLimitEnum;
@ -64,6 +67,9 @@ import static cn.axzo.workflow.common.constant.BpmnConstants.CONFIG_APPROVE;
import static cn.axzo.workflow.common.constant.BpmnConstants.CONFIG_APPROVER_EMPTY_HANDLE_TYPE;
import static cn.axzo.workflow.common.constant.BpmnConstants.CONFIG_APPROVER_SCOPE;
import static cn.axzo.workflow.common.constant.BpmnConstants.CONFIG_APPROVER_SPECIFY;
import static cn.axzo.workflow.common.constant.BpmnConstants.CONFIG_APPROVE_SPECIFY_COOPERATE_TYPE;
import static cn.axzo.workflow.common.constant.BpmnConstants.CONFIG_APPROVE_SPECIFY_RANGE;
import static cn.axzo.workflow.common.constant.BpmnConstants.CONFIG_APPROVE_SPECIFY_RANGE_UNIT;
import static cn.axzo.workflow.common.constant.BpmnConstants.CONFIG_BUTTON;
import static cn.axzo.workflow.common.constant.BpmnConstants.CONFIG_BUTTON_META;
import static cn.axzo.workflow.common.constant.BpmnConstants.CONFIG_BUTTON_TYPE_CARBON_COPY;
@ -99,6 +105,7 @@ import static cn.axzo.workflow.common.constant.BpmnConstants.ELEMENT_ATTRIBUTE_O
import static cn.axzo.workflow.common.constant.BpmnConstants.ELEMENT_ATTRIBUTE_ORG_LIMIT;
import static cn.axzo.workflow.common.constant.BpmnConstants.ELEMENT_ATTRIBUTE_TYPE;
import static cn.axzo.workflow.common.constant.BpmnConstants.ELEMENT_ATTRIBUTE_VALUE;
import static cn.axzo.workflow.common.constant.BpmnConstants.FLOW_CATEGORY_VERSION;
import static cn.axzo.workflow.common.constant.BpmnConstants.FLOW_SERVER_VERSION;
import static cn.axzo.workflow.common.constant.BpmnConstants.SUPPORT_BATCH_OPERATION_DEFAULT_VALUE;
import static cn.axzo.workflow.common.constant.BpmnConstants.TEMPLATE_CARBON_COPY_MESSAGE_ID;
@ -132,6 +139,21 @@ public final class BpmnMetaParserHelper {
return Optional.ofNullable(process.getAttributeValue(null, FLOW_SERVER_VERSION));
}
public static Optional<Integer> getCategoryVersion(Process process) {
String categoryVersion = process.getAttributeValue(null, FLOW_CATEGORY_VERSION);
if (StringUtils.hasText(categoryVersion)) {
try {
return Optional.of(Integer.parseInt(categoryVersion));
} catch (NumberFormatException e) {
// 如果转换失败返回空
return Optional.of(0);
}
} else {
// 如果没有设置版本号返回空
return Optional.of(0);
}
}
public static Optional<BpmnApproveConf> getProcessApproveConf(Process process) {
List<ExtensionElement> elements = process.getExtensionElements().getOrDefault(CONFIG_APPROVE, Collections.emptyList());
BpmnApproveConf conf = new BpmnApproveConf();
@ -453,6 +475,57 @@ public final class BpmnMetaParserHelper {
return defaultValid(userTask, CONFIG_APPROVER_SPECIFY).map(element -> ApproverSpecifyEnum.valueOf(element.getAttributeValue(null, ELEMENT_ATTRIBUTE_VALUE)));
}
public static Optional<ApproverSpecifyRangeEnum> getApproverSpecifyRange(FlowElement flowElement) {
if (Objects.nonNull(flowElement) && flowElement instanceof UserTask) {
return getApproverSpecifyRange((UserTask) flowElement);
}
return Optional.empty();
}
public static Optional<ApproverSpecifyRangeEnum> getApproverSpecifyRange(UserTask userTask) {
Optional<ApproverSpecifyEnum> approverSpecify = getApproverSpecify(userTask);
if (approverSpecify.isPresent() && Objects.equals(approverSpecify.get(), ApproverSpecifyEnum.position_v2)) {
return defaultValid(userTask, CONFIG_APPROVER_SPECIFY).map(element -> ApproverSpecifyRangeEnum.valueOf(element.getChildElements()
.getOrDefault(CONFIG_APPROVE_SPECIFY_RANGE, Collections.emptyList())
.get(0).getAttributeValue(null, ELEMENT_ATTRIBUTE_VALUE)));
}
return Optional.empty();
}
public static Optional<CooperateShipTypeEnum> getCooperateShipType(FlowElement flowElement) {
if (Objects.nonNull(flowElement) && flowElement instanceof UserTask) {
return getCooperateShipType((UserTask) flowElement);
}
return Optional.empty();
}
public static Optional<CooperateShipTypeEnum> getCooperateShipType(UserTask userTask) {
Optional<ApproverSpecifyEnum> approverSpecify = getApproverSpecify(userTask);
if (approverSpecify.isPresent() && Objects.equals(approverSpecify.get(), ApproverSpecifyEnum.position_v2)) {
return defaultValid(userTask, CONFIG_APPROVER_SPECIFY).map(element -> CooperateShipTypeEnum.valueOf(element.getChildElements()
.getOrDefault(CONFIG_APPROVE_SPECIFY_COOPERATE_TYPE, Collections.emptyList())
.get(0).getAttributeValue(null, ELEMENT_ATTRIBUTE_VALUE)));
}
return Optional.empty();
}
public static Optional<ApproverSpecifyRangeUnitEnum> getApproverSpecifyRangeUnit(FlowElement flowElement) {
if (Objects.nonNull(flowElement) && flowElement instanceof UserTask) {
return getApproverSpecifyRangeUnit((UserTask) flowElement);
}
return Optional.empty();
}
public static Optional<ApproverSpecifyRangeUnitEnum> getApproverSpecifyRangeUnit(UserTask userTask) {
Optional<ApproverSpecifyEnum> approverSpecify = getApproverSpecify(userTask);
if (approverSpecify.isPresent() && Objects.equals(approverSpecify.get(), ApproverSpecifyEnum.position_v2)) {
return defaultValid(userTask, CONFIG_APPROVER_SPECIFY).map(element -> ApproverSpecifyRangeUnitEnum.valueOf(element.getChildElements()
.getOrDefault(CONFIG_APPROVE_SPECIFY_RANGE_UNIT, Collections.emptyList())
.get(0).getAttributeValue(null, ELEMENT_ATTRIBUTE_VALUE)));
}
return Optional.empty();
}
public static Optional<InitiatorSpecifiedRangeEnum> getInitiatorSpecifyRange(FlowElement flowElement) {
if (Objects.nonNull(flowElement) && flowElement instanceof UserTask) {
return getInitiatorSpecifyRange((UserTask) flowElement);
@ -505,7 +578,7 @@ public final class BpmnMetaParserHelper {
return Optional.empty();
}
public static Optional<List<String>> getExcludeCooperateShipTypes(FlowElement flowElement) {
public static Optional<List<String>> getExcludeCooperateShipTypes(FlowElement flowElement) {
if (Objects.nonNull(flowElement) && flowElement instanceof UserTask) {
return getExcludeIdentityTypes((UserTask) flowElement);
}
@ -535,6 +608,17 @@ public final class BpmnMetaParserHelper {
return defaultValid(userTask, CONFIG_APPROVER_SPECIFY).map(element -> StringUtils.hasLength(element.getElementText()) ? element.getElementText() : "[]");
}
public static Optional<String> getApproverSpecifyValueV2(FlowElement flowElement) {
if (Objects.nonNull(flowElement) && flowElement instanceof UserTask) {
return getApproverSpecifyValueV2((UserTask) flowElement);
}
return Optional.empty();
}
public static Optional<String> getApproverSpecifyValueV2(UserTask userTask) {
return defaultValid(userTask, CONFIG_APPROVER_SPECIFY).map(element -> element.getChildElements().getOrDefault(TEMPLATE_UPGRADE_APPROVAL_SPECIFY_VALUE, Collections.emptyList()).get(0).getElementText());
}
public static Optional<ApproverEmptyHandleTypeEnum> getApproverEmptyHandleType(FlowElement flowElement) {
if (Objects.nonNull(flowElement) && flowElement instanceof UserTask) {
return getApproverEmptyHandleType((UserTask) flowElement);

View File

@ -319,19 +319,32 @@ public class UserTaskJsonConverter extends AbstractBpmnJsonConverter<UserTask> {
cooperateShipTypeDescAttribute.setName(ELEMENT_ATTRIBUTE_DESC);
cooperateShipTypeDescAttribute.setValue(property.getCooperateShipType().getDesc());
cooperateShipType.addAttribute(cooperateShipTypeDescAttribute);
approverSpecifyRangePosition.addChildElement(cooperateShipType);
approverSpecifyElement.addChildElement(cooperateShipType);
ExtensionElement approverSpecifyRangeUnit = new ExtensionElement();
approverSpecifyRangeUnit.setName(CONFIG_APPROVE_SPECIFY_RANGE_UNIT);
ExtensionAttribute approverSpecifyRangeUnitAttribute = new ExtensionAttribute();
approverSpecifyRangeUnitAttribute.setName(ELEMENT_ATTRIBUTE_VALUE);
approverSpecifyRangeUnitAttribute.setValue(property.getApproverSpecifyRangeUnit().getType());
approverSpecifyRangeUnit.addAttribute(approverSpecifyRangeUnitAttribute);
ExtensionAttribute approverSpecifyRangeUnitDescAttribute = new ExtensionAttribute();
approverSpecifyRangeUnitDescAttribute.setName(ELEMENT_ATTRIBUTE_DESC);
approverSpecifyRangeUnitDescAttribute.setValue(property.getApproverSpecifyRangeUnit().getDesc());
approverSpecifyRangeUnit.addAttribute(approverSpecifyRangeUnitDescAttribute);
approverSpecifyElement.addChildElement(approverSpecifyRangeUnit);
break;
case specified_org:
checkCascadeConfig(property, "岗位“审批单指定的末级组织”");
addCascadeConfig(property, approverSpecifyRangePosition);
addCascadeConfig(property, approverSpecifyElement);
break;
case initiator:
checkCascadeConfig(property, "岗位“审批单发起人”");
addCascadeConfig(property, approverSpecifyRangePosition);
addCascadeConfig(property, approverSpecifyElement);
break;
case pre_node_approver:
checkCascadeConfig(property, "岗位“上节点审批人”");
addCascadeConfig(property, approverSpecifyRangePosition);
addCascadeConfig(property, approverSpecifyElement);
break;
default:
break;
@ -374,15 +387,15 @@ public class UserTaskJsonConverter extends AbstractBpmnJsonConverter<UserTask> {
break;
case specified_org:
checkCascadeConfig(property, "角色“审批单指定的末级组织”");
addCascadeConfig(property, approverSpecifyRangeRole);
addCascadeConfig(property, approverSpecifyElement);
break;
case initiator:
checkCascadeConfig(property, "角色“审批单发起人”");
addCascadeConfig(property, approverSpecifyRangeRole);
addCascadeConfig(property, approverSpecifyElement);
break;
case pre_node_approver:
checkCascadeConfig(property, "角色“上节点审批人”");
addCascadeConfig(property, approverSpecifyRangeRole);
addCascadeConfig(property, approverSpecifyElement);
break;
default:
break;
@ -407,28 +420,18 @@ public class UserTaskJsonConverter extends AbstractBpmnJsonConverter<UserTask> {
switch (property.getApproverSpecifyRange()) {
case positions_within_the_project_construction_units:
// if (Objects.isNull(property.getCooperateShipType())) {
// throw new WorkflowEngineException(CONVERTOR_COMMON_ERROR, "身份“项目内角色”缺少级联配置");
// }
// ExtensionElement cooperateShipType = new ExtensionElement();
// cooperateShipType.setName(CONFIG_APPROVE_SPECIFY_COOPERATE_TYPE);
// ExtensionAttribute cooperateShipTypeAttribute = new ExtensionAttribute();
// cooperateShipTypeAttribute.setName(ELEMENT_ATTRIBUTE_VALUE);
// cooperateShipTypeAttribute.setValue(property.getCooperateShipType().name());
// cooperateShipType.addAttribute(cooperateShipTypeAttribute);
// approverSpecifyRangeIdentity.addChildElement(cooperateShipType);
throw new WorkflowEngineException(CONVERTOR_COMMON_ERROR, "身份不支持“项目内参建单位的企业身份”选项");
case specified_org:
checkCascadeConfig(property, "身份“审批单指定的末级组织”");
addCascadeConfig(property, approverSpecifyRangeIdentity, false);
addCascadeConfig(property, approverSpecifyElement, false);
break;
case initiator:
checkCascadeConfig(property, "身份“审批单发起人”");
addCascadeConfig(property, approverSpecifyRangeIdentity, false);
addCascadeConfig(property, approverSpecifyElement, false);
break;
case pre_node_approver:
checkCascadeConfig(property, "身份“上节点审批人”");
addCascadeConfig(property, approverSpecifyRangeIdentity, false);
addCascadeConfig(property, approverSpecifyElement, false);
break;
default:
break;
@ -612,17 +615,17 @@ public class UserTaskJsonConverter extends AbstractBpmnJsonConverter<UserTask> {
}
}
private static void addCascadeConfig(BpmnJsonNodeProperty property, ExtensionElement approverSpecifyRange) {
addCascadeConfig(property, approverSpecifyRange, true);
private static void addCascadeConfig(BpmnJsonNodeProperty property, ExtensionElement parentElement) {
addCascadeConfig(property, parentElement, true);
}
/**
* 添加级联配置协议转换
*
* @param property
* @param approverSpecifyRange
* @param parentElement
*/
private static void addCascadeConfig(BpmnJsonNodeProperty property, ExtensionElement approverSpecifyRange, boolean containsRangeUnit) {
private static void addCascadeConfig(BpmnJsonNodeProperty property, ExtensionElement parentElement, boolean containsRangeUnit) {
ExtensionElement specifiedOrg = new ExtensionElement();
specifiedOrg.setName(CONFIG_APPROVE_SPECIFY_RANGE_ORG_LIMIT);
ExtensionAttribute specifiedOrgAttribute = new ExtensionAttribute();
@ -634,7 +637,7 @@ public class UserTaskJsonConverter extends AbstractBpmnJsonConverter<UserTask> {
specifiedOrgDescAttribute.setName(ELEMENT_ATTRIBUTE_DESC);
specifiedOrgDescAttribute.setValue(property.getApproverSpecifyRangeOrgLimit().getDesc());
specifiedOrg.addAttribute(specifiedOrgDescAttribute);
approverSpecifyRange.addChildElement(specifiedOrg);
parentElement.addChildElement(specifiedOrg);
if (containsRangeUnit) {
ExtensionElement approverSpecifyRangeUnit = new ExtensionElement();
@ -648,7 +651,7 @@ public class UserTaskJsonConverter extends AbstractBpmnJsonConverter<UserTask> {
approverSpecifyRangeUnitDescAttribute.setName(ELEMENT_ATTRIBUTE_DESC);
approverSpecifyRangeUnitDescAttribute.setValue(property.getApproverSpecifyRangeUnit().getDesc());
approverSpecifyRangeUnit.addAttribute(approverSpecifyRangeUnitDescAttribute);
approverSpecifyRange.addChildElement(approverSpecifyRangeUnit);
parentElement.addChildElement(approverSpecifyRangeUnit);
}
}

View File

@ -63,6 +63,7 @@ import static cn.axzo.workflow.common.model.request.bpmn.task.BpmnTaskDelegateAs
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getApprovalMethod;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getApproverEmptyHandleType;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getApproverSpecify;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getCategoryVersion;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getNodeType;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getProcessServerVersion;
import static cn.axzo.workflow.core.engine.cmd.helper.CustomTaskHelper.getLimitedElementList;
@ -102,11 +103,12 @@ public class EngineExecutionStartListener implements ExecutionListener {
// version=1.2.1-SNAPSHOT 开始才给 process 节点增加了 serverVersion 属性
Optional<String> processServerVersion = getProcessServerVersion(mainProcess);
Optional<Integer> categoryVersion = getCategoryVersion(mainProcess);
if (processServerVersion.isPresent()) {
// 创建检查下个节点的配置
createCheckNextActivityJob(execution.getProcessInstanceId(), currentActivityId);
calcTaskAssigner121(execution, userTask, processServerVersion.get(), assigneeListVariableName,
currentActivityId);
currentActivityId, categoryVersion.orElse(0));
} else {
calcTaskAssignerDefault(execution, userTask, currentActivityId, assigneeListVariableName);
}
@ -139,7 +141,7 @@ public class EngineExecutionStartListener implements ExecutionListener {
}
private void calcTaskAssigner121(DelegateExecution execution, UserTask userTask, String processServerVersion,
String assigneeListVariableName, String currentActivityId) {
String assigneeListVariableName, String currentActivityId, Integer categoryVersion) {
Optional<BpmnFlowNodeType> nodeType = getNodeType(userTask);
DefaultArtifactVersion supportVersion = new DefaultArtifactVersion(FLOW_SERVER_VERSION_121);
DefaultArtifactVersion currentVersion = new DefaultArtifactVersion(processServerVersion);
@ -184,8 +186,11 @@ public class EngineExecutionStartListener implements ExecutionListener {
assigners.addAll(approverSelect(specify.getType(), userTask, execution, true));
});
// 审批候选人为空时的兜底
emptyAssigneeHandle(assigners, userTask, execution);
// 只有老版本的配置会走这里, 新版本配置会直接在找过的过程中直接由人岗架接口内部处理超管
if (categoryVersion < 2) {
// 审批候选人为空时的兜底,
emptyAssigneeHandle(assigners, userTask, execution);
}
List<BpmnTaskDelegateAssigner> resultAssigners = getLimitedElementList(assigners, APPROVAL_ASSIGNER_LIMIT_NUMBER);
for (BpmnTaskDelegateAssigner user : resultAssigners) {
assigneeIdList.add(user.buildAssigneeId());

View File

@ -165,7 +165,8 @@ public class BpmnProcessDefinitionServiceImpl implements BpmnProcessDefinitionSe
dto.getJsonModel().getNoticeConf(),
dto.getJsonModel().getButtonConf(),
dto.getJsonModel().getFieldConf(),
serviceVersion);
serviceVersion,
optCategory.get().getVersion());
byte[] bpmn = BpmnJsonConverterUtil.transformBytes(bpmnModel);
updateProcessDefinition(model.getId(), bpmn);
}

View File

@ -282,7 +282,8 @@ public class BpmnProcessModelServiceImpl implements BpmnProcessModelService {
dto.getJsonModel().getNoticeConf(),
dto.getJsonModel().getButtonConf(),
dto.getJsonModel().getFieldConf(),
serviceVersion);
serviceVersion,
optCategory.get().getVersion());
BpmnJsonConverterUtil.setCategory(bpmnModel, dto.getKey());
byte[] bpmn = BpmnJsonConverterUtil.transformBytes(bpmnModel);
processDefinitionService.updateProcessDefinition(model.getId(), bpmn);
@ -376,7 +377,8 @@ public class BpmnProcessModelServiceImpl implements BpmnProcessModelService {
dto.getJsonModel().getNoticeConf(),
dto.getJsonModel().getButtonConf(),
dto.getJsonModel().getFieldConf(),
serviceVersion);
serviceVersion,
optCategory.get().getVersion());
BpmnJsonConverterUtil.setCategory(bpmnModel, dto.getKey());
byte[] bpmn = BpmnJsonConverterUtil.transformBytes(bpmnModel);
processDefinitionService.updateProcessDefinition(originModel.getId(), bpmn);

View File

@ -0,0 +1,87 @@
package cn.axzo.workflow.server.controller.delegate;
import cn.axzo.orggateway.api.nodeuser.OrgNodeUserApi;
import cn.axzo.orggateway.api.nodeuser.dto.FlowTaskAssignerScopeDTO;
import cn.axzo.orggateway.api.nodeuser.enums.FlowTaskAssignerQuerySceneEnum;
import cn.axzo.orggateway.api.nodeuser.req.FlowTaskAssignerV2Req;
import cn.axzo.workflow.common.enums.ApproverSpecifyEnum;
import cn.axzo.workflow.common.enums.ApproverSpecifyRangeEnum;
import cn.axzo.workflow.common.enums.CooperateShipTypeEnum;
import cn.axzo.workflow.common.enums.SignApproverOrgLimitEnum;
import cn.axzo.workflow.common.exception.WorkflowEngineException;
import cn.axzo.workflow.common.model.dto.CooperationOrgDTO;
import cn.axzo.workflow.common.model.request.bpmn.task.BpmnTaskDelegateAssigner;
import com.google.common.collect.Sets;
import lombok.extern.slf4j.Slf4j;
import org.flowable.bpmn.model.FlowElement;
import org.flowable.engine.delegate.DelegateExecution;
import org.springframework.stereotype.Component;
import javax.annotation.Resource;
import java.util.Collections;
import java.util.List;
import java.util.Optional;
import static cn.axzo.workflow.common.code.FlowableEngineRespCode.ENGINE_POSITION_V2_CONFIG_INVALID;
import static cn.axzo.workflow.common.constant.BpmnConstants.BIZ_ORG_RELATION;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getApproverSpecifyRange;
import static cn.axzo.workflow.core.common.utils.BpmnMetaParserHelper.getCooperateShipType;
/**
* 基于新版配置的岗位查询审批人
*
* @author wangli
* @since 2025-08-15 10:58
*/
@Slf4j
@Component
public class BasedPositionV2TaskAssigneeSelector extends AbstractBpmnTaskAssigneeSelector {
@Resource
private OrgNodeUserApi orgNodeUserApi;
@Override
public String getType() {
return ApproverSpecifyEnum.position_v2.getType();
}
@Override
public List<BpmnTaskDelegateAssigner> select(FlowElement flowElement, DelegateExecution execution, Boolean throwException) {
Optional<ApproverSpecifyRangeEnum> optRange = getApproverSpecifyRange(flowElement);
if (!optRange.isPresent()) {
throw new WorkflowEngineException(ENGINE_POSITION_V2_CONFIG_INVALID, "级联配置", flowElement.getId());
}
CooperationOrgDTO orgDTO = (CooperationOrgDTO) execution.getVariables().get(BIZ_ORG_RELATION);
FlowTaskAssignerV2Req.FlowTaskAssignerV2ReqBuilder v2ReqBuilder = FlowTaskAssignerV2Req.builder()
.scene(FlowTaskAssignerQuerySceneEnum.BY_JOB);
switch (optRange.get()) {
case positions_within_the_project:
v2ReqBuilder.scope(FlowTaskAssignerScopeDTO.builder()
.nodeId(orgDTO.getNodeId())
.upLevel(SignApproverOrgLimitEnum.LV_ALL.getCode())
.crossDomain(false)
.build());
break;
case positions_within_the_project_construction_units:
CooperateShipTypeEnum workflowType = getCooperateShipType(flowElement).orElseThrow(() -> new WorkflowEngineException(ENGINE_POSITION_V2_CONFIG_INVALID, "缺少参建单位类型配置", flowElement.getId()));
cn.axzo.orgmanax.dto.cooperateship.enums.CooperateShipTypeEnum cooperateShipTypeEnum = cn.axzo.orgmanax.dto.cooperateship.enums.CooperateShipTypeEnum.valueOf(workflowType.name());
v2ReqBuilder.scope(FlowTaskAssignerScopeDTO.builder()
.nodeId(orgDTO.getNodeId())
.upLevel(SignApproverOrgLimitEnum.LV_ALL.getCode())
.cooperateTypes(Sets.newHashSet(cooperateShipTypeEnum))
.crossDomain(true)
.build());
break;
case specified_org:
break;
case initiator:
break;
case pre_node_approver:
break;
default:
break;
}
orgNodeUserApi.listFlowTaskAssignerV2(v2ReqBuilder.build());
return Collections.emptyList();
}
}

File diff suppressed because one or more lines are too long

View File

@ -13,11 +13,13 @@
"id": "node_779068202795_ltht",
"parentId": "NODE_STARTER",
"property": {
"approverSpecify": "initiatorSpecified_v2",
"initiatorSpecifyRange": "self_and_children_in_project",
"initiatorSpecifiedFilter": true,
"excludeIdentityTypes": ["1", "2"],
"excludeCooperateShipTypes": ["3","4"],
"approverSpecify": "position_v2",
"approverSpecifyRange": "positions_within_the_project_construction_units",
"cooperateShipType": "PROJ_SUPERVISION_UNIT",
"approverSpecifyRangeUnit": "in_group_lv_1",
// "initiatorSpecifiedFilter": true,
// "excludeIdentityTypes": ["1", "2"],
// "excludeCooperateShipTypes": ["3","4"],
"approvalMethod": "human",
"multiMode": "AND",
"sign": false,