钉钉审批功能完善、混炼示方新增是否附加料

This commit is contained in:
geht
2026-06-10 15:41:02 +08:00
parent de48bd2324
commit 39a9bd83f1
37 changed files with 2461 additions and 166 deletions

View File

@@ -254,6 +254,12 @@
previewFlowApprovers,
} from '/@/views/xslmes/dingtalk/mesXslDingProcessTpl/MesXslDingProcessTpl.api';
import { checkCanLaunch } from '/@/views/approval/gate/approvalGate.api';
import { resolveFieldValues } from '/@/views/xslmes/dingtalk/dingTplBind/dingTplBind.api';
import {
type ValueMode,
getNestedValue,
resolveFieldValueLocal,
} from '/@/views/xslmes/dingtalk/dingTplBind/dingTplFieldValue';
const emit = defineEmits(['success']);
const { createMessage } = useMessage();
@@ -330,7 +336,7 @@
if (f.componentName === 'TableField') tableValues[f.label] = [];
}
applyPrefillForRow(currentRowIndex.value);
applyPrefillForRowAsync(currentRowIndex.value);
const presetFlowId = tplRecord?.flowId;
if (presetFlowId) {
@@ -357,7 +363,7 @@
if (idx === currentRowIndex.value) return;
currentRowIndex.value = idx;
resetFieldValues();
applyPrefillForRow(idx);
applyPrefillForRowAsync(idx);
activeTab.value = 'form';
}
@@ -370,10 +376,10 @@
}
}
function applyPrefillForRow(idx: number) {
async function applyPrefillForRowAsync(idx: number) {
const rowData = allRows.value[idx];
if (rowData && tplData.value?.fieldMappingJson) {
applyPrefill(dingFields.value, tplData.value.fieldMappingJson, rowData);
await applyPrefill(dingFields.value, tplData.value.fieldMappingJson, rowData);
}
}
@@ -401,13 +407,48 @@
componentName: string;
parentId?: string;
bizField?: string;
valueMode?: ValueMode;
}
function applyPrefill(fields: any[], mappingJson: string, rowData: any) {
async function applyPrefill(fields: any[], mappingJson: string, rowData: any) {
let mapping: MappingItem[] = [];
try { mapping = JSON.parse(mappingJson); } catch { return; }
try {
mapping = JSON.parse(mappingJson);
} catch {
return;
}
const byId = new Map(mapping.map(m => [m.componentId, m]));
const byId = new Map(mapping.map((m) => [m.componentId, m]));
// 主表 text 模式字段批量解析(明细列在各行上本地解析)
const resolveItems = mapping
.filter((m) => m.valueMode === 'text' && m.bizField && !m.parentId)
.map((m) => ({
mapKey: m.componentId,
bizField: m.bizField!,
valueMode: 'text',
}));
let resolvedMap: Record<string, any> = {};
if (resolveItems.length && tplData.value?.bizCode) {
try {
resolvedMap = (await resolveFieldValues({
bizCode: tplData.value.bizCode,
rowData,
items: resolveItems,
})) || {};
} catch {
resolvedMap = {};
}
}
function pickValue(m: MappingItem, bizField: string): any {
if (resolvedMap[m.componentId] !== undefined) {
return resolvedMap[m.componentId];
}
const mode = (m.valueMode || 'raw') as ValueMode;
return resolveFieldValueLocal(rowData, bizField, mode);
}
for (const field of fields) {
if (field.componentName === 'TextNote') continue;
@@ -420,34 +461,30 @@
const arr: any[] = getNestedValue(rowData, slotName);
if (!Array.isArray(arr) || !arr.length) continue;
const childMappings = mapping.filter(x => x.parentId === cid && x.bizField);
tableValues[field.label] = arr.map(element => {
const childMappings = mapping.filter((x) => x.parentId === cid && x.bizField);
tableValues[field.label] = arr.map((element) => {
const row: Record<string, string> = {};
for (const child of childMappings) {
const parts = (child.bizField || '').split('.');
const colKey = parts.slice(1).join('.');
const val = colKey ? getNestedValue(element, colKey) : undefined;
const mode = (child.valueMode || 'raw') as ValueMode;
const val = colKey ? resolveFieldValueLocal(element, colKey, mode) : undefined;
row[child.componentLabel] = val !== undefined && val !== null ? String(val) : '';
}
for (const child of (field.children || [])) {
for (const child of field.children || []) {
if (!(child.label in row)) row[child.label] = '';
}
return row;
});
} else {
if (!m?.bizField) continue;
const val = getNestedValue(rowData, m.bizField);
const val = pickValue(m, m.bizField);
if (val === undefined || val === null) continue;
formValues[field.label] = formatForDisplay(val, field.componentName);
}
}
}
function getNestedValue(obj: any, path: string): any {
if (!obj || !path) return undefined;
return path.split('.').reduce((acc: any, k: string) => acc?.[k], obj);
}
function formatForDisplay(v: any, componentName: string): any {
if (v === null || v === undefined) return '';
if (['NumberField', 'MoneyField'].includes(componentName)) {