-2

I have an array data, using react-redux:

data = [{
    class: "A",
    seat: [
      { id: "A1", price: 7.5, status: false },
      { id: "A2", price: 7.5, status: false },
      { id: "A3", price: 7.5, status: false },
      { id: "A4", price: 7.5, status: false },
    ],
  },
  {
    class: "B",
    seat: [
      { id: "B1", price: 7.5, status: false },
      { id: "B2", price: 7.5, status: false },
      { id: "B3", price: 7.5, status: false },
      { id: "B4", price: 7.5, status: false },
    ],
  }
}

movieReducer:

    const stateMovie = {
      cart: [],
      data: data,
    };
    export const movieReducer = (state = stateMovie, action) => {
        case "ADD_TO_CART": {
  let cloneCart = [...state.cart];
  let index1 = cloneCart.findIndex((sp) => {
    return sp.id == action.seatItem.id;
  });
  let cloneData = [...state.data];
  if (index1 == -1) {
    cloneCart.push(action.seatItem);
    action.seatItem.status = "selecting";
  } 
  state.data = cloneData;
  state.cart = cloneCart;
  return { ...state };
}
case "REMOVE_FROM_CART": {
  let cloneCart = [...state.cart];
  cloneCart.splice(action.index, 1);
  let cloneData = [...state.data];
  state.data = cloneData;
  state.cart = cloneCart;
  return { ...state };
}
case "CONFIRM_BOOKING": {
  let cloneData = [...state.data]
  state.data = cloneData;
  return { ...state };
}

after i use button "ADD_TO_CART" to select a seat my state.data now become:

data = [{
    class: "A",
    seat: [
      { id: "A1", price: 7.5, status: false },
      { id: "A2", price: 7.5, status: false },
      { id: "A3", price: 7.5, status: false },
      { id: "A4", price: 7.5, status: false },
    ],
  },
  {
    class: "B",
    seat: [
      { id: "B1", price: 7.5, status: false },
      { id: "B2", price: 7.5, status: 'selecting' },
      { id: "B3", price: 7.5, status: false },
      { id: "B4", price: 7.5, status: false },
    ],
  }
}

in case "CONFIRM_BOOKING" my question is how can i change status in state.data with the seat i add to cart from "selecting" to "true"; i just have idea with 2 findIndex/map loop.

Jackson
  • 3
  • 3
  • 4
    What have you tried, and what exactly is the problem with it? – jonrsharpe Jun 07 '22 at 07:51
  • Iterate through your outer array and find class === "B". Then iterate on that objects seat array and find id === "B3". – Chris Jun 07 '22 at 07:54
  • You need to sketch-out a little more of the problem you are trying to solve IMO. Do you know ahead of time that objects A and B are in the array, in that order? – Ben Aston Jun 07 '22 at 08:37
  • sorry for my stupid question, i have update my problem, pls help... – Jackson Jun 07 '22 at 08:48

2 Answers2

0

You can iterate through the class objects in the array looking for the class to which the wanted seat belongs. Then fetch the seat object having the given id and change its properties. Since those are object are passed by reference, any change made to the fetched object will be made to the object in the original array.

I crafted a demo including a function that will fetch the wanted seat returning it.

The original data gets actually preserved by first deep cloning the source array that will be used to fetch and modify the seat object.

Ideas on how to clone the array can be found here:

How do you clone an array of objects in JavaScript?

I personally used: structuredClone

https://developer.mozilla.org/en-US/docs/Web/API/structuredClone

After obtaining the seat, the main caller changes its status before printing the original array to console.log:

data = [
  {
    class: "A",
    seat: [
      { id: "A1", price: 7.5, status: false },
      { id: "A2", price: 7.5, status: false },
      { id: "A3", price: 7.5, status: false },
      { id: "A4", price: 7.5, status: false },
    ],
  },
  {
    class: "B",
    seat: [
      { id: "B1", price: 7.5, status: false },
      { id: "B2", price: 7.5, status: false },
      { id: "B3", price: 7.5, status: false },
      { id: "B4", price: 7.5, status: false },
    ],
  }
];


//How do you clone an array of objects in JavaScript?
//https://stackoverflow.com/questions/597588/how-do-you-clone-an-array-of-objects-in-javascript
const clonedData = structuredClone(data);

const s = fetchSeat(clonedData, 'B3');
s.status = true;

console.log(data);
console.log(clonedData);

function fetchSeat(allSeats, id){
  const className = id.substring(0,1);
  const classSeats = allSeats.find(element => element.class == className);    
  const foundSeat = classSeats.seat.find(element => element.id == id);
  
  return foundSeat;
}
Diego D
  • 6,156
  • 2
  • 17
  • 30
  • I like your function which fetches the required seat. But mutating the original object may cause problems. – micha149 Jun 07 '22 at 08:27
  • you were not clear about that in your question. So does that mean that you need to clone the array and change the status property of an arbitrary seat contained there? and still have the original data untouched? it sounds a bit strange doing it like that because you are replicating the array every time you are going to change the status of each seat. Please can you better explain what you expect? By the way the other answer below (the meaningful one not the pointless one) does something like that .. it just needs to make the seat id a parameter – Diego D Jun 07 '22 at 08:41
0

you can do something like this

const data = [{
    class: "A",
    seat: [
      { id: "A1", price: 7.5, status: false },
      { id: "A2", price: 7.5, status: false },
      { id: "A3", price: 7.5, status: false },
      { id: "A4", price: 7.5, status: false },
    ],
  },
  {
    class: "B",
    seat: [
      { id: "B1", price: 7.5, status: false },
      { id: "B2", price: 7.5, status: false },
      { id: "B3", price: 7.5, status: false },
      { id: "B4", price: 7.5, status: false },
    ],
  }
]

const result = data.map(d => ({...d, seat: d.seat.map(s => s.id === 'B3'? {...s, status: true}: s)}))

console.log(result)
R4ncid
  • 6,944
  • 1
  • 4
  • 18
  • I like this approach because it doesn't mutate the original data object. What I dislike is that too much new arrays or objects are created. You only should create new instances for the path to the dedicated seat. I would search for the seat in the outer map and if it's not found I would return the original object. – micha149 Jun 07 '22 at 08:25
  • i change some code but logic is the same. thank you! – Jackson Jun 07 '22 at 09:48