Home > Back-end >  problem when adding item to hooks state react js
problem when adding item to hooks state react js

Time:06-18

I'm trying to store a list of items in localstorage using hooks and state like . but it returns an error

TypeError
cartList is not iterable

this is my code: (and this is the codesandbox)

import { useState, useEffect } from "react";
import { Button } from "react-bootstrap";

export default function App() {
  const [cartList, setCartList] = useState([]);
  const [cartItem, setCartItem] = useState([]);

  useEffect(() => {
    let localCart = localStorage.getItem("cartList") || "{}";
    console.log("localcart", localCart);
    if (localCart) {
      localCart = JSON.parse(localCart);
    }
    setCartList(localCart);
  }, []);

  const handleClick = (e, item) => {
    e.preventDefault();

    const arr = e.target.id.split("-");
    const selectID = arr[1];
    console.log("selectID", selectID);
    setCartItem({ ...cartItem, id: selectID });
    console.log("cartItem", cartItem);

    let itemIndex = -1;
    for (const entry of Object.entries(cartList)) {
      console.log("entry", entry);
    }
    if (itemIndex < 0) {
      setCartList([...cartList, cartItem]); // error occurs here according to codesandbox
      localStorage.setItem("cartList", JSON.stringify(cartList));
    }
  };

  return (
    <div className="App">
      <h1>Hello CodeSandbox</h1>
      <Button
        variant="link"
        id="item-12"
        onClick={(e) => handleClick(e, cartItem)}
      >
        item no.12
      </Button>
      <Button
        variant="link"
        id="item-100"
        onClick={(e) => handleClick(e, cartItem)}
      >
        item no.100
      </Button>
    </div>
  );
}

CodePudding user response:

Why you are getting TypeError: cartList is not iterable is because you have initialized the cartList incorrectly.

Please have a try in console following snippet, You will face exactly same error.

console.log( [...{ prop: 'value' }] )

So you should initialize cartList as [] rather than {} inside the useEffect hook like the following.

let localCart = localStorage.getItem("cartList") || "[]";

CodePudding user response:

I think you are confusing about a type of cartList. I guess it would be an Array.

const [cartList, setCartList] = useState([]); // It is declared as Array
 useEffect(() => {
    let localCart = localStorage.getItem("cartList") || "{}"; // But initialized as Object this line
    console.log("localcart", localCart);
    if (localCart) {
      localCart = JSON.parse(localCart);
    }
    setCartList(localCart);
  }, []);
 if (itemIndex < 0) {
    setCartList([...cartList, cartItem]); // It should be an Array, but error occured as it's an Obejct.
    localStorage.setItem("cartList", JSON.stringify(cartList));
 }

CodePudding user response:

As @pilchard pointed out, you are setting cartList as an object on that line:

localStorage.getItem("cartList") || "{}";

So on first render before setting the carlist value to localstorage you are setting the state as an object which cannot be spread inside an array

  • Related