React Todo集成localStorage时出现Cannot read properties of null错误的解决方法
修复React Todo应用localStorage集成的"Cannot read properties of null (reading 'concat')"错误
错误原因分析
- 首次加载应用时,localStorage中还未存储
todos数据,localStorage.getItem('todos')返回null,经过JSON.parse转换后结果仍为null,此时对null调用concat方法就会触发报错。 - 直接赋值修改
localTodos状态变量(如localTodos = localTodos.concat([todo]))违反React状态更新规范,会导致状态不同步,同时无法触发组件重新渲染。
修复后的完整代码
import { useState, useEffect } from 'react'; import TodoInput from './TodoInput'; import TodoList from './TodoList'; import './App.css'; const App = () => { const [todo, setTodo] = useState(''); const [localTodos, setLocalTodos] = useState([]); const localStorage = window.localStorage; useEffect(() => { // 读取localStorage数据,若为null则默认返回空数组 const savedTodos = JSON.parse(localStorage.getItem('todos')) || []; setLocalTodos(savedTodos); }, []); function addTodo() { if (todo.trim() !== '') { // 使用函数式更新获取最新状态,同步更新localStorage setLocalTodos(prevTodos => { const newTodos = prevTodos.concat([todo]); localStorage.setItem('todos', JSON.stringify(newTodos)); return newTodos; }); setTodo(''); } }; function deleteTodo(text) { // 函数式更新处理删除逻辑,同步更新localStorage setLocalTodos(prevTodos => { const filteredTodos = prevTodos.filter(item => item !== text); localStorage.setItem('todos', JSON.stringify(filteredTodos)); return filteredTodos; }); }; return ( <div className="App"> <h1>Your todos</h1> <TodoInput todo={todo} setTodo={setTodo} addTodo={addTodo} /> <TodoList list={localTodos} remove={deleteTodo} /> </div> ); } export default App;
关键修改说明
- 处理空值情况:读取localStorage数据时添加
|| [],确保数据不存在时返回空数组,避免对null调用数组方法。 - 函数式状态更新:调用
setLocalTodos时传入函数,通过prevTodos获取最新状态值,避免直接修改state变量,保证状态更新的准确性和组件渲染的同步性。 - 优化输入校验:将
todo !== ''改为todo.trim() !== '',防止添加空字符串的无效待办项。 - 精简冗余代码:移除了未使用的
todos状态变量,简化代码结构。
内容的提问来源于stack exchange,提问作者IcEWaRRiOr
相关产品推荐
相关产品推荐

