es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

¿Por qué tengo que hacer clic en el botón “Enviar” DOS VECES para actualizar mi hook useState()?

Estoy tratando de crear una función que redirija a una página diferente cuando esté autenticada, sin embargo, cuando hago clic en el botón onSubmit, authenticate no se actualiza inmediatamente. ¿Tengo que hacer clic en enviar dos veces para cambiar authenticate de null a false/true? ¿Por qué no se actualiza authenticate de inmediato, qué debo hacer para resolver esto? Gracias.

import React, { useEffect, useState } from 'react'
import Dashboard from './Dashboard'
import { useNavigate } from "react-router-dom"
import axios from 'axios'

function Register() {

const navigate = useNavigate()
const [username, setUsername] = useState('')
const [password, setPassword] = useState('')
const [authenticate, setAuthenticate] = useState(null)

const newUser = (event) => {
    event.preventDefault()
     axios({
        method: "POST",
        url: 'xxxxxxxxxxxxxxxxx',
        data:{
            username,
            password
        }
    }).then(res=>setAuthenticate(res.data))
    .then(()=>console.log(authenticate))
    .then(()=>authentication())

}

const authentication = () => {
    authenticate ? 
        navigate("/dashboard")
       : console.log('No se puede crear el usuario')
}


return (
    <div>
        <form onsubmit="{newUser}">
            <label>Usuario: </label>
            <input type="text" value="{username}" onchange="{e="> setUsername(e.target.value)}
             />
             <br>
             <label>Contraseña: </label>
             <input type="text" value="{password}" onchange="{e=">setPassword(e.target.value)}
             />
             <br>
             <button>Enviar</button>
        </form>
        <div>
            {username}
        </div>
    </div>
)
}

export default Register
Tags:  , , ,

Answer

  1. Avatar for davy.ai

    El problema es que setAuthenticate es una función asíncrona, por lo que authenticate no se actualizará inmediatamente después de llamar a esta función. Es por eso que necesitas hacer clic en el botón de enviar dos veces para ver los cambios.

    Para resolver esto, puedes usar useEffect para ejecutar una función después de que authenticate haya sido actualizado. Así es como puedes modificar tu código:

    import React, { useEffect, useState } from 'react';
    import Dashboard from './Dashboard';
    import { useNavigate } from 'react-router-dom';
    import axios from 'axios';
    
    function Register() {
      const navigate = useNavigate();
      const [username, setUsername] = useState('');
      const [password, setPassword] = useState('');
      const [authenticate, setAuthenticate] = useState(null);
    
      const newUser = (event) => {
        event.preventDefault();
        axios({
          method: 'POST',
          url: 'xxxxxxxxxxxxxxxxx',
          data: {
            username,
            password,
          },
        }).then((res) => setAuthenticate(res.data));
      };
    
      useEffect(() => {
        if (authenticate !== null) {
          authenticate ? navigate('/dashboard') : console.log('No se puede crear el usuario');
        }
      }, [authenticate]);
    
      return (
        <div>
          <form onsubmit="{newUser}">
            <label>Usuario: </label>
            <input type="text" value="{username}" onchange="{(e)" ==""> setUsername(e.target.value)} />
            <br>
            <label>Contraseña: </label>
            <input type="text" value="{password}" onchange="{(e)" ==""> setPassword(e.target.value)} />
            <br>
            <button>Enviar</button>
          </form>
          <div>{username}</div>
        </div>
      );
    }
    
    export default Register;
    

    En este código, hemos agregado un useEffect que se ejecuta cada vez que authenticate cambia. La función dentro del useEffect solo se ejecutará si authenticate no es nulo, y navegará al panel si el usuario ha sido autenticado.

Comments are closed.