Search code examples
javascriptreactjsselectinfinite-loop

How not to lose the values ​of an array in React?


I need to mount a dynamic 'select' on the react, but I have a problem.

I'm doing a 'for' to call an API, however as the 'for' is executed, I lose the previous values.

How can I maintain these values?

I tried to do this, but it generated an infinite loop:

const Form = (props) => {
  const [makes, setMakes] = useState([]);
  const [models, setModels] = useState([]);

  useEffect(() => {
    api.get("Make").then((response) => {
      setMakes([...response.data]);
    });
  }, []);

  async function handleModels() {
    for (let i = 0; i < makes.length; i++) {
      const response = await api.get(`Model?MakeID=${makes[i]["ID"]}`);
      const model = response.data;
      setModels([...models, model]);
    }
  }

  if (makes.length) {
    handleModels();
  }

Thanks!


Solution

  • You need to pass a function that takes in current state:

    setModels((models)=> [...models, model]);
    

    Or even better, push results to an array and then update state only once:

    async function handleModels() {
      let allModels = []
      for (let i = 0; i < makes.length; i++) {
        const response = await api.get(`Model?MakeID=${makes[i]["ID"]}`);
        const model = response.data;
        allModels.push(model);
      }
      setModels(allModels);
    }
    

    See working example: https://codesandbox.io/s/happy-sunset-nv3oc?file=/src/App.js