如何将带事件名称键的对象转为可使用.map()的结构渲染UI
问题描述
原始接口返回数据格式如下(对象结构,键为事件名称,值为对应事件列表):
{ "login": [ { "id": "clgtg0inx0005sy0llfq2gkvp", "user_id": "00004", "project_id": "clgqnhw9u0001syh9rbuvvpkv", "createdAt": "2023-04-23T13:26:20.541Z", "updatedAt": "2023-04-23T13:26:20.541Z" } ], "home_page": [ { "id": "clgtewvcw0003sy0lps4i694l", "user_id": "00004", "project_id": "clgqnhw9u0001syh9rbuvvpkv", "createdAt": "2023-04-23T12:55:30.753Z", "updatedAt": "2023-04-23T12:55:30.753Z" }, { "id": "clgtewood0001sy0lgevccham", "user_id": "00004", "project_id": "clgqnhw9u0001syh9rbuvvpkv", "createdAt": "2023-04-23T12:55:22.093Z", "updatedAt": "2023-04-23T12:55:22.093Z" } ], "event_3": [{...}], "event_4": [{...}] }
需求是将其渲染为嵌套列表(父项为事件名称,子项为事件详情),但因数据是对象格式,直接调用.map()会报错events.map is not a function,需要先转换数据结构。
之前尝试的分组函数方向错误(将数组转为对象,与需求相悖),无法实现预期效果:
const reGroup = (list, key) => { const newGroup = {}; list.forEach(item => { const newItem = Object.assign({}, item); delete newItem[key]; newGroup[item[key]] = newGroup[item[key]] || []; newGroup[item[key]].push(newItem); }); return newGroup; }; console.log(reGroup(res.data, 'name')); setEvents(reGroup(res.data, 'name'))
解决方案
1. 转换数据结构
使用Object.entries()将原始对象转为键值对数组,再映射为包含事件名称和对应列表的结构,适配.map()遍历:
// 假设originalData是接口返回的原始对象 const transformedEvents = Object.entries(originalData).map(([eventName, eventItems]) => ({ eventName, items: eventItems })); setEvents(transformedEvents);
2. 渲染嵌套列表
通过两层.map()实现嵌套结构渲染,外层遍历事件分组,内层遍历每个事件详情:
<ul> {events?.map((group, groupIndex) => ( <li key={groupIndex}> <strong>{group.eventName}</strong> <ul> {group.items.map((item, itemIndex) => ( <li key={itemIndex} className="df-row gap-l"> <InfoInput> {moment(new Date(item.createdAt)).format('MMM D, YYYY hh:mm a')} </InfoInput> <div> <p>ID: {item.id}</p> <p>用户ID: {item.user_id}</p> </div> </li> ))} </ul> </li> ))} </ul>
说明
Object.entries(originalData)会将对象转为[[key1, value1], [key2, value2], ...]的数组格式,完美适配.map()遍历- 转换后的每个元素包含
eventName(事件名称)和items(对应事件列表),清晰对应嵌套列表的层级关系
内容的提问来源于stack exchange,提问作者Sergio Casolari
相关产品推荐
相关产品推荐

