From: root Date: Thu, 10 Sep 2026 04:03:31 +0000 (+0800) Subject: feat(device-templates): 列表新增所属领域列,以彩色标签展示关联领域 X-Git-Url: http://acesimba.cloud/gitweb/?a=commitdiff_plain;h=08a68438eeeee189f67f5d98546ec56a825aac12;p=StationBuilder.git feat(device-templates): 列表新增所属领域列,以彩色标签展示关联领域 --- diff --git a/app/globals.css b/app/globals.css index 6a570bc..bbbb78c 100644 --- a/app/globals.css +++ b/app/globals.css @@ -320,7 +320,7 @@ html,body{font-family:Roboto,"Noto Sans SC","Microsoft YaHei",Arial,sans-serif;f .resource-table th:nth-child(7),.resource-table td:nth-child(7){width:96px}.resource-table th:nth-child(8),.resource-table td:nth-child(8){width:180px} .domain-resource-table th:first-child,.domain-resource-table td:first-child{width:260px;min-width:260px;text-align:left}.domain-resource-table .company-record-link{display:block;max-width:100%;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;text-align:left} .resource-detail>p{margin:8px 0;color:#666;line-height:1.8;white-space:pre-wrap}.resource-detail-image{display:block;width:100%;max-height:220px;object-fit:contain;border:1px solid var(--company-border);background:#f5f5f5;margin-bottom:20px} -.device-resource-table{min-width:760px}.device-resource-table th:nth-child(1),.device-resource-table td:nth-child(1){width:280px;min-width:280px;text-align:left}.device-resource-table th:nth-child(2),.device-resource-table td:nth-child(2){width:auto}.device-resource-table th:nth-child(3),.device-resource-table td:nth-child(3){width:90px;text-align:center}.device-resource-table th:nth-child(4),.device-resource-table td:nth-child(4){width:110px}.device-resource-table th:nth-child(5),.device-resource-table td:nth-child(5){width:64px}.device-resource-table .company-record-link{display:block;max-width:100%;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;text-align:left} +.device-resource-table{min-width:860px}.device-resource-table th:nth-child(1),.device-resource-table td:nth-child(1){width:280px;min-width:280px;text-align:left}.device-resource-table th:nth-child(2),.device-resource-table td:nth-child(2){width:auto}.device-resource-table th:nth-child(3),.device-resource-table td:nth-child(3){width:90px;text-align:center}.device-resource-table th:nth-child(4),.device-resource-table td:nth-child(4){width:110px}.device-resource-table th:nth-child(5),.device-resource-table td.domain-cell{width:180px;min-width:140px;text-align:left;white-space:normal}.device-resource-table th:nth-child(6),.device-resource-table td:nth-child(6){width:64px}.device-resource-table .company-record-link{display:block;max-width:100%;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;text-align:left} .resource-name-cell{display:flex;align-items:center;gap:12px;min-width:0}.resource-name-cell>img,.resource-placeholder{flex:none;width:48px;height:36px;border:1px solid var(--company-border);background:#f5f5f5;object-fit:cover;border-radius:2px}.resource-placeholder{display:grid;place-items:center;color:#999}.resource-name-cell .company-record-link{min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;text-align:left} .resource-point-list{border-top:1px solid #eee}.resource-point-list>div{height:40px;border-bottom:1px solid #eee;display:flex;align-items:center;justify-content:space-between}.resource-point-list span{color:var(--company-muted)}.resource-point-list>p{color:var(--company-muted)} .resource-back{height:44px;display:flex;align-items:center;border-bottom:1px solid var(--company-border);margin:0 0 16px}.resource-back .text-button{margin:0} diff --git a/app/page.tsx b/app/page.tsx index 5be30ed..eb38708 100644 --- a/app/page.tsx +++ b/app/page.tsx @@ -75,6 +75,14 @@ function Status({children}:{children:React.ReactNode}){const v=String(children); function Button({children,secondary,onClick,disabled,title}:{children:React.ReactNode;secondary?:boolean;onClick?:()=>void;disabled?:boolean;title?:string}){return {children}} function Panel({title,tools,children,className=""}:{title?:string;tools?:React.ReactNode;children:React.ReactNode;className?:string}){return
{title&&
{title}
{tools}
}
{children}
} function Field({label,required,hint,children}:{label:string;required?:boolean;hint?:string;children:React.ReactNode}){return } +function domainTagColor(name:string){ + const map:Record={"数据中心":"#009fe3","智慧水务":"#00b96b","燃气":"#ff990b","水务 · 自来水厂":"#42d067","新能源":"#7c3aed","其他":"#888888"}; + if(map[name]) return map[name]; + const palette=["#009fe3","#00b96b","#ff990b","#42d067","#7c3aed","#f05b49","#008cd6","#e58c35","#6d5ee9","#25a85b"]; + let hash=0; for(let i=0;i{name};} async function fetchDb(path:string, opts?:RequestInit){ const res = await fetch(`/api/db${path}`, opts); @@ -2478,6 +2486,7 @@ function CompanyDeviceTemplates({notify,onViewCpPrompt}:{notify:(m:string)=>void const load=async()=>{ try{ setList(await fetchDb("/device-templates") as any[]); }catch(e:any){ notify("加载失败:"+e.message); }finally{ setLoading(false); } }; useEffect(()=>{ load(); },[]); const pointCount=(row:any)=>(row.collection_points||[]).length; + const domainNames=(row:any)=>{ try{ return JSON.parse(row.domain_names||"[]") as string[]; }catch{ return []; } }; const remove=async(row:any)=>{ if(!(await confirm(`确定删除设备模板「${row.name}」?`))) return; try{ await fetchDb(`/device-templates/${row.id}`,{method:"DELETE"}); setPreview(null); await load(); notify("设备模板已删除"); }catch(e:any){ notify("删除失败:"+e.message); } }; const counts=useMemo(()=>({all:list.length,configured:list.filter(x=>pointCount(x)>0).length,empty:list.filter(x=>pointCount(x)===0).length}),[list]); const filtered=useMemo(()=>list.filter(row=>(!pointFilter||(pointFilter==="configured"?pointCount(row)>0:pointCount(row)===0))&&(!query.trim()||`${row.name} ${row.description||""}`.toLowerCase().includes(query.trim().toLowerCase()))),[list,pointFilter,query]); @@ -2494,7 +2503,7 @@ function CompanyDeviceTemplates({notify,onViewCpPrompt}:{notify:(m:string)=>void ].map(item=>)}
- {loading?
加载中…
:<>{filtered.slice((pageIndex-1)*pageSize,pageIndex*pageSize).map(row=>setPreview(row)}>)}
设备模板名称说明采集点配置状态操作
{row.description||"—"}{pointCount(row)}{pointCount(row)>0?"已配置":"待配置"}e.stopPropagation()}>},{key:"delete",label:"删除",danger:true,icon:}],onClick:({key})=>key==="edit"?setOpenId(row.id):remove(row)}}>}/>
{filtered.length===0&&
暂无符合条件的设备模板
}
{filtered.length} / 总数
} + {loading?
加载中…
:<>{filtered.slice((pageIndex-1)*pageSize,pageIndex*pageSize).map(row=>setPreview(row)}>)}
设备模板名称说明采集点配置状态所属领域操作
{row.description||"—"}{pointCount(row)}{pointCount(row)>0?"已配置":"待配置"}{domainNames(row).map(n=>)}e.stopPropagation()}>},{key:"delete",label:"删除",danger:true,icon:}],onClick:({key})=>key==="edit"?setOpenId(row.id):remove(row)}}>}/>
{filtered.length===0&&
暂无符合条件的设备模板
}
{filtered.length} / 总数
}
setPreview(null)} extra={preview&&}> {preview&&
{preview.image_path&&{preview.name}/}

基础信息

模板名称
{preview.name}
采集点数量
{pointCount(preview)}
配置状态
{pointCount(preview)>0?"已配置":"待配置"}

模板说明

{preview.description||"暂无说明"}

采集点预览

{(preview.collection_points||[]).slice(0,8).map((cp:any)=>
{cp.name}{cp.unit||cp.value_range||"—"}
)}{pointCount(preview)===0&&

暂无采集点

}
}