使用react router,我可以使用Link元素来创建由react route本地处理的链接。

我看到它在内部调用this.context.transitionTo(…)。

我想做导航。不是来自链接,而是来自下拉选择(例如)。我如何在代码中执行此操作?this.context是什么?

我看到了导航混合,但我可以在没有混合的情况下这样做吗?


当前回答

以下是最简单、最干净的方法,大约是当前的React Router 3.0.0和ES6:

使用ES6反应路由器3.x.x:

import { withRouter } from 'react-router';

class Example extends React.Component {
   // use `this.props.router.push('/some/path')` here
};

// Export the decorated class
export default withRouter(Example);

或者,如果不是默认类,则导出如下:

withRouter(Example);
export { Example };

注意,在3.x.x中,<Link>组件本身使用router.push,因此您可以传递任何传递<Linkto=标记的内容,例如:

   this.props.router.push({pathname: '/some/path', query: {key1: 'val1', key2: 'val2'})'

其他回答

React路由器v2

对于最新版本(v2.0.0-rc5),推荐的导航方法是直接推到历史单例。您可以在组件外部导航文档中看到这一点。

相关摘录:

import { browserHistory } from 'react-router';
browserHistory.push('/some/path');

如果使用更新的react router API,则需要在组件内部使用this.props中的历史记录,以便:

this.props.history.push('/some/path');

它还提供pushState,但对于每个记录的警告,它都是不推荐的。

如果使用react router redux,它提供了一个推送功能,您可以这样调度:

import { push } from 'react-router-redux';
this.props.dispatch(push('/some/path'));

然而,这可能仅用于更改URL,而不是实际导航到页面。

React路由器v4和ES6

您可以使用Router和this.props.history.push。

import {withRouter} from 'react-router-dom';

class Home extends Component {

    componentDidMount() {
        this.props.history.push('/redirect-to');
    }
}

export default withRouter(Home);

对于React路由器v4+

假设在初始渲染过程中不需要导航(可以使用<Redirect>组件),这就是我们在应用程序中所做的。

定义返回null的空路由。这将允许您访问历史对象。您需要在定义路由器的顶层执行此操作。

现在,您可以在历史上做所有可以做的事情,如history.push()、history.replace()、history.go(-1)等。!

import React from 'react';
import { HashRouter, Route } from 'react-router-dom';

let routeHistory = null;

export function navigateTo(path) {
  if(routeHistory !== null) {
    routeHistory.push(path);
  }
}

export default function App(props) {
  return (
    <HashRouter hashType="noslash">
      <Route
        render={({ history }) => {
          routeHistory = history;
          return null;
        }}
      />
      {/* Rest of the App */}
    </HashRouter>
  );
}

对于这一个,谁不控制服务器端,因此使用哈希路由器v2:

将历史记录放入单独的文件(例如app_history.js ES6):

import { useRouterHistory } from 'react-router'
import { createHashHistory } from 'history'
const appHistory = useRouterHistory(createHashHistory)({ queryKey: false });

export default appHistory;

并在任何地方使用它!

react router(app.js ES6)的入口点:

import React from 'react'
import { render } from 'react-dom'
import { Router, Route, Redirect } from 'react-router'
import appHistory from './app_history'
...
const render((
  <Router history={appHistory}>
  ...
  </Router>
), document.querySelector('[data-role="app"]'));

任何组件(ES6)内的导航:

import appHistory from '../app_history'
...
ajaxLogin('/login', (err, data) => {
  if (err) {
    console.error(err); // login failed
  } else {
    // logged in
    appHistory.replace('/dashboard'); // or .push() if you don't need .replace()
  }
})

对于ES6+React组件,以下解决方案适用于我。

我跟随费利佩·斯金纳,但添加了一个端到端解决方案,以帮助像我这样的初学者。

以下是我使用的版本:

“反应路由器”:“^2.7.0”“反应”:“^15.3.1”

下面是我的react组件,其中我使用react路由器进行编程导航:

import React from 'react';

class loginComp extends React.Component {
   constructor( context) {
    super(context);
    this.state = {
      uname: '',
      pwd: ''
    };
  }

  redirectToMainPage(){
        this.context.router.replace('/home');
  }

  render(){
    return <div>
           // skipping html code 
             <button onClick={this.redirectToMainPage.bind(this)}>Redirect</button>
    </div>;
  }
};

 loginComp.contextTypes = {
    router: React.PropTypes.object.isRequired
 }

 module.exports = loginComp;

以下是路由器的配置:

 import { Router, Route, IndexRedirect, browserHistory } from 'react-router'

 render(<Router history={browserHistory}>
          <Route path='/' component={ParentComp}>
            <IndexRedirect to = "/login"/>
            <Route path='/login' component={LoginComp}/>
            <Route path='/home' component={HomeComp}/>
            <Route path='/repair' component={RepairJobComp} />
            <Route path='/service' component={ServiceJobComp} />
          </Route>
        </Router>, document.getElementById('root'));