React router的switch语句不会呈现组件

时间:2018-01-01 01:53:30

标签: reactjs react-router

我遇到问题,当我点击导航栏中标题中的链接而不是下面的组件加载时,整个页面都会发生变化(并且是空白的。没有错误被明显抛出,但即使在该路线上应该呈现的组件也显示出来。

我将解释此网站设置的工作原理。



const initialState = {};
const history = createHistory();
const store = configureStore(initialState, history);
const MOUNT_NODE = document.getElementById('app');

const render = (messages) => {
  ReactDOM.render(
    <Provider store={store}>
      <LanguageProvider messages={messages}>
        <ConnectedRouter history={history}>
          <Switch>
            <Route exact path="/" component={Splash} />
            <Route path="/main" component={App} />
          </Switch>
        </ConnectedRouter>
      </LanguageProvider>
    </Provider>,
    MOUNT_NODE
  );
};
&#13;
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>
&#13;
&#13;
&#13;

当用户首次进入该网站时,他们会看到启动页面。然后他们点击一个按钮,将他们带到主页面。这是代码:

&#13;
&#13;
const AppWrapper = styled.div`
  max-width: calc(768px + 16px * 2);
  margin: 0 auto;
  display: flex;
  min-height: 100%;
  padding: 0 16px;
  flex-direction: column;
`;

class App extends React.Component {
  render() {
    return (
      <div>
        <Header />
        <AppWrapper>
          Below this are where the new components should render.
          <Switch>
            <Route path="/aboutme" component={AboutMe} />
            <Route path="/models" component={Models} />
            <Route path="/landscapes" component={Landscapes} />
          </Switch>
          <Footer />
        </AppWrapper>
      </div>
    );
  }
}

export default App;
&#13;
&#13;
&#13;

正如您所看到的,无论路线选择了哪个组件,我都希望标题保持在最顶层。

标题的导航栏如下所示:

&#13;
&#13;
class NavBar extends React.Component {

  render() {
    return (
      <div>

        <AppBar position="static" color="default" >
          <Toolbar>
            <Typography type="title" color="inherit">
              <Link to="/models">Models</Link>
            </Typography>
            <Typography type="title" color="inherit">
              <Link to="/landscapes">Adventures</Link>
            </Typography>
            <Typography type="title" color="inherit">
              <Link to="/aboutme">About Me</Link>
            </Typography>
          </Toolbar>
        </AppBar>
      </div>
    );
  }
}

export default NavBar;
&#13;
&#13;
&#13;

当我点击此处的链接时,地址栏中的路线会相应更改,但空白页面甚至不会显示标题/工具栏。有没有人对我在这里做错了什么有任何想法?我试图使用react / redux样板,我还在学习。

3 个答案:

答案 0 :(得分:1)

使用NavBar组件更新路径时,新路径(例如:/ models)将不会在MOUNT_NODE的渲染中捕获。

MOUNT_NODE处理的路由仅为“/”和“/ main”。这就是除了它们之外的任何路线呈现空白页面的原因。

要使它在您的情况下工作,您必须使NavBar中的所有链接以“/ main”开头,并且App组件中的路由匹配。

这是react-router v4的一些很好的信息。 CSS-Tricks React Router 4

答案 1 :(得分:1)

您正在将路由/main映射到App组件,路由/models/landscapes/aboutme将在App组件内呈现,所以你的路线看起来像这样:

  • /(完全匹配)
  • /主
    • /模型
    • /风景
    • / aboutme

看到问题?路线永远不能同时匹配/main/models,...所以这些路线从未被渲染过。

解决方案

App组件的路线更改为/(不完全匹配),因此index.js中的代码将如下所示:

...
<ConnectedRouter history={history}>
  <Switch>
    <Route exact path="/" component={Splash} />
    <Route path="/" component={App} />
  </Switch>
</ConnectedRouter>
...

说明

react-router的{​​{1}}将使用第一条路线与当前路线匹配(例如Switch)。如果URL以路径值开头(例如https://mywebsite.com/path/to/some/where/,...),则路径匹配,开头的/models字符表示网站的根(所以{ {1}}相当于/,这称为short absolute path)。

因此,当您在/models时,https://mywebsite.com/models将路径https://mywebsite.com/models与路径匹配:

  • react-router确切路由`:不匹配,因为确切路由需要路由to be exactly the same
  • /models路线:不匹配,/不能以/main开头

然后/models没有呈现任何内容,因为没有路由匹配。

当您将/main更改为react-router时,结果将如下所示:

然后路由器在内部交换机中呈现/组件:

  • /路线:不匹配,
  • App route:match,呈现/aboutme组件并跳过以下路线。

答案 2 :(得分:0)

这就是我设置它为我工作的方式。 使用React-router v4

我的索引文件

import React from 'react';
import ReactDOM from 'react-dom';
import './index.css';
import App from './App.jsx';
import 'bootstrap/dist/css/bootstrap.css';
import registerServiceWorker from './registerServiceWorker';
import 'font-awesome/css/font-awesome.min.css';
import { Provider } from 'react-redux'
import { createStore, applyMiddleware } from 'redux';
import thunk from 'redux-thunk';
import appReducer from './containers/reducers/index.js';

const store = createStore(appReducer, applyMiddleware(thunk));
ReactDOM.render(
     <Provider store={store}>
        <App />
      </Provider>,
      document.getElementById('app'));
 registerServiceWorker();

    store.subscribe(() => {
      console.log("Store Changed, ", store.getState());
     });

我的应用程序文件,我设置我的路线

import React, { Component } from 'react';
import { BrowserRouter, Switch, Route } from 'react-router-dom';

import Splash from './containers/home/Home.jsx';
import Model from './containers/home/About.jsx';

export default class Routes extends Component{
    render(){
       return (
         <BrowserRouter>
           <div>
            <Header />
            <Switch>
                <Route exact path="/" component={Splash} />
                <Route path="/models" component={Models} />
               <Route path="/landscapes" component={Landscapes} />
            </Switch>
            <Footer />
           </div>
         </BrowserRouter>
       )
      }
     }


       <Typography type="title" color="inherit">
          <Link to={"/models"} >Models</Link>
        </Typography>

注意:有一个<Header />组件和一个<Footer />组件。我这样做是因为我的页眉和页脚在我的应用程序中不变。 这应该工作,只需按照基本和编辑为你工作。