Created
June 24, 2013 08:34
-
-
Save carstenlenz/5848588 to your computer and use it in GitHub Desktop.
JavaScript optional result values
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
var optional = (function() { | |
var noneInternal = function() {}; | |
noneInternal.prototype.isNone = function() { return true; }; | |
noneInternal.prototype.isSome = function() { return false; }; | |
noneInternal.prototype.bind = function(fun) { return none(); }; | |
var none = function() { | |
return new noneInternal(); // make fiddling less probable | |
}; | |
someIsNone = function() { return false; }; | |
someIsSome = function() { return true; }; | |
someBind = function(fun) { | |
var ret = fun(this()); | |
return create(ret); | |
}; | |
var some = function(value) { | |
var result = function() { | |
return value; | |
}; | |
result.isNone = someIsNone; | |
result.isSome = someIsSome; | |
result.bind = someBind; | |
return result; | |
} | |
var create = function(value) { | |
if (value != null) { | |
return some(value); | |
} | |
return none(); | |
}; | |
return { | |
create: create, | |
none: none, | |
some: some | |
}; | |
})(); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
module("optional"); | |
test("null should yield none", function() { | |
var o = optional.create(null); | |
ok(o.isNone()); | |
ok(!o.isSome()); | |
o = optional.none(); | |
ok(o.isNone()); | |
ok(!o.isSome()); | |
}); | |
test("null should throw if called", function() { | |
throws( | |
function() { | |
var o = optional.none(); | |
o(); | |
}); | |
}); | |
test("null bind should always return none", function() { | |
var o = optional.none(); | |
var o1 = o.bind(function(value) { | |
return optional.create("not called"); | |
}); | |
ok(o1.isNone()); | |
}); | |
test("value should yield some", function() { | |
var o = optional.create("hello"); | |
ok(o.isSome()); | |
ok(!o.isNone()); | |
}); | |
test("invoking some should return value", function() { | |
var o = optional.some("hamsdi"); | |
equal(o(), "hamsdi"); | |
}); | |
test("binding some should be invoked", function() { | |
var o = optional.some("hamsdi"); | |
o.bind(function(value) { | |
equal(value, "hamsdi"); | |
}); | |
}); | |
test("non null result of binding should be itself be some", function() { | |
var o1 = optional.some("hamsdi"); | |
var o2 = o1.bind(function(value) { | |
equal(value, "hamsdi"); | |
return "bamsdi"; | |
}); | |
ok(o2.isSome()); | |
}); | |
test("null result of binding should be itself be none", function() { | |
var o1 = optional.some("hamsdi"); | |
var o2 = o1.bind(function(value) { | |
equal(value, "hamsdi"); | |
return null; | |
}); | |
ok(o2.isNone()); | |
}); | |
test("binding cascade", function() { | |
var my = optional.create("hamsdi"); | |
var r = my.bind(function(value) { | |
return value + " bamsdi"; | |
}).bind(function(value) { | |
return "Hello " + value; | |
}).bind(function(value) { | |
return value + "!"; | |
}); | |
equal(r(), "Hello hamsdi bamsdi!"); | |
}); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment