You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React动物投票应用如何将投票状态存到localStorage实现刷新后数据不丢失

实现方案

你可以通过两种主流方案实现刷新保留投票数据,根据你的使用场景选择即可:

方案1:前端本地存储(单用户本地使用,无需后端改动)

直接用浏览器自带的localStorage存储投票数据,实现成本最低:

  • 组件初始化时从localStorage读取已保存的投票数据作为state初始值
  • 每次投票更新state后,自动将最新数据同步到localStorage

修改后的组件代码如下:

import {fetchAll} from '../AppFetch';
import {useEffect, useState} from 'react';

export default function Animals() {
    
  useEffect(( ) => {
    fetchAll("http://localhost:3000/animals.json", setData)
  }, []);

  const [data, setData] = useState({});
  // 初始化时从localStorage读数据,没有就用空对象
  const [state, setState] = useState(() => {
    const savedVotes = localStorage.getItem('animalVotes');
    return savedVotes ? JSON.parse(savedVotes) : {};
  });

  // 监听state变化,每次更新自动存到localStorage
  useEffect(() => {
    localStorage.setItem('animalVotes', JSON.stringify(state));
  }, [state]);

  const upVote = ({ target: { name } }) => {
    setState({ ...state, [name]: (state[name] || 0) + 1 });
  };

  const downVote = ({target:{name}}) => {
    // 加了Math.max避免票数变负,不需要可以直接删掉保留原有逻辑
    setState({...state, [name]: Math.max((state[name] || 0) - 1, 0)})
  }

  const animalsArr = [];
  const airArr = [];

  for(let i=0; i<Object.entries(data).length; i++){
    const areas = Object.values(data)[i];

    for(let j=0; j < Object.keys(areas).length; j++){
      const animal=Object.entries(areas)[1][1]
      const air=Object.entries(areas)[0][1]
      
      animalsArr.push(animal[j]);
      airArr.push(air[j]);
    }
  }


  return <div className="row">
    <div className="land">
      {animalsArr.map(({ name }) => (
        <div key={name}>
          <button className="f" name={name} onClick={upVote}>
           &#129153;
          </button>
          <p>{name} - {state[name] || 0}</p>
          <button className="s" name={name} onClick={downVote}>
            &#129155;
          </button>
        </div>
      ))}
    </div>
    <div className="air">
      {airArr.map(({ name }) => (
        <div key={name}>
          <button className="f" name={name} onClick={upVote}>
            &#129153;
          </button>
          <p>{name} - {state[name] || 0}</p>
          <button className="s" name={name} onClick={downVote}>
            &#129155;
          </button>
        </div>
      ))}
    </div>
  </div>;
}

注:该方案的数据仅保存在当前用户的当前浏览器中,清理浏览器缓存会丢失数据,也无法实现多用户共享投票数据

方案2:后端持久化(多用户共享投票数据)

你现在用的animals.json是静态文件,无法直接通过前端修改,需要后端支持:

  • 快速测试可直接用json-server工具,一行命令启动animals.json为支持增删改查的REST接口,无需手动写后端代码
  • 正式场景可自行搭建后端服务(比如Node.js+Express、Java等),提供两个核心接口:
    • 拉取全量动物投票数据接口
    • 提交投票更新接口
  • 每次用户点击投票按钮时,除了更新本地state,还要发请求调用后端更新接口,修改服务端存储的投票数据(可存在json文件或者数据库中)
  • 组件初始化时直接从后端拉取最新的投票数据,不需要依赖本地存储

内容的提问来源于stack exchange,提问作者Egon Adelsberger

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.02 10:57:01