React-router-dom更改URL,但不更新样式化组件的ThemeProvider的内容

时间:2018-09-22 12:21:21

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

您能帮我说出什么问题吗?我正在使用react-router-dom,并且当我尝试切换到某个页面时-URL正在更新,但不是内容。如果我刷新页面-内容正常

这是我的演示: https://github.com/azat-io/react-router-dom-demo/blob/master/App.js

代码如下:

import React from 'react'
import {
  BrowserRouter as Router,
  Route,
  Switch,
  Link,
} from 'react-router-dom'
import { Provider } from 'react-redux'
import { createStore, combineReducers } from 'redux'
import { render } from 'react-dom'
import styled, { ThemeProvider, createGlobalStyle } from 'styled-components'
import { normalize, selection } from 'polished'

import Home from 'containers/Home'
import Categories from 'containers/Categories'
import NotFound from 'containers/NotFound'

import theme from 'etc/theme'

const rootReducer = combineReducers({})

const store = createStore(rootReducer, window.__REDUX_DEVTOOLS_EXTENSION__ &&
  window.__REDUX_DEVTOOLS_EXTENSION__())

const GlobalStyle = createGlobalStyle`
  ${normalize()}
  ${({ theme }) => selection({
    background: theme.primaryColor,
    color: theme.primaryContrastColor,
  })}
  a {
    display: block;
  }
`

const Container = styled.div`
  display: block;
  min-height: 100%;
`

const App = () => (
  <Provider store={store}>
    <Router>
      <ThemeProvider theme={theme}>
        <Container>
          <GlobalStyle />
          <menu>
            <Link to={'/'}>
              { 'to home' }
            </Link>
            <Link to={'/categories'}>
              { 'to categories' }
            </Link>
          </menu>
          <Switch>
            <Route exact path={'/'} component={Home} />
            <Route path={'/categories'} component={Categories} />
            <Route component={NotFound} />
          </Switch>
        </Container>
      </ThemeProvider>
    </Router>
  </Provider>
)

render(<App />, document.getElementById('app'))

2 个答案:

答案 0 :(得分:1)

您的Container组件没有更新其子代。因此,问题来自样式化组件。

一种可行的解决方案是将<Router>包装在您的<Container>中,而不是相反的方式……

const App = () => (
  <Provider store={store}>
    <ThemeProvider theme={theme}>
      <Container>
        <Router>
        <React.Fragment>
          <GlobalStyle />
          <menu>
            <Link to={"/"}>{"to home"}</Link>
            <Link to={"/categories"}>{"to categories"}</Link>
          </menu>
          <Switch>
            <Route exact path={"/"} component={Home} />
            <Route path={"/categories"} component={Categories} />
            <Route component={NotFound} />
          </Switch>
        </React.Fragment>
        </Router>
      </Container>
    </ThemeProvider>
  </Provider>
);

另一种解决方案(未试用)是使用styled('div')而不是styled.div,并使其余代码保持不变。

要尝试的另一件事(未经测试)是将<Container>替换为<ContainerWrapper>,这是其代码:const ContainerWrapper = props => <Container>{props.children}</Container> 这样做的原因是要具有无状态功能,我们可以确定该功能会在路线更改时更新。

请随时告诉我哪种方法最有效,以便调整此答案以供将来参考。

答案 1 :(得分:0)

Router组件和react-router-dom并不像您想象的那样灵活,但是无论如何它们还是可以很好地发挥作用。

Router不喜欢里面的“太多东西”,就我自己而言,我不使用Link组件。

无论如何,这是一个基本的示例工作:

import React from "react"
import { BrowserRouter as Router, Route, Switch, Link } from "react-router-dom"
import { render } from "react-dom"

const Home = () => <p>Home</p>
const Categories = () => <p>Categories</p>
const NotFound = () => <p>NotFound</p>

const App = props =>
  <div>
    App container
   {props.children}
  </div>


const Header = () => 
  <div>
    Menu
    <ul>
      <li><Link to='/'>Home</Link></li>
      <li><Link to='/categories'>Categories</Link></li>
    </ul>
  </div>

render(
  <App>
    <Router>
      <div>
        <Header/>
        <Switch>
          <Route exact path={'/'} component={Home} />
          <Route path={'/categories'} component={Categories} />
          <Route component={NotFound} />
        </Switch>    
      </div>
    </Router>
  </App>,
  document.getElementById("root")
)

Check this example out for more

Code of the above post is here