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

React注册表单无法获取邮箱,console无输出,无法对接nodemailer

问题排查与修复方案

核心问题梳理

你的代码存在多处逻辑冲突和语法错误,导致无法正确获取邮箱值、传递数据到后端,以下是具体问题和修复方法:


1. 状态管理冲突:邮箱字段绑定双状态

你给邮箱输入框同时绑定了独立的email状态和values对象里的email属性,导致数据分散,且handleInput方法给values赋值时错误使用数组格式:

// 错误写法:把值包装成数组
setValues(prev => ({ ...prev, [event.target.name]: [event.target.value] }))

修复:
统一用values管理所有表单状态,删除独立的email状态,修改绑定逻辑:

// 移除独立的email状态
// const [email, setEmail] = useState("");  

// 修改handleInput,赋值字符串而非数组
const handleInput = (event) => {  
  setValues(prev => ({ ...prev, [event.target.name]: event.target.value }))  
}

// 邮箱输入框改为绑定values里的email
<input 
  type="email" 
  placeholder="Email" 
  name='email' 
  value={values.email} 
  onChange={handleInput} 
/>

2. 提交逻辑冲突:按钮点击与表单提交重复绑定

提交按钮同时绑定onClick={sendEmail}和表单onSubmit={handleSubmit},两个函数都调用e.preventDefault(),导致逻辑混乱,sendEmail的控制台输出被阻断。
修复:
将发送邮件逻辑整合到handleSubmit中,移除按钮的onClick事件:

const handleSubmit = async (event) => {  
  event.preventDefault();  
  const validationErrors = Validation(values);
  setErrors(validationErrors);  

  if (!validationErrors.name && !validationErrors.email && !validationErrors.password) {  
    try {
      // 提交注册数据
      await axios.post('http://localhost:8081/signup', values);
      // 发送邮件请求
      const emailRes = await fetch('http://localhost:8081/signup', {
        method: "POST",
        headers: { // 注意是headers不是header
          "Content-Type": "application/json"
        },
        body: JSON.stringify({ email: values.email })
      });
      console.log(emailRes);
      navigate('/');  
    } catch(err) {
      console.error('请求失败:', err);
    }
  }  
}

同时修改按钮:

<button type='submit' className="submit-button">Sign Up</button>

3. 异步状态更新导致判断错误

setErrors是异步操作,调用后立即判断errors会拿到旧值,永远无法触发提交逻辑。
修复:
直接用Validation返回的结果判断,不依赖errors状态:

const validationErrors = Validation(values);
setErrors(validationErrors);  
if (!validationErrors.name && !validationErrors.email && !validationErrors.password) {
  // 提交逻辑
}

4. Fetch请求头拼写错误

sendEmail里的请求头写成header,正确应为headers,导致后端无法解析JSON数据:

// 错误
header: { "Content-Type": "application/json" }
// 正确
headers: { "Content-Type": "application/json" }

5. 缺失密码输入框

values状态包含password但表单无对应输入框,导致Validation因password为空报错,无法触发提交。
修复:
添加密码输入框并绑定values状态:

<div className="input">
  <img src={/* 密码图标路径 */} alt="" style={{ width: '20px', height: '20px' }} />
  <input 
    type="password" 
    placeholder="Password" 
    name='password' 
    value={values.password} 
    onChange={handleInput} 
  />
  {errors.password && <span className='text-danger'>{errors.password}</span>}
</div>

修复后的完整代码示例

import React, { useState } from 'react'  
import './LoginSignUp.css'  
import email_icon from '../Assets/email_icon.png'  
import person_icon from '../Assets/person_icon.png'  
import password_icon from '../Assets/password_icon.png' // 假设你有密码图标
import { Link, useNavigate } from 'react-router-dom'  
import Validation from './SignUpValidation';  
import axios from 'axios'  

export const SignUp = () => {

  const [values, setValues] = useState({
    name: '',
    email: '',
    password: ''
  })

  const navigate = useNavigate();
  const [errors, setErrors] = useState({})

  const handleInput = (event) => {  
    setValues(prev => ({ ...prev, [event.target.name]: event.target.value }))  
  }

  const handleSubmit = async (event) => {  
    event.preventDefault();  
    const validationErrors = Validation(values);
    setErrors(validationErrors);  

    if (!validationErrors.name && !validationErrors.email && !validationErrors.password) {  
      try {
        // 提交注册数据到后端
        await axios.post('http://localhost:8081/signup', values);
        
        // 发送邮件请求
        const emailRes = await fetch('http://localhost:8081/signup', {
          method: "POST",
          headers: {
            "Content-Type": "application/json"
          },
          body: JSON.stringify({ email: values.email })
        });
        
        console.log(emailRes);
        navigate('/');  
      } catch(err) {
        console.error('请求失败:', err);
      }
    }  
  }   

  return (
    <div className='container'>
      <div className="header">
        <div className="text">Sign Up</div>
        <div className="underline"></div>
      </div>
      <form className="inputs" onSubmit={handleSubmit}>
        <div className="row">
          <div className="input">
            <img src={person_icon} alt="用户名图标" style={{ width: '20px', height: '20px' }} />
            <input type="text" placeholder="Name" name='name' value={values.name} onChange={handleInput} />
            {errors.name && <span className='text-danger'>{errors.name}</span>}
          </div>

          <div className="input">
            <img src={email_icon} alt="邮箱图标" style={{ width: '20px', height: '20px' }} />
            <input type="email" placeholder="Email" name='email' value={values.email} onChange={handleInput} />
            {errors.email && <span className='text-danger'>{errors.email}</span>}
          </div>
        </div>

        <div className="input">
          <img src={password_icon} alt="密码图标" style={{ width: '20px', height: '20px' }} />
          <input type="password" placeholder="Password" name='password' value={values.password} onChange={handleInput} />
          {errors.password && <span className='text-danger'>{errors.password}</span>}
        </div>

        <div className="submit-container">
          <button type='submit' className="submit-button">Sign Up</button>
          <Link to="/" className="submit-button">Login</Link>
        </div>
      </form>
    </div>
  )
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.06 05:26:00