Reputation:
Although the text gets updated on the page, the console.log still logs out the initial value. Why is this? I know that setting the state is asynchronous but why does it still log out the old value even after waiting 1 second?
import { useState, useEffect, useRef } from "react";
function App() {
const [requestState, setRequestState] = useState("initial");
useEffect(() => {
setRequestState("changed");
setTimeout(() => {
console.log(requestState);
}, 1000);
}, []);
return (
<div className="App">
{requestState}
</div>
);
}
export default App;
Upvotes: 0
Views: 89
Reputation: 1
Your useEffect
depends on the requestState varible, so pass it inside the empty list like so:
useEffect(() => {some code},[used variables])
Upvotes: 0
Reputation: 1061
The useEffect()
hook "captures" state and props when it is executed. That is why it has a stale value. The value is from when the function in useEffect()
was run.
This is a beautiful article by Dan Abramov: https://overreacted.io/a-complete-guide-to-useeffect/. It has an explanation about almost the exact same problem as yours. Read it completely to have a great insight into useEffect()
Upvotes: 0
Reputation: 1659
useEffect will run when the component renders,To call a function conditionally, specify the list of dependencies. And the rule of thumb is to always add those dependencies that you are using inside the useEffect()
import { useState, useEffect, useRef } from "react";
function App() {
const [requestState, setRequestState] = useState("initial");
setRequestState("changed");
useEffect(() => {
setTimeout(() => {
console.log(requestState);
}, 1000);
}, [requestState]);
return (
<div className="App">
{requestState}
</div>
);
}
export default App;
Upvotes: 1