React路由问题:使用react-router-dom与react-router-redux无法跳转至/login
解决React项目中react-router-dom + react-router-redux路由跳转失效及本地报错问题
我帮你梳理了下这类路由跳转问题的常见成因和解决方案,咱们一步步来排查修复:
1. 核心问题:history实例未与Redux Store正确同步
很多开发者用react-router-redux(现在官方推荐用connected-react-router替代)时,容易忽略history和store的绑定,这会导致路由跳转的action无法被正确处理,进而出现跳转失效的情况。
修复步骤:
- 首先安装依赖(如果还没装):
npm install connected-react-router history - 创建独立的history实例文件(比如
src/history.js):import { createBrowserHistory } from 'history'; export const history = createBrowserHistory(); - 配置Root Reducer,合并router reducer:
import { connectRouter } from 'connected-react-router'; import { combineReducers } from 'redux'; // 导入你的其他reducer import userReducer from './userReducer'; const rootReducer = (history) => combineReducers({ router: connectRouter(history), user: userReducer // 你的其他业务reducer }); export default rootReducer; - 创建Store时注入router中间件:
import { createStore, applyMiddleware, compose } from 'redux'; import { routerMiddleware } from 'connected-react-router'; import rootReducer from './reducers'; import { history } from './history'; // 如果用了redux devtools可以保留,没有的话直接用applyMiddleware const composeEnhancers = window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ || compose; const store = createStore( rootReducer(history), composeEnhancers( applyMiddleware( routerMiddleware(history), // 必须添加这个中间件来处理路由action // 其他中间件比如redux-thunk/redux-saga等 ) ) ); export default store; - 用
ConnectedRouter替代原生BrowserRouter包裹路由:import { ConnectedRouter } from 'connected-react-router'; import { Route, Switch } from 'react-router-dom'; import { history } from './history'; import Login from './components/Login'; import Dashboard from './components/Dashboard'; function App() { return ( <ConnectedRouter history={history}> <Switch> <Route path="/login" component={Login} /> <Route path="/" component={Dashboard} /> </Switch> </ConnectedRouter> ); } export default App;
2. 正确触发路由跳转
不要直接调用history.push,而是通过Redux dispatch对应的action:
方式1:直接dispatch action
import { push } from 'connected-react-router'; import { useDispatch } from 'react-redux'; function YourComponent() { const dispatch = useDispatch(); const goToLogin = () => { // 如果是跳转到根目录下的login,用绝对路径'/login' // 如果是相对当前路由的路径(比如当前在/dashboard,想跳/dashboard/login),用'login' dispatch(push('/login')); }; return <button onClick={goToLogin}>前往登录页</button>; }
方式2:通过connect映射到props
import { connect } from 'react-redux'; import { push } from 'connected-react-router'; const YourComponent = ({ pushToLogin }) => ( <button onClick={pushToLogin}>前往登录页</button> ); export default connect(null, { pushToLogin: () => push('/login') })(YourComponent);
3. 解决本地运行报错
本地报错大概率是依赖版本不兼容导致的:
- 确保
react-router-dom和connected-react-router版本匹配:- react-router-dom v5 → connected-react-router v6
- react-router-dom v4 → connected-react-router v5
可以通过npm list命令查看版本,或者直接安装对应版本:
# 比如react-router-dom是v5的情况 npm install connected-react-router@6 - 不要同时使用
BrowserRouter和ConnectedRouter,两者只能选一个,否则会出现路由冲突报错。
内容的提问来源于stack exchange,提问作者Chasing Unicorn - Anshu
相关产品推荐
相关产品推荐

