Estoy haciendo una aplicación de lista de compras con React/Redux. Tengo problemas para eliminar un elemento de una lista. Después de ejecutar la acción 'removeItem', la página ya no puede leer el objeto que es la lista (que se almacenó previamente en el estado local y se podía leer antes de ejecutar la acción).
Intenté almacenar el objeto de la lista en una variable const y un estado local usando el gancho useEffect pero aún se rompe.
JSX
const { id } = useParams(); const shoppingLists = useSelector((state) => state.shoppingLists); const findList = shoppingLists.find((list) => list.listId === id); const [selectedList, setSelectedList] = useState({}); useEffect(() => { setSelectedList(findList); }); const removeItemForm = (item) => { const { itemName, itemId } = item; dispatch(removeItem({ itemName, itemId, listId: id })); }; <div className="listHeading mb-4"> <h2>{selectedList.listName}</h2> //Line that breaks </div>reductor
const shoppingListsSlice = createSlice({ name: "shoppingLists", initialState: [], reducers: { createList(state, action) { state.push({ listId: uuidv4(), listName: action.payload, items: [], color: "", createdAt: Date(), }); addItem(state, action) { state .find((list) => list.listId === action.payload.listId) .items.push({ itemId: uuidv4(), itemName: action.payload.itemName, isBought: false, }); }, removeItem(state, action) { return state .find((list) => list.listId === action.payload.listId) .items.filter((item) => item.itemId !== action.payload.itemId); },si solo desea eliminar el artículo del carrito, entonces la identificación del estado de su lista y la identificación del artículo actual filtran el almacén de datos en el estado nuevamente, eso es todo. y encuentra el índice primero aplica directamente el método de filtro.
Su problema es con su reductor removeItem . Lo que devuelvas de un reductor se convertirá en el nuevo valor estatal. En este caso, está devolviendo una matriz de items filtrados de un objeto de lista de compras en particular, que no es lo que desea establecer en su estado, ya que debería ser una matriz de listas, no elementos. Cuando eso suceda, shoppingLists se referirá a su matriz de items , lo que hará que .find() establezca findList en undefined . Dado que redux-toolkit usa immer, puede hacer actualizaciones mutables dentro de su reductor para que las cosas sean más fáciles de leer:
removeItem(state, action) { const list = state.find((list) => list.listId === action.payload.listId); list.items = list.items.filter((item) => item.itemId !== action.payload.itemId); } el enfoque inmutable sería .map() el estado de su lista de compras y devolver un nuevo objeto de lista que contiene una matriz de items filtrados:
removeItem(state, action) { return state.map((list) => list.listId === action.payload.listId ? {...list, items: list.items.filter((item) => item.itemId !== action.payload.itemId)} : list ); }