updux/src/upreducer.js

41 lines
1.1 KiB
JavaScript

import R from 'remeda';
import u from 'updeep';
const localMutation = (mutations) => (action) => (state) => {
const mutation = mutations[action.type];
const splatMutation = mutations['*'];
if (mutation) state = mutation(action.payload, action)(state);
if (splatMutation) state = splatMutation(action.payload, action)(state);
return state;
};
const subMutations = (subduxes) => (action) => (state) => {
const subReducers =
Object.keys(subduxes).length > 0
? R.mapValues(subduxes, R.prop('upreducer'))
: null;
if (!subReducers) return state;
if (subReducers['*']) {
return u.updateIn('*', subReducers['*'](action), state);
}
const update = R.mapValues(subReducers, (upReducer) => upReducer(action));
return u(update, state);
};
export function buildUpreducer(mutations, subduxes) {
return (action) => (state) => {
if (!mutations[action.type]?.terminal)
state = subMutations(subduxes)(action)(state);
return localMutation(mutations)(action)(state);
};
}