connected-react-router是一个绑定react-router到redux的组件,来实现双向绑定router的数据到redux store中,这么做的好处就是让应用更Redux化,可以在action中实现对路由的操作。

这个组件的关键就在于使用了react-router中的一个关键组件,也就是ReactTraining/history,这个组件看了下文档,作者是这么解释的

The history library is a lightweight layer over browsers' built-in History and Location APIs. The goal is not to provide a full implementation of these APIs, but rather to make it easy for users to opt-in to different methods of navigation.

按照我的理解应该是对浏览器原本的history对象做了一定的增强,同时应该对ReactNative等环境做了一定的polyfill。

使用connected-react-router这个库的关键点就在于创建合适的history对象

我当前connected-react-router的版本为v6,需要react router大于v4,并且react-redux大于v6,react大于v16.4.0

先看index.js

import React from 'react';
import ReactDOM from 'react-dom';
import { Provider } from 'react-redux'
import configureStore, { history } from './configureStore'
import { ConnectedRouter } from 'connected-react-router'
import routes from './routes' const store = configureStore() ReactDOM.render(
<Provider store={store}>// Provider使用context将store传给子组件
<ConnectedRouter history={history}>//ConnectedRouter传递history对象作为props
{ routes }
</ConnectedRouter>
</Provider>
, document.getElementById('root'));

configureStore.js提供history与store

import { createBrowserHistory } from 'history'
import { applyMiddleware, compose, createStore } from 'redux'
import { routerMiddleware } from 'connected-react-router'
import createRootReducer from './reducers'
export const history = createBrowserHistory()
export default function configureStore(preloadedState) {
  const composeEnhancer = window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ || 
  compose
  
  const store = createStore(
    createRootReducer(history),
    preloadedState,
    composeEnhancer(
      applyMiddleware(
        routerMiddleware(history),
      ),
    ),
  )
  return store
}

使用createBrowserHistory()创建history。

const history = createBrowserHistory()

使用redux-devtools-extension

window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__

reducers/index.js

import { combineReducers } from 'redux'
import { connectRouter } from 'connected-react-router'
import counterReducer from './counter' const rootReducer = (history) => combineReducers({
count: counterReducer,
router: connectRouter(history)
}) export default rootReducer

combineReducers方法,用于 Reducer 的拆分。你只要定义各个子 Reducer 函数,然后用这个方法,将它们合成一个大的 Reducer

reducers/counter.js

const counterReducer = (state = 0, action) => {
switch (action.type) {
case 'INCREMENT':
return state + 1
case 'DECREMENT':
return state - 1
default:
return state
}
} export default counterReducer

routes/index.js

import React from 'react'
import { Route, Switch } from 'react-router'
import Counter from '../components/Counter'
import { Link } from 'react-router-dom'
const routes = (
  <div>
    <div>
        <Link to="/">Home</Link> 
        <Link to="/hello">Hello</Link> 
        <Link to="/counter">Counter</Link>
    </div>
    <Switch>
      <Route exact path="/" ><div>Home</div></Route>
      <Route path="/hello" ><div>Hello</div></Route>
      <Route path="/counter" component={Counter} />
      <Route ><div>No Match</div></Route>
    </Switch>
  </div>
)
export default routes

components/Counter.js

import React from 'react'
import PropTypes from 'prop-types'
import { connect } from 'react-redux'
import { increment, decrement } from '../actions/counter' const Counter = (props) => (
<div>
Counter: {props.count}
<button onClick={props.increment}>+</button>
<button onClick={props.decrement}>-</button>
</div>
) Counter.propTypes = {
count: PropTypes.number,
increment: PropTypes.func.isRequired,
decrement: PropTypes.func.isRequired,
} const mapStateToProps = state => ({
count: state.count,
}) const mapDispatchToProps = dispatch => ({
increment: () => dispatch(increment()),
decrement: () => dispatch(decrement()),
}) export default connect(mapStateToProps, mapDispatchToProps)(Counter)

actions/counter.js

export const increment = () => ({
type: 'INCREMENT',
}) export const decrement = () => ({
type: 'DECREMENT',
})

使用connected-react-router使router与store同步的更多相关文章

  1. [React] 10 - Tutorial: router

    Ref: REACT JS TUTORIAL #6 - React Router & Intro to Single Page Apps with React JS Ref: REACT JS ...

  2. vue & vue router & dynamic router

    vue & vue router & dynamic router https://router.vuejs.org/guide/essentials/dynamic-matching ...

  3. router.go,router.push,router.replace的区别

    除了使用 <router-link> 创建 a 标签来定义导航链接,我们还可以借助 router 的实例方法,通过编写代码来实现.当你点击 <router-link> 时,这个 ...

  4. [Angular2 Router] Programmatic Router Navigation via the Router API - Relative And Absolute Router Navigation

    In this tutorial we are going to learn how to navigate programmatically (or imperatively) by using t ...

  5. vue router.push(),router.replace(),router.go()和router.replace后需要返回两次的问题

    转载:https://www.cnblogs.com/lwwen/p/7245083.html https://blog.csdn.net/qq_15385627/article/details/83 ...

  6. vue router.push(),router.replace(),router.go()

    1.router.push(location)=====window.history.pushState 想要导航到不同的 URL,则使用 router.push 方法.这个方法会向 history ...

  7. [Angular2 Router] Index router

    Index router as default router. import {RouterModule} from "@angular/router"; import {NotF ...

  8. $router和router区别

    this.$router.push({path:'/'})//这个是js编程式的一种动态跳转路由方式,是全局的路由对象. 而写在router声明文件中的router是自己定义实例化的一个对象.可以使用 ...

  9. React中setState 什么时候是同步的,什么时候是异步的?

    class Example extends React.Component { constructor() { super(); this.state = { val: 0 }; } componen ...

随机推荐

  1. linux网络编程之shutdown() 与 close()函数详解

    linux网络编程之shutdown() 与 close()函数详解 参考TCPIP网络编程和UNP: shutdown函数不能关闭套接字,只能关闭输入和输出流,然后发送EOF,假设套接字为A,那么这 ...

  2. 向量容器vector操作

    1.向量容器vector 1.1 vector说明 进行vector操作前应添加头文件#include<vector>: vector是向量类型,可以容纳许多类型的数据,因此也被称为容器: ...

  3. window 如何访问虚拟机的mapreduce(遇到的坑)

    首先 先把你虚拟机和本机网络链接弄通 (详情看上一篇)  一些关于mapreduce 和hadoop的配置都在上一篇 安装eclipse 的hadoop Map/Reduce插件详情 看其他博客园.. ...

  4. STM32之GD25Q256应用笔记

    前言 使用标准SPI指令格式: 3字节地址模式或4字节地址模式: 支持SPI 总线 模式0 和 模式3: 存储容量32MB: 时钟频率范围:80Mhz – 104Mhz: 主机:STM32F103ZE ...

  5. STL语句表跳转指令学习

    打开语句表程序状态监控 发现 被跳过的指令用普通字体显示 被执行的指令用加粗的字体表示 录制成视频 如果除数是0 发生了溢出 用 JUO 跳转指令,跳转到 M001 例程已经录制成视频 上传到百度网盘 ...

  6. JumpServer简单使用

    笔记内容:简单使用jumpserver笔记日期:2018-01-22 23.9 创建jumpserver普通用户 23.10 添加机器 23.11 添加系统用户并授权 23.12 添加授权规则 23. ...

  7. JS - input输入框点击回车提交或者进行别的操作

    $("input").keydown(function(event){ if (event.keyCode == 13) {         /* 提交或者别的操作 */ } }) ...

  8. 《学习R》笔记:科学计算器、检查变量和工作区、向量、矩阵和数组、列表和数据框

    一.第二章 科学计算器 要检查两个数字是否一样,要使用 all.equal() ,不要使用 == ,== 符号仅用于比较两个整型数是否存在相同 . > all.equal(sqrt(2)^2,2 ...

  9. 工作问题整理-- sqlserver 新增参数限制,maven pom邮件发送

    1.SqlServer连续新增参数限制 com.microsoft.sqlserver.jdbc.SQLServerException: 传入的请求具有过多的参数.该服务器支持最多 2100 个参数. ...

  10. UVA - 11346 Probability(概率)(连续概率)

    题意:在[-a, a]*[-b, b]区域内随机取一个点P,求以(0, 0)和P为对角线的长方形面积大于S的概率(a,b>0, S>=0). 分析: 1.若长方形面积>S,则选取的P ...