React Router v4 重定向不起作用

IT技术 javascript reactjs react-router react-router-v4
2021-04-03 23:34:54

我有一条在检查这样的条件后重定向的路线

<Route exact path="/" render={()=>(
Store.isFirstTime ? <Redirect to="intro" /> : <Home state={Store}/>)}/>

当条件为真但未安装组件时,url 会更改。其余的组件代码如下。

render() {
    return (
      <div>
        ...
        <Route exact path="/" render={()=>(
          Store.isFirstTime ? <Redirect to="intro" /> : <Home state={Store} />         
        )} />
        <Route path="/intro" render={()=>(<IntroWizard state={Store.userInfo}/>)} />
        <Route path="/home" render={()=>(<Home state={Store}/>)} />
        <Route render={()=>(<h1>404 Not Found</h1>)} />
        <Footer />
      </div>
    );
  }

我的应用程序组件包含在 BrowserRouter 中,如下所示

ReactDOM.render(<BrowserRouter>
    <App/>
</BrowserRouter>,
  document.getElementById('root')
);

当我直接在浏览器中点击 url 时,如 'localhost:3000/intro' 组件已成功安装,但是当它通过重定向时,它不会显示该组件。我如何解决它?

编辑

因此缺少一个细节,我尝试创建另一个项目来重现该问题。我的 App 组件是来自 mobx-react 的观察者,它的导出如下所示

let App = observer(class App { ... })
export default App

我用示例代码创建了这个 repo 来重现您可以使用它的问题 https://github.com/mdanishs/mobxtest/

因此,当组件被包装到 mobx-react 观察者中时,重定向不起作用,否则它工作正常

6个回答

提问者在 GitHub 上发布了一个问题,并得到了这个显然未发布的隐藏指南(编辑:现已发布),这也帮助了我。我在这里发布它是因为我遇到了同样的问题并希望其他人避免我们的痛苦。

问题是 mobx-react 和 react-redux 都提供了自己的shouldComponentUpdate()函数,只检查 prop 的变化,但是 react-router 通过上下文向下发送状态。当位置改变时,它不会改变任何props,所以它不会触发更新。

解决这个问题的方法是将位置作为props向下传递。上面的指南列出了几种方法,但最简单的方法是用withRouter()高阶组件包装容器

export default withRouter(observer(MyComponent))

或者,对于 redux:

export default withRouter(connect(mapStateToProps)(MyComponent))
是的,通常 React Router 和 Redux 一起工作得很好。但有时,应用程序的组件可能会在位置更改时不更新(子路由或活动导航链接不更新)。这称为阻止更新。问题是 Redux 实现了 shouldComponentUpdate 并且如果它没有从路由器接收道具,则没有任何迹象表明任何事情发生了变化。这很容易解决。找到连接组件的位置并将其包装在 withRouter 中。github.com/ReactTraining/react-router/blob/master/packages/...
2021-06-05 23:34:54

你应该只Redirect在你的渲染方法中渲染:

render() {
  return (<Redirect to="/" />);
}

但这是我最喜欢的不使用Redirect组件的解决方案

  1. 进口 import { withRouter } from 'react-router-dom';
  2. export default withRouter(MyComponent);
  3. 最后,在您的操作方法中,假设 handlingButtonClick
handlingButtonClick = () => {
  this.props.history.push("/") //doing redirect here.
}
我也是,只能使用 withRouter 和 this.props.history.push 谢谢兄弟
2021-05-28 23:34:54
this.props.history.push('/something') 是唯一对我有用的东西
2021-05-31 23:34:54
它不能解决所有情况。我已经尝试了两者,但它不起作用。所有仅适用于 FIRST 重定向,但如果我在第一页返回/重定向/history.push() 然后尝试像以前一样进行相同的重定向,它似乎刷新了 DOM/页面,但我卡在那里。
2021-06-09 23:34:54

<Redirect />不应该在<Switch></Switch>标签内。

试过了。在我的情况下没有帮助。
2021-05-22 23:34:54
大声笑,在此线程上的所有过度设计的解决方案中,这是唯一对我有用的解决方案,而且它是单衬。
2021-06-20 23:34:54
这解决了我的问题!将 <Redirect> 置于 <Switch> 之外后,组件将正确呈现。谢谢!
2021-06-21 23:34:54

将 Router 与其他组件(如翻译提供程序、主题提供程序等)组合时要小心。 一段时间后,我发现您的应用程序必须由 Router 严格包装,如下所示:

<Provider store={store}>
  <ThemeProvider theme={theme}>
    <TranslationProvider
      namespaces={['Common', 'Rental']}
      translations={translations}
      defaultNS={'Common'}
    >
      <Router>
        <App />
      </Router>
    </TranslationProvider>
  </ThemeProvider>
</Provider>

希望这可以帮助某人

太好了,这对我来说也是问题,已经包裹了ThemeProvider导致问题的路线
2021-05-26 23:34:54
非常感谢,你帮了我很多!在我的情况下IntlProvider是罪魁祸首。我认为这可能是因为上下文或一些shouldComponentUpdate魔法。
2021-06-05 23:34:54

你在介绍前面少了一个 /

<Route exact path="/" render={()=>(
  Store.isFirstTime ? <Redirect to="/intro" /> : <Home state={Store} />         
)} />
哇,就是这样。我正在从接受的答案中阅读各种文档,但我只需要一个/:)
2021-06-06 23:34:54
您(或您正在使用的库)是否在任何地方使用 shouldComponentUpdate?github.com/ReactTraining/react-router/blob/v4/packages/...
2021-06-19 23:34:54