Skip to content

Instantly share code, notes, and snippets.

@rohozhnikoff
Last active November 22, 2015 03:58
Show Gist options
  • Save rohozhnikoff/4c32922841cd7849fa61 to your computer and use it in GitHub Desktop.
Save rohozhnikoff/4c32922841cd7849fa61 to your computer and use it in GitHub Desktop.
memux = redux + memoize for stream-like flow
/**
* {key: reducerFunc}, {key: initialReducerValue}
* */
function createStore(reducers, initial) {
var _handle = function () {
};
var _STATE = initial || {},
_reducersNames = Object.keys(reducers);
return {
subscribe: function (handle) {
_handle = handle
},
getState: function () {
return _STATE
},
dispatch: function (action) {
console.log('[ACTION:FIRED]:', action)
var reducersNames = cloneArray(_reducersNames);
// create wrappers
var reducersWithMemo = reduceTree(reducers, function (hash, func, key) {
hash[key] = function () {
if (contain(reducersNames, key)) {
console.log('try to call reducer ' + key + '(prevState, action)...')
_STATE[key] = func(_STATE[key], action, reducersWithMemo);
reducersNames = withoutFirst(reducersNames, key)
}
return _STATE[key]
};
return hash;
}, {});
while (reducersNames.length > 0) {
reducersWithMemo[reducersNames[0]](_STATE[reducersNames[0]], action, reducersWithMemo)
}
_handle(_STATE);
}
}
}
/**
* REDUCERS (Memucers)
*
* you can use store[reducer name] like getter,
* even if this reducer not resolved yet
*
* */
function filter(state, action, store) {
var params = store.params();
return store.list().filter(function (item) {
return params === 'odd'
? (item % 2 === 0)
: (item % 2 !== 0)
})
}
function list(state, action, list) {
if (action.type === 'add numbers') {
return state.concat(action.numbers)
}
return state
}
function params(state, action, list) {
return (action.type === 'change param' && action.param) || state
}
/**
* INITIALIZE
* */
var store = createStore({
filter: filter,
list: list,
params: params,
}, {
list: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9],
params: 'odd'
});
store.subscribe(console.log.bind(console, '[STATE:REFRESH]:\n'));
/**
* SOMEWHERE IN BUSINESS-LOGIC
* */
store.dispatch({
type: 'change param',
param: 'even'
});
store.dispatch({
type: 'add numbers',
numbers: [10, 11, 12, 13, 14]
});
store.dispatch({
type: 'change param',
param: 'odd'
});
store.dispatch({
type: 'unknown action type'
});
store.dispatch({
type: 'add numbers',
numbers: [15, 16, 17, 18, 19, 20]
});
store.dispatch({
type: 'change param',
param: 'even'
});
/** --------- UTILS --------- */
function reduceTree(hash, iterator, memo) {
for (var key in hash) {
memo = iterator(memo, hash[key], key, hash)
}
return memo
}
function cloneArray(list) {
return list.concat([])
}
function contain(list, el) {
return list.indexOf(el) !== -1
}
function withoutFirst(list, el) {
var firstIndex = list.indexOf(el);
return list.slice(0, firstIndex).concat(list.slice(firstIndex + 1))
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment