Firestore文档分类展示异常:点击切换按钮出现循环问题
问题原因
你遇到的无限循环异常,核心问题是按钮的onClick属性错误地直接执行了函数,而非传递函数引用。组件每次渲染时,handleUpcoming()和handlePast()都会被立即调用,调用后通过setAccounts更新状态,触发组件重新渲染,再次执行函数,形成无限循环。
修复后的完整代码
import React, { useState, useMemo } from 'react'; import './App.css'; import db from './firebase'; import 'react-toastify/dist/ReactToastify.css'; const App = () => { // 用useMemo缓存当前日期,避免每次渲染重复计算 const currentDate = useMemo(() => new Date().toISOString().slice(0, 10), []); const [accounts, setAccounts] = useState([]); const handleUpcoming = async () => { try { const response = db.collection('accounts').where('schedule', '>', currentDate); const data = await response.get(); const newAccounts = data.docs.map(item => ({ ...item.data(), id: item.id })); setAccounts(newAccounts); } catch (error) { console.error('获取即将到来的预约失败:', error); // 可在此添加toast提示用户错误 } }; const handlePast = async () => { try { const response = db.collection('accounts').where('schedule', '<', currentDate); const data = await response.get(); const newAccounts = data.docs.map(item => ({ ...item.data(), id: item.id })); setAccounts(newAccounts); } catch (error) { console.error('获取历史预约失败:', error); // 可在此添加toast提示用户错误 } }; return ( <div className="app-container"> <h1>Appointments</h1> <div className="button-container"> {/* 关键修改:去掉函数后的括号,传递函数引用 */} <button onClick={handleUpcoming}>Upcoming</button> <button onClick={handlePast}>Past</button> <div className="scrollbar"> <table> {accounts.map(account => ( /* 列表项添加唯一key属性,符合React性能优化要求 */ <tr key={account.id}> <td className="appointmentDataOne"> {account.name} <div className="appointmentDataTwo">{account.email}</div> </td> <td className="appointmentDataOne">{account.schedule}</td> <td className="appointmentDataTwo">{account.service}</td> <td className="appointmentDataTwo">{account.mobileNumber}</td> </tr> ))} </table> </div> </div> </div> ); }; export default App;
关键修改说明
- 修复循环问题:将
onClick={handleUpcoming()}改为onClick={handleUpcoming},确保只有点击按钮时才执行函数,而非组件每次渲染都执行。 - 缓存当前日期:用
useMemo缓存currentDate,避免组件每次渲染都重新创建Date对象并格式化,提升性能。 - 添加列表key:为表格的
<tr>添加key={account.id},React需要唯一key来高效更新列表,避免控制台警告。 - 错误捕获:在异步函数中添加
try/catch,捕获Firestore请求可能出现的错误,避免页面崩溃,同时方便调试。 - 优化数据结构:将Firestore文档的id添加到数据中,既作为列表的唯一key,也方便后续对单个预约进行操作(如删除、编辑)。
内容的提问来源于stack exchange,提问作者Christian
相关产品推荐
相关产品推荐

