Redux集成setProps方法
---- 适用于react和react-native开发
作者:陈浩
联系:chenhao455@yeah.net
说明:在当前store里新增一个变量(我称之为新增props,下同)
当前redux使用方式
在react和react-native中经常用到redux
我们用redux建立了一个store,用来存储项目数据,它相对项目的单页面是props
项目入口文件
index.html
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title> </title>
</head>
<body>
<div id="root"></div>
</body>
</html>
index.js
import {Promise,polyfill} from 'es6-promise'
import React,{Component} from 'react';
import { render } from 'react-dom';
import {Provider} from 'react-redux';
/*import containers*/
import App from './containers/App';
import configureStore from './store/configureStore';
const store = configureStore();
appInit();
render(
<Provider store={store} >
<App/>
</Provider>,
document.getElementById('root')
);
redux store配置
store/configureStore.js
import { createStore, applyMiddleware } from 'redux';
import thunk from 'redux-thunk';
import rootReducer from '../reducers';
const createStoreWithMiddleware = applyMiddleware(
thunk
)(createStore);
export default function configureStore (initialState) {
try{
const store = createStoreWithMiddleware(rootReducer,initialState);
return store;
}catch(e){
// alert(e);
console.log(e);
}
}
constants配置
/* APP Page Constants */
export const GET_CLIENTINFO = 'GET_CLIENTINFO';
export const GET_LOCATIONINFO = 'GET_LOCATIONINFO';
export const SET_NETWORK_STATUS = 'SET_NETWORK_STATUS';
/* Book Page Constants */
export const SET_CONTACT = 'SET_CONTACT';
/****************************************** 这里省略了N多条常量声明 */
export const INVOICE_HISTORY = 'INVOICE_HISTORY';
/* OrderDetail Page Constants */
export const GET_ORDERDETAIL = 'GET_ORDERDETAIL';
export const GET_INVOICE_PROGRESS = 'GET_INVOICE_PROGRESS';
reducers配置
reducers/index.js
import { combineReducers } from 'redux';
import orderDetail from './orderDetail';
import book from './book';
import app from './app';
const rootReducer = combineReducers({
orderDetail,
book,
app
});
export default rootReducer;
reducers/app.js(reducers/book.js、 reducers/ orderDetail.js与此类似)
import assign from 'object-assign';
import {
GET_CLIENTINFO,
/**********这里省略了N多条相似语句*/
SET_PROPS_APP
} from '../constants';
var initialState = {
osType: '',//操作系统
/**********这里省略了N多变量*/
customerServiceURL:'',//获取客服地址链接
};
export default function app(state = initialState, action) {
switch (action.type) {
case SET_PROPS_APP: //获取客户端信息
return assign({}, state, action.newObj);
/*************************** 这里省略了N多条相似case语句*/
case SET_NETWORK_STATUS:
return assign({},state,{networkStatus: action.networkStatus});
}
return state;
}
actions/app.js (actions/book.js、 actions/ orderDetail.js与此类似)
import {GET_CLIENTINFO,GET_LOCATIONINFO,SET_NETWORK_STATUS,SET_PROPS_APP} from '../constants';
/**设置联系人*/
export function setContact(contactInfo) {
return {
type: ActionTypes.SET_CONTACT,
contactInfo
}
}
/*****************************此处省略N多个dispatch action方法******************************/
/**设置地址*/
export function setStartAddress(addressInfo) {
return {
type: ActionTypes.SET_START_ADDRESS,
addressInfo
};
}
/*****************************下面才是真正的业务方法******************************/
...
当前store里新增一个变量(我称之为新增props,下同)需要干这么工作:
1.Constants里面新建的Action常量
2.reducers/app.js,新增对该变量的处理方法switch-case再加一条case语句;
3.action/app.js里,新增一个方法,用来分发该常量;
4.Containers/app.js,引用上一步的方法,并调用;
新增props遇到的问题:
reducers/app.js和action/app.js里,新建的Action常量容易忘记引用
reducers/app.js里,每新增一个Action常量,就需要增加一条switch-case语句, switch-case语句结构相似,代码冗余了
action/app.js里,每新增一个Action常量,就需要增加类似 dispatch({type: TRACK_EVENT_ID, trackEventID: trackEventID}); 的代码,这样的代码会出现很多次
思考解决这个问题:
有个setState(obj)是不是很牛掰,想更新啥state就操作一下即可,咱们可以参考它的思路
setState更新state的;咱们写个setProps用来更新props不就行了嘛!
app、book、orderDetail,只写一个setProps的话,book页面,需要调用自己的setProps更新订单信息,也需要调用app.js的setProps更新联系人,都叫setProps就混淆了,所以分别可以叫setPropsApp、 setPropsBook、 setPropsDetail
修改前后的constants对比
修改前的constants
/* APP Page Constants */
export const GET_CLIENTINFO = 'GET_CLIENTINFO';
export const GET_LOCATIONINFO = 'GET_LOCATIONINFO';
export const SET_NETWORK_STATUS = 'SET_NETWORK_STATUS';
/* Book Page Constants */
export const SET_CONTACT = 'SET_CONTACT';
/****************************************** 这里省略了N多条常量声明 */
export const INVOICE_HISTORY = 'INVOICE_HISTORY';
/* OrderDetail Page Constants */
export const GET_ORDERDETAIL = 'GET_ORDERDETAIL';
export const GET_INVOICE_PROGRESS = 'GET_INVOICE_PROGRESS';
修改后的constants
export const SET_PROPS_APP = 'SET_PROPS_APP';
export const SET_PROPS_BOOK = 'SET_PROPS_BOOK';
export const SET_PROPS_DETAIL = 'SET_PROPS_DETAIL';
修改前后的reducers/app.js对比
修改前
import assign from 'object-assign';
import {
GET_CLIENTINFO,
/**********这里省略了N多条相似语句*/
SET_PROPS_APP
} from '../constants';
var initialState = {
osType: '',//操作系统
/**********这里省略了N多变量*/
customerServiceURL:'',//获取客服地址链接
};
export default function app(state = initialState, action) {
switch (action.type) {
case SET_PROPS_APP: //获取客户端信息
return assign({}, state, action.newObj);
/*************************** 这里省略了N多条相似case语句*/
case SET_NETWORK_STATUS:
return assign({},state,{networkStatus: action.networkStatus});
}
return state;
}
修改后
import * as ActionTypes from '../constants/ActionTypes';
import assign from 'object-assign';
var initialState = {
osType: '',//操作系统
/**********这里省略了N多变量*/
customerServiceURL:'',//获取客服地址链接
};
export default function app(state = initialState,action){
if(action.type == ActionTypes.SET_PROPS_APP){
state = assign({}, state, action.newObj);
}
return state;
}
修改前后的actions/app.js对比
修改前
import {GET_CLIENTINFO,GET_LOCATIONINFO,SET_NETWORK_STATUS,SET_PROPS_APP} from '../constants';
/**设置联系人*/
export function setContact(contactInfo) {
return {
type: ActionTypes.SET_CONTACT,
contactInfo
}
}
/*****************************此处省略N多个dispatch action方法******************************/
/**设置地址*/
export function setStartAddress(addressInfo) {
return {
type: ActionTypes.SET_START_ADDRESS,
addressInfo
};
}
/*****************************下面才是真正的业务方法******************************/
...
修改后
import * as ActionTypes from '../constants/ActionTypes';
/**************************只有一个dispatch Action 方法**************************/
export function setPropsApp(newObj){
return {
type: ActionTypes.SET_PROPS_APP,
newObj
};
}
/*****************************下面是真正的业务方法******************************/
...
完整demo代码
以后提供
实际使用经验
App、Book、OrderDetail 3大页面值外的页面不需要再定义setPropsXXX,使用前3个页面定义的setPropsApp、 setPropsBook、 setPropsDetail即可;
setPropsApp、 setPropsBook、 setPropsDetail可以继续合并:
export function setProps(state,dataPage,newObj){
state[dataPage] = assign({}, state[dataPage], newObj);
return state;
}
var data ={
app:{version:1,name:'cbd'},
book:{saleDays:30,orderAmountMoney:0},
detail:{orderSerialId:"订单流水号",remark:'备注信息'}
};
data = setProps(data,'app',{version:2});
console.log('data1',data);
data = setProps(data,'book',{saleDays:40});
console.log('data2',data);
data = setProps(data,'detail',{remark:'备注信息22'});
console.log('data3',data);
以后更新store中的数据只需要一行代码
setPropsApp({ variablesName : variablesValue });
setPropsApp:更新APP页面的props变量方法
setPropsApp、 setPropsBook、 setPropsDetail同理
variablesName :要更新的变量名
variablesValue :要更新的变量新值
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。