2017-05-07 73 views
6

我试图使用browserHistory.push以编程方式更改页面。在我的其中一个组件中,但不在我嵌入其中的组件中。this.props.history.push适用于某些组件,而不适用于其他组件

有没有人知道为什么我的项目抛出的错误只在子组件而不是父组件?

无法读取未定义

父组件的特性 '推'

import React, {Component} from 'react'; 
import { browserHistory } from 'react-router'; 
import ChildView from './ChildView'; 

class ParentView extends Component { 

constructor(props) { 
    super(props); 
    this.addEvent = this.addEvent.bind(this); 
    } 

changePage() { 
    this.props.history.push("/someNewPage"); 
    } 

render() { 
    return (
     <div> 
     <div> 
      <button onClick={this.changePage}>Go to a New Page!</button> 
     </div> 

     <ChildView /> // this is the child component where this.props.history.push doesn't work 

     </div> 
    ); 
    } 
} 

function mapStateToProps(state) { 
    return { 
     user: state.user 
    }; 
} 

function matchDispatchToProps(dispatch) { 
    return bindActionCreators({ 
     setName: setName 
    }, dispatch) 
} 

export default connect(mapStateToProps, matchDispatchToProps)(ParentView); 

辅元件

import React, {Component} from 'react'; 
    import { browserHistory } from 'react-router'; 

    class ChildView extends Component { 

    constructor(props) { 
     super(props); 
     this.addEvent = this.addEvent.bind(this); 
     } 

    changePage() { 
     this.props.history.push("/someNewPage"); 
     } 

    render() { 
     return (
      <div> 
      <div> 
       <button onClick={this.changePage}>Go to a New Page!</button> 
      </div> 

      </div> 
     ); 
     } 
    } 

    function mapStateToProps(state) { 
     return { 
      user: state.user 
     }; 
    } 

    function matchDispatchToProps(dispatch) { 
     return bindActionCreators({ 
      setName: setName 
     }, dispatch) 
    } 

    export default connect(mapStateToProps, matchDispatchToProps)(ChildView); 

路由器

// Libraries 
import React from 'react'; 
import { BrowserRouter as Router, Route, Switch } from 'react-router-dom'; 
import { browserHistory } from 'react-router'; 

// Components 
import NotFound from './components/NotFound'; 
import ParentView from './components/ParentView'; 
import ChildView from './components/ChildView'; 
import SomeNewPage from './components/SomeNewPage'; 

// Redux 
import { Provider } from 'react-redux'; 
import {createStore} from 'redux'; 
import allReducers from './reducers'; 

const store = createStore(
    allReducers, 
    window.devToolsExtension && window.devToolsExtension() 
); 

const routes = (
    <Router history={browserHistory}> 
     <div> 
     <Provider store={store}> 
      <Switch> 
       <Route path="/" exact component={Home} /> 
       <Route path="/parentView" component={ParentView} /> 
       <Route path="/someNewPage" component={SomeNewPage} /> 
       <Route path="/childView" component={ChildView} /> 
       <Route component={NotFound} /> 
      </Switch> 
     </Provider> 
     </div> 
    </Router> 
); 

export default routes; 

正如你所看到的,组件几乎一致,除了孩子一个是父一个内部相同。

注意我曾尝试这些方法,但他们不解决这个问题对我来说:

+0

起反应路由器您使用的版本? – CraigRodrigues

回答

11

你在你的问题回答了你的问题。

正如您所看到的,除 之外,组件几乎完全相同,子组件在父组件内。

事实上,组件进一步嵌套是您的问题。 React路由器仅将路由道具注入到路由到的组件,但不注入嵌套在其中的组件。

请参阅this问题的接受答案。基本的想法是,你现在需要找到一种方法将路由道具注入到子组件中。 您可以通过将孩子包裹在HOC withRouter中来做到这一点。

export default withRouter(connect(mapStateToProps, matchDispatchToProps)(ChildView)); 

我希望这会有所帮助。

+0

由于我仍然想继续连接我的组件到redux,你知道如何将我的'export default connect(mapStateToProps,matchDispatchToProps)(ChildView);'line和推荐的'export default withRouter(Child)从你的链接线? – Rbar

+1

只是为了回答他人的问题,'出口默认与路由器(连接(mapStateToProps,matchDispatchToProps)(ChildView));'就像一个魅力。巨大的感谢,@ promisified! – Rbar

+0

请随时将这段代码添加到我的答案中。 –

0

使用withRouter是好的,另一种选择是将历史作为父项传递给子项(不使用路由器),例如,G:

家长

<SignupForm history={this.props.history}/> 

儿童

this.props.history.push('/dashboard'); 
相关问题