React - 使用 Context 向下传递数组变量,但是当有更新时,组件接收数组变量不会重新渲染
React - using Context to pass down array variable, but when there is an update, component receiving array variable not re-render
我正在使用 Context
将 exerciseList
数组变量传递给 2 个不同的组件,
ExerciseList
组件和 Exercise
组件。
Exercise
组件呈现单个练习,然后
ExerciseList
组件导入并实现它。
但是现在的问题是当有更新的时候,
t.ex练习已被删除,所以ExerciseList
应该重新渲染。
但除非我刷新页面,否则它不会发生。
这是我的 Context
,
function ContextProvider(props) {
const [ exerciseList, setExerciseList ] = useState([])
useEffect(() => {
axios.get('http://localhost:5000/exercises/')
.then(response => {
setExerciseList(response.data)
})
.catch(err => console.log(err))
}, [])
return (
<Context.Provider value={{exerciseList,
setExerciseList,
}}>
{props.children}
</Context.Provider>
)
}
export { Context, ContextProvider }
并且我在 ExerciseList
组件中收到 exerciseList
这样的
export default function ExerciseList(){
const { exerciseList } = useContext(Context)
const exerciseData = exerciseList.map( exercise => (
<Exercise key={exercise._id}
id={exercise._id}
username={exercise.username}
description={exercise.description}
duration={exercise.duration}
date={exercise.date}
/>
))
return(
<div>
<h3>Exercise List</h3>
<table className="exercise-table">
<thead>
<tr>
<th>Name</th>
<th>Description</th>
<th>Duration</th>
<th>Date</th>
<th>Actions</th>
</tr>
</thead>
<tbody>
{exerciseData}
</tbody>
</table>
</div>
)
}
而我具有 delete
功能的 Exercise
组件是这样的
export default function Exercise({id, username, description, duration, date}) {
const { setExerciseList } = useContext(Context)
const deleteExercise = (id) => {
axios.delete('http://localhost:5000/exercises/' + id)
.then(res => console.log(res.data))
.catch(err => console.log(err))
setExerciseList(exercises => exercises.filter(exercise => exercise.id !== id))
}
return (
<tr>
<td>{username}</td>
<td>{description}</td>
<td>{duration}</td>
<td>{date}</td>
<td>
<Link to={"/edit/" + id}>edit</Link> | <button onClick={() => deleteExercise(id)}>delete</button>
</td>
</tr>
)
}
我想知道为什么?我把 console.log(exerciseList.length > 0)
放在 ExerciseList 组件中,
看看它是否捕捉到数组的变化,但它没有。
求助!
你把 console.log(exerciseList.length > 0)
放在 ExerciseList 的什么地方了?如果你把它放在 exerciseList.map
上面,那么你应该会看到一些日志。
这可能是您遇到的问题。
useState
中的 setState
与 class 组件中的 this.setState
不同。
它不接受函数作为参数。
所以setExerciseList
应该是这样
const deleteExercise = (id) => {
axios.delete('http://localhost:5000/exercises/' + id)
.then(res => console.log(res.data))
.catch(err => console.log(err))
// setExerciseList(exercises => exercises.filter(exercise => exercise.id !== id))
setExerciseList(exercises.filter(exercise => exercise.id !== id))
}
注意:在删除UI中的项目之前,您应该确保axios.delete
正常执行。例如,将 setExerciseList
移动到 .then
回调内部并为其提供一些更新状态。
我正在使用 Context
将 exerciseList
数组变量传递给 2 个不同的组件,
ExerciseList
组件和 Exercise
组件。
Exercise
组件呈现单个练习,然后
ExerciseList
组件导入并实现它。
但是现在的问题是当有更新的时候,
t.ex练习已被删除,所以ExerciseList
应该重新渲染。
但除非我刷新页面,否则它不会发生。
这是我的 Context
,
function ContextProvider(props) {
const [ exerciseList, setExerciseList ] = useState([])
useEffect(() => {
axios.get('http://localhost:5000/exercises/')
.then(response => {
setExerciseList(response.data)
})
.catch(err => console.log(err))
}, [])
return (
<Context.Provider value={{exerciseList,
setExerciseList,
}}>
{props.children}
</Context.Provider>
)
}
export { Context, ContextProvider }
并且我在 ExerciseList
组件中收到 exerciseList
这样的
export default function ExerciseList(){
const { exerciseList } = useContext(Context)
const exerciseData = exerciseList.map( exercise => (
<Exercise key={exercise._id}
id={exercise._id}
username={exercise.username}
description={exercise.description}
duration={exercise.duration}
date={exercise.date}
/>
))
return(
<div>
<h3>Exercise List</h3>
<table className="exercise-table">
<thead>
<tr>
<th>Name</th>
<th>Description</th>
<th>Duration</th>
<th>Date</th>
<th>Actions</th>
</tr>
</thead>
<tbody>
{exerciseData}
</tbody>
</table>
</div>
)
}
而我具有 delete
功能的 Exercise
组件是这样的
export default function Exercise({id, username, description, duration, date}) {
const { setExerciseList } = useContext(Context)
const deleteExercise = (id) => {
axios.delete('http://localhost:5000/exercises/' + id)
.then(res => console.log(res.data))
.catch(err => console.log(err))
setExerciseList(exercises => exercises.filter(exercise => exercise.id !== id))
}
return (
<tr>
<td>{username}</td>
<td>{description}</td>
<td>{duration}</td>
<td>{date}</td>
<td>
<Link to={"/edit/" + id}>edit</Link> | <button onClick={() => deleteExercise(id)}>delete</button>
</td>
</tr>
)
}
我想知道为什么?我把 console.log(exerciseList.length > 0)
放在 ExerciseList 组件中,
看看它是否捕捉到数组的变化,但它没有。
求助!
你把 console.log(exerciseList.length > 0)
放在 ExerciseList 的什么地方了?如果你把它放在 exerciseList.map
上面,那么你应该会看到一些日志。
这可能是您遇到的问题。
useState
中的 setState
与 class 组件中的 this.setState
不同。
它不接受函数作为参数。
所以setExerciseList
应该是这样
const deleteExercise = (id) => {
axios.delete('http://localhost:5000/exercises/' + id)
.then(res => console.log(res.data))
.catch(err => console.log(err))
// setExerciseList(exercises => exercises.filter(exercise => exercise.id !== id))
setExerciseList(exercises.filter(exercise => exercise.id !== id))
}
注意:在删除UI中的项目之前,您应该确保axios.delete
正常执行。例如,将 setExerciseList
移动到 .then
回调内部并为其提供一些更新状态。