【问题标题】:Component is not re-rendering upon url change组件不会在 url 更改时重新呈现
【发布时间】:2021-01-26 02:16:55
【问题描述】:

Router 配置如下所示

App.js

<Router>
  <Switch>
    <Route exact path="/" render={() => <Home />} />
    <Route exact path="/products/:productId" component={ ProductDetail } />
    <Redirect to="/" />
  </Switch>
</Router>

这是ProductDetail 组件的样子

ProductDetail.js

export const ProductDetail = ({ match }) => {
  const productId = match.params.productId;
    useEffect(() => {
        dispatch(fetchProductById(productId));
  }, [productId, dispatch]);

const product = useSelector((state) => selectProductById(state, productId));
return(<.....>)
}

现在,当我从 Home 导航到 ProductDetail 时,一切正常。但是,如果我尝试直接点击 url http://localhost:3000/products/someId,则该组件不会呈现并且不会调用 useEffect 钩子。

我已经阅读了Router 文档,上面写着

当您使用组件(而不是渲染或子组件,如下所示)时,路由器使用 React.createElement 从给定组件创建一个新的 React 元素。

这不应该意味着新创建的组件(在我的例子中是ProductDetail)应该渲染并调用钩子吗? 我是 React 的新手,所以我可能会遗漏一些相当简单的东西。

【问题讨论】:

  • Home 组件是否初始化了ProductDetail 所依赖的某种状态? “组件不渲染”是指它渲染了Home 组件还是根本不渲染任何东西?
  • 是的,Home 组件也有useEffect(async func...),它会为主页预取产品。现在ProductDetail 只是显示单个产品的详细信息。 “组件不渲染”是指 ProductDetails 组件如果我直接使用 productId
  • “休息”是什么意思?有错误吗?
  • 错误提示为can't read property title of undefined,表示未获取它尝试渲染的产品product.title
  • 当组件渲染时 会触发钩子。组件不会等待操作的结果。

标签: reactjs react-hooks react-router-dom


【解决方案1】:

如 cmets 中所述,当直接导航到 ProductDetail 组件时,该产品还不会出现在商店中。 useEffect 钩子启动产品的加载,但在完成之前,product 将是未定义的(或 null,或其他取决于您的减速器)。您需要单独处理这种情况。

处理它的最简单方法是呈现某种加载指示器,例如

export const ProductDetail = ({ match }) => {
  const productId = match.params.productId;
    useEffect(() => {
        dispatch(fetchProductById(productId));
  }, [productId, dispatch]);

  const product = useSelector((state) => selectProductById(state, productId));

  if (!product) {
    return <p>Loading...</p>
  }

  return(<.....>)
}

此外,正如 cmets 中也提到的,钩子通常会在 组件呈现时触发。该组件不会等待由useEffect 挂钩启动的操作完成。来自React's docs:

传递给useEffect的函数将在渲染提交到屏幕后运行。

【讨论】:

    猜你喜欢
    • 2021-07-10
    • 2020-09-14
    • 1970-01-01
    • 2016-12-25
    • 2020-06-27
    • 2016-12-05
    • 2016-12-26
    • 1970-01-01
    • 2019-01-09
    相关资源
    最近更新 更多