1 | import chai = require('chai');
|
2 | import Promise = require('bluebird');
|
3 | import async = require('../src/async/index');
|
4 | import await = require('../src/await/index');
|
5 | var expect = chai.expect;
|
6 |
|
7 |
|
8 |
|
9 |
|
10 |
|
11 | function runTestsFor(variant?: string, acceptsCallback = false) {
|
12 | var name = 'async' + (variant ? ('.' + variant) : '');
|
13 | var func = async;
|
14 | if (variant) variant.split('.').forEach(prop => func = func[prop]);
|
15 | var arity = fn => fn.length + (acceptsCallback ? 1 : 0);
|
16 |
|
17 | describe('The ' + name + '(...) function', () => {
|
18 |
|
19 |
|
20 |
|
21 |
|
22 |
|
23 |
|
24 |
|
25 |
|
26 | it('synchronously returns a function', () => {
|
27 | var foo = func(() => { });
|
28 | expect(foo).to.be.a('function');
|
29 | });
|
30 |
|
31 | it('returns a function whose arity matches that of its definition', () => {
|
32 |
|
33 | var defns: any[] = [
|
34 | (a, b, c) => {},
|
35 | () => {},
|
36 | (a, b, c, d, e, f, g, h) => {},
|
37 | x => {}
|
38 | ];
|
39 | for (var i = 0; i < defns.length; ++i) {
|
40 | var foo = func(defns[i]);
|
41 | expect(foo.length).to.equal(arity(defns[i]));
|
42 | }
|
43 | });
|
44 | });
|
45 | }
|
46 | runTestsFor(null);
|
47 | runTestsFor('cps', true);
|
48 | runTestsFor('thunk');
|
49 | runTestsFor('iterable');
|
50 |
|
51 |
|
52 | describe('A suspendable function returned by async(...)', () => {
|
53 |
|
54 | it('synchronously returns a promise', () => {
|
55 | var foo = async (() => {});
|
56 | var syncResult = foo();
|
57 | expect(syncResult).instanceOf(Promise);
|
58 | });
|
59 |
|
60 | it('begins executing synchronously and completes asynchronously', done => {
|
61 | var x = 5;
|
62 | var foo = async (() => { x = 7; });
|
63 | foo()
|
64 | .then(() => expect(x).to.equal(9))
|
65 | .then(() => done())
|
66 | .catch(done);
|
67 | expect(x).to.equal(7);
|
68 | x = 9;
|
69 | });
|
70 |
|
71 | it("preserves the 'this' context of the call", done => {
|
72 | var foo = { bar: async (function () { return this; }) }, baz = {x:7};
|
73 | foo.bar()
|
74 | .then(result => expect(result).to.equal(foo))
|
75 | .then(() => foo.bar.call(baz))
|
76 | .then(result => expect(result).to.equal(baz))
|
77 | .then(() => done())
|
78 | .catch(done);
|
79 | });
|
80 |
|
81 | it('eventually resolves with its definition\'s returned value', done => {
|
82 | var foo = async (() => { return 'blah'; });
|
83 | (<Promise<any>> foo())
|
84 | .then(result => expect(result).to.equal('blah'))
|
85 | .then(() => done())
|
86 | .catch(done);
|
87 | });
|
88 |
|
89 | it('eventually rejects with its definition\'s thrown value', done => {
|
90 | var act, exp = new Error('Expected thrown value to match rejection value');
|
91 | var foo = async (() => { throw exp; return 'blah'; });
|
92 | (<Promise<any>> foo())
|
93 | .catch(err => act = err)
|
94 | .then(() => {
|
95 | if (!act) done(new Error("Expected function to throw"))
|
96 | else if (act !== exp) done(exp);
|
97 | else done();
|
98 | });
|
99 | });
|
100 |
|
101 | it('works with await', done => {
|
102 | var foo = async (() => { return await (Promise.delay(20).then(() => 'blah')); });
|
103 | foo()
|
104 | .then(result => expect(result).to.equal('blah'))
|
105 | .then(() => done())
|
106 | .catch(done);
|
107 | });
|
108 |
|
109 | it('triggers the global unhandledException event if a rejection goes unhandled', done => {
|
110 | var foo = async (() => { throw new Error('nobody handled me'); });
|
111 | foo();
|
112 |
|
113 | var didTrigger = false;
|
114 | process.on('unhandledRejection', err => {
|
115 | didTrigger = true;
|
116 | done();
|
117 | });
|
118 | setTimeout(() => {
|
119 | if (!didTrigger) done(new Error('unhandledRejection event not triggered'));
|
120 | }, 20);
|
121 | });
|
122 |
|
123 |
|
124 |
|
125 |
|
126 |
|
127 |
|
128 |
|
129 |
|
130 |
|
131 |
|
132 |
|
133 | });
|