React+Vite项目刷新页面后已访问国家列表消失求助
解决React+Vite中localStorage持久化国家列表的问题
问题说明
使用React + Vite开发记录已访问国家的站点,期望页面刷新后已添加的国家列表不会丢失,但当前代码无法实现该localStorage持久化效果。
问题分析
当前代码的核心读写localStorage逻辑本身合理,但存在两个关键问题导致持久化失效:
- 添加区域的「Cancelar」按钮错误绑定了删除列表项的函数,点击后会意外修改
countries数组,导致localStorage存储异常数据 - 组件初始化时通过
useEffect读取localStorage,不如直接在useState初始化时读取更可靠,易出现初始渲染空列表的状态
修复后的完整代码
import React, { useState, useEffect } from 'react'; import './App.css'; function App() { // 初始化时直接从localStorage读取数据,替代后续useEffect读取 const [countries, setCountries] = useState(() => { const stored = localStorage.getItem('countries'); return stored ? JSON.parse(stored) : []; }); const [newCountry, setNewCountry] = useState(''); const [newDate, setNewDate] = useState(''); // 监听countries变化,同步到localStorage useEffect(() => { localStorage.setItem('countries', JSON.stringify(countries)); }, [countries]); const handleCountryChange = (e) => { setNewCountry(e.target.value); }; const handleDateChange = (e) => { setNewDate(e.target.value); }; const handleAdd = () => { if (newCountry && newDate) { const newCountryObj = { country: newCountry, date: newDate }; setCountries((prevCountries) => [...prevCountries, newCountryObj]); setNewCountry(''); setNewDate(''); } }; // 新增清空输入框的函数,替换原错误绑定 const handleClearInput = () => { setNewCountry(''); setNewDate(''); }; const handleEdit = (index) => { const updatedCountries = [...countries]; const editedCountry = updatedCountries[index]; const newCountryName = prompt( 'Enter the new country name:', editedCountry.country ); if (newCountryName) { editedCountry.country = newCountryName; setCountries(updatedCountries); } }; const handleDelete = (index) => { const updatedCountries = [...countries]; updatedCountries.splice(index, 1); setCountries(updatedCountries); }; return ( <div className="container"> <div className="card"> {/* Form card */} <div className="form-group"> <label htmlFor="countryInput">País:</label> <input type="text" id="countryInput" value={newCountry} onChange={handleCountryChange} className="form-control" /> </div> <div className="form-group"> <label htmlFor="dateInput">Data:</label> <input type="date" id="dateInput" value={newDate} onChange={handleDateChange} className="form-control" /> </div> <div className="button-group"> <button onClick={handleAdd} className="btn btn-green"> Adicionar </button> {/* 绑定正确的清空输入函数 */} <button onClick={handleClearInput} className="btn btn-red"> Cancelar </button> </div> </div> {/* Countries card */} {countries.length > 0 && ( <div className="card"> {countries.map((country, index) => ( <div key={index} className="country-item"> <div className="country-info"> <span>{country.country}</span> <span>{country.date}</span> </div> <div className="country-actions"> <button onClick={() => handleEdit(index)} className="btn btn-edit" > Editar </button> {/* 绑定删除函数,避免命名混淆 */} <button onClick={() => handleDelete(index)} className="btn btn-red" > Apagar </button> </div> </div> ))} </div> )} </div> ); } export default App;
关键修复点
- 初始化优化:将
useState的初始值改为函数,直接从localStorage读取数据,确保组件渲染时就加载已存储的列表 - 按钮绑定修正:新增
handleClearInput函数负责清空输入框,替换原错误绑定的删除函数,避免误操作修改列表 - 函数命名规范:将原
handleCancel改为handleDelete,明确其删除列表项的功能,避免命名混淆
内容的提问来源于stack exchange,提问作者lpotenza
相关产品推荐
相关产品推荐

