配合后端「发布表单与模块页对齐」:前端补齐三类控件与序列化。
- FormCard: 新增 multiselect 与 scopes 多选控件(「全部 XX」哨兵恒为首项,
选中后仍可叠加具体项;提交时若只有哨兵则按 scopeType 折成
[{scopeType:1,scopeId:0,scopeName}]);新增 file 附件控件(带登录态 POST
multipart 到 uploadPath,遇登录跳转先预热模块会话再重试)
- FormCard: allFields 的表单渲染全部字段(不再只渲染缺失必填);file 控件
显示已传文件名并可移除
- types: widget 联合加 multiselect/file,FormField 补 joinSeparator/uploadPath/
multiple/allToken/allTokenLabel/scopeType,FormRequest 补 allFields
- module-session: parseOptionItems 支持 labelKey 用「+」拼多字段
(如 buildingName+roomNo →「1 号楼 101」),组织树自动拍平到叶子
验证:.scratch/verify-module-publish-form.mjs 真机断言三个发布表单
(notice 24/24、dorm 35/35、activity 33/33 通过),npm run build 通过
This commit is contained in:
@@ -147,11 +147,20 @@ export function parseOptionItems(
|
||||
const vk = valueKey || "id";
|
||||
const lk = labelKey || "name";
|
||||
const out: { value: string; label: string }[] = [];
|
||||
for (const item of arr) {
|
||||
// 组织树(年级→班级 / 学部→年级→班级)要拍平成叶子,否则下拉里只会出现「年级」这一层的 id。
|
||||
// 判定:任一项带非空 children 数组即视为树;否则按平铺字典处理(多数字典接口是平铺的)。
|
||||
const flat = arr.some(it => it && Array.isArray((it as any).children) && (it as any).children.length)
|
||||
? flattenLeaves(arr)
|
||||
: arr;
|
||||
for (const item of flat) {
|
||||
if (item == null || typeof item !== "object") continue;
|
||||
const v = (item as any)[vk];
|
||||
if (v === undefined || v === null || String(v) === "") continue;
|
||||
const l = (item as any)[lk];
|
||||
// labelKey 支持用「+」拼多个字段(如房间的 buildingName+roomNo →「1号楼 305」),
|
||||
// 因为这类 VO 里没有现成的展示名,靠单一字段会出现「同名房间分不清楼栋」。
|
||||
const l = lk.includes("+")
|
||||
? lk.split("+").map(k => (item as any)[k.trim()]).filter(V => V !== undefined && V !== null && String(V) !== "").join(" ")
|
||||
: (item as any)[lk];
|
||||
out.push({
|
||||
value: String(v),
|
||||
label: l === undefined || l === null || String(l) === "" ? String(v) : String(l),
|
||||
@@ -160,6 +169,17 @@ export function parseOptionItems(
|
||||
return out;
|
||||
}
|
||||
|
||||
/** 把「组→子」的树拍平成叶子列表(叶子 = 没有非空 children 的节点) */
|
||||
function flattenLeaves(nodes: any[]): any[] {
|
||||
const out: any[] = [];
|
||||
for (const n of nodes || []) {
|
||||
const kids = n && Array.isArray(n.children) ? n.children : null;
|
||||
if (kids && kids.length) out.push(...flattenLeaves(kids));
|
||||
else out.push(n);
|
||||
}
|
||||
return out;
|
||||
}
|
||||
|
||||
/** 递归找第一个数组(限深,容忍 data 外面再包一层 list/records/rows) */
|
||||
function findArray(node: any, depth: number): any[] | null {
|
||||
if (node == null || depth > 3) return null;
|
||||
|
||||
Reference in New Issue
Block a user