Проверка формы Реагирует функциональный компонент с useState

#reactjs #use-state

#reactjs #состояние использования

Вопрос:

Я работаю над формой проверки на стороне клиента с помощью React, используя функцию компонента и useState. проблема в том, что когда я нажимаю «Отправить», handleSubmit обновляет состояния «проверки» с ошибками, но они не отображаются при изменении состояния. они отображаются только тогда, когда я ввожу некоторые значения в поля ввода. Как я мог это исправить?

ниже вы можете найти код:

 import React, { useState } from 'react';

function RegistrationView() {
  const [inputValues, setInputValue] = useState({
    fName: '',
    lName: '',
    email: '',
    password: '',
    confirmPassword: '',
  });

  const [validation, setValidation] = useState({
    fName: '',
    lName: '',
    email: '',
    password: '',
    confirmPassword: '',
  });

  //handle submit updates
  function handleChange(event) {
    const { name, value } = event.target;
    setInputValue({ ...inputValues, [name]: value });
  }

  const handleSubmit = (e) => {
    e.preventDefault();
    let errors = validation;

    //first Name validation
    if (!inputValues.fName.trim()) {
      errors.fName = 'First name is required';
    } else {
      errors.fName = '';
    }
    //last Name validation
    if (!inputValues.lName.trim()) {
      errors.lName = 'Last name is required';
    } else {
      errors.lName = '';
    }

    // email validation
    const emailCond =
      "/^[a-zA-Z0-9.!#$%amp;'* /=?^_`{|}~-] @[a-zA-Z0-9-] (?:.[a-zA-Z0-9-] )*$/";
    if (!inputValues.email.trim()) {
      errors.email = 'Email is required';
    } else if (!inputValues.email.match(emailCond)) {
      errors.email = 'Please ingress a valid email address';
    } else {
      errors.email = '';
    }

    //password validation
    const cond1 = '/^(?=.*[a-z]).{6,20}$/';
    const cond2 = '/^(?=.*[A-Z]).{6,20}$/';
    const cond3 = '/^(?=.*[0-9]).{6,20}$/';
    const password = inputValues.password;
    if (!password) {
      errors.password = 'password is required';
    } else if (password.length < 6) {
      errors.password = 'Password must be longer than 6 characters';
    } else if (password.length >= 20) {
      errors.password = 'Password must shorter than 20 characters';
    } else if (!password.match(cond1)) {
      errors.password = 'Password must contain at least one lowercase';
    } else if (!password.match(cond2)) {
      errors.password = 'Password must contain at least one capital letter';
    } else if (!password.match(cond3)) {
      errors.password = 'Password must contain at least a number';
    } else {
      errors.password = '';
    }

    //matchPassword validation
    if (!inputValues.confirmPassword) {
      errors.confirmPassword = 'Password confirmation is required';
    } else if (inputValues.confirmPassword !== inputValues.Password) {
      errors.confirmPassword = 'Password does not match confirmation password';
    } else {
      errors.password = '';
    }

    return setValidation(errors);
  };

  return (
    <div>
      <div className='sign-up-form'>
        <form
          id='registrationForm'
          action='/'
          method='POST'
          onSubmit={handleSubmit}
        >
          <div className='form-control'>
            <input
              placeholder='First Name'
              type='string'
              name='fName'
              id='fName'
              className='input-field'
              onChange={(e) => handleChange(e)}
              value={inputValues.fName}
            />
            {validation.fName amp;amp; <p>{validation.fName}</p>}
            {validation.fName amp;amp; console.log(validation)}
          </div>
          <div className='form-control'>
            <input
              placeholder='Last Name'
              type='string'
              id='lName'
              name='lName'
              className='input-field'
              onChange={(e) => handleChange(e)}
              value={inputValues.lName}
            />
            {validation.lName amp;amp; <p>{validation.lName}</p>}
          </div>
          <div className='form-control'>
            <input
              placeholder='email'
              type='email'
              name='email'
              className='input-field'
              onChange={(e) => handleChange(e)}
              value={inputValues.email}
            />
          </div>
          {validation.email amp;amp; <p>{validation.email}</p>}

          <div className='form-control'>
            <input
              placeholder='password'
              type='password'
              name='password'
              className='input-field'
              onChange={(e) => handleChange(e)}
              value={inputValues.password}
              required
            />
            {validation.password amp;amp; <p>{validation.password}</p>}
          </div>
          <div className='form-control'>
            <input
              placeholder='confirm password'
              type='password'
              name='confirmPassword'
              className='input-field'
              onChange={(e) => handleChange(e)}
              value={inputValues.confirmPassword}
              required
            />
          </div>
          <button type='submit' id='submit-button'>
            submit
          </button>
          <span className='form-input-login'>
            Already have an account? Login <a href='#'>here</a>
          </span>
        </form>
      </div>
    </div>
  );
}

export default RegistrationView;
 

Спасибо

Комментарии:

1. Правильно ли я вас понимаю, что вы хотите проверять во время ввода пользователем, а не после отправки? Если да, то поместите операторы if и setValidation из handleSubmit в handleChange.

Ответ №1:

Вы можете поместить логику проверки в отдельную функцию и вызывать ее при изменении TextInput с помощью useEffect перехвата. Я надеюсь, что это поможет. Вы можете улучшить логику проверки любым удобным вам способом.

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

function RegistrationView() {
  const [inputValues, setInputValue] = useState({
    fName: "",
    lName: "",
    email: "",
    password: "",
    confirmPassword: "",
  });

  const [validation, setValidation] = useState({
    fName: "",
    lName: "",
    email: "",
    password: "",
    confirmPassword: "",
  });

  //handle submit updates
  function handleChange(event) {
    const { name, value } = event.target;
    setInputValue({ ...inputValues, [name]: value });
  }

  const checkValidation = () => {
    let errors = validation;

    //first Name validation
    if (!inputValues.fName.trim()) {
      errors.fName = "First name is required";
    } else {
      errors.fName = "";
    }
    //last Name validation
    if (!inputValues.lName.trim()) {
      errors.lName = "Last name is required";
    } else {
      errors.lName = "";
    }

    // email validation
    const emailCond =
      "/^[a-zA-Z0-9.!#$%amp;'* /=?^_`{|}~-] @[a-zA-Z0-9-] (?:.[a-zA-Z0-9-] )*$/";
    if (!inputValues.email.trim()) {
      errors.email = "Email is required";
    } else if (!inputValues.email.match(emailCond)) {
      errors.email = "Please ingress a valid email address";
    } else {
      errors.email = "";
    }

    //password validation
    const cond1 = "/^(?=.*[a-z]).{6,20}$/";
    const cond2 = "/^(?=.*[A-Z]).{6,20}$/";
    const cond3 = "/^(?=.*[0-9]).{6,20}$/";
    const password = inputValues.password;
    if (!password) {
      errors.password = "password is required";
    } else if (password.length < 6) {
      errors.password = "Password must be longer than 6 characters";
    } else if (password.length >= 20) {
      errors.password = "Password must shorter than 20 characters";
    } else if (!password.match(cond1)) {
      errors.password = "Password must contain at least one lowercase";
    } else if (!password.match(cond2)) {
      errors.password = "Password must contain at least one capital letter";
    } else if (!password.match(cond3)) {
      errors.password = "Password must contain at least a number";
    } else {
      errors.password = "";
    }

    //matchPassword validation
    if (!inputValues.confirmPassword) {
      errors.confirmPassword = "Password confirmation is required";
    } else if (inputValues.confirmPassword !== inputValues.Password) {
      errors.confirmPassword = "Password does not match confirmation password";
    } else {
      errors.password = "";
    }

    setValidation(errors);
  };

  useEffect(() => {
    checkValidation();
  }, [inputValues]);

  const handleSubmit = (e) => {
    e.preventDefault();
  };

  return (
    <div>
      <div className="sign-up-form">
        <form
          id="registrationForm"
          action="/"
          method="POST"
          onSubmit={handleSubmit}
        >
          <div className="form-control">
            <input
              placeholder="First Name"
              type="string"
              name="fName"
              id="fName"
              className="input-field"
              onChange={(e) => handleChange(e)}
              value={inputValues.fName}
            />
            {validation.fName amp;amp; <p>{validation.fName}</p>}
            {validation.fName amp;amp; console.log(validation)}
          </div>
          <div className="form-control">
            <input
              placeholder="Last Name"
              type="string"
              id="lName"
              name="lName"
              className="input-field"
              onChange={(e) => handleChange(e)}
              value={inputValues.lName}
            />
            {validation.lName amp;amp; <p>{validation.lName}</p>}
          </div>
          <div className="form-control">
            <input
              placeholder="email"
              type="email"
              name="email"
              className="input-field"
              onChange={(e) => handleChange(e)}
              value={inputValues.email}
            />
          </div>
          {validation.email amp;amp; <p>{validation.email}</p>}

          <div className="form-control">
            <input
              placeholder="password"
              type="password"
              name="password"
              className="input-field"
              onChange={(e) => handleChange(e)}
              value={inputValues.password}
              required
            />
            {validation.password amp;amp; <p>{validation.password}</p>}
          </div>
          <div className="form-control">
            <input
              placeholder="confirm password"
              type="password"
              name="confirmPassword"
              className="input-field"
              onChange={(e) => handleChange(e)}
              value={inputValues.confirmPassword}
              required
            />
          </div>
          <button type="submit" id="submit-button">
            submit
          </button>
          <span className="form-input-login">
            Already have an account? Login <a href="#">here</a>
          </span>
        </form>
      </div>
    </div>
  );
}

export default RegistrationView;
 

Комментарии:

1. спасибо, я посмотрю на это!

Ответ №2:

Как указано в вашем коде, ошибки устанавливают базу проверки при вызове по ссылке, поэтому после установленного состояния компонент не отображается. Пожалуйста, попробуйте глубоко клонировать вашу ошибку, как показано ниже.

  let errors = JSON.parse(JSON.stringify(validation));
 

Я надеюсь, что это сработает для вас. Спасибо

Комментарии:

1. Спасибо! это работает!

Ответ №3:

Вы можете попробовать клонировать с помощью отдельного оператора.

 let errors = {...validation}
 

Или вы можете использовать библиотеку react-hook-form. Он прост в использовании и очень изолирован.

форма перехвата реакции

Комментарии:

1. Потрясающе! это работает! Спасибо! Могу ли я спросить вас, почему это работает таким образом??

2. В javascript объект и функции имеют непримитивный тип. это означает, что если вы назначаете объект другой переменной, в памяти обе переменные указывают на одну и ту же переменную. С помощью отдельного оператора (…) вы можете клонировать содержимое объекта вместо ссылки. вы можете посмотреть эту статью: edureka.co/blog/data-types-in-javascript