删除状态并获取新状态问题

问题描述 投票:0回答:2

从 React 应用程序中删除收藏夹时,它会删除该菜肴,但会引发错误

const favorites = props.favorites.favorites[0].dishes.map((dish), {.. TypeError: 无法读取未定义的属性“dishes”...

重新加载应用程序后,它仅显示剩余的未删除菜肴(工作正常)

在主组件中将“favorite”属性传递给最喜欢的组件

<Favorites
  favorites={this.props.favorites}
  deleteFavorite={this.props.deleteFavorite}
/>

在最喜欢的组件中检查道具结果并将道具传递给渲染菜单组件

if (props.favorites.favorites) {
  const favorites = props.favorites.favorites[0].dishes.map((dish) => {
    return (
      <div key={dish._id} className="col-12 mt-5">
        <RenderMenuItem dish={dish} deleteFavorite={props.deleteFavorite} />
      </div>
    );
  })

渲染菜单组件接收上面传递的道具

function RenderMenuItem({ dish, deleteFavorite }) {
  return (
    <Media tag="li">
      <Media left middle>
        <Media object src={baseUrl + dish.image} alt={dish.name} />
      </Media>
      <Media body className="ml-5">
        <Media heading>{dish.name}</Media>
        <p>{dish.description}</p>
        <Button outline color="danger" onClick={() => deleteFavorite(dish._id)}>
           <span className="fa fa-times"></span>
        </Button>
      </Media>
    </Media>
  );
}

删除收藏夹项目的动作创建者

export const deleteFavorite = (dishId) => (dispatch) => {
const bearer = "Bearer " + localStorage.getItem("token");

return fetch(baseUrl + "favorites/" + dishId, {
  method: "DELETE",
  headers: {
    Authorization: bearer,
  },
  credentials: "same-origin",
 })
  .then(
    (response) => {
      if (response.ok) {
        return response;
      } else {
       var error = new Error(
         "Error " + response.status + ": " + response.statusText
       );
       error.response = response;
       throw error;
     }
   },
    (error) => {
      throw error;
    }
  )
   .then((response) => response.json())
   .then((favorites) => {
   // console.log("Favorite Deleted", favorites);
   dispatch(addFavorites(favorites));
  })
   .catch((error) => dispatch(favoritesFailed(error.message)));
};
     
export const favoritesLoading = () => ({
  type: ActionTypes.FAVORITES_LOADING,
}); 

export const favoritesFailed = (errmess) => ({
  type: ActionTypes.FAVORITES_FAILED,
  payload: errmess,
});

export const addFavorites = (favorites) => ({
  type: ActionTypes.ADD_FAVORITES,
  payload: favorites,
});

收藏夹项目的减速器

import * as ActionTypes from "./ActionTypes";

export const favorites = (
  state = {
    isLoading: true,
    errMess: null,
    favorites: null,
  },
  action
) => {
  switch (action.type) {
    case ActionTypes.ADD_FAVORITES:
      return {
        ...state,
        isLoading: false,
        errMess: null,
        favorites: action.payload,
      };

    case ActionTypes.FAVORITES_LOADING:
      return { ...state, isLoading: true, errMess: null, favorites: null };

    case ActionTypes.FAVORITES_FAILED:
      return {
        ...state,
        isLoading: false,
        errMess: action.payload,
        favorites: null,
      };

    default:
      return state;
  }
};
javascript reactjs redux react-redux
2个回答
0
投票

检查您的 REST DELETE 方法。它返回的内容可能与数组不同(一个对象,我想可能是删除的对象)。

因此,在调用此 DELETE 之后,您将使用其响应,并将 redux 存储中的

favorites
设置为此响应。由于它不是数组,所以
props.favorites.favorites[0]
处没有定义任何内容。


0
投票

仅仅因为

props.favorites.favorites
存在、已定义且不为空, 也意味着它是一个数组,也意味着它已被填充,例如
props.favorites.favorites[0]
已定义。

您可以检查

dishes
数组的完整路径是否可访问:

if (props.favorites.favorites?.[0]?.dishes) {
  const favorites = props.favorites.favorites[0].dishes.map((dish) => {
    return (
      <div key={dish._id} className="col-12 mt-5">
        <RenderMenuItem dish={dish} deleteFavorite={props.deleteFavorite} />
      </div>
    );
  });

  ...

}

如果您无法使用可选链接运算符,请改用空检查/防护子句:

if (
  props.favorites.favorites &&
  props.favorites.favorites[0] &&
  props.favorites.favorites[0].dishes
) {
  const favorites = props.favorites.favorites[0].dishes.map((dish) => {
    return (
      <div key={dish._id} className="col-12 mt-5">
        <RenderMenuItem dish={dish} deleteFavorite={props.deleteFavorite} />
      </div>
    );
  });

  ...

}
© www.soinside.com 2019 - 2024. All rights reserved.