Skip to content

Instantly share code, notes, and snippets.

@dfkaye
Last active November 17, 2019 00:13
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save dfkaye/68dc3c925ae153a916ad56a7fc4d7f3c to your computer and use it in GitHub Desktop.
Save dfkaye/68dc3c925ae153a916ad56a7fc4d7f3c to your computer and use it in GitHub Desktop.
derive state from selectors (filters)
// 4 June 2019
// ES5 version of create and test taken from Nick Scialli's articl,
// "Calculating Derived State in JavaScript Using Selectors"
// @see https://nick.scialli.me/calculating-derived-state-in-javascript-using-selectors/
function createSelector(functions) {
var len = arguments.length;
if (!len || (len == 1 && typeof functions == 'function')) {
throw new SyntaxError("expects more than one function: " + functions);
}
var funcs = len > 1 ? [].slice.call(arguments) : [].slice.call(functions)
var last = funcs.length > 1 ? funcs.pop() : null;
return function(state) {
var inputs = funcs.map(function(func) {
return func(state);
});
return last ? last.apply(0, inputs) : inputs;
};
};
/* test it out */
function allowed(who) { return who.age >= 21 || who.employee; }
function friendly(who) { return who.isFriendly; }
function both(allowed, friendly) { return allowed && friendly; }
var testVarArgs = createSelector(allowed, friendly, both);
var testVarArray = createSelector([ allowed, friendly, both ]);
var tests = [
{
name: "TTT",
age: 22,
employee: true,
isFriendly: true
},
{
name: "TTF",
age: 22,
employee: true,
isFriendly: false
},
{
name: "TFT",
age: 22,
employee: false,
isFriendly: true
},
{
name: "TFF",
age: 22,
employee: false,
isFriendly: false
},
{
name: "FTT",
age: 19,
employee: true,
isFriendly: true
},
{
name: "FFT",
age: 19,
employee: false,
isFriendly: true
},
{
name: "FTF",
age: 19,
employee: true,
isFriendly: false
},
{
name: "FFF",
age: 19,
employee: false,
isFriendly: false
}
];
console.log(
tests.map(test => testVarArgs(test))
);
console.log(
tests.map(test => testVarArray(test))
);
~(function enforcesTwoFunctions() {
var testVarOne;
var error = 'No errors. All is fine.'
try { testVarOne = createSelector(allowed); }
catch (e) {
error = e
}
finally {
console.error(error);
}
}());
/*
// Should see:
// [ true, false, true, false, true, false, false, false ]
// [ true, false, true, false, true, false, false, false ]
// SyntaxError: "expects more than one function as argument: function allowed(who) { return who.age >= 21 || who.employee; }"
*/
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment