数据在按钮 onClick 事件上更新两次
Data get updated twice on button onClick event
我有一个非常简单的 React Web App
,我想在其中添加 review
的新 object
到 object
的 array
:-
我正在使用 useReducer
来处理我的数据的默认 state
,如下所示:-
reducer
函数:-
const reducer = (state, action) => {
switch (action.type) {
case "ADD_REVIEW_ITEM":
state.forEach(
(data) =>
data.id === action.payload.selectedDataId &&
data.listOfReview.push(action.payload.newReview)
);
return [...state];
default:
return state;
}
};
default data
我的 reducer
:-
const data = [
{
id: 1607089645363,
name: "john",
noOfReview: 1,
listOfReview: [
{
reviewId: 1607089645361,
name: "john doe",
occupation: "hero",
rating: 5,
review: "lorem ipsum"
}
]
},
{
id: 1507089645363,
name: "smith",
noOfReview: 1,
listOfReview: [
{
reviewId: 1507089645361,
name: "smith doe",
occupation: "villain",
rating: 5,
review: "lorem ipsum"
}
]
}
];
App.js
,正在发生的事情的演示:-
import React, { useState, useEffect, useReducer } from "react";
import "./styles.css";
export default function App() {
const [state, dispatch] = useReducer(reducer, data);
// hnadle adding of new review
const handleAddNewReview = (id) => {
dispatch({
type: "ADD_REVIEW_ITEM",
payload: {
selectedDataId: id,
newReview: {
reviewId: new Date().getTime().toString(),
name: "doe doe",
occupation: "doctor",
rating: 5,
review: "lorem ipsum"
}
}
});
};
return (
<>
<div className="App">
<h1>Hello CodeSandbox</h1>
<h2>Start editing to see some magic happen!</h2>
</div>
{state?.length > 0 &&
state.map((data) => (
<div key={data.id}>
<h1>{data.name}</h1>
{data.listOfReview?.length > 0 &&
data.listOfReview.map((review) => (
<div key={review.reviewId}>
<h3>{review.name}</h3>
<p>{review.occupation}</p>
</div>
))}
<button onClick={() => handleAddNewReview(data.id)}>
Add new review
</button>
</div>
))}
</>
);
}
问题是,一旦我第一次点击 button
,state
已更新正确。但是,如果我单击它第二次,它会以某种方式添加两个相同的review
。我应该如何更改 reducer
中的 code
来解决这个问题?
这是上述案例的有效 sandbox。
尝试将减速器更改为:
case "ADD_REVIEW_ITEM":
return state.map((data) => {
if (data.id === action.payload.selectedDataId) {
return {
...data,
listOfReview: [...data.listOfReview, action.payload.newReview]
};
}
return data;
});
目前,您正在改变状态变量并推入一个可能导致副作用的数组。
我有一个非常简单的 React Web App
,我想在其中添加 review
的新 object
到 object
的 array
:-
我正在使用 useReducer
来处理我的数据的默认 state
,如下所示:-
reducer
函数:-
const reducer = (state, action) => {
switch (action.type) {
case "ADD_REVIEW_ITEM":
state.forEach(
(data) =>
data.id === action.payload.selectedDataId &&
data.listOfReview.push(action.payload.newReview)
);
return [...state];
default:
return state;
}
};
default data
我的reducer
:-
const data = [
{
id: 1607089645363,
name: "john",
noOfReview: 1,
listOfReview: [
{
reviewId: 1607089645361,
name: "john doe",
occupation: "hero",
rating: 5,
review: "lorem ipsum"
}
]
},
{
id: 1507089645363,
name: "smith",
noOfReview: 1,
listOfReview: [
{
reviewId: 1507089645361,
name: "smith doe",
occupation: "villain",
rating: 5,
review: "lorem ipsum"
}
]
}
];
App.js
,正在发生的事情的演示:-
import React, { useState, useEffect, useReducer } from "react";
import "./styles.css";
export default function App() {
const [state, dispatch] = useReducer(reducer, data);
// hnadle adding of new review
const handleAddNewReview = (id) => {
dispatch({
type: "ADD_REVIEW_ITEM",
payload: {
selectedDataId: id,
newReview: {
reviewId: new Date().getTime().toString(),
name: "doe doe",
occupation: "doctor",
rating: 5,
review: "lorem ipsum"
}
}
});
};
return (
<>
<div className="App">
<h1>Hello CodeSandbox</h1>
<h2>Start editing to see some magic happen!</h2>
</div>
{state?.length > 0 &&
state.map((data) => (
<div key={data.id}>
<h1>{data.name}</h1>
{data.listOfReview?.length > 0 &&
data.listOfReview.map((review) => (
<div key={review.reviewId}>
<h3>{review.name}</h3>
<p>{review.occupation}</p>
</div>
))}
<button onClick={() => handleAddNewReview(data.id)}>
Add new review
</button>
</div>
))}
</>
);
}
问题是,一旦我第一次点击 button
,state
已更新正确。但是,如果我单击它第二次,它会以某种方式添加两个相同的review
。我应该如何更改 reducer
中的 code
来解决这个问题?
这是上述案例的有效 sandbox。
尝试将减速器更改为:
case "ADD_REVIEW_ITEM":
return state.map((data) => {
if (data.id === action.payload.selectedDataId) {
return {
...data,
listOfReview: [...data.listOfReview, action.payload.newReview]
};
}
return data;
});
目前,您正在改变状态变量并推入一个可能导致副作用的数组。