網站首頁 編程語言 正文
1. 概述
使用 redux 庫中提供的 combineReducers 方法,可以將多個拆分 reducer 函數合并成統一的 reducer 函數,提供給 createStore 來使用。我們可以將 Redux 進行模塊化拆分,再利用這個函數,將多個拆分 reducer 函數合并成統一的 reducer 函數,再傳給 createStore 來使用。
2. 方式1-單純文件拆分
redux 入口文件(store/index.js):
// 導入redux中的createStore創建倉庫數據的方法
// combineReducers 用來合并多個拆分后的 reducer方式,返回一個新 reducer
// applyMiddleware 擴展redux功能
import { createStore, combineReducers, applyMiddleware } from 'redux'
// 配合瀏覽器安裝的插件來進行redux調試所用
// 開發時有用,生產要關閉
import { composeWithDevTools } from '@redux-devtools/extension'
// 導入拆分開的模塊
import count from './reducers/count'
import film from './reducers/film'
// 合并多個模塊中的 reducer 函數,并且返回一個新的 reducer 函數
const reducer = combineReducers({
// key:value
// key:它是在獲取 state 數據時的命名空間名稱,redux 中沒有 dispatch 操作的命名空間名稱
// 如果你進行了 redux 模塊化拆分,則需要注意 type 的類型名稱不能重名,如果重名則都會執行
// type: 以拆分后的文件名稱為前綴:xxx_type 類型名,不會重名
// value:拆分后的 reducr 純函數
count,
film
})
const store = createStore(
reducer,
composeWithDevTools()
)
// 導出
export default store
計數模塊(count.js):
// 計數模塊
// 初始state數據
const initState = {
num: 100
}
// 定義一個純函數reducer,專門用來操作state中的數據,要返回一個新的state
const reducer = (state = initState, action) => {
if (action.type === 'count_add_num') return { ...state, num: state.num + action.payload }
return state;
}
// 導出
export default reducer
電影列表模塊(film.js):
// 電影列表展示模塊
// 初始state數據
const initState = {
nowplayings: []
}
// 定義一個純函數reducer,專門用來操作state中的數據,要返回一個新的state
const reducer = (state = initState, action) => {
if (action.type === 'film_set_nowplayings') return { ...state, nowplayings: action.payload }
return state;
}
// 導出
export default reducer
計數器模塊的裝飾器函數(connect.js):
import { connect } from 'react-redux'
// todo... 一會要配置路徑別名,它引入時就會短一些
// import countAction from '../../store/actionCreators/countAction'
import countAction from '@/store/actionCreators/countAction'
const mapDispatchToProps = dispatch => ({
...countAction(dispatch)
})
export default connect(state => state.count, mapDispatchToProps)
countAction.js:
export default dispatch => ({
add(n = 1) {
dispatch({ type: 'count_add_num', payload: n })
}
})
App.jsx:
import React, { Component } from 'react'
import { Switch, Route, Link } from 'react-router-dom'
import Count from './views/Count'
import Nowplaying from './views/Nowplaying'
class App extends Component {
render() {
return (
<div>
<div>
<Link to='/nowplaying'>nowplaying</Link> --
<Link to='/count'>count</Link>
</div>
<hr />
{/* 定義路由規則 */}
<Switch>
<Route path="/nowplaying" component={Nowplaying} />
<Route path="/count" component={Count} />
</Switch>
</div>
)
}
}
export default App
計數器視圖(index.jsx):
// 計數組件
import React, { Component } from 'react'
import connect from './connect'
@connect
class Count extends Component {
render() {
return (
<div>
<h3>{this.props.num}</h3>
<button onClick={() => this.props.add()}>累加NUM</button>
</div>
)
}
}
export default Count
上面是同步操作的模塊拆分(針對計數器模塊做的演示),下面是異步操作的模塊化拆分,以電影播放列表為例。
電影模塊的裝飾器函數(connect.js):
import { connect } from 'react-redux'
import filmAction from '@/store/actionCreators/filmAction'
export default connect(state => state.film, dispatch => filmAction(dispatch))
filmAction.js:
import { getNowPlayingFilmListApi } from '@/api/filmApi'
export default dispatch => ({
add(page = 1) {
getNowPlayingFilmListApi(page).then(ret => {
dispatch({ type: 'film_set_nowplayings', payload: ret.data.films })
})
}
})
// async 和 await 寫法
// export default dispatch => ({
// async add(page = 1) {
// let ret = await getNowPlayingFilmListApi(page)
// dispatch({ type: 'film_set_nowplayings', payload: ret.data.films })
// }
// })
filmApi.js:
import { get } from '@/utils/http'
export const getNowPlayingFilmListApi = (page = 1) => {
return get(`/api/v1/getNowPlayingFilmList?cityId=110100&pageNum=${page}&pageSize=10`)
}
電影模塊視圖(index.jsx):
// 電影展示列表組件
import React, { Component } from 'react'
import connect from './connect'
@connect
class Nowplaying extends Component {
componentDidMount() {
this.props.add()
}
render() {
return (
<div>
{this.props.nowplayings.length === 0 ? (
<div>加載中...</div>
) : (
this.props.nowplayings.map(item => <div key={item.filmId}>{item.name}</div>)
)}
</div>
)
}
}
export default Nowplaying
3. 方式2-使用中間件redux-thunk進行模塊拆分
關于 Redux 的中間件的原理,可以去閱讀下面這篇文章,文章寫得非常精彩!
傳送門
概述:
redux-thunk 它是由 redux 官方開發出來的 redux 中間件,它的作用:解決 redux 中使用異步處理方案。redux-thunk 中間件可以允許在 connect 參數 2 中派發任務時返回的是一個函數,此函數形參中,redux-thunk 會自動注入一個 dispatch 派發函數,從而讓你調用 dispath 函數來派發任務給 redux,從而實現異步處理。
安裝:
yarn add redux-thunk
使用:
上文提到了對異步操作的處理,在上文基礎上,我們修改成使用中間件進行處理的寫法。
index.js:
// 導入redux中的createStore創建倉庫數據的方法
// combineReducers 用來合并多個拆分后的 reducer方式,返回一個新 reducer
// applyMiddleware 擴展redux功能
import { createStore, combineReducers, applyMiddleware } from 'redux'
// 配合瀏覽器安裝的插件來進行redux調試所用
// 開發時有用,生產要關閉
import { composeWithDevTools } from '@redux-devtools/extension'
// 導入拆分開的模塊
import count from './reducers/count'
import film from './reducers/film'
import thunk from 'redux-thunk'
// 合并多個模塊中的 reducer 函數,并且返回一個新的 reducer 函數
const reducer = combineReducers({
count,
film
})
const store = createStore(
reducer,
composeWithDevTools(applyMiddleware(thunk))
)
// 導出
export default store
connect.js:
import { connect } from 'react-redux'
// actions 這是一個對象 {a:funtion(){}}
import * as actions from '@/store/actionCreators/filmAction'
export default connect(state => state.film, actions)
filmAction.js:
import { getNowPlayingFilmListApi } from '@/api/filmApi'
const addActionCreator = data => ({ type: 'film_set_nowplayings', payload: data })
// 異步
export const add = (page = 1) => async dispatch => {
let ret = await getNowPlayingFilmListApi(page)
dispatch(addActionCreator(ret.data.films))
}
原文鏈接:https://blog.csdn.net/weixin_45605541/article/details/127078701
相關推薦
- 2022-12-14 Android?Studio?gradle配置packagingOptions打包so庫重復_And
- 2022-08-12 Linux?中ls命令的使用詳細介紹_linux shell
- 2023-04-09 利用Matplotlib實現單畫布繪制多個子圖_python
- 2022-10-02 Android?NTP?時間同步機制詳解_Android
- 2022-06-30 利用Python刪除電腦中重復文件的方法_python
- 2022-04-18 C#實現在窗體上的統計圖效果_C#教程
- 2022-07-08 python中的annotate函數使用_python
- 2022-05-22 云原生Kubernetes初始化容器Init使用教程_云其它
- 最近更新
-
- window11 系統安裝 yarn
- 超詳細win安裝深度學習環境2025年最新版(
- Linux 中運行的top命令 怎么退出?
- MySQL 中decimal 的用法? 存儲小
- get 、set 、toString 方法的使
- @Resource和 @Autowired注解
- Java基礎操作-- 運算符,流程控制 Flo
- 1. Int 和Integer 的區別,Jav
- spring @retryable不生效的一種
- Spring Security之認證信息的處理
- Spring Security之認證過濾器
- Spring Security概述快速入門
- Spring Security之配置體系
- 【SpringBoot】SpringCache
- Spring Security之基于方法配置權
- redisson分布式鎖中waittime的設
- maven:解決release錯誤:Artif
- restTemplate使用總結
- Spring Security之安全異常處理
- MybatisPlus優雅實現加密?
- Spring ioc容器與Bean的生命周期。
- 【探索SpringCloud】服務發現-Nac
- Spring Security之基于HttpR
- Redis 底層數據結構-簡單動態字符串(SD
- arthas操作spring被代理目標對象命令
- Spring中的單例模式應用詳解
- 聊聊消息隊列,發送消息的4種方式
- bootspring第三方資源配置管理
- GIT同步修改后的遠程分支