“开启掘金成长之旅!这是我参与「掘金日新计划 · 2 月更文挑战」的第 9 天,点击查看活动详情”
1. 简介
Redux 是 JavaScript 应用的状态容器,提供可预测的状态管理。
Redux 本身是一个独立的库,可以与任何 UI 层或框架一起使用。
Redux 就类似 Vue中的 Vuex
2. 代码学习
1. 安装
pnpm i redux react-redux
- Redux 本身是一个独立的库.
- React-Redux 是 React 的官方 Redux UI 绑定库.
- 想要同时使用 Redux 和 React,使用 React-Redux 来绑定这两个库.
2. 创建Store,控制状态的方法
- 新建store文件
- 再创建index.tx文件
import { legacy_createStore as createStore } from 'redux' export interface stateType { name: string, age: number } interface actionType { type: string, payload: any } const userStore = (state: stateType = {name: '张三', age: 20 }, action: actionType) =>{ switch (action.type) { case 'setName': console.log("修改name") return { ...state, name: action.payload } case 'setAge': console.log("修改age") return { ...state, age: action.payload } default: return state } } export default createStore(userStore) - state 需要共享的数据
- action 修改 state的动作
- action 中有两个属性,type 是类型, payload是更新的最新值
3. 绑定store
- 全局状态必须放在跟组件 main.tsx文件中
import React from 'react'
import ReactDOM from 'react-dom/client'
import App from './App'
import { Provider } from 'react-redux'
import store from './store'
ReactDOM.createRoot(document.getElementById('root') as HTMLElement).render(
<Provider store={store}>
<App/>
</Provider>
)
4. 在组件中使用
- 获取数据
useSelector 用于获取全局状态
import { useSelector } from "react-redux";
import { stateType } from '../store'
export default function Header() {
// 获取 redux 中定义的全局状态
const user = useSelector(state => state as stateType)
return <div>
<p>用户: {user.name}, {user.age}</p>
<ChangeBtn/>
</div>
}
- 修改数据
useDispatch 用于获取全局状态
import { useDispatch } from "react-redux";
function ChangeBtn() {
const dispatch = useDispatch()
return <>
<button onClick={() => dispatch({ type: 'setName', payload: '王五' })}>修改用户名</button>
</>
}
- 以上只是简单的使用如果status有多个对象
- 定义复制性的store
export interface stateType {
user: {
name: string,
age: number
}
job: { name: string, total: number }
}
interface actionType {
type: string,
payload: any
}
const userStore = (state: stateType = {
user: { name: '张三', age: 20 },
job: { name: '程序员', total: 50 }
}, action: actionType) => {
switch (action.type) {
case 'setUserName':
return {
...state,
user: {
...state.user,
name: action.payload
}
}
case 'setAge':
return {
...state,
user: action.payload
}
default:
return state
}
}
export default createStore(userStore)
function ChangeBtn() {
const { user } = useSelector(state => state as stateType)
const dispatch = useDispatch()
return <>
<button onClick={() => dispatch({ type: 'setUserName', payload: '王五' })}>修改用户名</button>
<button onClick={() => dispatch({ type: 'setAge', payload: { ...user, age: 30 } })}>修改age</button>
</>
}
5. 多个store
在开发中如果按照上面写法 数据如果再多一些会越来越难以维护,action会变得庞大无比,我们就应该创建多个store,拆分刚才store
- 重新创建store
export interface stateType {
user: {
name: string,
age: number
}
job: { name: string, total: number }
}
interface actionType {
type: string,
payload: any
}
const userStore = (state: stateType['user'] = {
name: '张三', age: 20
}, action: actionType) => {
switch (action.type) {
case 'setUserName':
console.log("修改name")
return {
...state,
name: action.payload
}
case 'setUserAge':
return {
...state,
age: action.payload
}
default:
return state
}
}
const jonStore = (state: stateType['job'] = {
name: '程序员', total: 10
}, action: actionType) => {
switch (action.type) {
case 'setJobName':
return {
...state,
name: action.payload
}
case 'setJobTotal':
return {
...state,
total: action.payload
}
default:
return state
}
}
- 合并reducer
const reducers = combineReducers({
user: userStore,
job: jonStore
})
- 需要注意action中的type不能同名
- 这样好处便于维护一些
3. 总结
- 以一个简单的用例快速入门了 redux 状态管理工具
- 在使用中总觉得还是有一点差强人意,但是在社区中还有其他的替换方案 例如 Mobx
- 他们本质上都是解决态管理混乱,无法有效同步的问题