redux-actions详解教程记录( redux使用更简单???)

redux-actions「乐闻世界」

前言

Redux 的诟病是重复的模块代码太多,各路大佬都开始尝试解决这些问题,Redux-actions 悄然而生。

刚开始使用 Redux-actions 时遇到一些问题,那么专门写一篇博客全面详细的记录 Redux-actions 的使用。

安装

npm install redux-actions

DEMO项目结构

入口

// index.jsx

import React from 'react';
import ReactDOM from 'react-dom';
import App from './App';
import { Provider } from 'react-redux';
import { store } from './store';

ReactDOM.render(
  <Provider store={store}>
    <App />
  </Provider>,
  document.getElementById('root'),
);

App 组件

// App.jsx

import React, { Component } from 'react';
import { connect } from 'react-redux';
import { bindActionCreators } from 'redux';
import * as actions from './action';
import './App.css';

function App(props) {
  console.log('!! props 📢:', props);
  return (
    <div className="action">
      <button
        onClick={() => {
          props.normalAction('测试');
          props.normalAction('测试');
        }}
      >
        测试Action
      </button>
    </div>
  );
}

export default connect(
  (state) => state,
  (dispatch) => {
    return {
      ...bindActionCreators(actions, dispatch),
    };
  },
)(App);

🏁 如果不熟悉 bindActionCreators 的用法可以参考我前面记录的 bindActionCreators & combineReducers 使用记录

action 文件

import { createAction, createActions } from 'redux-actions';

// 通常 action 方式定义
export const normalAction = (params) => {
  return {
    type'ACTIONS',
    payload: params,
  };
};

reducer 与 store

import { createStore } from 'redux';

const reducer = (state, action) => {
  switch (action.type) {
  case 'ACTIONS':
      return { ...state, ACTIONS: action.payload };    
    default:
      return state;
  }
};

const store = createStore(reducer, {});

export { store };

后续介绍 redux-actions 方法会修改对应的 action 和 reducer 文件。

方法列表

  • createAction
// 参数列表
createAction(
  type
  payloadCreator = Identity,
  ?metaCreator
)

action.js

import { createAction, createActions } from 'redux-actions';

export const normalAction = (params) => {
  return {
    type'ACTIONS',
    payload: params,
  };
};

export const specialAction = createAction(
  'ACTIONS',
  (params) => {
    return params;
  },
  (meta) => {
    return { admin: true };
  },
);

console.log('normalAction', normalAction('levenx'));
console.log('specialAction', specialAction('levenx'));
image-20201203114022414
  • createActions
// 参数列表
createActions(
  actionMap,
  ?...identityActions,
  ?options
)

action.js

import { createActions } from 'redux-actions';

// 同时生成多个 action 方法,并集合到一个对象中,
// !!🏁 但是这种方式生成的action不能通过 bindActionCreators 方法来绑定
// 具体问题分析与解决方案可以参考 https://blog.csdn.net/m0_37890289/article/details/110493826
// 文末贴出问题解决代码
export const specialActions = createActions({
    //只考虑 payload
  ACTION1: (params) => {
    return params;
  },
  // 处理meta
  ACTION2: [
    (params) => {
      return params;
    },
    (meta) => {
      return { meta };
    },
  ],
  ACTION3: (params) => {
    return params;
  },
});
console.log('specialActions', specialActions);
image-20201203120446356

嵌套定义

export const specialActions = createActions({
  //增加层级,拓展命名空间
  APP: {
    ACTION1: (params) => {
      return params;
    },
    ACTION3: (params) => {
      return params;
    },
  },
  MY: {
    ACTION1: (params) => {
      return params;
    },
    ACTION3: (params) => {
      return params;
    },
  },
});
image-20201203120918140
  • handleAction
// 参数列表
createAction(
  type
  payloadCreator = Identity,
  ?metaCreator
)

reducer.js

import { createStore } from 'redux';
import { handleAction } from 'redux-actions';

// 正常使用方式
const specialReducer = handleAction(
  'ACTIONS',
  (state, { type, payload, meta }) => {
    debugger;
    return { payload };
  },
  { init: 'levenx' },
);

// 处理 action 错误情况使用这种方式
const specialReducer = handleAction(
  'ACTIONS',
  {
    next(state, action) {
      return { payload };
    },
    throw(state, action) {
     return { error };
    },
  },
  { init: 'levenx' },
);


// console.log('📢 specialReducer', specialReducer);

const store = createStore(specialReducer, {});

export { store };

image-20201203114905282
image-20201203114905282
  • handleActions
// 参数列表
handleActions( reducerMap, defaultState);
import { handleActions } from 'redux-actions';

const specialReducer = handleActions(
  {
    ACTION1: (state, action) => {
      return { levenx: '1' };
    },
    ACTIONS2: {
      next(state, action) {
        return { levenx: '1' };
      },
      throw(state, action) {
        return { levenx: '1' };
      },
    },
  },
  { INIT_DATA: 'levenx' },
);
  • combineActions

顾名思义,合并actions

这个方法是合并 reducer 中 type,使多个action 可以触发同一个 reducer 处理方法。

// 参数列表
combineActions(...types);

actions.js

const { action1, action3 } = createActions({
  ACTION1: (params) => {
    return params;
  },
  ACTION3: (params) => {
    return params;
  },
});
export { action1, action3 };

reducer.js

import { handleActions, combineActions } from 'redux-actions';
import { action1, action3 } from './action';

const specialReducer = handleActions(
  {
    // action1, action3 都触发该方法
    [combineActions(action1, action3)]: (state, action) => {
      return { action };
    },
  },
  {}
);

嵌套 action 绑定组件方案

新建 bindActionCreatorsPlus.js

// bindActionCreatorsPlus.js
import { bindActionCreators } from 'redux';

export default function bindActionCreatorsPlus(actions, dispatch) {
  if (typeof actions !== 'object' || !actions) {
    throw new Error('invalid actions');
  }

  let result = {};
  for (let key in actions) {
    if (actions.hasOwnProperty(key)) {
      const creator = actions[key];
      if (typeof creator === 'object' && creator) {
        //递归执行
        result[key] = bindActionCreatorsPlus(creator, dispatch);
      } else if (typeof creator === 'function') {
        result[key] = bindActionCreators(creator, dispatch);
      }
    }
  }
  return result;
}

应用组件 App.js

import React, { Component } from 'react';
import { connect } from 'react-redux';
import bindActionCreatorsPlus from './bindActionCreatorsPlus';
import * as actions from './action';

function App(props) {
  console.log('!! props 📢:', props);
  return (
    <div className="action">
    </div>
  );
}

export default connect(
  (state) => state,
  (dispatch) => {
    return {
     //使用自定义的  bindActionCreatorsPlus方法处理action
      ...bindActionCreatorsPlus(actions.actions, dispatch),
    };
  },
)(App);

嵌套 action.js

export const actions = createActions({
  App: {
    ACTION1: (params) => {
      return params;
    },
    ACTION3: (params) => {
      debugger;
      return params;
    },
  },
});

Redux相关文章推荐

参考

- END -
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

乐闻x

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值