You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React组件调用传入的refresh函数后页面未刷新如何解决?

定位步骤

你可以按如下顺序快速定位问题:

  • 在refreshProducts函数内加入打印日志,确认子组件调用props.refresh()时该函数能正常触发,如果能正常打印说明子组件传值逻辑没问题,问题出在父组件的刷新逻辑
  • 在原useMemo的回调函数内加打印日志,触发refresh后会发现该回调不会执行,即可确认是请求触发逻辑存在问题

问题根因

你代码中触发刷新的逻辑存在3个核心错误,导致调用refresh后没有重新拉取数据刷新页面:

  • 误用useMemo执行网络请求副作用:useMemo是用于缓存计算结果的Hook,不适合用来触发请求这类副作用,应当使用useEffect
  • 依赖项配置错误:useMemo的第二个参数要求是依赖数组,你当前直接传入了shouldRefresh变量没有包在数组中,所以依赖监听完全不生效
  • 状态更新存在闭包风险:refreshProducts中直接使用!shouldRefresh更新状态,可能因为闭包拿到旧值导致状态没有按预期翻转

修复方案

1. 替换useMemo为useEffect,正确配置依赖

将原来的useMemo块替换为如下useEffect代码:

useEffect(() => {
  axios.get("/products", { headers: headers }).then((resp) => {
    setProduct(resp.data)
  })
}, [shouldRefresh])

2. 修正状态更新逻辑,规避闭包问题

修改refreshProducts函数:

function refreshProducts() {
    setRefresh(prev => !prev)
}

3. 补充列表渲染key属性

给InfoCard加上唯一key,避免React列表渲染异常:

{products.map((product) => (
    <InfoCard key={product.id} product={product} refresh={refreshProducts}></InfoCard>
)).reverse()}

完整修复后代码

function ProductsPage(props) {
    const [products, setProduct] = useState([])
    const [shouldRefresh, setRefresh] = useState(false)

    function refreshProducts() {
        setRefresh(prev => !prev)
    }

    const token = localStorage.getItem("token")
    const headers = { Authorization: "Token " + token }

    useEffect(() => {
        axios.get("/products", { headers: headers }).then((resp) => {
            setProduct(resp.data)
        })
    }, [shouldRefresh])

    return (
        <Box className="cardDeck">
            <Redirect_if_not_logged_in />
            {products.map((product) => (
                <InfoCard key={product.id} product={product} refresh={refreshProducts}></InfoCard>
            )).reverse()}
        </Box>
    )
}

内容的提问来源于stack exchange,提问作者Omar Alhussani

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.27 06:06:08