UNPKG

plexus-csp

Version:

A Go-inspired async library based on ES6 generators

449 lines (404 loc) 11.5 kB
'use strict'; var csp = require('../../dist/index'); var t = function(val) { var out = csp.defer(); csp.go(wrapGenerator.mark(function() { return wrapGenerator(function($ctx0) { while (1) switch ($ctx0.next) { case 0: $ctx0.next = 2; return null; case 2: out.resolve(val); case 3: case "end": return $ctx0.stop(); } }, this); })); return out; }; describe('the join function', function() { it('transforms an array of deferreds into a deferred array', function(done) { csp.go(wrapGenerator.mark(function() { var a; return wrapGenerator(function($ctx1) { while (1) switch ($ctx1.next) { case 0: a = csp.join([t(1), t(2), t(3)]); expect(typeof a.then).toEqual('function'); $ctx1.next = 4; return a; case 4: $ctx1.t0 = $ctx1.sent; expect($ctx1.t0).toEqual([1,2,3]); done(); case 7: case "end": return $ctx1.stop(); } }, this); })); }); }); describe('the lift function', function() { it('lifts an ordinary function to a function on deferreds', function(done) { csp.go(wrapGenerator.mark(function() { var a; return wrapGenerator(function($ctx2) { while (1) switch ($ctx2.next) { case 0: a = csp.lift(Array)(t(1), t(2), t(3)); expect(typeof a.then).toEqual('function'); $ctx2.next = 4; return a; case 4: $ctx2.t1 = $ctx2.sent; expect($ctx2.t1).toEqual([1,2,3]); done(); case 7: case "end": return $ctx2.stop(); } }, this); })); }); it('handles a passed in object context correctly', function(done) { var obj = { val: 287, fun: function(x) { return this.val + x; } }; csp.go(wrapGenerator.mark(function() { return wrapGenerator(function($ctx3) { while (1) switch ($ctx3.next) { case 0: $ctx3.next = 2; return csp.lift(obj.fun, obj)(t(314)); case 2: $ctx3.t2 = $ctx3.sent; expect($ctx3.t2).toEqual(601); done(); case 5: case "end": return $ctx3.stop(); } }, this); })); }); }); describe('the chain function', function() { var fn = function() { var args = Array.prototype.slice.call(arguments); return csp.go(wrapGenerator.mark(function() { return wrapGenerator(function($ctx4) { while (1) switch ($ctx4.next) { case 0: $ctx4.rval = '#' + args.join('#') + '#'; delete $ctx4.thrown; $ctx4.next = 4; break; case 4: case "end": return $ctx4.stop(); } }, this); })); }; it('when given only an initial value, returns it unchanged', function(done) { csp.go(wrapGenerator.mark(function() { return wrapGenerator(function($ctx5) { while (1) switch ($ctx5.next) { case 0: $ctx5.next = 2; return csp.chain(5); case 2: $ctx5.t3 = $ctx5.sent; expect($ctx5.t3).toEqual(5); done(); case 5: case "end": return $ctx5.stop(); } }, this); })); }); it('when given a single form, applies it', function(done) { csp.go(wrapGenerator.mark(function() { return wrapGenerator(function($ctx6) { while (1) switch ($ctx6.next) { case 0: $ctx6.next = 2; return csp.chain(5, fn); case 2: $ctx6.t4 = $ctx6.sent; expect($ctx6.t4).toEqual('#5#'); $ctx6.next = 6; return csp.chain(5, ['toString', 2]); case 6: $ctx6.t5 = $ctx6.sent; expect($ctx6.t5).toEqual('101'); $ctx6.next = 10; return csp.chain(5, [fn, [], 7, 11]); case 10: $ctx6.t6 = $ctx6.sent; expect($ctx6.t6).toEqual('#5#7#11#'); $ctx6.next = 14; return csp.chain(5, [fn, 3]); case 14: $ctx6.t7 = $ctx6.sent; expect($ctx6.t7).toEqual('#3#5#'); $ctx6.next = 18; return csp.chain(5, [fn, [2,3]]); case 18: $ctx6.t8 = $ctx6.sent; expect($ctx6.t8).toEqual('#2#3#5#'); $ctx6.next = 22; return csp.chain(5, [fn, 3, 7, 11]); case 22: $ctx6.t9 = $ctx6.sent; expect($ctx6.t9).toEqual('#3#5#7#11#'); $ctx6.next = 26; return csp.chain(5, [fn, [2, 3], 7, 11]); case 26: $ctx6.t10 = $ctx6.sent; expect($ctx6.t10).toEqual('#2#3#5#7#11#'); done(); case 29: case "end": return $ctx6.stop(); } }, this); })); }); it('when given multiple forms, applies them in order', function(done) { var toInt = function(s) { return parseInt(s); }; csp.go(wrapGenerator.mark(function() { return wrapGenerator(function($ctx7) { while (1) switch ($ctx7.next) { case 0: $ctx7.next = 2; return csp.chain(5, [fn, [2, 3], 7, 11], ['split', '#'], ['slice', 1, 6], ['map', toInt]); case 2: $ctx7.t11 = $ctx7.sent; expect($ctx7.t11).toEqual([2, 3, 5, 7, 11]); done(); case 5: case "end": return $ctx7.stop(); } }, this); })); }); it('interprets non-form arguments as replacement values', function(done) { csp.go(wrapGenerator.mark(function() { return wrapGenerator(function($ctx8) { while (1) switch ($ctx8.next) { case 0: $ctx8.next = 2; return csp.chain(5, [fn, 3, 7], 'hello', [fn, 2, 9]); case 2: $ctx8.t12 = $ctx8.sent; expect($ctx8.t12).toEqual('#2#hello#9#'); done(); case 5: case "end": return $ctx8.stop(); } }, this); })); }); }); describe('the sleep function', function() { it('delays execution for approximately the specified time', function(done) { csp.go(wrapGenerator.mark(function() { var d, t; return wrapGenerator(function($ctx9) { while (1) switch ($ctx9.next) { case 0: d = 17; t = Date.now(); $ctx9.next = 4; return csp.sleep(d); case 4: expect(Math.abs(Date.now() - t - d)).toBeLessThan(2); done(); case 6: case "end": return $ctx9.stop(); } }, this); })); }); }); describe('the ncallback function returns a callback that', function() { var result, cb; beforeEach(function() { result = csp.defer(); cb = csp.ncallback(result); }); it('when called with no error, resolves its deferred', function(done) { cb(null, 5); csp.go(wrapGenerator.mark(function() { return wrapGenerator(function($ctx10) { while (1) switch ($ctx10.next) { case 0: $ctx10.next = 2; return result; case 2: $ctx10.t13 = $ctx10.sent; expect($ctx10.t13).toEqual(5); done(); case 5: case "end": return $ctx10.stop(); } }, this); })); }); it('when called with an error, rejects its deferred', function(done) { cb('Nope!'); csp.go(wrapGenerator.mark(function() { var thrown; return wrapGenerator(function($ctx11) { while (1) switch ($ctx11.next) { case 0: thrown = {}; $ctx11.pushTry(7, null, null); $ctx11.next = 4; return result; case 4: $ctx11.popCatch(7); $ctx11.next = 11; break; case 7: $ctx11.popCatch(7); $ctx11.t14 = $ctx11.thrown; delete $ctx11.thrown; thrown = $ctx11.t14; case 11: expect(thrown.message).toEqual('Nope!'); done(); case 13: case "end": return $ctx11.stop(); } }, this); })); }); }); describe('the nbind function returns a wrapper that', function() { var obj = { value: 5, method: function(x, cb) { if (x != this.value) cb('expecting a ' + this.value); else cb(null, 'thanks for the ' + this.value); } }; var wrapper = csp.nbind(obj.method, obj); it('upon success resolves the deferred it returns', function(done) { var val = obj.value; csp.go(wrapGenerator.mark(function() { return wrapGenerator(function($ctx12) { while (1) switch ($ctx12.next) { case 0: $ctx12.next = 2; return wrapper(val); case 2: $ctx12.t15 = $ctx12.sent; $ctx12.t16 = 'thanks for the ' + val; expect($ctx12.t15).toEqual($ctx12.t16); done(); case 6: case "end": return $ctx12.stop(); } }, this); })); }); it('upon success rejects the deferred it returns', function(done) { var val = obj.value + 1; csp.go(wrapGenerator.mark(function() { var thrown; return wrapGenerator(function($ctx13) { while (1) switch ($ctx13.next) { case 0: thrown = {}; $ctx13.pushTry(7, null, null); $ctx13.next = 4; return wrapper(val); case 4: $ctx13.popCatch(7); $ctx13.next = 11; break; case 7: $ctx13.popCatch(7); $ctx13.t17 = $ctx13.thrown; delete $ctx13.thrown; thrown = $ctx13.t17; case 11: expect(thrown.message).toEqual('expecting a ' + obj.value); done(); case 13: case "end": return $ctx13.stop(); } }, this); })); }); }); describe('the nodeify function', function() { var result; beforeEach(function() { result = csp.defer(); }); describe('when given a callback', function() { var outcome; beforeEach(function() { outcome = null; csp.nodeify(result, function(err, val) { outcome = err ? { err: err } : { val: val }; }); }); it('calls it with no error upon deferred resolution', function(done) { result.resolve('Hello callback!'); csp.go(wrapGenerator.mark(function() { return wrapGenerator(function($ctx14) { while (1) switch ($ctx14.next) { case 0: expect(outcome).toEqual({ val: 'Hello callback!' }); done(); case 2: case "end": return $ctx14.stop(); } }, this); })); }); it('calls it with an error upon deferred rejection', function(done) { result.reject('O noes!'); csp.go(wrapGenerator.mark(function() { return wrapGenerator(function($ctx15) { while (1) switch ($ctx15.next) { case 0: expect(outcome).toEqual({ err: 'O noes!' }); done(); case 2: case "end": return $ctx15.stop(); } }, this); })); }); }); describe('when given no callback', function() { it('simply returns its argument', function() { expect(csp.nodeify(result)).toBe(result); }); }); });