Mehdi Faraji
Mehdi Faraji

Reputation: 3836

How can I change the value of an object in an array in react redux when the action is called?

This is the action that when it's called it gets an id so it can filter the object with the same id in reducer .

export const buyItem = (24) => {
    return {
        type: BUY_ITEM,
        payload: 24
    };
};

This is the array of products in reducer file

    products: [
        {
            id: 1,
            price: 4500000,
            number: 0,
            inCart: false
        },
        {
            id: 24,
            price: 7210000,
            number: 0,
            inCart: false
        },
        {
            id: 10,
            inCart: false,
            category: 'electronics',
            number: 0,
        }
]

This is the reducer action case that I filter the product filter then I try to update inCart and number value of it

    switch (action.type) {
        case BUY_ITEM:
            let item = state.products.filter((item) => {
                if (item.id === action.payload) {
                    return item;
                }
            });

            console.log(state.products);

            return {
                ...state,
                productsInCart: state.productsInCart + 1,
                cartPrice: state.cartPrice + item[0].price,
                products: [
                    ...state.products,
                    state.products.map((item) => {
                        if (item.id === action.payload) {
                            item.inCart = true;
                            item.number += 1;
                        }
                    })
                ]
            };

The problem is it's not doing it properly it actually changes the object values successfully but when console log happens after the action is done it shows me this :

21: {id: 19, nam, number: 0, …}
22: {id: 22,  number: 0, …}
23: {id: 23, n,…}
24: {id: 25, name: "Adidas کیف", pric دهید", number: 0, …}
25: (25) [undefined, undefined, undefined, undefined, undefined, undefined, undefined, undefined, undefined]
26: (26) [undefined, undefined, undefined, undefined, undefined, undefined, undefined, undefined, undefined]
27: (27) [undefined, undefined, undefined, undefined, undefined, undefined, undefined, undefined, undefined]
28: (28) [undefined, undefined, undefined, undefined, undefined, undefined, undefined, undefined, undefined, undefined]
29: (29) [undefined, undefined, undefined, undefined, {…}, undefined, undefined, undefined, undefined,  undefined, undefined]
30: (30) [undefined, undefined, undefined, undefined, undefined, undefined, undefined, undefined, undefined]
31: (31) [undefined, undefined, undefined, undefined, undefined, undefined, undefined, {…}, undefined, undefined, undefined, undefined]

It basically adds multiple null arrays to the end of products array which is how I see is not what I want . How can I properly update an object's value in an array when the action is called ?

Upvotes: 1

Views: 43

Answers (1)

Drew Reese
Drew Reese

Reputation: 202846

Products is copied (spread) back into itself, and then also a mapped products is nested into it (the undefined values come from not returning/mapping to new values). You can simply set the new products to be the mapped product array.

products: state.products.map((item) => {
    const newItem = { ...item }; // copy item
    if (item.id === action.payload) { // update if id matches
      newItem.inCart = true;
      newItem.number += 1;
    }
    return newItem; // return copied item
  })

Upvotes: 1

Related Questions