jasmine-core 2.6.4 → 2.7.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -91,6 +91,13 @@ describe("Env", function() {
91
91
  env.it('pending spec');
92
92
  }).not.toThrow();
93
93
  });
94
+
95
+ it('accepts an async function', function() {
96
+ jasmine.getEnv().requireAsyncAwait();
97
+ expect(function() {
98
+ env.it('async', jasmine.getEnv().makeAsyncAwaitFunction());
99
+ }).not.toThrow();
100
+ });
94
101
  });
95
102
 
96
103
  describe('#xit', function() {
@@ -114,6 +121,13 @@ describe("Env", function() {
114
121
  env.xit('pending spec');
115
122
  }).not.toThrow();
116
123
  });
124
+
125
+ it('accepts an async function', function() {
126
+ jasmine.getEnv().requireAsyncAwait();
127
+ expect(function() {
128
+ env.xit('async', jasmine.getEnv().makeAsyncAwaitFunction());
129
+ }).not.toThrow();
130
+ });
117
131
  });
118
132
 
119
133
  describe('#fit', function () {
@@ -130,6 +144,13 @@ describe("Env", function() {
130
144
  env.beforeEach(undefined);
131
145
  }).toThrowError(/beforeEach expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/);
132
146
  });
147
+
148
+ it('accepts an async function', function() {
149
+ jasmine.getEnv().requireAsyncAwait();
150
+ expect(function() {
151
+ env.beforeEach(jasmine.getEnv().makeAsyncAwaitFunction());
152
+ }).not.toThrow();
153
+ });
133
154
  });
134
155
 
135
156
  describe('#beforeAll', function () {
@@ -138,6 +159,13 @@ describe("Env", function() {
138
159
  env.beforeAll(undefined);
139
160
  }).toThrowError(/beforeAll expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/);
140
161
  });
162
+
163
+ it('accepts an async function', function() {
164
+ jasmine.getEnv().requireAsyncAwait();
165
+ expect(function() {
166
+ env.beforeAll(jasmine.getEnv().makeAsyncAwaitFunction());
167
+ }).not.toThrow();
168
+ });
141
169
  });
142
170
 
143
171
  describe('#afterEach', function () {
@@ -146,6 +174,13 @@ describe("Env", function() {
146
174
  env.afterEach(undefined);
147
175
  }).toThrowError(/afterEach expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/);
148
176
  });
177
+
178
+ it('accepts an async function', function() {
179
+ jasmine.getEnv().requireAsyncAwait();
180
+ expect(function() {
181
+ env.afterEach(jasmine.getEnv().makeAsyncAwaitFunction());
182
+ }).not.toThrow();
183
+ });
149
184
  });
150
185
 
151
186
  describe('#afterAll', function () {
@@ -154,5 +189,12 @@ describe("Env", function() {
154
189
  env.afterAll(undefined);
155
190
  }).toThrowError(/afterAll expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/);
156
191
  });
192
+
193
+ it('accepts an async function', function() {
194
+ jasmine.getEnv().requireAsyncAwait();
195
+ expect(function() {
196
+ env.afterAll(jasmine.getEnv().makeAsyncAwaitFunction());
197
+ }).not.toThrow();
198
+ });
157
199
  });
158
200
  });
@@ -33,6 +33,26 @@ describe("jasmineUnderTest.pp", function () {
33
33
  })
34
34
  });
35
35
 
36
+ describe('stringify maps', function() {
37
+ it("should stringify maps properly", function() {
38
+ jasmine.getEnv().requireFunctioningMaps();
39
+ expect(jasmineUnderTest.pp(new Map([[1, 2]]))).toEqual("Map( [ 1, 2 ] )");
40
+ });
41
+
42
+ it("should truncate maps with more elments than jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH", function() {
43
+ jasmine.getEnv().requireFunctioningMaps();
44
+ var originalMaxSize = jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH;
45
+
46
+ try {
47
+ jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = 2;
48
+ expect(jasmineUnderTest.pp(new Map([["a", 1], ["b", 2], ["c", 3]]))).toEqual("Map( [ 'a', 1 ], [ 'b', 2 ], ... )");
49
+ } finally {
50
+ jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = originalMaxSize;
51
+ }
52
+ })
53
+ });
54
+
55
+
36
56
  describe('stringify arrays', function() {
37
57
  it("should stringify arrays properly", function() {
38
58
  expect(jasmineUnderTest.pp([1, 2])).toEqual("[ 1, 2 ]");
@@ -99,6 +119,18 @@ describe("jasmineUnderTest.pp", function () {
99
119
  }, bar: [1, 2, 3]})).toEqual("Object({ foo: Function, bar: [ 1, 2, 3 ] })");
100
120
  });
101
121
 
122
+ it("should truncate objects with too many keys", function () {
123
+ var originalMaxLength = jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH;
124
+ var long = {a: 1, b: 2, c: 3};
125
+
126
+ try {
127
+ jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = 2;
128
+ expect(jasmineUnderTest.pp(long)).toEqual("Object({ a: 1, b: 2, ... })");
129
+ } finally {
130
+ jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = originalMaxLength;
131
+ }
132
+ });
133
+
102
134
  it("should print 'null' as the constructor of an object with its own constructor property", function() {
103
135
  expect(jasmineUnderTest.pp({constructor: function() {}})).toContain("null({");
104
136
  expect(jasmineUnderTest.pp({constructor: 'foo'})).toContain("null({");
@@ -225,6 +257,18 @@ describe("jasmineUnderTest.pp", function () {
225
257
  }
226
258
  });
227
259
 
260
+ it("should stringify objects have have a toString that isn't a function", function() {
261
+ var obj = {
262
+ toString: "foo"
263
+ };
264
+
265
+ if (jasmine.getEnv().ieVersion < 9) {
266
+ expect(jasmineUnderTest.pp(obj)).toEqual("Object({ })");
267
+ } else {
268
+ expect(jasmineUnderTest.pp(obj)).toEqual("Object({ toString: 'foo' })");
269
+ }
270
+ });
271
+
228
272
  it("should stringify objects from anonymous constructors with custom toString", function () {
229
273
  var MyAnonymousConstructor = (function() { return function () {}; })();
230
274
  MyAnonymousConstructor.toString = function () { return ''; };
@@ -19,6 +19,26 @@ describe("QueueRunner", function() {
19
19
  expect(calls).toEqual(['fn1', 'fn2']);
20
20
  });
21
21
 
22
+ it("runs cleanup functions after the others", function() {
23
+ var calls = [],
24
+ queueableFn1 = { fn: jasmine.createSpy('fn1') },
25
+ queueableFn2 = { fn: jasmine.createSpy('fn2') },
26
+ queueRunner = new jasmineUnderTest.QueueRunner({
27
+ queueableFns: [queueableFn1],
28
+ cleanupFns: [queueableFn2]
29
+ });
30
+ queueableFn1.fn.and.callFake(function() {
31
+ calls.push('fn1');
32
+ });
33
+ queueableFn2.fn.and.callFake(function() {
34
+ calls.push('fn2');
35
+ });
36
+
37
+ queueRunner.execute();
38
+
39
+ expect(calls).toEqual(['fn1', 'fn2']);
40
+ });
41
+
22
42
  it("calls each function with a consistent 'this'-- an empty object", function() {
23
43
  var queueableFn1 = { fn: jasmine.createSpy('fn1') },
24
44
  queueableFn2 = { fn: jasmine.createSpy('fn2') },
@@ -31,7 +51,7 @@ describe("QueueRunner", function() {
31
51
  queueRunner.execute();
32
52
 
33
53
  var context = queueableFn1.fn.calls.first().object;
34
- expect(context).toEqual({});
54
+ expect(context).toEqual(new jasmineUnderTest.UserContext());
35
55
  expect(queueableFn2.fn.calls.first().object).toBe(context);
36
56
  expect(asyncContext).toBe(context);
37
57
  });
@@ -170,7 +190,6 @@ describe("QueueRunner", function() {
170
190
 
171
191
  queueRunner.execute();
172
192
 
173
- jasmine.clock().tick();
174
193
  expect(onComplete).toHaveBeenCalled();
175
194
  expect(onException).toHaveBeenCalled();
176
195
 
@@ -303,6 +322,84 @@ describe("QueueRunner", function() {
303
322
  });
304
323
  });
305
324
 
325
+ describe("with a function that returns a promise", function() {
326
+ function StubPromise() {}
327
+
328
+ StubPromise.prototype.then = function(resolve, reject) {
329
+ this.resolveHandler = resolve;
330
+ this.rejectHandler = reject;
331
+ };
332
+
333
+ beforeEach(function() {
334
+ jasmine.clock().install();
335
+ });
336
+
337
+ afterEach(function() {
338
+ jasmine.clock().uninstall();
339
+ });
340
+
341
+ it("runs the function asynchronously, advancing once the promise is settled", function() {
342
+ var onComplete = jasmine.createSpy('onComplete'),
343
+ fnCallback = jasmine.createSpy('fnCallback'),
344
+ p1 = new StubPromise(),
345
+ p2 = new StubPromise(),
346
+ queueableFn1 = { fn: function() {
347
+ setTimeout(function() {
348
+ p1.resolveHandler();
349
+ }, 100);
350
+ return p1;
351
+ } };
352
+ queueableFn2 = { fn: function() {
353
+ fnCallback();
354
+ setTimeout(function() {
355
+ p2.resolveHandler();
356
+ }, 100);
357
+ return p2;
358
+ } },
359
+ queueRunner = new jasmineUnderTest.QueueRunner({
360
+ queueableFns: [queueableFn1, queueableFn2],
361
+ onComplete: onComplete
362
+ });
363
+
364
+ queueRunner.execute();
365
+ expect(fnCallback).not.toHaveBeenCalled();
366
+ expect(onComplete).not.toHaveBeenCalled();
367
+
368
+ jasmine.clock().tick(100);
369
+
370
+ expect(fnCallback).toHaveBeenCalled();
371
+ expect(onComplete).not.toHaveBeenCalled();
372
+
373
+ jasmine.clock().tick(100);
374
+
375
+ expect(onComplete).toHaveBeenCalled();
376
+ });
377
+
378
+ it("fails the function when the promise is rejected", function() {
379
+ var promise = new StubPromise(),
380
+ queueableFn1 = { fn: function() {
381
+ setTimeout(function() { promise.rejectHandler('foo'); }, 100);
382
+ return promise;
383
+ } },
384
+ queueableFn2 = { fn: jasmine.createSpy('fn2') },
385
+ failFn = jasmine.createSpy('fail'),
386
+ queueRunner = new jasmineUnderTest.QueueRunner({
387
+ queueableFns: [queueableFn1, queueableFn2],
388
+ fail: failFn
389
+ });
390
+
391
+ queueRunner.execute();
392
+
393
+ expect(failFn).not.toHaveBeenCalled();
394
+ expect(queueableFn2.fn).not.toHaveBeenCalled();
395
+
396
+ jasmine.clock().tick(100);
397
+
398
+ expect(failFn).toHaveBeenCalledWith('foo');
399
+ expect(queueableFn2.fn).toHaveBeenCalled();
400
+ });
401
+ });
402
+
306
403
  it("calls exception handlers when an exception is thrown in a fn", function() {
307
404
  var queueableFn = { type: 'queueable',
308
405
  fn: function() {
@@ -336,20 +433,95 @@ describe("QueueRunner", function() {
336
433
  it("continues running the functions even after an exception is thrown in an async spec", function() {
337
434
  var queueableFn = { fn: function(done) { throw new Error("error"); } },
338
435
  nextQueueableFn = { fn: jasmine.createSpy("nextFunction") },
339
- timeout = { setTimeout: jasmine.createSpy("setTimeout"),
340
- clearTimeout: jasmine.createSpy("setTimeout")
341
- },
342
436
  queueRunner = new jasmineUnderTest.QueueRunner({
343
- queueableFns: [queueableFn, nextQueueableFn],
344
- timeout: timeout
437
+ queueableFns: [queueableFn, nextQueueableFn]
345
438
  });
346
439
 
347
440
  queueRunner.execute();
348
- timeout.setTimeout.calls.argsFor(0)[0]();
349
-
350
441
  expect(nextQueueableFn.fn).toHaveBeenCalled();
351
442
  });
352
443
 
444
+ describe("When configured to complete on first error", function() {
445
+ it("skips to cleanup functions on the first exception", function() {
446
+ var queueableFn = { fn: function() { throw new Error("error"); } },
447
+ nextQueueableFn = { fn: jasmine.createSpy("nextFunction") },
448
+ cleanupFn = { fn: jasmine.createSpy("cleanup") },
449
+ queueRunner = new jasmineUnderTest.QueueRunner({
450
+ queueableFns: [queueableFn, nextQueueableFn],
451
+ cleanupFns: [cleanupFn],
452
+ completeOnFirstError: true
453
+ });
454
+
455
+ queueRunner.execute();
456
+ expect(nextQueueableFn.fn).not.toHaveBeenCalled();
457
+ expect(cleanupFn.fn).toHaveBeenCalled();
458
+ });
459
+
460
+ it("does not skip when a cleanup function throws", function() {
461
+ var queueableFn = { fn: function() { } },
462
+ cleanupFn1 = { fn: function() { throw new Error("error"); } },
463
+ cleanupFn2 = { fn: jasmine.createSpy("cleanupFn2") },
464
+ queueRunner = new jasmineUnderTest.QueueRunner({
465
+ queueableFns: [queueableFn],
466
+ cleanupFns: [cleanupFn1, cleanupFn2],
467
+ completeOnFirstError: true
468
+ });
469
+
470
+ queueRunner.execute();
471
+ expect(cleanupFn2.fn).toHaveBeenCalled();
472
+ });
473
+
474
+ describe("with an asynchronous function", function() {
475
+ beforeEach(function() {
476
+ jasmine.clock().install();
477
+ });
478
+
479
+ afterEach(function() {
480
+ jasmine.clock().uninstall();
481
+ });
482
+
483
+
484
+ it("skips to cleanup functions on the first exception", function() {
485
+ var errorListeners = [],
486
+ queueableFn = { fn: function(done) {} },
487
+ nextQueueableFn = { fn: jasmine.createSpy('nextFunction') },
488
+ cleanupFn = { fn: jasmine.createSpy('cleanup') },
489
+ queueRunner = new jasmineUnderTest.QueueRunner({
490
+ globalErrors: {
491
+ pushListener: function(f) { errorListeners.push(f); },
492
+ popListener: function() { errorListeners.pop(); },
493
+ },
494
+ queueableFns: [queueableFn, nextQueueableFn],
495
+ cleanupFns: [cleanupFn],
496
+ completeOnFirstError: true,
497
+ });
498
+
499
+ queueRunner.execute();
500
+ errorListeners[errorListeners.length - 1](new Error('error'));
501
+ expect(nextQueueableFn.fn).not.toHaveBeenCalled();
502
+ expect(cleanupFn.fn).toHaveBeenCalled();
503
+ });
504
+
505
+ it("skips to cleanup functions when next.fail is called", function() {
506
+ var queueableFn = { fn: function(done) {
507
+ done.fail('nope');
508
+ } },
509
+ nextQueueableFn = { fn: jasmine.createSpy('nextFunction') },
510
+ cleanupFn = { fn: jasmine.createSpy('cleanup') },
511
+ queueRunner = new jasmineUnderTest.QueueRunner({
512
+ queueableFns: [queueableFn, nextQueueableFn],
513
+ cleanupFns: [cleanupFn],
514
+ completeOnFirstError: true,
515
+ });
516
+
517
+ queueRunner.execute();
518
+ jasmine.clock().tick();
519
+ expect(nextQueueableFn.fn).not.toHaveBeenCalled();
520
+ expect(cleanupFn.fn).toHaveBeenCalled();
521
+ });
522
+ });
523
+ });
524
+
353
525
  it("calls a provided complete callback when done", function() {
354
526
  var queueableFn = { fn: jasmine.createSpy('fn') },
355
527
  completeCallback = jasmine.createSpy('completeCallback'),
@@ -393,4 +565,53 @@ describe("QueueRunner", function() {
393
565
  expect(completeCallback).toHaveBeenCalled();
394
566
  });
395
567
  });
568
+
569
+ describe('when user context has not been defined', function() {
570
+ beforeEach(function() {
571
+ var fn;
572
+
573
+ this.fn = fn = jasmine.createSpy('fn1');
574
+ this.queueRunner = new jasmineUnderTest.QueueRunner({
575
+ queueableFns: [{ fn: fn }]
576
+ });
577
+ });
578
+
579
+ it('runs the functions on the scope of a UserContext', function() {
580
+ var calls = [],
581
+ context;
582
+
583
+ this.fn.and.callFake(function() {
584
+ context = this;
585
+ });
586
+
587
+ this.queueRunner.execute();
588
+
589
+ expect(context.constructor).toBe(jasmineUnderTest.UserContext);
590
+ });
591
+ });
592
+
593
+ describe('when user context has been defined', function() {
594
+ beforeEach(function() {
595
+ var fn, context;
596
+
597
+ this.fn = fn = jasmine.createSpy('fn1');
598
+ this.context = context = new jasmineUnderTest.UserContext();
599
+ this.queueRunner = new jasmineUnderTest.QueueRunner({
600
+ queueableFns: [{ fn: fn }],
601
+ userContext: context
602
+ });
603
+ });
604
+
605
+ it('runs the functions on the scope of a UserContext', function() {
606
+ var calls = [],
607
+ context;
608
+ this.fn.and.callFake(function() {
609
+ context = this;
610
+ });
611
+
612
+ this.queueRunner.execute();
613
+
614
+ expect(context).toBe(this.context);
615
+ });
616
+ });
396
617
  });
@@ -103,8 +103,26 @@ describe("Spec", function() {
103
103
 
104
104
  spec.execute();
105
105
 
106
- var allSpecFns = fakeQueueRunner.calls.mostRecent().args[0].queueableFns;
107
- expect(allSpecFns).toEqual([before, queueableFn, after]);
106
+ var options = fakeQueueRunner.calls.mostRecent().args[0];
107
+ expect(options.queueableFns).toEqual([before, queueableFn]);
108
+ expect(options.cleanupFns).toEqual([after]);
109
+ });
110
+
111
+ it("tells the queue runner that it's a leaf node", function() {
112
+ var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner'),
113
+ spec = new jasmineUnderTest.Spec({
114
+ queueableFn: { fn: function() {} },
115
+ beforeAndAfterFns: function() {
116
+ return {befores: [], afters: []}
117
+ },
118
+ queueRunnerFactory: fakeQueueRunner
119
+ });
120
+
121
+ spec.execute();
122
+
123
+ expect(fakeQueueRunner).toHaveBeenCalledWith(jasmine.objectContaining({
124
+ isLeaf: true
125
+ }));
108
126
  });
109
127
 
110
128
  it("is marked pending if created without a function body", function() {
@@ -123,7 +141,8 @@ describe("Spec", function() {
123
141
  });
124
142
 
125
143
  it("can be disabled, but still calls callbacks", function() {
126
- var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner'),
144
+ var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner')
145
+ .and.callFake(function(attrs) { attrs.onComplete(); }),
127
146
  startCallback = jasmine.createSpy('startCallback'),
128
147
  specBody = jasmine.createSpy('specBody'),
129
148
  resultCallback = jasmine.createSpy('resultCallback'),
@@ -140,7 +159,7 @@ describe("Spec", function() {
140
159
 
141
160
  spec.execute();
142
161
 
143
- expect(fakeQueueRunner).not.toHaveBeenCalled();
162
+ expect(fakeQueueRunner).toHaveBeenCalled();
144
163
  expect(specBody).not.toHaveBeenCalled();
145
164
 
146
165
  expect(startCallback).toHaveBeenCalled();
@@ -148,7 +167,8 @@ describe("Spec", function() {
148
167
  });
149
168
 
150
169
  it("can be disabled at execution time by a parent", function() {
151
- var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner'),
170
+ var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner')
171
+ .and.callFake(function(attrs) { attrs.onComplete(); }),
152
172
  startCallback = jasmine.createSpy('startCallback'),
153
173
  specBody = jasmine.createSpy('specBody'),
154
174
  resultCallback = jasmine.createSpy('resultCallback'),
@@ -163,7 +183,7 @@ describe("Spec", function() {
163
183
 
164
184
  expect(spec.result.status).toBe('disabled');
165
185
 
166
- expect(fakeQueueRunner).not.toHaveBeenCalled();
186
+ expect(fakeQueueRunner).toHaveBeenCalled();
167
187
  expect(specBody).not.toHaveBeenCalled();
168
188
 
169
189
  expect(startCallback).toHaveBeenCalled();
@@ -171,7 +191,8 @@ describe("Spec", function() {
171
191
  });
172
192
 
173
193
  it("can be marked pending, but still calls callbacks when executed", function() {
174
- var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner'),
194
+ var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner')
195
+ .and.callFake(function(attrs) { attrs.onComplete(); }),
175
196
  startCallback = jasmine.createSpy('startCallback'),
176
197
  resultCallback = jasmine.createSpy('resultCallback'),
177
198
  spec = new jasmineUnderTest.Spec({
@@ -191,7 +212,7 @@ describe("Spec", function() {
191
212
 
192
213
  spec.execute();
193
214
 
194
- expect(fakeQueueRunner).not.toHaveBeenCalled();
215
+ expect(fakeQueueRunner).toHaveBeenCalled();
195
216
 
196
217
  expect(startCallback).toHaveBeenCalled();
197
218
  expect(resultCallback).toHaveBeenCalledWith({