React表格点击Apply按钮无法提交数据到API问题排查
功能需求
- 表格默认仅展示
apply字段值为0的数据 - 点击
Apply按钮时,向API提交全量行的应用状态,提交数据格式示例:data:{apply: [3], notApply:[1,2]}apply数组内的ID对应行apply值为1,不在表格中展示notApply数组内的ID对应行apply值为0,在表格中展示
运行异常
- 点击「显示」列的toggle开关后,对应行
apply状态置为1并隐藏的逻辑未生效 - 点击
Cancel按钮后未向API发送任何请求
未生效的实现代码
export default function MenuDisplayApi() { const { menuId } = useParams(); const { match } = JsonData; const [selected, setSelected] = useState({}); const [hidden, setHidden] = useState({}); const [menus, setMenus] = useState([]); const [applyStatus, setApplyStatus]=useState(false) useEffect(() => { axios.post(url,{menuId:parseInt(menuId)}) .then(res => { console.log(res) setMenus(res.data.menus) }) .catch(err => { console.log(err) }) }, [menuId]); // 存在选中行时按钮为Apply状态,否则为Cancel状态 const [data, setData]= useState({ notApply:data.notApply, apply: data.apply }) function submit(e){ e.preventDefault() axios.post(url,{ notApply:data.notApply, apply: data.apply }) .then(res => { console.log(res) }) } const buttonMode = Object.values(selected).some((isSelected) => isSelected) ? "apply" : "cancel"; const rowSelectHandler = (id) => (checked) => { setSelected((selected) => ({ ...selected, [id]: checked })); }; const handleClick = () => { if (buttonMode === "apply") { // 隐藏当前选中项 const currentlySelected = {}; Object.entries(selected).forEach(([id, isSelected]) => { if (isSelected) { currentlySelected[id] = isSelected; } }); setHidden({ ...hidden, ...currentlySelected }); // 清空所有选中状态 const newSelected = {}; Object.keys(selected).forEach((id) => { newSelected[id] = false; }); setSelected(newSelected); } else { // 选中所有当前隐藏项 const currentlyHidden = {}; Object.entries(hidden).forEach(([id, isHidden]) => { if (isHidden) { currentlyHidden[id] = isHidden; } }); setSelected({ ...selected, ...currentlyHidden }); // 清空所有隐藏状态 const newHidden = {}; Object.keys(hidden).forEach((id) => { newHidden[id] = false; }); setHidden(newHidden); } }; const matchData = ( menus.filter(({ _id }) => { return !hidden[_id]; }); const getRowProps = (row) => { return { style: { backgroundColor: selected[row.values.id] ? "lightgrey" : "white" } }; }; const columns = [ { Header: "id", accessor: (row) => row._id }, { Header: "Name", accessor: (row) => ( <Link to={{ pathname: `/menu/${menuId}/${row._id}` }}>{row.name}</Link> ) }, { Header: "Description", accessor: (row) => row.description }, { Header: "Dishes", accessor: (row) => row.dishes, id: "dishes", Cell: ({ value }) => value && Object.values(value[0]).join(", ") }, { Header: "Show", accessor: (row) => ( <Toggle value={selected[row._id]} onChange={rowSelectHandler(row._id)} /> ) } ]; const initialState = { sortBy: [ { desc: false, id: "id" }, { desc: false, id: "description" } ], hiddenColumns: ["dishes", "id"] }; if (menus.apply === 0) { setApplyStatus(true) } if (menus.apply === 1) { setApplyStatus(false) } return ( <div> <button type="submit" onClick={handleClick}> {buttonMode === "cancel" ? "Cancel" : "Apply"} </button> <Table data={matchData && (applyStatus ? true : i.apply !== 1)} columns={columns} initialState={initialState} withCellBorder withRowBorder withSorting withPagination rowProps={getRowProps} /> </div> ); }
API返回数据示例
请求参数为menuId:1时,接口返回的JSON数据结构示例:
[ // ...其他菜单数据 { "_id": 3, "name": "Cucumber Soup ", "description": "Cucumber Soup", "dishes": [ { "meat": "N/A", "vegetables": "cucumber" } ], "taste": "Medium", "comments": "2/4", "price": "Medium", "availability": 1, "trust": 1, "status": "Not started", "apply": 0 } ]
内容的提问来源于stack exchange,提问作者Zokulko
相关产品推荐
相关产品推荐

