react状态管理store用法二: 使用Hooks 配置redux

react最通用的状态管理方案就是的redux,下面介绍通过Hooks的方式使用redux

npm install react-redux @reduxjs/toolkit -S

 

创建store

1.新建store文件夹,在下面新建index.tsx文件和slices文件夹,其中slices文件夹用来定义需要放进store的数据结构和方法

slices文件夹下新建app.ts文件,内容

import api from '@/api';
import {createAsyncThunk, createSlice} from '@reduxjs/toolkit';
import type {RootState} from '../index';

export interface BInfo {
    title: string;
    link?: string;
}
interface AppState {
    bInfo: BInfo[];
    collapsed: boolean;
    user: {
        userName: string;
        loading: boolean;
        authList: string[];
    };
}

interface QueryUserInfoReturned {
    userName: string;
    authList: string[];
}
export const queryUserInfo = createAsyncThunk<QueryUserInfoReturned>('app/userinfo', async (_, {rejectWithValue}) => {
    try {
        const res = await api.getUserInfo();
        const userName: string = res?.loginEmail || '"';
        const roleList: any[] = res?.authList || [];
        const authList: string[] = Array.from(
            new Set(
                roleList
                    .map((item) => {
                        const authKeyList: string | undefined = item.resourceIds;
                        return authKeyList ? authKeyList.split(',') : [];
                    })
                    .flat()
            )
        );
        return {
            userName,
            authList
        };
    } catch (err: any) {
        return rejectWithValue(err?.msg || '网络错误');
    }
});

const initialState: AppState = {
    bInfo: [],
    collapsed: false,
    user: {
        loading: true,
        userName: '',
        authList: []
    }
};

export const appSlice = createSlice({
    name: 'app',
    initialState,
    reducers: {
        setBInfo(state, {payload}) {
            Array.isArray(payload) && (state.binfo = payload);
        },
        toggleCollapse(state) {
            state.collapsed = !state.collapsed;
        }
    },
    extraReducers: (builder) =>
        builder
            .addCase(queryUserInfo.pending, (state) => {
                state.user.loading = true;
            })
            .addCase(queryUserInfo.fulfilled, (state, {payload}) => {
                state.user.loading = false;
                state.user.userName = payload.userName;
                state.user.authList = payload.authList;
            })
            .addCase(queryUserInfo.rejected, (state) => {
                state.user.loading = false;
            })
});

export const {setBInfo, toggleCollapse} = appSlice.actions;
export const selectApp = (state: RootState) => state.app;

export default appSlice.reducer;

 createAsyncThunk用来处理异步数据,正常情况使用createSlice的action即可。

 index.tsx文件

import {configureStore} from '@reduxjs/toolkit';

import app from './slices/app';
// import pageList from './slices/pageList'; //     组件状态


const store = configureStore({
    reducer: {
        app,
       // pageList
    },
        //关闭redux序列化检测
    middleware: getDefaultMiddleware => [
        ...getDefaultMiddleware({serializableCheck: false}),
    ],
});

export default store;

export type RootState = ReturnType<typeof store.getState>;
export type AppDispatch = typeof store.dispatch;
export interface AppThunkApiConfig {
    state: RootState;
    rejectValue: string;
}

使用

import {Provider} from 'react-redux';
import store from '@/store';
const App = () => {
  return (
  <Provider store={store} >
    <Component>      
</Provider>  
)  
}
export default App;

调用

import React, { useEffect} from 'react';
import {useDispatch, useSelector} from 'react-redux';
import {queryUserInfo, setBinfo,selectApp} from '@/store/slices/app';

const Mycomponent =() => {
    const dispatch = useDispatch();
    const {user} = useSelector(selectApp);
    useEffect(() => {
        dispatch(queryUserInfo());
    }, [dispatch]);
    useEffect(() => {
        dispatch(setBInfo([1,2,3]));
    }, [dispatch]);
  return (<div>


</div>)  
}
export default Mycomponent;

ps: 上面只是介绍了hooks使用方式,但也可以在类组件中正常使用,你可以按原来的方式使用redux

// 类组件使用
import store from '@/store';
// 你自己的数据结构
const {
        pageList: {
                        pageName:{
                            selectedRow: [],
                            selectedRowKeys: [],
                        },
                    },
         } = store.getState();

store.dispatch(setSelectedRowKeys(
                    {
                        pageName,
                        selectedRowKeys: _selectedRowKeys,
                    }
   ));

 

posted @ 2023-05-15 15:09  anin  阅读(586)  评论(0编辑  收藏  举报