Tengo un problema (en React):
Después de que ocurre la recuperación, cuando consola.log el valor de User_ID, me muestra el valor de id actualizado correcto que es 1, pero cuando configuro el estado de UserID y luego lo consola.log, todavía me muestra el valor predeterminado que es 0 y no el actualizado que es igual a 1. ¿Alguien puede echar un vistazo a mi código y decirme dónde está el problema? Y si el problema es el retraso, ¿alguien puede decirme cómo solucionarlo?
El código:
export default function Login() { const [Email, setEmail] = useState(""); const [UserID, setUserID] = useState(0); const [Password, setPassword] = useState(""); const navigate = useNavigate(); const btnLogin = async () => { console.log(1); console.log(Email + "," + Password); let s = await checkUserDetails( Email, Password ); console.log("returned value=" + s + "and id = " +s.User_ID); //here the it returns the right User ID ( id = 1) setUserID(s.User_ID) // for some reason here it doesnt update the right value of the User ID if (s != null) { console.log("user_id is =" + UserID); // here it still prints User ID = 0 .. why? alert("Logged In Successfully!!"); navigate('/') console.log("h1"); } else { console.log("err login!"); alert("failed to login"); } }; const checkUserDetails = async (Email, Password) => { console.log("we are in func checkUserDetails, email = " + Email); try { let result = await fetch(url + `?email=${Email}&pass=${Password}`, { method: "GET", // 'GET', 'POST', 'PUT', 'DELETE', etc. headers: new Headers({ "Content-Type": "application/json", Accept: "application/json", }), }); let resultData = result.json(); console.log("meowwww"); console.log(resultData); if (resultData) { return resultData; } else { alert("unable to login"); } } catch (e) { console.log("Error Login", e); alert("lo mevin"); } }; return ( <div className="login-form"> <button type="button" className="button-LoginSign" onClick={btnLogin} > Login </button> </div>Gracias por todos los ayudantes
¡eso se debe a que las actualizaciones de estado de reacción no son síncronas! si desea usar el valor más reciente dentro de la función que está usando, puede usar directamente la respuesta o crear un efecto de uso con ID de usuario como dependencia, también sus nombres de variables deben ser camelCase: contraseña, ID de usuario, etc. useEffect(()=> { this effect will have the latest value of ID}, [userId] y se ejecutará cada vez que se llame a setUserId
El elemento de estado UserId no mostrará el valor actualizado hasta la próxima representación de ese componente. Entonces, en esa ejecución inicial a través de la función btnLogin , todavía tiene el valor original. Use s.User_ID allí nuevamente si es necesario. Pero no veo que realmente necesite acceso a ese valor que no sea un registro de la consola.
Si necesita hacer algo una vez que el ID de usuario se ha establecido en el estado, póngalo dentro de un useEffect
useEffect(() => { if (UserId > 0) { // do something with id } }, [UserID])Nunca puede obtener su estado actualizado de esta manera. Porque está escribiendo la declaración de la consola después del gancho setUserId(), que es de naturaleza asíncrona. Para obtener el valor actualizado, debe escribir un gancho useEffect con el estado en una matriz de dependencia como esta. Entonces, cada vez que establezca UserID, el estado actualizado se reflejará en este useEffect.
useEffect(()=>{ console.log(userId) //Now desired computation on base of updated state },[userId])