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

React Class组件转Hooks:登录记住密码功能失效求助

React Hooks版本「记住我」功能失效问题排查

问题描述

需要实现登录时的「记住我」功能,从CodeSandbox获取了React Class组件版本的实现代码,转换为React Hooks版本后功能无法正常运行,请求排查代码问题。

原React Class组件代码

import React from "react";

class RememberMe extends React.Component {
  static displayName = "RememberMe";

  state = {
    email: "",
    password: "",
    isChecked: false
  };

  componentDidMount() {
    if (localStorage.checkbox && localStorage.username !== "") {
      this.setState({
        isChecked: true,
        email: localStorage.username,
        password: localStorage.password
      });
    }
  }

  onChangeValue = (event) => {
    this.setState({
      [event.target.name]: event.target.value
    });
  };

  onChangeCheckbox = (event) => {
    this.setState({
      isChecked: event.target.checked
    });
  };

  loginSubmit = () => {
    const { email, password, isChecked } = this.state;
    if (isChecked && email !== "") {
      localStorage.username = email;
      localStorage.password = password;
      localStorage.checkbox = isChecked;
    }
  };

  render() {
    const { email, password, isChecked } = this.state;
    return (
      <div>
        <form>
          <table align="center">
            <tr>
              <td>
                <label>Email</label>
              </td>
              <td>
                <input
                  type="email"
                  name="email"
                  value={email}
                  onChange={this.onChangeValue}
                />
              </td>
            </tr>
            <tr>
              <td>
                <label>Password</label>
              </td>
              <td>
                <input
                  type="password"
                  name="password"
                  value={password}
                  onChange={this.onChangeValue}
                />
              </td>
            </tr>
            <tr>
              <td colSpan="2">
                <input
                  type="checkbox"
                  checked={isChecked}
                  name="lsRememberMe"
                  onChange={this.onChangeCheckbox}
                />
                <label>Remember me</label>
              </td>
            </tr>
            <tr>
              <td colSpan="2">
                <input type="button" value="Login" onClick={this.loginSubmit} />
              </td>
            </tr>
          </table>
        </form>
      </div>
    );
  }
}

export default RememberMe;

自行编写的React Hooks版本代码

import React, { useState, useEffect } from "react";

const Me = () => {
  const [email, setEmail] = useState("");
  const [password, setPassword] = useState("");
  const [isChecked, setIsChecked] = useState(false);

  useEffect(() => {
    if (localStorage.checkbox && localStorage.email !== "") {
      setEmail({ email: localStorage.username });
      setPassword({ password: localStorage.password });
      setIsChecked({
        isChecked: true
      });
    }
  }, []);

  const onChangeValue = (event) => {
    setIsChecked({
      [event.target.name]: event.target.value
    });
  };

  const onChangeCheckbox = (event) => {
    setIsChecked({
      isChecked: event.target.checked
    });
  };

  const loginSubmit = () => {
    if (isChecked && email !== "") {
      localStorage.username = email;
      localStorage.password = password;
      localStorage.checkbox = isChecked;
    }
  };

  return (
    <div>
      <form>
        <table align="center">
          <tr>
            <td>
              <label>Email</label>
            </td>
            <td>
              <input
                type="email"
                name="email"
                value={email}
                onChange={onChangeValue}
              />
            </td>
          </tr>
          <tr>
            <td>
              <label>Password</label>
            </td>
            <td>
              <input
                type="password"
                name="password"
                value={password}
                onChange={onChangeValue}
              />
            </td>
          </tr>
          <tr>
            <td colSpan="2">
              <input
                type="checkbox"
                checked={isChecked}
                name="lsRememberMe"
                onChange={onChangeCheckbox}
              />
              <label>Remember me</label>
            </td>
          </tr>
          <tr>
            <td colSpan="2">
              <input type="button" value="Login" onClick={loginSubmit} />
            </td>
          </tr>
        </table>
      </form>
    </div>
  );
};

export default Me;

问题排查与修正

你的Hooks版本代码存在以下几个关键错误:

1. 状态更新方式错误

useState返回的setter函数需要直接传入状态值,而非对象。你在useEffect、onChangeValue、onChangeCheckbox中错误地传入了对象,导致状态类型混乱:

  • 正确写法:setEmail(localStorage.username) 而非 setEmail({ email: localStorage.username })
  • 正确写法:setIsChecked(event.target.checked) 而非 setIsChecked({ isChecked: event.target.checked })

2. onChangeValue函数绑定错误

该函数应该根据输入框的name属性更新对应的email或password状态,但你错误地调用了setIsChecked,导致输入框内容无法正常更新。

3. localStorage读取判断条件错误

原Class组件中判断的是localStorage.username !== "",而你写成了localStorage.email !== "",导致组件挂载时无法正确读取存储的账号信息。

修正后的Hooks代码

import React, { useState, useEffect } from "react";

const Me = () => {
  const [email, setEmail] = useState("");
  const [password, setPassword] = useState("");
  const [isChecked, setIsChecked] = useState(false);

  useEffect(() => {
    // 修正判断条件,匹配原Class逻辑
    if (localStorage.checkbox && localStorage.username !== "") {
      setEmail(localStorage.username);
      setPassword(localStorage.password);
      setIsChecked(true);
    }
  }, []);

  const onChangeValue = (event) => {
    const { name, value } = event.target;
    // 根据name更新对应状态
    if (name === "email") {
      setEmail(value);
    } else if (name === "password") {
      setPassword(value);
    }
  };

  const onChangeCheckbox = (event) => {
    // 直接传入布尔值更新状态
    setIsChecked(event.target.checked);
  };

  const loginSubmit = () => {
    if (isChecked && email !== "") {
      localStorage.username = email;
      localStorage.password = password;
      localStorage.checkbox = isChecked;
    }
  };

  return (
    <div>
      <form>
        <table align="center">
          <tr>
            <td>
              <label>Email</label>
            </td>
            <td>
              <input
                type="email"
                name="email"
                value={email}
                onChange={onChangeValue}
              />
            </td>
          </tr>
          <tr>
            <td>
              <label>Password</label>
            </td>
            <td>
              <input
                type="password"
                name="password"
                value={password}
                onChange={onChangeValue}
              />
            </td>
          </tr>
          <tr>
            <td colSpan="2">
              <input
                type="checkbox"
                checked={isChecked}
                name="lsRememberMe"
                onChange={onChangeCheckbox}
              />
              <label>Remember me</label>
            </td>
          </tr>
          <tr>
            <td colSpan="2">
              <input type="button" value="Login" onClick={loginSubmit} />
            </td>
          </tr>
        </table>
      </form>
    </div>
  );
};

export default Me;

内容的提问来源于stack exchange,提问作者Kia Kalista

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.31 21:35:16