如何将REST API数据推入useState避免覆盖?点击时数据被覆盖问题
解决方案
你的问题出在每次更新状态时直接用新数据覆盖了原数组,没有基于之前的状态做追加或删除操作。要实现勾选添加、取消删除的逻辑,需要用函数式更新来获取最新的状态值,再根据复选框的选中状态处理数据。
修正后的代码示例
// 替换原来的getDataCategory,改用复选框的onChange事件处理 const handleCheckboxChange = async (event) => { const { id, checked } = event.target; // 统一用async/await处理请求,避免混用then const response = await fetch(`http://api.tmweb.com/category?filter[parent_id][in]=${id}&filter[type]=0`, { headers: { 'Accept': 'application/json', 'Authorization': token, }, }); const result = await response.json(); const targetData = result.data; // 函数式更新状态,确保拿到最新的prev状态 setCategorySub(prevCategory => { if (checked) { // 勾选时:添加数据,同时去重(根据id判断是否已存在) const newItems = targetData.filter(item => !prevCategory.some(existing => existing.id === item.id) ); return [...prevCategory, ...newItems]; } else { // 取消勾选时:移除对应的数据(匹配id) return prevCategory.filter(item => !targetData.some(toBeRemoved => toBeRemoved.id === item.id) ); } }); };
关键说明
- 函数式更新:
setCategorySub(prev => ...)能确保我们获取到最新的状态值,避免因状态异步更新导致的覆盖问题。 - 去重逻辑:添加数据时先过滤掉已存在的项,防止数组里出现重复数据。
- 删除逻辑:取消勾选时,通过id匹配移除对应的数据项。
- 统一异步处理:把原来的
await和then混用改成纯async/await,代码更清晰易维护。
内容的提问来源于stack exchange,提问作者Александр
相关产品推荐
相关产品推荐

