Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

setState loop seems to only run on the last iteration

So I have an app with friends and events, where each friends has specific events.
I just want to retrieve every single event from every single friend.
I have an ‘event’ state const [events, setEvents] = useState([]);
Then here is the problematic useEffect snippet:

useEffect(() => {
  getFriendsIds()
    .then(idsArray => {
      Promise.all(idsArray.map(id => {
        getUserEvents(id)
          .then(evs => {
            if (evs.length > 0) {
              for (let i=0; i<evs.length; i++) {
                setEvents([...events, evs[i]]);
              }
            }
          })
      }))
    })
}, [])

This should store the aforementioned events in the ‘events’ state variable.
However, when I try to render them with {events.map(ev => renderItem(ev))}, I only get the very last event of the last friend in the loop (It is guaranteed that renderItem works fine).
I would love an explanation of how this works, and if possible an alternative algorithm that actually achieves what I aim to do.
Thanks

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

>Solution :

Actually, this happens because your useEffect() doesn’t have the events state in its dependency array.

useEffect(() => {
   ...
}, [events])

However event this solution will not work properly because the setState() function works asynchronously.

You have to use state updater function in this case:

useEffect(() => {
  ...
  setEvents((prevEvents) => [...prevEvents, evs[i]]);
  ...
}, []);

Read more about dependency array and state updater in the official documentation

Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading