Daein
Daein

Reputation: 37

Array containing objects is duplicating them rather than overwriting their values

I'm creating a shopping cart app. When the user changes the quantity of an item, the price of the item should be updated along with it. However, in trying to implement this, I've encountered a bug where the items in the shopping cart are being duplicated rather than updated. Any help would be appreciated. Here is my code:

const [cart, setCart] = useState([]);

const handleQuantityChange = (e, product) => {

setCart((prevState) => [
  ...prevState,
  ...prevState.map((item) => {
    if (item.id === product.id) {
      return {
        ...item,
        price: item.originalPrice * e.target.value,
        quantity: e.target.value,
      };
    } else {
      return item;
    }
  }),
]);
}

Upvotes: 0

Views: 38

Answers (2)

Liki Crus
Liki Crus

Reputation: 2062

[...prevState, ...prevState.map()] is duplicated one.

You can find the corresponding item in prevState by find function and update its price and quantity.

You can update setCart function call like the following.

    setCart(prevState => {
      const newState = prevState? [...prevState] : [];
      const item = newState.find(x => x.id === product.id);
      let qty = parseFloat(e.target.value);
      qty = isNaN(qty) ? 0 : qty; 
      item.price = item.originalPrice * qty;
      item.quantity = qty;
      return newState;
    });

Upvotes: 0

Nick Vu
Nick Vu

Reputation: 15520

[...prevState, ...prevState.map()] is duplicating your list twice (one is the prevState, one is prevState.map())

You should modify your code like this

const [cart, setCart] = useState([]);

const handleQuantityChange = (e, product) => {

setCart((prevState) => [
  ...prevState.map((item) => {
    if (item.id === product.id) {
      return {
        ...item,
        price: item.originalPrice * e.target.value,
        quantity: e.target.value,
      };
    } else {
      return item;
    }
  }),
]);
}

Another way without prevState but cart state

const [cart, setCart] = useState([]);

const handleQuantityChange = (e, product) => {

  const updatedCart = cart.map((item) => {
    if (item.id === product.id) {
      return {
        ...item,
        price: item.originalPrice * e.target.value,
        quantity: e.target.value,
      };
    } else {
      return item;
    }
  });

  setCart(updatedCart);
}

Upvotes: 2

Related Questions