解决useEffect依赖自定义hook引发的无限API请求循环问题
解决useEffect依赖导致的无限API请求循环问题
我编写了以下组件代码,代码检查工具提示必须将employeesApi添加到useEffect的依赖数组中,但添加后代码会陷入无限循环,持续发起API请求。
export const EmployeesListPage = () => { const navigate = useNavigate(); const [employees, setEmployees] = useState<EmployeeListDto[]>([]); const employeesApi = useApi(new EmployeesApi()); useEffect(() => { async function getEmployeesList() { const employeesList = await employeesApi.getEmployeesList(); setEmployees(employeesList); } getEmployeesList(); }, []); return (...) }
问题原因
每次组件渲染时,useApi(new EmployeesApi())都会创建一个全新的EmployeesApi实例。React对对象类型的依赖比较是基于引用的(和原始值的比较逻辑不同),这就导致每次渲染时employeesApi的引用都发生变化,一旦把它加入useEffect依赖数组,就会不断触发useEffect执行,进而引发无限循环。
解决方案
修改自定义的useApi hook,用useState存储API实例,让实例的引用保持稳定:
export const useApi = <T extends IApi>(ApiType: new () => T): T => { const { loggedUser } = useUserManagement(); const [api] = useState<T>(new ApiType()); api.setUser(loggedUser); return api; };
修改后的组件使用
现在在组件中调用useApi时传入类本身而非实例,API实例的引用会始终保持一致,将其加入useEffect依赖数组后既符合代码检查要求,也不会触发无限循环:
export const EmployeesListPage = () => { const navigate = useNavigate(); const [employees, setEmployees] = useState<EmployeeListDto[]>([]); const employeesApi = useApi(EmployeesApi); useEffect(() => { async function getEmployeesList() { const employeesList = await employeesApi.getEmployeesList(); setEmployees(employeesList); } getEmployeesList(); }, [employeesApi]); return (...) }
内容的提问来源于stack exchange,提问作者gabriel.santos
相关产品推荐
相关产品推荐

