这些数据的页面结构是这样的:
这些数据是从form表单的values获取的,通过数字下标可以区分有几组数据,并且区分一组数据里面又有几组二级数据
要转成成树形结构的数据:
所以要对values那些数据进行处理:
// 点击提交按钮时调用form表单校验函数
const handleSave = () => {
form.validateFields().then(values => {
const arr = Object.entries(values); // 处理values(有两层数组,把key和value拆开来了)
// 处理arr,把key和value都存进一个数组里面
const value = [];
arr?.map(v => {
const arrs = v[0]; // key
const arrs2 = v[1]; // value
if (arrs?.split('_')?.length > 1) {
value.push({ key: arrs?.split('_'), value: arrs2});
}
return v;
});
// 对value进行扁平化处理
const keyResult = value?.map(k => {
if (k.key.length === 2) {
const [key, panelIndex] = k.key;
return {...k, key, panelIndex};
} else {
const [key, panelIndex, index] = k.key;
return {...k, key, panelIndex, index};
}
});
// 把修改后的数据放进list里面,通过遍历原来的panels即可
const list = panels?.map(v => {
// 拆分不同的折叠面板的数据
const arr = keyResult.filter(item => Number(item.panelIndex) === v.key);
// 拆分多层级表单(有index就说明是枚举值那一块的表单)
const firstList = arr.filter(item => !item.index); // 二级表单(菜单名称,类型)
const secondList = arr.filter(item => item.index); // 三级表单(枚举值,维度)
// 合并对象(二级表单)
let firstPanel = {};
firstList.forEach(item => {
firstPanel = { ...firstPanel, [item.key]: item.value };
});
// 三级表单(数量不固定,要合并对象后放入一个数组里面存起来)
const secondPanel = [];
// 通过index可以区分是否是同一行表单,是一行就放入一个对象里面
_.values(_.groupBy(secondList, 'index')).forEach(itemList => {
let data = {};
itemList.forEach(d => {
data = { ...data, [d.key]: d.value, key: Number(d.index) }; // key要加上,防止保存时表单会显示空
});
return secondPanel.push(data);
});
const mergeList = { ...firstPanel, permission: [...secondPanel] }
return { ...v, ...mergeList }
});
// 判断菜单名称是否重复,只要有两个是一样就判断为重复
const dataRepeat = list.map(v => v.resourceName);
const dataRepeat2 = [];
dataRepeat.forEach(v => {
if (v.indexOf('-') > -1) {
dataRepeat2.push(v.split('-')[0]);
} else {
dataRepeat2.push(v);
}
});
setPanels(list);
// 传参
const params = {
permissionCategorys: [
{
permissionCategory: values.permissionCategory,
resourceNames: list?.map(i => {
return {
permissionType: i.permissionType?.toString(),
resourceId: i.resourceName?.split('-')[1] || i.resourceId,
resourceName: i.resourceName?.split('-')[0],
permission: i.permission?.map(v => {
return {
permissionKey: v.permissionKey,
permissionValue: v.permissionValue,
};
}),
};
}),
},
],
};
// 判断折叠面板里面的数据是否发生改变
const data = [];
// rowPanels是一进这个页面获取到的数据,拿来跟改变后的数据进行对比
rowPanels?.forEach(it => {
// 把跟params里没有的字段去掉,要保证字段的统一才能进行比较
const { key, ...restData } = it;
if (it.permission) {
it.permission?.forEach(i => {
const { key, isCheckedValue, ...restData2 } = i;
data.push({
...restData,
permission: [{ ...restData2 }],
permissionType: it.permissionType.join(','),
});
});
}
});
// loadsh里面有个isEqual可以深度比较两个数组是否相同
const isChange = _.isEqual(params.permissionCategorys[0].resourceNames, data);
// 判断菜单名称是否重复,利用去重,如果数量相同,则无重复,反之...
if (dataRepeat2.length === new Set(dataRepeat2).size) {
// 判断进这个页面是新增还是编辑,区分接口isType是上级页面传过来的字段
if (isType === 'edit') {
// 判断折叠面板数据是否发生变动
if (isChange) {
console.log('相同,直接调编辑接口')
} else {
console.log('不相同,弹框提示用户,调编辑接口')
}
} else {
console.log('新增接口')
}
} else {
message.error('菜单名称不能重复!')
}
});
}
至此,数据就处理好了,传给后端就可以正常调接口了。