From 35968e4a60f0f6f133104390f11986432797af36 Mon Sep 17 00:00:00 2001 From: Alexey Prokhorov Date: Fri, 26 Apr 2019 01:46:56 +0400 Subject: [PATCH 001/201] Add toBeRejectedWithError matcher --- .../async/toBeRejectedWithErrorSpec.js | 100 ++++++++++++++++++ .../matchers/async/toBeRejectedWithError.js | 88 +++++++++++++++ src/core/matchers/requireAsyncMatchers.js | 3 +- 3 files changed, 190 insertions(+), 1 deletion(-) create mode 100644 spec/core/matchers/async/toBeRejectedWithErrorSpec.js create mode 100644 src/core/matchers/async/toBeRejectedWithError.js diff --git a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js new file mode 100644 index 00000000..0bb53edc --- /dev/null +++ b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js @@ -0,0 +1,100 @@ +describe('#toBeRejectedWithError', function () { + it('passes when Error type matches', function () { + jasmine.getEnv().requirePromises(); + + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + actual = Promise.reject(new TypeError('foo')); + + return matcher.compare(actual, TypeError).then(function (result) { + expect(result).toEqual(jasmine.objectContaining({ pass: true })); + }); + }); + + it('passes when Error type and message matches', function () { + jasmine.getEnv().requirePromises(); + + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + actual = Promise.reject(new TypeError('foo')); + + return matcher.compare(actual, TypeError, 'foo').then(function (result) { + expect(result).toEqual(jasmine.objectContaining({ pass: true })); + }); + }); + + it('passes when Error message matches a string', function () { + jasmine.getEnv().requirePromises(); + + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + actual = Promise.reject(new Error('foo')); + + return matcher.compare(actual, 'foo').then(function (result) { + expect(result).toEqual(jasmine.objectContaining({ pass: true })); + }); + }); + + it('passes when Error message matches a RegExp', function () { + jasmine.getEnv().requirePromises(); + + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + actual = Promise.reject(new Error('foo')); + + return matcher.compare(actual, /foo/).then(function (result) { + expect(result).toEqual(jasmine.objectContaining({ pass: true })); + }); + }); + + it('passes when Error message is empty', function () { + jasmine.getEnv().requirePromises(); + + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + actual = Promise.reject(new Error()); + + return matcher.compare(actual, '').then(function (result) { + expect(result).toEqual(jasmine.objectContaining({ pass: true })); + }); + }); + + it('fails when resolved', function () { + jasmine.getEnv().requirePromises(); + + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + actual = Promise.resolve(new Error('foo')); + + return matcher.compare(actual, 'foo').then(function (result) { + expect(result).toEqual(jasmine.objectContaining({ pass: false })); + }); + }); + + it('fails when rejected with non Error type', function () { + jasmine.getEnv().requirePromises(); + + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + actual = Promise.reject('foo'); + + return matcher.compare(actual, 'foo').then(function (result) { + expect(result).toEqual(jasmine.objectContaining({ pass: false })); + }); + }); + + it('fails when Error type mismatches', function () { + jasmine.getEnv().requirePromises(); + + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + actual = Promise.reject(new Error('foo')); + + return matcher.compare(actual, TypeError, 'foo').then(function (result) { + expect(result).toEqual(jasmine.objectContaining({ pass: false })); + }); + }); + + it('fails when Error message mismatches', function () { + jasmine.getEnv().requirePromises(); + + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + actual = Promise.reject(new Error('foo')); + + return matcher.compare(actual, 'bar').then(function (result) { + expect(result).toEqual(jasmine.objectContaining({ pass: false })); + }); + }); +}); diff --git a/src/core/matchers/async/toBeRejectedWithError.js b/src/core/matchers/async/toBeRejectedWithError.js new file mode 100644 index 00000000..28f07890 --- /dev/null +++ b/src/core/matchers/async/toBeRejectedWithError.js @@ -0,0 +1,88 @@ +getJasmineRequireObj().toBeRejectedWithError = function(j$) { + /** + * Expect a promise to be rejected with a value matched to the expected + * @function + * @async + * @name async-matchers#toBeRejectedWithError + * @param {Error} [expected] - `Error` constructor the object that was thrown needs to be an instance of. If not provided, `Error` will be used. + * @param {RegExp|String} [message] - The message that should be set on the thrown `Error` + * @example + * await expectAsync(aPromise).toBeRejectedWithError(MyCustomError, 'Error message'); + * await expectAsync(aPromise).toBeRejectedWithError(MyCustomError, /Error message/); + * await expectAsync(aPromise).toBeRejectedWithError(MyCustomError); + * await expectAsync(aPromise).toBeRejectedWithError('Error message'); + * return expectAsync(aPromise).toBeRejectedWithError(/Error message/); + */ + return function toBeRejectedWithError() { + return { + compare: function(actualPromise, arg1, arg2) { + var expected = getExpectedFromArgs(arg1, arg2); + + return actualPromise.then( + function() { + return { + pass: false, + message: 'Expected a promise to be rejected but it was resolved.' + }; + }, + function(actualValue) { return matchError(actualValue, expected); } + ); + } + }; + }; + + function matchError(actual, expected) { + if (!j$.isError_(actual)) { + return fail(expected, 'not rejected with Error.'); + } + + if (!(actual instanceof expected.error)) { + return fail(expected, 'rejected with type ' + j$.fnNameFor(actual.constructor) + '.'); + } + + var actualMessage = actual.message; + + if (actualMessage === expected.message || typeof expected.message === 'undefined') { + return pass(expected); + } + + if (expected.message instanceof RegExp && expected.message.test(actualMessage)) { + return pass(expected); + } + + return fail(expected, 'rejected with ' + j$.pp(actual) + '.'); + } + + function pass(expected) { + return { + pass: true, + message: 'Expected a promise to be rejected with ' + expected.printValue + '.' + }; + } + + function fail(expected, message) { + return { + pass: false, + message: 'Expected a promise to be rejected with ' + expected.printValue + ' but it was ' + message + }; + } + + + function getExpectedFromArgs(arg1, arg2) { + var error, message; + + if (typeof arg1 === 'function' && j$.isError_(arg1.prototype)) { + error = arg1; + message = arg2; + } else { + error = Error; + message = arg1; + } + + return { + error: error, + message: message, + printValue: j$.fnNameFor(error) + ': ' + j$.pp(message) + }; + } +}; diff --git a/src/core/matchers/requireAsyncMatchers.js b/src/core/matchers/requireAsyncMatchers.js index 1474c22d..faa91c02 100644 --- a/src/core/matchers/requireAsyncMatchers.js +++ b/src/core/matchers/requireAsyncMatchers.js @@ -3,7 +3,8 @@ getJasmineRequireObj().requireAsyncMatchers = function(jRequire, j$) { 'toBeResolved', 'toBeRejected', 'toBeResolvedTo', - 'toBeRejectedWith' + 'toBeRejectedWith', + 'toBeRejectedWithError' ], matchers = {}; From 8ab46566ac17a344a9151c0c42ed4ad1ed62746d Mon Sep 17 00:00:00 2001 From: Alexey Prokhorov Date: Fri, 3 May 2019 09:37:11 +0400 Subject: [PATCH 002/201] Fix failure messages for toBeRejectedWithError matcher --- .../async/toBeRejectedWithErrorSpec.js | 59 ++++++++++++++++--- .../matchers/async/toBeRejectedWithError.js | 12 ++-- 2 files changed, 56 insertions(+), 15 deletions(-) diff --git a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js index 0bb53edc..6ec2a31a 100644 --- a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js @@ -6,7 +6,10 @@ describe('#toBeRejectedWithError', function () { actual = Promise.reject(new TypeError('foo')); return matcher.compare(actual, TypeError).then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ pass: true })); + expect(result).toEqual(jasmine.objectContaining({ + pass: true, + message: 'Expected a promise not to be rejected with TypeError, but it was.' + })); }); }); @@ -17,7 +20,10 @@ describe('#toBeRejectedWithError', function () { actual = Promise.reject(new TypeError('foo')); return matcher.compare(actual, TypeError, 'foo').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ pass: true })); + expect(result).toEqual(jasmine.objectContaining({ + pass: true, + message: 'Expected a promise not to be rejected with TypeError: \'foo\', but it was.' + })); }); }); @@ -28,7 +34,10 @@ describe('#toBeRejectedWithError', function () { actual = Promise.reject(new Error('foo')); return matcher.compare(actual, 'foo').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ pass: true })); + expect(result).toEqual(jasmine.objectContaining({ + pass: true, + message: 'Expected a promise not to be rejected with Error: \'foo\', but it was.' + })); }); }); @@ -39,7 +48,10 @@ describe('#toBeRejectedWithError', function () { actual = Promise.reject(new Error('foo')); return matcher.compare(actual, /foo/).then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ pass: true })); + expect(result).toEqual(jasmine.objectContaining({ + pass: true, + message: 'Expected a promise not to be rejected with Error: /foo/, but it was.' + })); }); }); @@ -50,7 +62,24 @@ describe('#toBeRejectedWithError', function () { actual = Promise.reject(new Error()); return matcher.compare(actual, '').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ pass: true })); + expect(result).toEqual(jasmine.objectContaining({ + pass: true, + message: 'Expected a promise not to be rejected with Error: \'\', but it was.' + })); + }); + }); + + it('passes when no arguments', function () { + jasmine.getEnv().requirePromises(); + + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + actual = Promise.reject(new Error()); + + return matcher.compare(actual, void 0).then(function (result) { + expect(result).toEqual(jasmine.objectContaining({ + pass: true, + message: 'Expected a promise not to be rejected with Error, but it was.' + })); }); }); @@ -61,7 +90,10 @@ describe('#toBeRejectedWithError', function () { actual = Promise.resolve(new Error('foo')); return matcher.compare(actual, 'foo').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ pass: false })); + expect(result).toEqual(jasmine.objectContaining({ + pass: false, + message: 'Expected a promise to be rejected but it was resolved.' + })); }); }); @@ -72,7 +104,10 @@ describe('#toBeRejectedWithError', function () { actual = Promise.reject('foo'); return matcher.compare(actual, 'foo').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ pass: false })); + expect(result).toEqual(jasmine.objectContaining({ + pass: false, + message: 'Expected a promise to be rejected with Error: \'foo\' but it was rejected with \'foo\'.' + })); }); }); @@ -83,7 +118,10 @@ describe('#toBeRejectedWithError', function () { actual = Promise.reject(new Error('foo')); return matcher.compare(actual, TypeError, 'foo').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ pass: false })); + expect(result).toEqual(jasmine.objectContaining({ + pass: false, + message: 'Expected a promise to be rejected with TypeError: \'foo\' but it was rejected with type Error.' + })); }); }); @@ -94,7 +132,10 @@ describe('#toBeRejectedWithError', function () { actual = Promise.reject(new Error('foo')); return matcher.compare(actual, 'bar').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ pass: false })); + expect(result).toEqual(jasmine.objectContaining({ + pass: false, + message: 'Expected a promise to be rejected with Error: \'bar\' but it was rejected with Error: foo.' + })); }); }); }); diff --git a/src/core/matchers/async/toBeRejectedWithError.js b/src/core/matchers/async/toBeRejectedWithError.js index 28f07890..88f1c11f 100644 --- a/src/core/matchers/async/toBeRejectedWithError.js +++ b/src/core/matchers/async/toBeRejectedWithError.js @@ -33,11 +33,11 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { function matchError(actual, expected) { if (!j$.isError_(actual)) { - return fail(expected, 'not rejected with Error.'); + return fail(expected, 'rejected with ' + j$.pp(actual)); } if (!(actual instanceof expected.error)) { - return fail(expected, 'rejected with type ' + j$.fnNameFor(actual.constructor) + '.'); + return fail(expected, 'rejected with type ' + j$.fnNameFor(actual.constructor)); } var actualMessage = actual.message; @@ -50,20 +50,20 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return pass(expected); } - return fail(expected, 'rejected with ' + j$.pp(actual) + '.'); + return fail(expected, 'rejected with ' + j$.pp(actual)); } function pass(expected) { return { pass: true, - message: 'Expected a promise to be rejected with ' + expected.printValue + '.' + message: 'Expected a promise not to be rejected with ' + expected.printValue + ', but it was.' }; } function fail(expected, message) { return { pass: false, - message: 'Expected a promise to be rejected with ' + expected.printValue + ' but it was ' + message + message: 'Expected a promise to be rejected with ' + expected.printValue + ' but it was ' + message + '.' }; } @@ -82,7 +82,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return { error: error, message: message, - printValue: j$.fnNameFor(error) + ': ' + j$.pp(message) + printValue: j$.fnNameFor(error) + (typeof message === 'undefined' ? '' : ': ' + j$.pp(message)) }; } }; From 17a9a6417a2157fbcc2e8f5190cabd27cc65a230 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 4 May 2019 10:46:59 -0700 Subject: [PATCH 003/201] Fixed test failure in Firefox 66.0.2 --- spec/html/PrettyPrintHtmlSpec.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/spec/html/PrettyPrintHtmlSpec.js b/spec/html/PrettyPrintHtmlSpec.js index 4ff969b3..b4eb1158 100644 --- a/spec/html/PrettyPrintHtmlSpec.js +++ b/spec/html/PrettyPrintHtmlSpec.js @@ -21,7 +21,8 @@ describe("jasmineUnderTest.pp (HTML Dependent)", function () { it("should print Firefox's wrapped native objects correctly", function() { if(jasmine.getEnv().firefoxVersion) { try { new CustomEvent(); } catch(e) { var err = e; }; - expect(jasmineUnderTest.pp(err)).toMatch(/Not enough arguments/); + // Different versions of FF produce different error messages. + expect(jasmineUnderTest.pp(err)).toMatch(/Not enough arguments|CustomEvent requires at least 1 argument, but only 0 were passed/); } }); From 72aa0bbe4d7f230cc9c202d302f25a71408abe5a Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Sun, 5 May 2019 08:08:34 -0400 Subject: [PATCH 004/201] Add resolveValue and rejectValue spy strategies --- spec/core/EnvSpec.js | 17 +++++++++++ spec/core/SpyStrategySpec.js | 56 ++++++++++++++++++++++++++++++++++++ spec/core/baseSpec.js | 15 ++++++++++ src/core/Env.js | 24 +++++++++++++++- src/core/SpyStrategy.js | 38 ++++++++++++++++++++++++ src/core/base.js | 4 +++ 6 files changed, 153 insertions(+), 1 deletion(-) diff --git a/spec/core/EnvSpec.js b/spec/core/EnvSpec.js index f731d36b..3b34e2e2 100644 --- a/spec/core/EnvSpec.js +++ b/spec/core/EnvSpec.js @@ -46,6 +46,23 @@ describe("Env", function() { })); }); + it('can configure a custom promise library', function() { + var myLibrary = { resolve: jasmine.createSpy(), reject: jasmine.createSpy() }; + expect(env.getPromise()).toBeUndefined(); + + env.configure({ promiseLibrary: myLibrary }); + expect(env.getPromise()).toBe(myLibrary); + }); + + it('fails to configure a custom promise library if library is invalid', function() { + var myLibrary = {}; + expect(env.getPromise()).toBeUndefined(); + + expect(function() { + env.configure({ promiseLibrary: myLibrary }); + }).toThrowError('Custom promise library missing `resolve`/`reject` functions'); + }); + it('defaults to multiple failures for specs', function() { spyOn(jasmineUnderTest, 'Spec'); env.it('bar', function() {}); diff --git a/spec/core/SpyStrategySpec.js b/spec/core/SpyStrategySpec.js index 10e4f583..25078e4c 100644 --- a/spec/core/SpyStrategySpec.js +++ b/spec/core/SpyStrategySpec.js @@ -110,6 +110,62 @@ describe("SpyStrategy", function() { }) }); + describe("#resolveValue", function() { + it("allows a resolved promise to be returned", function(done) { + if (!jasmineUnderTest.getPromise()) { + pending('Environment does not support promises.'); + } + + var originalFn = jasmine.createSpy("original"), + spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); + + spyStrategy.resolveValue(37); + spyStrategy.exec().then(function (returnValue) { + expect(returnValue).toEqual(37); + done(); + }).catch(done.fail); + }); + + it("fails if promises are not available", function() { + var originalFn = jasmine.createSpy("original"), + spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); + + spyOn(jasmineUnderTest, 'getPromise'); + + expect(function() { + spyStrategy.resolveValue(37); + }).toThrowError('resolveValue is unavailable because the environment does not support promises.'); + }); + }); + + describe("#rejectValue", function() { + it("allows a rejected promise to be returned", function(done) { + if (!jasmineUnderTest.getPromise()) { + pending('Environment does not support promises.'); + } + + var originalFn = jasmine.createSpy("original"), + spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); + + spyStrategy.rejectValue(new Error('oops')); + spyStrategy.exec().then(done.fail).catch(function (error) { + expect(error).toEqual(new Error('oops')); + done(); + }).catch(done.fail); + }); + + it("fails if promises are not available", function() { + var originalFn = jasmine.createSpy("original"), + spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); + + spyOn(jasmineUnderTest, 'getPromise'); + + expect(function() { + spyStrategy.rejectValue(new Error('oops')); + }).toThrowError('rejectValue is unavailable because the environment does not support promises.'); + }); + }); + it("allows a custom strategy to be used", function() { var plan = jasmine.createSpy('custom strategy') .and.returnValue('custom strategy result'), diff --git a/spec/core/baseSpec.js b/spec/core/baseSpec.js index 7f17265b..d7be476f 100644 --- a/spec/core/baseSpec.js +++ b/spec/core/baseSpec.js @@ -27,4 +27,19 @@ describe('base helpers', function() { }, 100); }); }); + + describe('getPromise', function() { + it('returns a custom library if configured', function() { + var myLibrary = { resolve: jasmine.createSpy(), reject: jasmine.createSpy() }; + jasmineUnderTest.getEnv().configure({ promiseLibrary: myLibrary }); + expect(jasmineUnderTest.getPromise()).toBe(myLibrary); + }); + + it('returns global library if not configured', function() { + var globalLibrary = {}; + var global = { Promise: globalLibrary }; + spyOn(jasmineUnderTest, 'getGlobal').and.returnValue(global); + expect(jasmineUnderTest.getPromise()).toBe(globalLibrary); + }); + }); }); diff --git a/src/core/Env.js b/src/core/Env.js index 680d0d49..7841fe34 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -76,7 +76,16 @@ getJasmineRequireObj().Env = function(j$) { * @type Boolean * @default false */ - hideDisabled: false + hideDisabled: false, + /** + * Set to provide a custom promise library that Jasmine will use if it needs + * to create a promise. If not set, it will default to whatever global promise + * library is available (if any). + * @name Configuration#promiseLibrary + * @type function + * @default undefined + */ + promiseLibrary: undefined }; var currentSuite = function() { @@ -142,6 +151,15 @@ getJasmineRequireObj().Env = function(j$) { if (configuration.hasOwnProperty('hideDisabled')) { config.hideDisabled = configuration.hideDisabled; } + + if (configuration.hasOwnProperty('promiseLibrary')) { + if (typeof configuration.promiseLibrary.resolve === 'function' && + typeof configuration.promiseLibrary.reject === 'function') { + config.promiseLibrary = configuration.promiseLibrary; + } else { + throw new Error('Custom promise library missing `resolve`/`reject` functions'); + } + } }; /** @@ -193,6 +211,10 @@ getJasmineRequireObj().Env = function(j$) { } }; + this.getPromise = function() { + return config.promiseLibrary; + }; + j$.Expectation.addCoreMatchers(j$.matchers); j$.Expectation.addAsyncCoreMatchers(j$.asyncMatchers); diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index ae5d4451..27a42f8e 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -84,6 +84,44 @@ getJasmineRequireObj().SpyStrategy = function(j$) { return this.getSpy(); }; + /** + * Tell the spy to return a promise resolving to the specified value when invoked. + * @name SpyStrategy#resolveValue + * @function + * @param {*} value The value to return. + */ + SpyStrategy.prototype.resolveValue = function(value) { + var Promise = j$.getPromise(); + + if (!Promise) { + throw new Error('resolveValue is unavailable because the environment does not support promises.'); + } + + this.plan = function() { + return Promise.resolve(value); + }; + return this.getSpy(); + }; + + /** + * Tell the spy to return a promise rejecting with the specified value when invoked. + * @name SpyStrategy#rejectValue + * @function + * @param {*} value The value to return. + */ + SpyStrategy.prototype.rejectValue = function(value) { + var Promise = j$.getPromise(); + + if (!Promise) { + throw new Error('rejectValue is unavailable because the environment does not support promises.'); + } + + this.plan = function() { + return Promise.reject(value); + }; + return this.getSpy(); + }; + /** * Tell the spy to throw an error when invoked. * @name SpyStrategy#throwError diff --git a/src/core/base.js b/src/core/base.js index 3a584f09..6609ef81 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -45,6 +45,10 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return env; }; + j$.getPromise = function() { + return j$.getEnv().getPromise() || j$.getGlobal().Promise; + }; + j$.isArray_ = function(value) { return j$.isA_('Array', value); }; From 95e1890e647dff97b593be4bc1b390c389f3cb09 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Tue, 7 May 2019 16:30:48 -0400 Subject: [PATCH 005/201] Improved resolveValue/rejectValue error messages --- spec/core/SpyStrategySpec.js | 12 ++++-------- src/core/SpyStrategy.js | 4 ++-- 2 files changed, 6 insertions(+), 10 deletions(-) diff --git a/spec/core/SpyStrategySpec.js b/spec/core/SpyStrategySpec.js index 25078e4c..cedc5338 100644 --- a/spec/core/SpyStrategySpec.js +++ b/spec/core/SpyStrategySpec.js @@ -112,9 +112,7 @@ describe("SpyStrategy", function() { describe("#resolveValue", function() { it("allows a resolved promise to be returned", function(done) { - if (!jasmineUnderTest.getPromise()) { - pending('Environment does not support promises.'); - } + jasmine.getEnv().requirePromises(); var originalFn = jasmine.createSpy("original"), spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); @@ -134,15 +132,13 @@ describe("SpyStrategy", function() { expect(function() { spyStrategy.resolveValue(37); - }).toThrowError('resolveValue is unavailable because the environment does not support promises.'); + }).toThrowError('resolveValue requires global Promise, or a `promiseLibrary` configured with `jasmine.getEnv().configure()`'); }); }); describe("#rejectValue", function() { it("allows a rejected promise to be returned", function(done) { - if (!jasmineUnderTest.getPromise()) { - pending('Environment does not support promises.'); - } + jasmine.getEnv().requirePromises(); var originalFn = jasmine.createSpy("original"), spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); @@ -162,7 +158,7 @@ describe("SpyStrategy", function() { expect(function() { spyStrategy.rejectValue(new Error('oops')); - }).toThrowError('rejectValue is unavailable because the environment does not support promises.'); + }).toThrowError('rejectValue requires global Promise, or a `promiseLibrary` configured with `jasmine.getEnv().configure()`'); }); }); diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index 27a42f8e..3aada4b2 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -94,7 +94,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { var Promise = j$.getPromise(); if (!Promise) { - throw new Error('resolveValue is unavailable because the environment does not support promises.'); + throw new Error('resolveValue requires global Promise, or a `promiseLibrary` configured with `jasmine.getEnv().configure()`'); } this.plan = function() { @@ -113,7 +113,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { var Promise = j$.getPromise(); if (!Promise) { - throw new Error('rejectValue is unavailable because the environment does not support promises.'); + throw new Error('rejectValue requires global Promise, or a `promiseLibrary` configured with `jasmine.getEnv().configure()`'); } this.plan = function() { From eb30e8179a9073482d07cb7a066183a9fc786a27 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Tue, 7 May 2019 17:09:26 -0700 Subject: [PATCH 006/201] Update deprecation messages to indicate _future_ removal - Fixes #1628 --- src/core/Env.js | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/src/core/Env.js b/src/core/Env.js index 680d0d49..82609252 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -160,11 +160,11 @@ getJasmineRequireObj().Env = function(j$) { Object.defineProperty(this, 'specFilter', { get: function() { - self.deprecated('Getting specFilter directly from Env is deprecated, please check the specFilter option from `configuration`'); + self.deprecated('Getting specFilter directly from Env is deprecated and will be removed in a future version of Jasmine, please check the specFilter option from `configuration`'); return config.specFilter; }, set: function(val) { - self.deprecated('Setting specFilter directly on Env is deprecated, please use the specFilter option in `configure`'); + self.deprecated('Setting specFilter directly on Env is deprecated and will be removed in a future version of Jasmine, please use the specFilter option in `configure`'); config.specFilter = val; } }); @@ -300,12 +300,12 @@ getJasmineRequireObj().Env = function(j$) { * @deprecated Use the `oneFailurePerSpec` option with {@link Env#configure} */ this.throwOnExpectationFailure = function(value) { - this.deprecated('Setting throwOnExpectationFailure directly on Env is deprecated, please use the oneFailurePerSpec option in `configure`'); + this.deprecated('Setting throwOnExpectationFailure directly on Env is deprecated and will be removed in a future version of Jasmine, please use the oneFailurePerSpec option in `configure`'); this.configure({oneFailurePerSpec: !!value}); }; this.throwingExpectationFailures = function() { - this.deprecated('Getting throwingExpectationFailures directly from Env is deprecated, please check the oneFailurePerSpec option from `configuration`'); + this.deprecated('Getting throwingExpectationFailures directly from Env is deprecated and will be removed in a future version of Jasmine, please check the oneFailurePerSpec option from `configuration`'); return config.oneFailurePerSpec; }; @@ -317,12 +317,12 @@ getJasmineRequireObj().Env = function(j$) { * @deprecated Use the `failFast` option with {@link Env#configure} */ this.stopOnSpecFailure = function(value) { - this.deprecated('Setting stopOnSpecFailure directly is deprecated, please use the failFast option in `configure`'); + this.deprecated('Setting stopOnSpecFailure directly is deprecated and will be removed in a future version of Jasmine, please use the failFast option in `configure`'); this.configure({failFast: !!value}); }; this.stoppingOnSpecFailure = function() { - this.deprecated('Getting stoppingOnSpecFailure directly from Env is deprecated, please check the failFast option from `configuration`'); + this.deprecated('Getting stoppingOnSpecFailure directly from Env is deprecated and will be removed in a future version of Jasmine, please check the failFast option from `configuration`'); return config.failFast; }; @@ -334,12 +334,12 @@ getJasmineRequireObj().Env = function(j$) { * @deprecated Use the `random` option with {@link Env#configure} */ this.randomizeTests = function(value) { - this.deprecated('Setting randomizeTests directly is deprecated, please use the random option in `configure`'); + this.deprecated('Setting randomizeTests directly is deprecated and will be removed in a future version of Jasmine, please use the random option in `configure`'); config.random = !!value; }; this.randomTests = function() { - this.deprecated('Getting randomTests directly from Env is deprecated, please check the random option from `configuration`'); + this.deprecated('Getting randomTests directly from Env is deprecated and will be removed in a future version of Jasmine, please check the random option from `configuration`'); return config.random; }; @@ -351,7 +351,7 @@ getJasmineRequireObj().Env = function(j$) { * @deprecated Use the `seed` option with {@link Env#configure} */ this.seed = function(value) { - this.deprecated('Setting seed directly is deprecated, please use the seed option in `configure`'); + this.deprecated('Setting seed directly is deprecated and will be removed in a future version of Jasmine, please use the seed option in `configure`'); if (value) { config.seed = value; } @@ -359,7 +359,7 @@ getJasmineRequireObj().Env = function(j$) { }; this.hidingDisabled = function(value) { - this.deprecated('Getting hidingDisabled directly from Env is deprecated, please check the hideDisabled option from `configuration`'); + this.deprecated('Getting hidingDisabled directly from Env is deprecated and will be removed in a future version of Jasmine, please check the hideDisabled option from `configuration`'); return config.hideDisabled; }; @@ -368,7 +368,7 @@ getJasmineRequireObj().Env = function(j$) { * @function */ this.hideDisabled = function(value) { - this.deprecated('Setting hideDisabled directly is deprecated, please use the hideDisabled option in `configure`'); + this.deprecated('Setting hideDisabled directly is deprecated and will be removed in a future version of Jasmine, please use the hideDisabled option in `configure`'); config.hideDisabled = !!value; }; From 4731b4ee4d215a28db291e3ab6c878a17ad6f39d Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Wed, 8 May 2019 09:07:01 -0400 Subject: [PATCH 007/201] Keep all Promise implementation details internal --- spec/core/EnvSpec.js | 24 +++++------ spec/core/SpySpec.js | 24 ++++++++++- spec/core/SpyStrategySpec.js | 14 +++---- spec/core/baseSpec.js | 15 ------- src/core/Env.js | 38 +++++++++-------- src/core/Spy.js | 6 +-- src/core/SpyFactory.js | 4 +- src/core/SpyStrategy.js | 80 +++++++++++++++++++----------------- src/core/base.js | 4 -- 9 files changed, 107 insertions(+), 102 deletions(-) diff --git a/spec/core/EnvSpec.js b/spec/core/EnvSpec.js index 3b34e2e2..0cdad2cd 100644 --- a/spec/core/EnvSpec.js +++ b/spec/core/EnvSpec.js @@ -46,21 +46,19 @@ describe("Env", function() { })); }); - it('can configure a custom promise library', function() { - var myLibrary = { resolve: jasmine.createSpy(), reject: jasmine.createSpy() }; - expect(env.getPromise()).toBeUndefined(); + describe('promise library', function() { + it('can be configured with a custom library', function() { + var myLibrary = { resolve: jasmine.createSpy(), reject: jasmine.createSpy() }; + env.configure({ Promise: myLibrary }); + }); - env.configure({ promiseLibrary: myLibrary }); - expect(env.getPromise()).toBe(myLibrary); - }); + it('cannot be configured with an invalid promise library', function() { + var myLibrary = {}; - it('fails to configure a custom promise library if library is invalid', function() { - var myLibrary = {}; - expect(env.getPromise()).toBeUndefined(); - - expect(function() { - env.configure({ promiseLibrary: myLibrary }); - }).toThrowError('Custom promise library missing `resolve`/`reject` functions'); + expect(function() { + env.configure({ Promise: myLibrary }); + }).toThrowError('Custom promise library missing `resolve`/`reject` functions'); + }); }); it('defaults to multiple failures for specs', function() { diff --git a/spec/core/SpySpec.js b/spec/core/SpySpec.js index 2639aa98..e12a9d83 100644 --- a/spec/core/SpySpec.js +++ b/spec/core/SpySpec.js @@ -171,7 +171,29 @@ describe('Spies', function () { expect(spy('foo')).toEqual(17); }); - describe("When withArgs is used without a base strategy", function() { + describe('any promise-based strategy', function() { + it('works with global Promise library when available', function(done) { + jasmine.getEnv().requirePromises(); + + var spy = env.createSpy('foo').and.resolveValue(42); + spy().then(function(result) { + expect(result).toEqual(42); + done(); + }).catch(done.fail); + }); + + it('works with a custom Promise library', function() { + var customPromise = { resolve: jasmine.createSpy(), reject: jasmine.createSpy() }; + customPromise.resolve.and.returnValue('resolved'); + env.configure({ Promise: customPromise }); + + var spy = env.createSpy('foo').and.resolveValue(42); + expect(spy()).toEqual('resolved'); + expect(customPromise.resolve).toHaveBeenCalledWith(42); + }); + }); + + describe("when withArgs is used without a base strategy", function() { it("uses the matching strategy", function() { var spy = env.createSpy('foo'); spy.withArgs('baz').and.returnValue(-1); diff --git a/spec/core/SpyStrategySpec.js b/spec/core/SpyStrategySpec.js index cedc5338..ab13e4ab 100644 --- a/spec/core/SpyStrategySpec.js +++ b/spec/core/SpyStrategySpec.js @@ -115,7 +115,8 @@ describe("SpyStrategy", function() { jasmine.getEnv().requirePromises(); var originalFn = jasmine.createSpy("original"), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); + getPromise = function() { return Promise; }, + spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn, getPromise: getPromise}); spyStrategy.resolveValue(37); spyStrategy.exec().then(function (returnValue) { @@ -128,11 +129,9 @@ describe("SpyStrategy", function() { var originalFn = jasmine.createSpy("original"), spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); - spyOn(jasmineUnderTest, 'getPromise'); - expect(function() { spyStrategy.resolveValue(37); - }).toThrowError('resolveValue requires global Promise, or a `promiseLibrary` configured with `jasmine.getEnv().configure()`'); + }).toThrowError('resolveValue requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`'); }); }); @@ -141,7 +140,8 @@ describe("SpyStrategy", function() { jasmine.getEnv().requirePromises(); var originalFn = jasmine.createSpy("original"), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); + getPromise = function() { return Promise; }, + spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn, getPromise: getPromise}); spyStrategy.rejectValue(new Error('oops')); spyStrategy.exec().then(done.fail).catch(function (error) { @@ -154,11 +154,9 @@ describe("SpyStrategy", function() { var originalFn = jasmine.createSpy("original"), spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); - spyOn(jasmineUnderTest, 'getPromise'); - expect(function() { spyStrategy.rejectValue(new Error('oops')); - }).toThrowError('rejectValue requires global Promise, or a `promiseLibrary` configured with `jasmine.getEnv().configure()`'); + }).toThrowError('rejectValue requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`'); }); }); diff --git a/spec/core/baseSpec.js b/spec/core/baseSpec.js index d7be476f..7f17265b 100644 --- a/spec/core/baseSpec.js +++ b/spec/core/baseSpec.js @@ -27,19 +27,4 @@ describe('base helpers', function() { }, 100); }); }); - - describe('getPromise', function() { - it('returns a custom library if configured', function() { - var myLibrary = { resolve: jasmine.createSpy(), reject: jasmine.createSpy() }; - jasmineUnderTest.getEnv().configure({ promiseLibrary: myLibrary }); - expect(jasmineUnderTest.getPromise()).toBe(myLibrary); - }); - - it('returns global library if not configured', function() { - var globalLibrary = {}; - var global = { Promise: globalLibrary }; - spyOn(jasmineUnderTest, 'getGlobal').and.returnValue(global); - expect(jasmineUnderTest.getPromise()).toBe(globalLibrary); - }); - }); }); diff --git a/src/core/Env.js b/src/core/Env.js index 7841fe34..f401526c 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -10,6 +10,7 @@ getJasmineRequireObj().Env = function(j$) { var self = this; var global = options.global || j$.getGlobal(); + var customPromise; var totalSpecsDefined = 0; @@ -79,13 +80,13 @@ getJasmineRequireObj().Env = function(j$) { hideDisabled: false, /** * Set to provide a custom promise library that Jasmine will use if it needs - * to create a promise. If not set, it will default to whatever global promise + * to create a promise. If not set, it will default to whatever global Promise * library is available (if any). - * @name Configuration#promiseLibrary + * @name Configuration#Promise * @type function * @default undefined */ - promiseLibrary: undefined + Promise: undefined }; var currentSuite = function() { @@ -152,10 +153,10 @@ getJasmineRequireObj().Env = function(j$) { config.hideDisabled = configuration.hideDisabled; } - if (configuration.hasOwnProperty('promiseLibrary')) { - if (typeof configuration.promiseLibrary.resolve === 'function' && - typeof configuration.promiseLibrary.reject === 'function') { - config.promiseLibrary = configuration.promiseLibrary; + if (configuration.hasOwnProperty('Promise')) { + if (typeof configuration.Promise.resolve === 'function' && + typeof configuration.Promise.reject === 'function') { + customPromise = configuration.Promise; } else { throw new Error('Custom promise library missing `resolve`/`reject` functions'); } @@ -211,10 +212,6 @@ getJasmineRequireObj().Env = function(j$) { } }; - this.getPromise = function() { - return config.promiseLibrary; - }; - j$.Expectation.addCoreMatchers(j$.matchers); j$.Expectation.addAsyncCoreMatchers(j$.asyncMatchers); @@ -642,15 +639,20 @@ getJasmineRequireObj().Env = function(j$) { reporter.clearReporters(); }; - var spyFactory = new j$.SpyFactory(function() { - var runnable = currentRunnable(); + var spyFactory = new j$.SpyFactory( + function getCustomStrategies() { + var runnable = currentRunnable(); - if (runnable) { - return runnableResources[runnable.id].customSpyStrategies; + if (runnable) { + return runnableResources[runnable.id].customSpyStrategies; + } + + return {}; + }, + function getPromise() { + return customPromise || global.Promise; } - - return {}; - }); + ); var spyRegistry = new j$.SpyRegistry({ currentSpies: function() { diff --git a/src/core/Spy.js b/src/core/Spy.js index 639d76f8..e4072f1b 100644 --- a/src/core/Spy.js +++ b/src/core/Spy.js @@ -13,7 +13,7 @@ getJasmineRequireObj().Spy = function (j$) { * @constructor * @name Spy */ - function Spy(name, originalFn, customStrategies) { + function Spy(name, originalFn, customStrategies, getPromise) { var numArgs = (typeof originalFn === 'function' ? originalFn.length : 0), wrapper = makeFunc(numArgs, function () { return spy.apply(this, Array.prototype.slice.call(arguments)); @@ -24,7 +24,8 @@ getJasmineRequireObj().Spy = function (j$) { getSpy: function () { return wrapper; }, - customStrategies: customStrategies + customStrategies: customStrategies, + getPromise: getPromise }), callTracker = new j$.CallTracker(), spy = function () { @@ -98,7 +99,6 @@ getJasmineRequireObj().Spy = function (j$) { return wrapper; } - function SpyStrategyDispatcher(strategyArgs) { var baseStrategy = new j$.SpyStrategy(strategyArgs); var argsStrategies = new StrategyDict(function() { diff --git a/src/core/SpyFactory.js b/src/core/SpyFactory.js index d4821321..4df28e55 100644 --- a/src/core/SpyFactory.js +++ b/src/core/SpyFactory.js @@ -1,10 +1,10 @@ getJasmineRequireObj().SpyFactory = function(j$) { - function SpyFactory(getCustomStrategies) { + function SpyFactory(getCustomStrategies, getPromise) { var self = this; this.createSpy = function(name, originalFn) { - return j$.Spy(name, originalFn, getCustomStrategies()); + return j$.Spy(name, originalFn, getCustomStrategies(), getPromise); }; this.createSpyObj = function(baseName, methodNames) { diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index 3aada4b2..7365f87c 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -6,6 +6,8 @@ getJasmineRequireObj().SpyStrategy = function(j$) { function SpyStrategy(options) { options = options || {}; + var self = this; + /** * Get the identifying information for the spy. * @name SpyStrategy#identity @@ -23,6 +25,46 @@ getJasmineRequireObj().SpyStrategy = function(j$) { this[k] = createCustomPlan(cs[k]); } } + + var getPromise = (typeof options.getPromise === 'function') ? options.getPromise : function() {}; + + var requirePromise = function(name) { + var Promise = getPromise(); + + if (!Promise) { + throw new Error(name + ' requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`'); + } + + return Promise; + }; + + /** + * Tell the spy to return a promise resolving to the specified value when invoked. + * @name SpyStrategy#resolveValue + * @function + * @param {*} value The value to return. + */ + this.resolveValue = function(value) { + var Promise = requirePromise('resolveValue'); + self.plan = function() { + return Promise.resolve(value); + }; + return self.getSpy(); + }; + + /** + * Tell the spy to return a promise rejecting with the specified value when invoked. + * @name SpyStrategy#rejectValue + * @function + * @param {*} value The value to return. + */ + this.rejectValue = function(value) { + var Promise = requirePromise('rejectValue'); + self.plan = function() { + return Promise.reject(value); + }; + return self.getSpy(); + }; } function createCustomPlan(factory) { @@ -84,44 +126,6 @@ getJasmineRequireObj().SpyStrategy = function(j$) { return this.getSpy(); }; - /** - * Tell the spy to return a promise resolving to the specified value when invoked. - * @name SpyStrategy#resolveValue - * @function - * @param {*} value The value to return. - */ - SpyStrategy.prototype.resolveValue = function(value) { - var Promise = j$.getPromise(); - - if (!Promise) { - throw new Error('resolveValue requires global Promise, or a `promiseLibrary` configured with `jasmine.getEnv().configure()`'); - } - - this.plan = function() { - return Promise.resolve(value); - }; - return this.getSpy(); - }; - - /** - * Tell the spy to return a promise rejecting with the specified value when invoked. - * @name SpyStrategy#rejectValue - * @function - * @param {*} value The value to return. - */ - SpyStrategy.prototype.rejectValue = function(value) { - var Promise = j$.getPromise(); - - if (!Promise) { - throw new Error('rejectValue requires global Promise, or a `promiseLibrary` configured with `jasmine.getEnv().configure()`'); - } - - this.plan = function() { - return Promise.reject(value); - }; - return this.getSpy(); - }; - /** * Tell the spy to throw an error when invoked. * @name SpyStrategy#throwError diff --git a/src/core/base.js b/src/core/base.js index 6609ef81..3a584f09 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -45,10 +45,6 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return env; }; - j$.getPromise = function() { - return j$.getEnv().getPromise() || j$.getGlobal().Promise; - }; - j$.isArray_ = function(value) { return j$.isA_('Array', value); }; From df818f3fbcdec59aadee88dd72efb512dcc70170 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Wed, 8 May 2019 09:36:12 -0400 Subject: [PATCH 008/201] rejectValue wraps non-Errors like throwError does --- spec/core/SpyStrategySpec.js | 14 ++++++++++++++ src/core/SpyStrategy.js | 4 +++- 2 files changed, 17 insertions(+), 1 deletion(-) diff --git a/spec/core/SpyStrategySpec.js b/spec/core/SpyStrategySpec.js index ab13e4ab..f299792a 100644 --- a/spec/core/SpyStrategySpec.js +++ b/spec/core/SpyStrategySpec.js @@ -150,6 +150,20 @@ describe("SpyStrategy", function() { }).catch(done.fail); }); + it("allows a non-Error to be rejected, wrapping it in an exception when executed", function(done) { + jasmine.getEnv().requirePromises(); + + var originalFn = jasmine.createSpy("original"), + getPromise = function() { return Promise; }, + spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn, getPromise: getPromise}); + + spyStrategy.rejectValue('oops'); + spyStrategy.exec().then(done.fail).catch(function (error) { + expect(error).toEqual(new Error('oops')); + done(); + }).catch(done.fail); + }); + it("fails if promises are not available", function() { var originalFn = jasmine.createSpy("original"), spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index 7365f87c..b8a3db88 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -60,8 +60,10 @@ getJasmineRequireObj().SpyStrategy = function(j$) { */ this.rejectValue = function(value) { var Promise = requirePromise('rejectValue'); + var error = (value instanceof Error) ? value : new Error(value); + self.plan = function() { - return Promise.reject(value); + return Promise.reject(error); }; return self.getSpy(); }; From b2fb92eedd1fe017cfe154b04e04abdad34b3e19 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Thu, 9 May 2019 06:12:06 -0400 Subject: [PATCH 009/201] Promise-based strategies are now named resolveWith and rejectWith --- spec/core/SpySpec.js | 4 ++-- spec/core/SpyStrategySpec.js | 18 +++++++++--------- src/core/SpyStrategy.js | 12 ++++++------ 3 files changed, 17 insertions(+), 17 deletions(-) diff --git a/spec/core/SpySpec.js b/spec/core/SpySpec.js index e12a9d83..04734e2f 100644 --- a/spec/core/SpySpec.js +++ b/spec/core/SpySpec.js @@ -175,7 +175,7 @@ describe('Spies', function () { it('works with global Promise library when available', function(done) { jasmine.getEnv().requirePromises(); - var spy = env.createSpy('foo').and.resolveValue(42); + var spy = env.createSpy('foo').and.resolveWith(42); spy().then(function(result) { expect(result).toEqual(42); done(); @@ -187,7 +187,7 @@ describe('Spies', function () { customPromise.resolve.and.returnValue('resolved'); env.configure({ Promise: customPromise }); - var spy = env.createSpy('foo').and.resolveValue(42); + var spy = env.createSpy('foo').and.resolveWith(42); expect(spy()).toEqual('resolved'); expect(customPromise.resolve).toHaveBeenCalledWith(42); }); diff --git a/spec/core/SpyStrategySpec.js b/spec/core/SpyStrategySpec.js index f299792a..709c268b 100644 --- a/spec/core/SpyStrategySpec.js +++ b/spec/core/SpyStrategySpec.js @@ -110,7 +110,7 @@ describe("SpyStrategy", function() { }) }); - describe("#resolveValue", function() { + describe("#resolveWith", function() { it("allows a resolved promise to be returned", function(done) { jasmine.getEnv().requirePromises(); @@ -118,7 +118,7 @@ describe("SpyStrategy", function() { getPromise = function() { return Promise; }, spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn, getPromise: getPromise}); - spyStrategy.resolveValue(37); + spyStrategy.resolveWith(37); spyStrategy.exec().then(function (returnValue) { expect(returnValue).toEqual(37); done(); @@ -130,12 +130,12 @@ describe("SpyStrategy", function() { spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); expect(function() { - spyStrategy.resolveValue(37); - }).toThrowError('resolveValue requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`'); + spyStrategy.resolveWith(37); + }).toThrowError('resolveWith requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`'); }); }); - describe("#rejectValue", function() { + describe("#rejectWith", function() { it("allows a rejected promise to be returned", function(done) { jasmine.getEnv().requirePromises(); @@ -143,7 +143,7 @@ describe("SpyStrategy", function() { getPromise = function() { return Promise; }, spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn, getPromise: getPromise}); - spyStrategy.rejectValue(new Error('oops')); + spyStrategy.rejectWith(new Error('oops')); spyStrategy.exec().then(done.fail).catch(function (error) { expect(error).toEqual(new Error('oops')); done(); @@ -157,7 +157,7 @@ describe("SpyStrategy", function() { getPromise = function() { return Promise; }, spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn, getPromise: getPromise}); - spyStrategy.rejectValue('oops'); + spyStrategy.rejectWith('oops'); spyStrategy.exec().then(done.fail).catch(function (error) { expect(error).toEqual(new Error('oops')); done(); @@ -169,8 +169,8 @@ describe("SpyStrategy", function() { spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); expect(function() { - spyStrategy.rejectValue(new Error('oops')); - }).toThrowError('rejectValue requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`'); + spyStrategy.rejectWith(new Error('oops')); + }).toThrowError('rejectWith requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`'); }); }); diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index b8a3db88..5a785d4f 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -40,12 +40,12 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to return a promise resolving to the specified value when invoked. - * @name SpyStrategy#resolveValue + * @name SpyStrategy#resolveWith * @function * @param {*} value The value to return. */ - this.resolveValue = function(value) { - var Promise = requirePromise('resolveValue'); + this.resolveWith = function(value) { + var Promise = requirePromise('resolveWith'); self.plan = function() { return Promise.resolve(value); }; @@ -54,12 +54,12 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to return a promise rejecting with the specified value when invoked. - * @name SpyStrategy#rejectValue + * @name SpyStrategy#rejectWith * @function * @param {*} value The value to return. */ - this.rejectValue = function(value) { - var Promise = requirePromise('rejectValue'); + this.rejectWith = function(value) { + var Promise = requirePromise('rejectWith'); var error = (value instanceof Error) ? value : new Error(value); self.plan = function() { From 49c03d4a22a1a13a41b6a6b809e1f60822c748f9 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Fri, 10 May 2019 06:18:35 -0400 Subject: [PATCH 010/201] Improve error handling in CI test launcher --- ci.js | 18 ++++++++++++++---- 1 file changed, 14 insertions(+), 4 deletions(-) diff --git a/ci.js b/ci.js index 49a122f4..b4dd45e1 100644 --- a/ci.js +++ b/ci.js @@ -120,6 +120,17 @@ async function getResults(driver) { return {specResults: flatten(specResults), failedSuiteResults: flatten(failedSuiteResults)}; } +function cleanup() { + return Promise.resolve().then(() => { + return Promise.all([ + driver ? driver.close() : true, + new Promise(resolve => server ? server.close(resolve) : resolve()) + ]); + }).catch(error => { + console.error(error); + }); +} + (async function () { await new Promise(resolve => { console.log("Creating an express app for browers to run the tests...") @@ -202,7 +213,6 @@ async function getResults(driver) { if (useSauce) { driver.executeScript(`sauce:job-result=${process.exitCode === 0}`); } -})().finally(() => { - return Promise.all([driver.close(), new Promise(resolve => server.close(resolve))]); -}); - +})().catch(error => { + console.error(error); +}).then(cleanup); From ee15309a8f97acd8b547490fd354276c1eb76702 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Sat, 11 May 2019 18:20:13 -0400 Subject: [PATCH 011/201] Extend spyOnAllFunctions to include prototype and parent methods --- spec/core/SpyRegistrySpec.js | 42 +++++++++++++++++++++++++++++++++--- src/core/SpyRegistry.js | 22 ++++++++++++++----- 2 files changed, 56 insertions(+), 8 deletions(-) diff --git a/spec/core/SpyRegistrySpec.js b/spec/core/SpyRegistrySpec.js index 920502d1..c7f53fe1 100644 --- a/spec/core/SpyRegistrySpec.js +++ b/spec/core/SpyRegistrySpec.js @@ -222,7 +222,7 @@ describe("SpyRegistry", function() { }).toThrowError(/spyOnAllFunctions could not find an object to spy upon/); }); - it("overrides all writable and configurable functions of the object", function() { + it("overrides all writable and configurable functions of the object and its parents", function() { var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: function() { return 'I am a spy'; }}); @@ -234,7 +234,7 @@ describe("SpyRegistry", function() { var noop5 = createNoop(); var parent = { - notSpied1: noop1 + parentSpied1: noop1 }; var subject = Object.create(parent); Object.defineProperty(subject, 'spied1', { @@ -291,7 +291,7 @@ describe("SpyRegistry", function() { var spiedObject = spyRegistry.spyOnAllFunctions(subject); - expect(subject.notSpied1).toBe(noop1); + expect(subject.parentSpied1).toBe('I am a spy'); expect(subject.notSpied2).toBe(noop2); expect(subject.notSpied3).toBe(noop3); expect(subject.notSpied4).toBe(noop4); @@ -303,6 +303,42 @@ describe("SpyRegistry", function() { expect(subject.spied4).toBe('I am a spy'); expect(spiedObject).toBe(subject); }); + + it("overrides prototype methods on the object", function() { + var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: function() { + return 'I am a spy'; + }}); + + var noop1 = function() { }; + var noop2 = function() { }; + + var MyClass = function() { + this.spied1 = noop1; + }; + MyClass.prototype.spied2 = noop2; + + var subject = new MyClass(); + spyRegistry.spyOnAllFunctions(subject); + + expect(subject.spied1).toBe('I am a spy'); + expect(subject.spied2).toBe('I am a spy'); + expect(MyClass.prototype.spied2).toBe(noop2); + }); + + it("does not override non-enumerable properties (like Object.prototype methods)", function() { + var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: function() { + return 'I am a spy'; + }}); + var subject = { + spied1: function() { } + }; + + spyRegistry.spyOnAllFunctions(subject); + + expect(subject.spied1).toBe('I am a spy'); + expect(subject.toString).not.toBe('I am a spy'); + expect(subject.hasOwnProperty).not.toBe('I am a spy'); + }); }); describe("#clearSpies", function() { diff --git a/src/core/SpyRegistry.js b/src/core/SpyRegistry.js index 17fd1971..595ce461 100644 --- a/src/core/SpyRegistry.js +++ b/src/core/SpyRegistry.js @@ -125,13 +125,25 @@ getJasmineRequireObj().SpyRegistry = function(j$) { throw new Error('spyOnAllFunctions could not find an object to spy upon'); } - for (var prop in obj) { - if (Object.prototype.hasOwnProperty.call(obj, prop) && obj[prop] instanceof Function) { - var descriptor = Object.getOwnPropertyDescriptor(obj, prop); - if ((descriptor.writable || descriptor.set) && descriptor.configurable) { - this.spyOn(obj, prop); + var pointer = obj, + props = [], + prop, + descriptor; + + while (pointer) { + for (prop in pointer) { + if (Object.prototype.hasOwnProperty.call(pointer, prop) && pointer[prop] instanceof Function) { + descriptor = Object.getOwnPropertyDescriptor(pointer, prop); + if ((descriptor.writable || descriptor.set) && descriptor.configurable) { + props.push(prop); + } } } + pointer = Object.getPrototypeOf(pointer); + } + + for (var i = 0; i < props.length; i++) { + this.spyOn(obj, props[i]); } return obj; From 91fe87ca56aca1ab4174237b01d3ec5e39a5ad5f Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Tue, 14 May 2019 06:57:46 -0400 Subject: [PATCH 012/201] Simplify error checks in ci.js --- ci.js | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/ci.js b/ci.js index b4dd45e1..350996a5 100644 --- a/ci.js +++ b/ci.js @@ -121,12 +121,10 @@ async function getResults(driver) { } function cleanup() { - return Promise.resolve().then(() => { - return Promise.all([ - driver ? driver.close() : true, - new Promise(resolve => server ? server.close(resolve) : resolve()) - ]); - }).catch(error => { + return Promise.all([ + driver ? driver.close() : true, + new Promise(resolve => server ? server.close(resolve) : resolve()) + ]).catch(error => { console.error(error); }); } From c88c772ffb7bb16d647bf52fc4167984684e5e3e Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Wed, 15 May 2019 11:39:45 -0400 Subject: [PATCH 013/201] Print global errors encountered during CI runs --- ci.js | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/ci.js b/ci.js index 350996a5..ffa1457e 100644 --- a/ci.js +++ b/ci.js @@ -198,6 +198,7 @@ function cleanup() { const details = await driver.executeScript(` return { overallStatus: jsApiReporter.runDetails.overallStatus, + overallFailures: jsApiReporter.runDetails.failedExpectations, executionTime: jsApiReporter.executionTime(), random: jsApiReporter.runDetails.order.random, seed: jsApiReporter.runDetails.order.seed @@ -208,6 +209,12 @@ function cleanup() { console.log(`Randomized with seed ${details.seed} ( ${host}/?random=${details.random}&seed=${details.seed} )`); process.exitCode = details.overallStatus === 'passed' ? 0 : 1; + // Print details of global errors encountered during the test run. (Most likely, + // some type of file loading or syntax error.) + if (details.overallFailures && details.overallFailures.length > 0) { + console.error('Failures encountered during test run:', JSON.stringify(details.overallFailures, undefined, 2)); + } + if (useSauce) { driver.executeScript(`sauce:job-result=${process.exitCode === 0}`); } From 0fded24d35fa854496d66188176c9fee80e412a5 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Wed, 15 May 2019 11:51:46 -0400 Subject: [PATCH 014/201] Introduce matchers#toBeInstanceOf --- spec/core/matchers/toBeInstanceOfSpec.js | 235 +++++++++++++++++++++++ src/core/matchers/requireMatchers.js | 1 + src/core/matchers/toBeInstanceOf.js | 45 +++++ 3 files changed, 281 insertions(+) create mode 100644 spec/core/matchers/toBeInstanceOfSpec.js create mode 100644 src/core/matchers/toBeInstanceOf.js diff --git a/spec/core/matchers/toBeInstanceOfSpec.js b/spec/core/matchers/toBeInstanceOfSpec.js new file mode 100644 index 00000000..1c4819a2 --- /dev/null +++ b/spec/core/matchers/toBeInstanceOfSpec.js @@ -0,0 +1,235 @@ +describe('toBeInstanceOf', function() { + function setPrototypeOf(object, proto) { + // Support older environments + Object.setPrototypeOf ? Object.setPrototypeOf(object, proto) : object.__proto__ = proto; + } + + describe('when expecting Number', function() { + it('passes for literal number', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(3, Number); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of Number not to be an instance of Number' + }); + }); + + it('passes for NaN', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(NaN, Number); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of NaN not to be an instance of Number' + }); + }); + + it('passes for Infinity', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(Infinity, Number); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of Number not to be an instance of Number' + }); + }); + + it('fails for a non-number', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare('foo', Number); + expect(result).toEqual({ + pass: false, + message: 'Expected instance of String to be an instance of Number' + }); + }); + }); + + describe('when expecting String', function() { + it('passes for a string', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare('foo', String); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of String not to be an instance of String' + }); + }); + + it('fails for a non-string', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare({}, String); + expect(result).toEqual({ + pass: false, + message: 'Expected instance of Object to be an instance of String' + }); + }); + }); + + describe('when expecting Boolean', function() { + it('passes for a boolean', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(true, Boolean); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of Boolean not to be an instance of Boolean' + }); + }); + + it('fails for a non-boolean', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare('false', Boolean); + expect(result).toEqual({ + pass: false, + message: 'Expected instance of String to be an instance of Boolean' + }); + }); + }); + + describe('when expecting RegExp', function() { + it('passes for a literal regular expression', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(/foo/, RegExp); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of RegExp not to be an instance of RegExp' + }); + }); + }); + + describe('when expecting Function', function() { + it('passes for a function', function() { + var fn = function() { }; + + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(fn, Function); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of Function not to be an instance of Function' + }); + }); + + it('passes for an async function', function() { + jasmine.getEnv().requireAsyncAwait(); + + var fn = eval("(async function fn() { return 'foo'; })"); + console.log(fn); + + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(fn, Function); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of AsyncFunction not to be an instance of Function' + }); + }); + }); + + describe('when expecting Object', function() { + function Animal() { } + + it('passes for any object', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare({ foo: 'bar' }, Object); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of Object not to be an instance of Object' + }); + }); + + it('passes for an Error object', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(new Error('example'), Object); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of Error not to be an instance of Object' + }); + }); + + it('passes for a user-defined class', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(new Animal(), Object); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of Animal not to be an instance of Object' + }); + }); + + it('fails for a non-object', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare('foo', Object); + expect(result).toEqual({ + pass: false, + message: 'Expected instance of String to be an instance of Object' + }); + }); + + it('passes for objects with no constructor', function() { + var object = {}; + setPrototypeOf(object, null); + + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(object, Object); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of null({ }) not to be an instance of Object' + }); + }); + }); + + describe('when expecting a user-defined class', function() { + // Base class + function Animal() { } + + // Subclasses, defined using syntax that is as old as possible + function Dog() { + Animal.call(this); + } + Dog.prototype = new Animal(); + Dog.prototype.constructor = Dog; + + function Cat() { + Animal.call(this); + } + Cat.prototype = new Animal(); + Cat.prototype.constructor = Cat; + + it('passes for instances of that class', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(new Animal(), Animal); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of Animal not to be an instance of Animal' + }); + }); + + it('passes for instances of a subclass', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(new Cat(), Animal); + expect(result).toEqual({ + pass: true, + message: 'Expected instance of Cat not to be an instance of Animal' + }); + }); + + it('does not pass for sibling classes', function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var result = matcher.compare(new Dog(), Cat); + expect(result).toEqual({ + pass: false, + message: 'Expected instance of Dog to be an instance of Cat' + }); + }); + }); + + it('raises an error if passed an invalid expected value', function() { + expect(function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + matcher.compare({}, 'Error'); + }).toThrowError(' : Expected value is not a constructor function\n' + + 'Usage: expect(value).toBeInstanceOf()'); + }); + + it('raises an error if missing an expected value', function() { + expect(function() { + var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + matcher.compare({}, undefined); + }).toThrowError(' : Expected value is not a constructor function\n' + + 'Usage: expect(value).toBeInstanceOf()'); + }); +}); diff --git a/src/core/matchers/requireMatchers.js b/src/core/matchers/requireMatchers.js index 52a68a40..c40df70e 100644 --- a/src/core/matchers/requireMatchers.js +++ b/src/core/matchers/requireMatchers.js @@ -4,6 +4,7 @@ getJasmineRequireObj().requireMatchers = function(jRequire, j$) { 'toBe', 'toBeCloseTo', 'toBeDefined', + 'toBeInstanceOf', 'toBeFalse', 'toBeFalsy', 'toBeGreaterThan', diff --git a/src/core/matchers/toBeInstanceOf.js b/src/core/matchers/toBeInstanceOf.js new file mode 100644 index 00000000..55d419b3 --- /dev/null +++ b/src/core/matchers/toBeInstanceOf.js @@ -0,0 +1,45 @@ +getJasmineRequireObj().toBeInstanceOf = function(j$) { + var usageError = j$.formatErrorMsg('', 'expect(value).toBeInstanceOf()'); + + /** + * {@link expect} the actual to be an instance of the expected class + * @function + * @name matchers#toBeInstanceOf + * @param {Object} expected - The class or constructor function to check for + * @example + * expect('foo').toBeInstanceOf(String); + * expect(3).toBeInstanceOf(Number); + * expect(new Error()).toBeInstanceOf(Error); + */ + function toBeInstanceOf(util, customEqualityTesters) { + return { + compare: function(actual, expected) { + var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : j$.pp(actual), + expectedType = expected ? j$.fnNameFor(expected) : j$.pp(expected), + expectedMatcher, + pass; + + try { + expectedMatcher = new j$.Any(expected); + pass = expectedMatcher.asymmetricMatch(actual); + } catch (error) { + throw new Error(usageError('Expected value is not a constructor function')); + } + + if (pass) { + return { + pass: true, + message: 'Expected instance of ' + actualType + ' not to be an instance of ' + expectedType + }; + } else { + return { + pass: false, + message: 'Expected instance of ' + actualType + ' to be an instance of ' + expectedType + }; + } + } + }; + } + + return toBeInstanceOf; +}; From 0129a7d007827e3d6a747b2a052a89cc35a1aacd Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Wed, 15 May 2019 17:34:57 -0700 Subject: [PATCH 015/201] Update contributing doc based on some of the newer tooling - Fixes #1702 --- .github/CONTRIBUTING.md | 53 ++++++++++++++++++++++------------------- 1 file changed, 29 insertions(+), 24 deletions(-) diff --git a/.github/CONTRIBUTING.md b/.github/CONTRIBUTING.md index c8d6ea55..25a848fd 100644 --- a/.github/CONTRIBUTING.md +++ b/.github/CONTRIBUTING.md @@ -30,7 +30,6 @@ Once you've pushed a feature branch to your forked repo, you're ready to open a ### Directory Structure * `/src` contains all of the source files - * `/src/console` - Node.js-specific files * `/src/core` - generic source files * `/src/html` - browser-specific files * `/spec` contains all of the tests @@ -47,37 +46,33 @@ The tests should always use `jasmineUnderTest` to refer to the objects and funct ### `boot.js` -__This is new for Jasmine 2.0.__ - This file does all of the setup necessary for Jasmine to work. It loads all of the code, creates an `Env`, attaches the global functions, and builds the reporter. It also sets up the execution of the `Env` - for browsers this is in `window.onload`. While the default in `lib` is appropriate for browsers, projects may wish to customize this file. For example, for Jasmine development there is a different `dev_boot.js` for Jasmine development that does more work. ### Compatibility -* Browser Minimum - * IE8 - * Firefox 3.x - * Chrome ?? - * Safari 5 +Jasmine supports the following environments: + +* Browsers + * IE10+ + * Edge Latest + * Firefox Latest + * Chrome Latest + * Safari 8+ + +* Node.js + * 8 + * 10 + * 11 ## Development -All source code belongs in `src/`. The `core/` directory contains the bulk of Jasmine's functionality. This code should remain browser- and environment-agnostic. If your feature or fix cannot be, as mentioned above, please degrade gracefully. Any code that should only be in a non-browser environment should live in `src/console/`. Any code that depends on a browser (specifically, it expects `window` to be the global or `document` is present) should live in `src/html/`. +All source code belongs in `src/`. The `core/` directory contains the bulk of Jasmine's functionality. This code should remain browser- and environment-agnostic. If your feature or fix cannot be, as mentioned above, please degrade gracefully. Any code that depends on a browser (specifically, it expects `window` to be the global or `document` is present) should live in `src/html/`. ### Install Dependencies -Jasmine Core relies on Ruby and Node.js. - -To install the Ruby dependencies, you will need Ruby, Rubygems, and Bundler available. Then: - - $ bundle - -...will install all of the Ruby dependencies. If the ffi gem fails to build its native extensions, you may need to manually install some system dependencies. On Ubuntu: - - $ apt-get install gcc ruby ruby-dev libxml2 libxml2-dev libxslt1-dev - -...should get you to the point that `bundle` can install everything. +Jasmine Core relies on Node.js. To install the Node dependencies, you will need Node.js, Npm, and [Grunt](http://gruntjs.com/), the [grunt-cli](https://github.com/gruntjs/grunt-cli) and ensure that `grunt` is on your path. @@ -104,20 +99,30 @@ Follow these tips and your pull request, patch, or suggestion is much more likel ### Running Specs -Jasmine uses the [Jasmine Ruby gem](http://github.com/jasmine/jasmine-gem) to test itself in browser. +Jasmine uses some internal tooling to test itself in browser on Travis. This tooling _should_ work locally as well. - $ bundle exec rake jasmine + $ node ci.js -...and then visit `http://localhost:8888` to run specs. +You can also set the `JASMINE_BROWSER` environment variable to specify which browser should be used. Jasmine uses the [Jasmine NPM package](http://github.com/jasmine/jasmine-npm) to test itself in a Node.js/npm environment. - $ grunt execSpecsInNode + $ npm test ...and then the results will print to the console. All specs run except those that expect a browser (the specs in `spec/html` are ignored). The easiest way to run the tests in **Internet Explorer** is to run a VM that has IE installed. It's easy to do this with VirtualBox. +__Note__: these steps currently still rely on the Jasmine ruby gem and not the new Node.js based tooling. To install the Ruby dependencies, you will need Ruby, Rubygems, and Bundler available. Then: + + $ bundle + +...will install all of the Ruby dependencies. If the ffi gem fails to build its native extensions, you may need to manually install some system dependencies. On Ubuntu: + + $ apt-get install gcc ruby ruby-dev libxml2 libxml2-dev libxslt1-dev + +...should get you to the point that `bundle` can install everything. + 1. Download and install [VirtualBox](https://www.virtualbox.org/wiki/Downloads). 1. Download a VM image [from Microsoft](https://developer.microsoft.com/en-us/microsoft-edge/tools/vms/). Select "VirtualBox" as the platform. 1. Unzip the downloaded archive. There should be an OVA file inside. From 1e13039478b66961bda33f686f53cee82a6f1e4e Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Fri, 17 May 2019 11:43:22 -0400 Subject: [PATCH 016/201] spyOnProperty respects the allowRespy flag --- spec/core/SpyRegistrySpec.js | 50 ++++++++++++++++++++++++------------ src/core/SpyRegistry.js | 9 ++++--- 2 files changed, 40 insertions(+), 19 deletions(-) diff --git a/spec/core/SpyRegistrySpec.js b/spec/core/SpyRegistrySpec.js index c7f53fe1..dcf414a2 100644 --- a/spec/core/SpyRegistrySpec.js +++ b/spec/core/SpyRegistrySpec.js @@ -137,22 +137,6 @@ describe("SpyRegistry", function() { }).toThrowError(/does not have access type/); }); - it("checks if it has already been spied upon", function() { - var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: createSpy}), - subject = {}; - - Object.defineProperty(subject, 'spiedProp', { - get: function() { return 1; }, - configurable: true - }); - - spyRegistry.spyOnProperty(subject, 'spiedProp'); - - expect(function() { - spyRegistry.spyOnProperty(subject, 'spiedProp'); - }).toThrowError(/has already been spied upon/); - }); - it("checks if it can be spied upon", function() { var subject = {}; @@ -212,6 +196,40 @@ describe("SpyRegistry", function() { expect(subject.spiedProperty).toEqual(returnValue); expect(setter).toEqual(spy); }); + + describe("when the property is already spied upon", function() { + it("throws an error if respy is not allowed", function() { + var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: createSpy}), + subject = {}; + + Object.defineProperty(subject, 'spiedProp', { + get: function() { return 1; }, + configurable: true + }); + + spyRegistry.spyOnProperty(subject, 'spiedProp'); + + expect(function() { + spyRegistry.spyOnProperty(subject, 'spiedProp'); + }).toThrowError(/spiedProp#get has already been spied upon/); + }); + + it("returns the original spy if respy is allowed", function() { + var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: createSpy}), + subject = {}; + + spyRegistry.allowRespy(true); + + Object.defineProperty(subject, 'spiedProp', { + get: function() { return 1; }, + configurable: true + }); + + var originalSpy = spyRegistry.spyOnProperty(subject, 'spiedProp'); + + expect(spyRegistry.spyOnProperty(subject, 'spiedProp')).toBe(originalSpy); + }); + }); }); describe("#spyOnAllFunctions", function() { diff --git a/src/core/SpyRegistry.js b/src/core/SpyRegistry.js index 595ce461..90d93490 100644 --- a/src/core/SpyRegistry.js +++ b/src/core/SpyRegistry.js @@ -27,7 +27,7 @@ getJasmineRequireObj().SpyRegistry = function(j$) { } if (obj[methodName] && j$.isSpy(obj[methodName]) ) { - if ( !!this.respy ){ + if (this.respy) { return obj[methodName]; }else { throw new Error(getErrorMsg(methodName + ' has already been spied upon')); @@ -91,8 +91,11 @@ getJasmineRequireObj().SpyRegistry = function(j$) { } if (j$.isSpy(descriptor[accessType])) { - //TODO?: should this return the current spy? Downside: may cause user confusion about spy state - throw new Error(propertyName + ' has already been spied upon'); + if (this.respy) { + return descriptor[accessType]; + } else { + throw new Error(propertyName + '#' + accessType + ' has already been spied upon'); + } } var originalDescriptor = j$.util.clone(descriptor), From befb8995e6e3d3f9df424570778ee60f5c03519c Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Fri, 17 May 2019 12:02:44 -0400 Subject: [PATCH 017/201] spyOnProperty jasmine-style error messages with usage note --- src/core/SpyRegistry.js | 20 ++++++++++++-------- 1 file changed, 12 insertions(+), 8 deletions(-) diff --git a/src/core/SpyRegistry.js b/src/core/SpyRegistry.js index 595ce461..60b21a75 100644 --- a/src/core/SpyRegistry.js +++ b/src/core/SpyRegistry.js @@ -1,6 +1,7 @@ getJasmineRequireObj().SpyRegistry = function(j$) { - var getErrorMsg = j$.formatErrorMsg('', 'spyOn(, )'); + var spyOnMsg = j$.formatErrorMsg('', 'spyOn(, )'); + var spyOnPropertyMsg = j$.formatErrorMsg('', 'spyOnProperty(, , [accessType])'); function SpyRegistry(options) { options = options || {}; @@ -8,11 +9,12 @@ getJasmineRequireObj().SpyRegistry = function(j$) { var createSpy = options.createSpy; var currentSpies = options.currentSpies || function() { return []; }; - this.allowRespy = function(allow){ + this.allowRespy = function(allow) { this.respy = allow; }; this.spyOn = function(obj, methodName) { + var getErrorMsg = spyOnMsg; if (j$.util.isUndefined(obj) || obj === null) { throw new Error(getErrorMsg('could not find an object to spy upon for ' + methodName + '()')); @@ -66,33 +68,35 @@ getJasmineRequireObj().SpyRegistry = function(j$) { }; this.spyOnProperty = function (obj, propertyName, accessType) { + var getErrorMsg = spyOnPropertyMsg; + accessType = accessType || 'get'; if (j$.util.isUndefined(obj)) { - throw new Error('spyOn could not find an object to spy upon for ' + propertyName + ''); + throw new Error(getErrorMsg('spyOn could not find an object to spy upon for ' + propertyName + '')); } if (j$.util.isUndefined(propertyName)) { - throw new Error('No property name supplied'); + throw new Error(getErrorMsg('No property name supplied')); } var descriptor = j$.util.getPropertyDescriptor(obj, propertyName); if (!descriptor) { - throw new Error(propertyName + ' property does not exist'); + throw new Error(getErrorMsg(propertyName + ' property does not exist')); } if (!descriptor.configurable) { - throw new Error(propertyName + ' is not declared configurable'); + throw new Error(getErrorMsg(propertyName + ' is not declared configurable')); } if(!descriptor[accessType]) { - throw new Error('Property ' + propertyName + ' does not have access type ' + accessType); + throw new Error(getErrorMsg('Property ' + propertyName + ' does not have access type ' + accessType)); } if (j$.isSpy(descriptor[accessType])) { //TODO?: should this return the current spy? Downside: may cause user confusion about spy state - throw new Error(propertyName + ' has already been spied upon'); + throw new Error(getErrorMsg(propertyName + ' has already been spied upon')); } var originalDescriptor = j$.util.clone(descriptor), From 309e6df8fd61b17d8672ab0d37668754d68dd214 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Fri, 17 May 2019 16:31:15 -0700 Subject: [PATCH 018/201] Use `Object.create` to make an object with `null` prototype --- spec/core/matchers/toBeInstanceOfSpec.js | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/spec/core/matchers/toBeInstanceOfSpec.js b/spec/core/matchers/toBeInstanceOfSpec.js index 61cb5374..d31845e9 100644 --- a/spec/core/matchers/toBeInstanceOfSpec.js +++ b/spec/core/matchers/toBeInstanceOfSpec.js @@ -1,9 +1,4 @@ describe('toBeInstanceOf', function() { - function setPrototypeOf(object, proto) { - // Support older environments - Object.setPrototypeOf ? Object.setPrototypeOf(object, proto) : object.__proto__ = proto; - } - describe('when expecting Number', function() { it('passes for literal number', function() { var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); @@ -159,8 +154,7 @@ describe('toBeInstanceOf', function() { }); it('passes for objects with no constructor', function() { - var object = {}; - setPrototypeOf(object, null); + var object = Object.create(null); var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); var result = matcher.compare(object, Object); From e04d3d8a625b83ce778df39a420d4c840766f2da Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Fri, 17 May 2019 17:07:47 -0700 Subject: [PATCH 019/201] Fix bad merge for spyOnProperty error message --- lib/jasmine-core/jasmine.js | 2 +- src/core/SpyRegistry.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 44e564ba..f461a3bf 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -6491,7 +6491,7 @@ getJasmineRequireObj().SpyRegistry = function(j$) { if (this.respy) { return descriptor[accessType]; } else { - throw new Error(getErrorMsg(propertyName + ' has already been spied upon')); + throw new Error(getErrorMsg(propertyName + '#' + accessType + ' has already been spied upon')); } } diff --git a/src/core/SpyRegistry.js b/src/core/SpyRegistry.js index 3f6d79e8..3f4e3bc9 100644 --- a/src/core/SpyRegistry.js +++ b/src/core/SpyRegistry.js @@ -98,7 +98,7 @@ getJasmineRequireObj().SpyRegistry = function(j$) { if (this.respy) { return descriptor[accessType]; } else { - throw new Error(getErrorMsg(propertyName + ' has already been spied upon')); + throw new Error(getErrorMsg(propertyName + '#' + accessType + ' has already been spied upon')); } } From 1e855aa9b8aaa6925b3b8e7e9330c88e6d449d5a Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Sat, 18 May 2019 08:10:11 -0400 Subject: [PATCH 020/201] Cleanup: whitespace --- src/core/CallTracker.js | 2 +- src/core/Expector.js | 2 +- src/core/MockDate.js | 2 +- src/core/PrettyPrinter.js | 6 +++--- src/core/QueueRunner.js | 2 +- src/core/StackTrace.js | 2 +- src/core/base.js | 8 ++++---- src/html/HtmlReporter.js | 2 +- 8 files changed, 13 insertions(+), 13 deletions(-) diff --git a/src/core/CallTracker.js b/src/core/CallTracker.js index f1fdfbc5..9a26b38b 100644 --- a/src/core/CallTracker.js +++ b/src/core/CallTracker.js @@ -64,7 +64,7 @@ getJasmineRequireObj().CallTracker = function(j$) { */ this.allArgs = function() { var callArgs = []; - for(var i = 0; i < calls.length; i++){ + for(var i = 0; i < calls.length; i++) { callArgs.push(calls[i].args); } diff --git a/src/core/Expector.js b/src/core/Expector.js index a8c717f2..55667f51 100644 --- a/src/core/Expector.js +++ b/src/core/Expector.js @@ -3,7 +3,7 @@ getJasmineRequireObj().Expector = function(j$) { this.util = options.util || { buildFailureMessage: function() {} }; this.customEqualityTesters = options.customEqualityTesters || []; this.actual = options.actual; - this.addExpectationResult = options.addExpectationResult || function(){}; + this.addExpectationResult = options.addExpectationResult || function() {}; this.filters = new j$.ExpectationFilterChain(); } diff --git a/src/core/MockDate.js b/src/core/MockDate.js index 0e5a8008..9dfc0628 100644 --- a/src/core/MockDate.js +++ b/src/core/MockDate.js @@ -76,7 +76,7 @@ getJasmineRequireObj().MockDate = function() { FakeDate.parse = GlobalDate.parse; FakeDate.UTC = GlobalDate.UTC; } - } + } return MockDate; }; diff --git a/src/core/PrettyPrinter.js b/src/core/PrettyPrinter.js index cb738d28..91a42e86 100644 --- a/src/core/PrettyPrinter.js +++ b/src/core/PrettyPrinter.js @@ -113,7 +113,7 @@ getJasmineRequireObj().pp = function(j$) { } this.format(array[i]); } - if(array.length > length){ + if(array.length > length) { this.append(', ...'); } @@ -153,7 +153,7 @@ getJasmineRequireObj().pp = function(j$) { i++; }, this ); - if (set.size > size){ + if (set.size > size) { this.append(', ...'); } this.append(' )'); @@ -178,7 +178,7 @@ getJasmineRequireObj().pp = function(j$) { i++; }, this ); - if (map.size > size){ + if (map.size > size) { this.append(', ...'); } this.append(' )'); diff --git a/src/core/QueueRunner.js b/src/core/QueueRunner.js index 1566bcd3..c183c1d4 100644 --- a/src/core/QueueRunner.js +++ b/src/core/QueueRunner.js @@ -22,7 +22,7 @@ getJasmineRequireObj().QueueRunner = function(j$) { this.queueableFns = queueableFns.concat(attrs.cleanupFns || []); this.firstCleanupIx = queueableFns.length; this.onComplete = attrs.onComplete || emptyFn; - this.clearStack = attrs.clearStack || function(fn) {fn();}; + this.clearStack = attrs.clearStack || function(fn) { fn(); }; this.onException = attrs.onException || emptyFn; this.userContext = attrs.userContext || new j$.UserContext(); this.timeout = attrs.timeout || {setTimeout: setTimeout, clearTimeout: clearTimeout}; diff --git a/src/core/StackTrace.js b/src/core/StackTrace.js index c10ec951..6c6ec458 100644 --- a/src/core/StackTrace.js +++ b/src/core/StackTrace.js @@ -104,6 +104,6 @@ getJasmineRequireObj().StackTrace = function(j$) { return messageLines.length; } - + return StackTrace; }; diff --git a/src/core/base.js b/src/core/base.js index 3a584f09..9c8be408 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -171,7 +171,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @name jasmine.truthy * @function */ - j$.truthy = function() {return new j$.Truthy();}; + j$.truthy = function() { return new j$.Truthy(); }; /** * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), @@ -179,7 +179,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @name jasmine.falsy * @function */ - j$.falsy = function() {return new j$.Falsy();}; + j$.falsy = function() { return new j$.Falsy(); }; /** * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), @@ -187,7 +187,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @name jasmine.empty * @function */ - j$.empty = function() {return new j$.Empty();}; + j$.empty = function() { return new j$.Empty(); }; /** * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), @@ -195,7 +195,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @name jasmine.notEmpty * @function */ - j$.notEmpty = function() {return new j$.NotEmpty();}; + j$.notEmpty = function() { return new j$.NotEmpty(); }; /** * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), diff --git a/src/html/HtmlReporter.js b/src/html/HtmlReporter.js index c9be5590..880f9558 100644 --- a/src/html/HtmlReporter.js +++ b/src/html/HtmlReporter.js @@ -108,7 +108,7 @@ jasmineRequire.HtmlReporter = function(j$) { console.error('Spec \'' + result.fullName + '\' has no expectations.'); } - if (!symbols){ + if (!symbols) { symbols = find('.jasmine-symbol-summary'); } From b1da6e39605801114de27340404fda261b9695e9 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Sat, 18 May 2019 08:11:47 -0400 Subject: [PATCH 021/201] Cleanup: unused vars, dangling commas, negation --- src/core/Env.js | 11 ++++------- src/core/Spec.js | 2 +- src/core/Suite.js | 2 +- src/core/matchers/matchersUtil.js | 5 ----- src/core/matchers/requireMatchers.js | 2 +- src/core/matchers/toBe.js | 2 +- src/core/matchers/toBeFalsy.js | 2 +- src/core/matchers/toHaveBeenCalledTimes.js | 2 +- src/core/util.js | 14 -------------- 9 files changed, 10 insertions(+), 32 deletions(-) diff --git a/src/core/Env.js b/src/core/Env.js index e06d7546..b0c09040 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -255,7 +255,7 @@ getJasmineRequireObj().Env = function(j$) { var defaultResourcesForRunnable = function(id, parentRunnableId) { var resources = {spies: [], customEqualityTesters: [], customMatchers: {}, customSpyStrategies: {}}; - if(runnableResources[parentRunnableId]){ + if(runnableResources[parentRunnableId]) { resources.customEqualityTesters = j$.util.clone(runnableResources[parentRunnableId].customEqualityTesters); resources.customMatchers = j$.util.clone(runnableResources[parentRunnableId].customMatchers); } @@ -307,9 +307,6 @@ getJasmineRequireObj().Env = function(j$) { return buildExpectationResult(attrs); }; - var maximumSpecCallbackDepth = 20; - var currentSpecCallbackDepth = 0; - /** * Sets whether Jasmine should throw an Error when an expectation fails. * This causes a spec to only have one expectation failure. @@ -666,7 +663,7 @@ getJasmineRequireObj().Env = function(j$) { } }); - this.allowRespy = function(allow){ + this.allowRespy = function(allow) { spyRegistry.allowRespy(allow); }; @@ -830,7 +827,7 @@ getJasmineRequireObj().Env = function(j$) { timeout: timeout || 0 }, throwOnExpectationFailure: config.oneFailurePerSpec, - timer: new j$.Timer(), + timer: new j$.Timer() }); return spec; @@ -879,7 +876,7 @@ getJasmineRequireObj().Env = function(j$) { return spec; }; - this.fit = function(description, fn, timeout){ + this.fit = function(description, fn, timeout) { ensureIsNotNested('fit'); ensureIsFunctionOrAsync(fn, 'fit'); var spec = specFactory(description, fn, currentDeclarationSuite, timeout); diff --git a/src/core/Spec.js b/src/core/Spec.js index 8adbacd7..4b31925d 100644 --- a/src/core/Spec.js +++ b/src/core/Spec.js @@ -40,7 +40,7 @@ getJasmineRequireObj().Spec = function(j$) { passedExpectations: [], deprecationWarnings: [], pendingReason: '', - duration: null, + duration: null }; } diff --git a/src/core/Suite.js b/src/core/Suite.js index e076e73f..bbb582a8 100644 --- a/src/core/Suite.js +++ b/src/core/Suite.js @@ -34,7 +34,7 @@ getJasmineRequireObj().Suite = function(j$) { fullName: this.getFullName(), failedExpectations: [], deprecationWarnings: [], - duration: null, + duration: null }; } diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index 3352fc30..14647dd6 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -225,7 +225,6 @@ getJasmineRequireObj().matchersUtil = function(j$) { }); for (i = 0; i < aLength || i < bLength; i++) { - var formatter = false; diffBuilder.withPath(i, function() { if (i >= bLength) { diffBuilder.record(a[i], void 0, actualArrayIsLongerFormatter); @@ -417,10 +416,6 @@ getJasmineRequireObj().matchersUtil = function(j$) { return extraKeys; } - function has(obj, key) { - return Object.prototype.hasOwnProperty.call(obj, key); - } - function isFunction(obj) { return typeof obj === 'function'; } diff --git a/src/core/matchers/requireMatchers.js b/src/core/matchers/requireMatchers.js index c40df70e..e8b1fd58 100644 --- a/src/core/matchers/requireMatchers.js +++ b/src/core/matchers/requireMatchers.js @@ -28,7 +28,7 @@ getJasmineRequireObj().requireMatchers = function(jRequire, j$) { 'toMatch', 'toThrow', 'toThrowError', - 'toThrowMatching', + 'toThrowMatching' ], matchers = {}; diff --git a/src/core/matchers/toBe.js b/src/core/matchers/toBe.js index 96b236a7..f92ed1ba 100644 --- a/src/core/matchers/toBe.js +++ b/src/core/matchers/toBe.js @@ -13,7 +13,7 @@ getJasmineRequireObj().toBe = function(j$) { return { compare: function(actual, expected) { var result = { - pass: actual === expected, + pass: actual === expected }; if (typeof expected === 'object') { diff --git a/src/core/matchers/toBeFalsy.js b/src/core/matchers/toBeFalsy.js index 7e06f55f..9ef75792 100644 --- a/src/core/matchers/toBeFalsy.js +++ b/src/core/matchers/toBeFalsy.js @@ -10,7 +10,7 @@ getJasmineRequireObj().toBeFalsy = function() { return { compare: function(actual) { return { - pass: !!!actual + pass: !actual }; } }; diff --git a/src/core/matchers/toHaveBeenCalledTimes.js b/src/core/matchers/toHaveBeenCalledTimes.js index 786b9547..b05ee8fe 100644 --- a/src/core/matchers/toHaveBeenCalledTimes.js +++ b/src/core/matchers/toHaveBeenCalledTimes.js @@ -20,7 +20,7 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { var args = Array.prototype.slice.call(arguments, 0), result = { pass: false }; - if (!j$.isNumber_(expected)){ + if (!j$.isNumber_(expected)) { throw new Error(getErrorMsg('The expected times failed is a required argument and must be a number.')); } diff --git a/src/core/util.js b/src/core/util.js index 7bf93d3f..f885d2cb 100644 --- a/src/core/util.js +++ b/src/core/util.js @@ -100,18 +100,6 @@ getJasmineRequireObj().util = function(j$) { return Object.prototype.hasOwnProperty.call(obj, key); }; - function anyMatch(pattern, lines) { - var i; - - for (i = 0; i < lines.length; i++) { - if (lines[i].match(pattern)) { - return true; - } - } - - return false; - } - util.errorWithStack = function errorWithStack () { // Don't throw and catch if we don't have to, because it makes it harder // for users to debug their code with exception breakpoints. @@ -138,8 +126,6 @@ getJasmineRequireObj().util = function(j$) { var result; return function() { - var trace; - if (!result) { result = callerFile(); } From 69a7449e508907c50c547f6d087cb1a329c24622 Mon Sep 17 00:00:00 2001 From: Paul van Brenk Date: Sun, 19 May 2019 12:46:32 -0400 Subject: [PATCH 022/201] Fix toBeCloseTo matcher for Node.js 12 and Chrome 74 --- spec/core/matchers/toBeCloseToSpec.js | 14 ++++++++++++++ src/core/matchers/toBeCloseTo.js | 2 +- 2 files changed, 15 insertions(+), 1 deletion(-) diff --git a/spec/core/matchers/toBeCloseToSpec.js b/spec/core/matchers/toBeCloseToSpec.js index bf04c153..402ce88e 100644 --- a/spec/core/matchers/toBeCloseToSpec.js +++ b/spec/core/matchers/toBeCloseToSpec.js @@ -90,4 +90,18 @@ describe("toBeCloseTo", function() { result = matcher.compare(1.23, 1.234); expect(result.pass).toBe(true); }); + + it("handles edge cases with rounding", function () { + var matcher = jasmineUnderTest.matchers.toBeCloseTo(), + result; + + // these cases resulted in false negatives in version of V8 + // included in Node.js 12 and Chrome 74 (and Edge Chromium) + result = matcher.compare(4.030904708957288, 4.0309, 5); + expect(result.pass).toBe(true); + result = matcher.compare(4.82665525779431,4.82666, 5); + expect(result.pass).toBe(true); + result = matcher.compare(-2.82665525779431, -2.82666, 5); + expect(result.pass).toBe(true); + }); }); diff --git a/src/core/matchers/toBeCloseTo.js b/src/core/matchers/toBeCloseTo.js index 31c79456..b57ca1ad 100644 --- a/src/core/matchers/toBeCloseTo.js +++ b/src/core/matchers/toBeCloseTo.js @@ -26,7 +26,7 @@ getJasmineRequireObj().toBeCloseTo = function() { var maxDelta = Math.pow(10, -precision) / 2; return { - pass: Math.round(delta * pow) / pow <= maxDelta + pass: Math.round(delta * pow) <= maxDelta * pow }; } }; From 9f704b6f3a72a377f11406945bd0b1cedb99df87 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Mon, 20 May 2019 09:01:10 -0400 Subject: [PATCH 023/201] PrettyPrinter handles objects with invalid toString implementations --- spec/core/PrettyPrintSpec.js | 23 +++++++++++++++++++++++ src/core/PrettyPrinter.js | 6 ++++++ 2 files changed, 29 insertions(+) diff --git a/spec/core/PrettyPrintSpec.js b/spec/core/PrettyPrintSpec.js index 47a5758a..64dea0fd 100644 --- a/spec/core/PrettyPrintSpec.js +++ b/spec/core/PrettyPrintSpec.js @@ -333,4 +333,27 @@ describe("jasmineUnderTest.pp", function () { expect(jasmineUnderTest.pp(obj)).toEqual("null({ foo: 'bar' })"); }); + + it("should gracefully handle objects with invalid toString implementations", function () { + var obj = { + foo: { + toString: function() { + // Invalid: toString returning a number + return 3; + } + }, + bar: { + toString: function() { + // Invalid: toString returning an object + return new Error("bar"); + } + }, + // Valid: an actual number + baz: 3, + // Valid: an actual Error object + qux: new Error("bar") + }; + + expect(jasmineUnderTest.pp(obj)).toEqual("Object({ foo: [object Number], bar: [object Error], baz: 3, qux: Error: bar })"); + }); }); diff --git a/src/core/PrettyPrinter.js b/src/core/PrettyPrinter.js index cb738d28..42b89784 100644 --- a/src/core/PrettyPrinter.js +++ b/src/core/PrettyPrinter.js @@ -266,6 +266,12 @@ getJasmineRequireObj().pp = function(j$) { }; PrettyPrinter.prototype.append = function(value) { + // This check protects us from the rare case where an object has overriden + // `toString()` with an invalid implementation (returning a non-string). + if (typeof value !== 'string') { + value = Object.prototype.toString.call(value); + } + var result = truncate(value, j$.MAX_PRETTY_PRINT_CHARS - this.length); this.length += result.value.length; this.stringParts.push(result.value); From 8225bb935fb249ddf0010f32b0f34a370e3c3892 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Mon, 20 May 2019 09:09:07 -0400 Subject: [PATCH 024/201] Explicitly test pretty printing objects with nested invalid toString --- spec/core/PrettyPrintSpec.js | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/spec/core/PrettyPrintSpec.js b/spec/core/PrettyPrintSpec.js index 64dea0fd..4accef96 100644 --- a/spec/core/PrettyPrintSpec.js +++ b/spec/core/PrettyPrintSpec.js @@ -344,8 +344,12 @@ describe("jasmineUnderTest.pp", function () { }, bar: { toString: function() { - // Invalid: toString returning an object - return new Error("bar"); + // Really invalid: a nested bad toString(). + return { + toString: function() { + return new Date(); + } + }; } }, // Valid: an actual number @@ -354,6 +358,6 @@ describe("jasmineUnderTest.pp", function () { qux: new Error("bar") }; - expect(jasmineUnderTest.pp(obj)).toEqual("Object({ foo: [object Number], bar: [object Error], baz: 3, qux: Error: bar })"); + expect(jasmineUnderTest.pp(obj)).toEqual("Object({ foo: [object Number], bar: [object Object], baz: 3, qux: Error: bar })"); }); }); From d1adbdc72b1aacc0ee1c9ded1c121d5eb8e03cc9 Mon Sep 17 00:00:00 2001 From: johnjbarton Date: Mon, 20 May 2019 09:12:05 -0700 Subject: [PATCH 025/201] fix(PrettyPrint): jasmine.createSpyObj('obj', ['toString']); The PrettyPrint handler for scalars uses toString() but if that method has been spyed on, then the stringify fails with TypeError: Cannot read property 'length' of undefined. By hanlding this case earlier in format() we avoid the error. Add unit test covering this case. --- spec/core/PrettyPrintSpec.js | 19 +++++++++++++++++++ src/core/PrettyPrinter.js | 2 ++ 2 files changed, 21 insertions(+) diff --git a/spec/core/PrettyPrintSpec.js b/spec/core/PrettyPrintSpec.js index 47a5758a..853eb05a 100644 --- a/spec/core/PrettyPrintSpec.js +++ b/spec/core/PrettyPrintSpec.js @@ -285,6 +285,25 @@ describe("jasmineUnderTest.pp", function () { expect(jasmineUnderTest.pp(env.createSpy("something"))).toEqual("spy on something"); }); + it("should stringify spyOn toString properly", function() { + var TestObject = { + someFunction: function() {} + }, + env = new jasmineUnderTest.Env(); + + var spyRegistry = new jasmineUnderTest.SpyRegistry({ + currentSpies: function() {return [];}, + createSpy: function(name, originalFn) { + return jasmineUnderTest.Spy(name, originalFn); + } + }); + + spyRegistry.spyOn(TestObject, 'toString'); + const testSpyObj = env.createSpyObj('TheClassName', ['toString']); + + expect(jasmineUnderTest.pp(testSpyObj)).toEqual("spy on TheClassName.toString"); + }); + it("should stringify objects that implement jasmineToString", function () { var obj = { jasmineToString: function () { return "strung"; } diff --git a/src/core/PrettyPrinter.js b/src/core/PrettyPrinter.js index cb738d28..7f1ee68b 100644 --- a/src/core/PrettyPrinter.js +++ b/src/core/PrettyPrinter.js @@ -30,6 +30,8 @@ getJasmineRequireObj().pp = function(j$) { this.emitString(value); } else if (j$.isSpy(value)) { this.emitScalar('spy on ' + value.and.identity); + } else if (j$.isSpy(value.toString)) { + this.emitScalar('spy on ' + value.toString.and.identity); } else if (value instanceof RegExp) { this.emitScalar(value.toString()); } else if (typeof value === 'function') { From 88c8c905badc50e6521a3d1276396f7ca7a54341 Mon Sep 17 00:00:00 2001 From: Gabriel Elkind Date: Mon, 20 May 2019 15:25:38 -0500 Subject: [PATCH 026/201] Adds width to root level html-reporter class --- lib/jasmine-core/jasmine.css | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/jasmine-core/jasmine.css b/lib/jasmine-core/jasmine.css index 6543aab4..81dd5b3e 100644 --- a/lib/jasmine-core/jasmine.css +++ b/lib/jasmine-core/jasmine.css @@ -1,7 +1,7 @@ @charset "UTF-8"; body { overflow-y: scroll; } -.jasmine_html-reporter { background-color: #eee; padding: 5px; margin: -8px; font-size: 11px; font-family: Monaco, "Lucida Console", monospace; line-height: 14px; color: #333; } +.jasmine_html-reporter { width: 100%; background-color: #eee; padding: 5px; margin: -8px; font-size: 11px; font-family: Monaco, "Lucida Console", monospace; line-height: 14px; color: #333; } .jasmine_html-reporter a { text-decoration: none; } From b12981a3e716ccc622b55be7ae50d7d4cd6e4b64 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Mon, 20 May 2019 17:17:55 -0700 Subject: [PATCH 027/201] build dist for rounding fix --- lib/jasmine-core/jasmine.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index f461a3bf..26b25192 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -4185,7 +4185,7 @@ getJasmineRequireObj().toBeCloseTo = function() { var maxDelta = Math.pow(10, -precision) / 2; return { - pass: Math.round(delta * pow) / pow <= maxDelta + pass: Math.round(delta * pow) <= maxDelta * pow }; } }; From 9f875ce666da5b0f297148cad10c8391b3cc1ceb Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Mon, 20 May 2019 17:56:27 -0700 Subject: [PATCH 028/201] Older versions don't support `const`, use `var` --- spec/core/PrettyPrintSpec.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/core/PrettyPrintSpec.js b/spec/core/PrettyPrintSpec.js index e3d0d508..b62d191d 100644 --- a/spec/core/PrettyPrintSpec.js +++ b/spec/core/PrettyPrintSpec.js @@ -299,7 +299,7 @@ describe("jasmineUnderTest.pp", function () { }); spyRegistry.spyOn(TestObject, 'toString'); - const testSpyObj = env.createSpyObj('TheClassName', ['toString']); + var testSpyObj = env.createSpyObj('TheClassName', ['toString']); expect(jasmineUnderTest.pp(testSpyObj)).toEqual("spy on TheClassName.toString"); }); From 4e10cf84d5f28ef26d4ea3dea8be4cde04d18974 Mon Sep 17 00:00:00 2001 From: Gabriel Elkind Date: Mon, 20 May 2019 23:51:29 -0500 Subject: [PATCH 029/201] Adds in the source-- whoops! --- src/html/_HTMLReporter.scss | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/html/_HTMLReporter.scss b/src/html/_HTMLReporter.scss index 1ea2a030..2b128a04 100644 --- a/src/html/_HTMLReporter.scss +++ b/src/html/_HTMLReporter.scss @@ -27,6 +27,7 @@ body { } .jasmine_html-reporter { + width: 100%; background-color: $page-background-color; padding: 5px; margin: -8px; @@ -305,7 +306,7 @@ body { &.jasmine-excluded a { color: $neutral-color; - } + } } } @@ -329,7 +330,7 @@ body { &.jasmine-excluded a:before { content: $passing-mark + $space; - } + } } } From b4cbe9850fbe192eaffeae450669f96e79a574ed Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Tue, 21 May 2019 17:44:38 -0700 Subject: [PATCH 030/201] add prettier and eslint --- .gitattributes | 1 + .jshintrc | 17 - Gruntfile.js | 7 +- grunt/config/jshint.js | 11 - lib/jasmine-core/jasmine-html.js | 355 +++-- lib/jasmine-core/jasmine.js | 1364 +++++++++++++------- package.json | 45 +- spec/core/AsyncExpectationSpec.js | 167 ++- spec/core/CallTrackerSpec.js | 62 +- spec/core/ClearStackSpec.js | 157 ++- spec/core/ClockSpec.js | 688 +++++++--- spec/core/DelayedFunctionSchedulerSpec.js | 77 +- spec/core/EnvSpec.js | 141 +- spec/core/ExceptionFormatterSpec.js | 83 +- spec/core/ExceptionsSpec.js | 27 +- spec/core/ExpectationFilterChainSpec.js | 32 +- spec/core/ExpectationResultSpec.js | 97 +- spec/core/ExpectationSpec.js | 373 +++--- spec/core/GlobalErrorsSpec.js | 136 +- spec/core/JsApiReporterSpec.js | 123 +- spec/core/MockDateSpec.js | 60 +- spec/core/PrettyPrintSpec.js | 343 +++-- spec/core/QueueRunnerSpec.js | 409 +++--- spec/core/ReportDispatcherSpec.js | 120 +- spec/core/SpecSpec.js | 276 ++-- spec/core/SpyRegistrySpec.js | 305 +++-- spec/core/SpySpec.js | 168 ++- spec/core/SpyStrategySpec.js | 261 ++-- spec/core/StackTraceSpec.js | 55 +- spec/core/SuiteSpec.js | 63 +- spec/core/TimerSpec.js | 10 +- spec/core/TreeProcessorSpec.js | 676 +++++----- spec/core/UserContextSpec.js | 7 +- spec/core/UtilSpec.js | 125 +- spec/core/baseSpec.js | 9 +- spec/core/formatErrorMsgSpec.js | 2 +- spec/helpers/BrowserFlags.js | 5 +- spec/helpers/asyncAwait.js | 7 +- spec/helpers/checkForMap.js | 33 +- spec/helpers/checkForSet.js | 33 +- spec/helpers/checkForSymbol.js | 3 +- spec/helpers/checkForTypedArrays.js | 13 +- spec/helpers/integrationMatchers.js | 30 +- spec/helpers/nodeDefineJasmineUnderTest.js | 22 +- spec/helpers/promises.js | 3 +- spec/html/HtmlReporterSpec.js | 1027 +++++++++------ spec/html/HtmlSpecFilterSpec.js | 19 +- spec/html/MatchersHtmlSpec.js | 13 +- spec/html/PrettyPrintHtmlSpec.js | 30 +- spec/html/QueryStringSpec.js | 70 +- spec/html/ResultsNodeSpec.js | 42 +- spec/html/SpyRegistryHtmlSpec.js | 6 +- spec/npmPackage/npmPackageSpec.js | 37 +- spec/performance/large_object_test.js | 20 +- spec/performance/performance_test.js | 6 +- src/core/CallTracker.js | 6 +- src/core/ClearStack.js | 6 +- src/core/Clock.js | 69 +- src/core/DelayedFunctionScheduler.js | 41 +- src/core/Env.js | 416 +++--- src/core/ExceptionFormatter.js | 17 +- src/core/Expectation.js | 21 +- src/core/ExpectationFilterChain.js | 9 +- src/core/ExpectationResult.js | 2 +- src/core/Expector.js | 47 +- src/core/GlobalErrors.js | 11 +- src/core/JsApiReporter.js | 3 +- src/core/MockDate.js | 39 +- src/core/Order.js | 15 +- src/core/PrettyPrinter.js | 94 +- src/core/QueueRunner.js | 47 +- src/core/ReportDispatcher.js | 10 +- src/core/Spec.js | 67 +- src/core/Spy.js | 73 +- src/core/SpyFactory.js | 4 +- src/core/SpyRegistry.js | 86 +- src/core/SpyStrategy.js | 26 +- src/core/StackTrace.js | 31 +- src/core/Suite.js | 22 +- src/core/Timer.js | 10 +- src/core/TreeProcessor.js | 97 +- src/core/UserContext.js | 5 +- src/core/base.js | 59 +- src/core/errors.js | 2 +- src/core/requireCore.js | 16 +- src/core/requireInterface.js | 2 +- src/core/util.js | 13 +- src/html/HtmlReporter.js | 339 +++-- src/html/HtmlSpecFilter.js | 5 +- src/html/QueryString.js | 11 +- 90 files changed, 6345 insertions(+), 3647 deletions(-) create mode 100644 .gitattributes delete mode 100644 .jshintrc delete mode 100644 grunt/config/jshint.js diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 00000000..6313b56c --- /dev/null +++ b/.gitattributes @@ -0,0 +1 @@ +* text=auto eol=lf diff --git a/.jshintrc b/.jshintrc deleted file mode 100644 index 6c4da922..00000000 --- a/.jshintrc +++ /dev/null @@ -1,17 +0,0 @@ -{ - "bitwise": true, - "curly": true, - "globals": { - "clearTimeout": false, - "console": false, - "getJasmineRequireObj": true, - "jasmineRequire": true, - "setTimeout": false - }, - "immed": true, - "newcap": true, - "trailing": true, - "loopfunc": true, - "quotmark": "single", - "undef": true -} diff --git a/Gruntfile.js b/Gruntfile.js index fa22201d..14077d78 100644 --- a/Gruntfile.js +++ b/Gruntfile.js @@ -4,7 +4,6 @@ module.exports = function(grunt) { grunt.initConfig({ pkg: pkg, - jshint: require('./grunt/config/jshint.js'), concat: require('./grunt/config/concat.js'), sass: require('./grunt/config/sass.js'), compress: require('./grunt/config/compress.js'), @@ -15,7 +14,7 @@ module.exports = function(grunt) { grunt.loadTasks('grunt/tasks'); - grunt.registerTask('default', ['jshint:all', 'sass:dist', "cssUrlEmbed"]); + grunt.registerTask('default', ['sass:dist', "cssUrlEmbed"]); var version = require('./grunt/tasks/version.js'); @@ -28,9 +27,7 @@ module.exports = function(grunt) { [ 'sass:dist', "cssUrlEmbed", - 'jshint:beforeConcat', - 'concat', - 'jshint:afterConcat' + 'concat' ] ); diff --git a/grunt/config/jshint.js b/grunt/config/jshint.js deleted file mode 100644 index 253c739d..00000000 --- a/grunt/config/jshint.js +++ /dev/null @@ -1,11 +0,0 @@ -module.exports = { - beforeConcat: ['src/**/*.js'], - afterConcat: [ - 'lib/jasmine-core/jasmine-html.js', - 'lib/jasmine-core/jasmine.js' - ], - options: { - jshintrc: '.jshintrc' - }, - all: ['src/**/*.js'] -}; diff --git a/lib/jasmine-core/jasmine-html.js b/lib/jasmine-core/jasmine-html.js index 3e6950d5..be86ad18 100644 --- a/lib/jasmine-core/jasmine-html.js +++ b/lib/jasmine-core/jasmine-html.js @@ -52,8 +52,7 @@ jasmineRequire.HtmlReporter = function(j$) { } }; - ResultsStateBuilder.prototype.specStarted = function(result) { - }; + ResultsStateBuilder.prototype.specStarted = function(result) {}; ResultsStateBuilder.prototype.specDone = function(result) { this.currentParent.addChild(result, 'spec'); @@ -71,15 +70,16 @@ jasmineRequire.HtmlReporter = function(j$) { } }; - - function HtmlReporter(options) { - var config = function() { return (options.env && options.env.configuration()) || {}; }, + var config = function() { + return (options.env && options.env.configuration()) || {}; + }, getContainer = options.getContainer, createElement = options.createElement, createTextNode = options.createTextNode, navigateWithNewParam = options.navigateWithNewParam || function() {}, - addToExistingQueryString = options.addToExistingQueryString || defaultQueryString, + addToExistingQueryString = + options.addToExistingQueryString || defaultQueryString, filterSpecs = options.filterSpecs, timer = options.timer || j$.noopTimer, htmlReporterMain, @@ -88,15 +88,25 @@ jasmineRequire.HtmlReporter = function(j$) { this.initialize = function() { clearPrior(); - htmlReporterMain = createDom('div', {className: 'jasmine_html-reporter'}, - createDom('div', {className: 'jasmine-banner'}, - createDom('a', {className: 'jasmine-title', href: 'http://jasmine.github.io/', target: '_blank'}), - createDom('span', {className: 'jasmine-version'}, j$.version) + htmlReporterMain = createDom( + 'div', + { className: 'jasmine_html-reporter' }, + createDom( + 'div', + { className: 'jasmine-banner' }, + createDom('a', { + className: 'jasmine-title', + href: 'http://jasmine.github.io/', + target: '_blank' + }), + createDom('span', { className: 'jasmine-version' }, j$.version) ), - createDom('ul', {className: 'jasmine-symbol-summary'}), - createDom('div', {className: 'jasmine-alert'}), - createDom('div', {className: 'jasmine-results'}, - createDom('div', {className: 'jasmine-failures'}) + createDom('ul', { className: 'jasmine-symbol-summary' }), + createDom('div', { className: 'jasmine-alert' }), + createDom( + 'div', + { className: 'jasmine-results' }, + createDom('div', { className: 'jasmine-failures' }) ) ); getContainer().appendChild(htmlReporterMain); @@ -108,7 +118,7 @@ jasmineRequire.HtmlReporter = function(j$) { timer.start(); }; - var summary = createDom('div', {className: 'jasmine-summary'}); + var summary = createDom('div', { className: 'jasmine-summary' }); var stateBuilder = new ResultsStateBuilder(); @@ -133,20 +143,25 @@ jasmineRequire.HtmlReporter = function(j$) { this.specDone = function(result) { stateBuilder.specDone(result); - if(noExpectations(result) && typeof console !== 'undefined' && typeof console.error !== 'undefined') { - console.error('Spec \'' + result.fullName + '\' has no expectations.'); + if ( + noExpectations(result) && + typeof console !== 'undefined' && + typeof console.error !== 'undefined' + ) { + console.error("Spec '" + result.fullName + "' has no expectations."); } if (!symbols) { symbols = find('.jasmine-symbol-summary'); } - symbols.appendChild(createDom('li', { + symbols.appendChild( + createDom('li', { className: this.displaySpecInCorrectFormat(result), id: 'spec_' + result.id, title: result.fullName - } - )); + }) + ); if (result.status === 'failed') { failures.push(failureDom(result)); @@ -156,12 +171,16 @@ jasmineRequire.HtmlReporter = function(j$) { }; this.displaySpecInCorrectFormat = function(result) { - return noExpectations(result) ? 'jasmine-empty' : this.resultStatus(result.status); + return noExpectations(result) + ? 'jasmine-empty' + : this.resultStatus(result.status); }; this.resultStatus = function(status) { - if(status === 'excluded') { - return config().hideDisabled ? 'jasmine-excluded-no-display' : 'jasmine-excluded'; + if (status === 'excluded') { + return config().hideDisabled + ? 'jasmine-excluded-no-display' + : 'jasmine-excluded'; } return 'jasmine-' + status; }; @@ -171,16 +190,33 @@ jasmineRequire.HtmlReporter = function(j$) { var alert = find('.jasmine-alert'); var order = doneResult && doneResult.order; var i; - alert.appendChild(createDom('span', {className: 'jasmine-duration'}, 'finished in ' + timer.elapsed() / 1000 + 's')); + alert.appendChild( + createDom( + 'span', + { className: 'jasmine-duration' }, + 'finished in ' + timer.elapsed() / 1000 + 's' + ) + ); banner.appendChild(optionsMenu(config())); if (stateBuilder.specsExecuted < totalSpecsDefined) { - var skippedMessage = 'Ran ' + stateBuilder.specsExecuted + ' of ' + totalSpecsDefined + ' specs - run all'; + var skippedMessage = + 'Ran ' + + stateBuilder.specsExecuted + + ' of ' + + totalSpecsDefined + + ' specs - run all'; var skippedLink = addToExistingQueryString('spec', ''); alert.appendChild( - createDom('span', {className: 'jasmine-bar jasmine-skipped'}, - createDom('a', {href: skippedLink, title: 'Run all specs'}, skippedMessage) + createDom( + 'span', + { className: 'jasmine-bar jasmine-skipped' }, + createDom( + 'a', + { href: skippedLink, title: 'Run all specs' }, + skippedMessage + ) ) ); } @@ -190,34 +226,66 @@ jasmineRequire.HtmlReporter = function(j$) { var failed = stateBuilder.failureCount + globalFailures.length > 0; if (totalSpecsDefined > 0 || failed) { - statusBarMessage += pluralize('spec', stateBuilder.specsExecuted) + ', ' + pluralize('failure', stateBuilder.failureCount); - if (stateBuilder.pendingSpecCount) { statusBarMessage += ', ' + pluralize('pending spec', stateBuilder.pendingSpecCount); } + statusBarMessage += + pluralize('spec', stateBuilder.specsExecuted) + + ', ' + + pluralize('failure', stateBuilder.failureCount); + if (stateBuilder.pendingSpecCount) { + statusBarMessage += + ', ' + pluralize('pending spec', stateBuilder.pendingSpecCount); + } } if (doneResult.overallStatus === 'passed') { statusBarClassName += ' jasmine-passed '; } else if (doneResult.overallStatus === 'incomplete') { statusBarClassName += ' jasmine-incomplete '; - statusBarMessage = 'Incomplete: ' + doneResult.incompleteReason + ', ' + statusBarMessage; + statusBarMessage = + 'Incomplete: ' + + doneResult.incompleteReason + + ', ' + + statusBarMessage; } else { statusBarClassName += ' jasmine-failed '; } var seedBar; if (order && order.random) { - seedBar = createDom('span', {className: 'jasmine-seed-bar'}, + seedBar = createDom( + 'span', + { className: 'jasmine-seed-bar' }, ', randomized with seed ', - createDom('a', {title: 'randomized with seed ' + order.seed, href: seedHref(order.seed)}, order.seed) + createDom( + 'a', + { + title: 'randomized with seed ' + order.seed, + href: seedHref(order.seed) + }, + order.seed + ) ); } - alert.appendChild(createDom('span', {className: statusBarClassName}, statusBarMessage, seedBar)); + alert.appendChild( + createDom( + 'span', + { className: statusBarClassName }, + statusBarMessage, + seedBar + ) + ); var errorBarClassName = 'jasmine-bar jasmine-errored'; var afterAllMessagePrefix = 'AfterAll '; - for(i = 0; i < globalFailures.length; i++) { - alert.appendChild(createDom('span', {className: errorBarClassName}, globalFailureMessage(globalFailures[i]))); + for (i = 0; i < globalFailures.length; i++) { + alert.appendChild( + createDom( + 'span', + { className: errorBarClassName }, + globalFailureMessage(globalFailures[i]) + ) + ); } function globalFailureMessage(failure) { @@ -225,7 +293,9 @@ jasmineRequire.HtmlReporter = function(j$) { var prefix = 'Error during loading: ' + failure.message; if (failure.filename) { - return prefix + ' in ' + failure.filename + ' line ' + failure.lineno; + return ( + prefix + ' in ' + failure.filename + ' line ' + failure.lineno + ); } else { return prefix; } @@ -237,9 +307,15 @@ jasmineRequire.HtmlReporter = function(j$) { addDeprecationWarnings(doneResult); var warningBarClassName = 'jasmine-bar jasmine-warning'; - for(i = 0; i < deprecationWarnings.length; i++) { + for (i = 0; i < deprecationWarnings.length; i++) { var warning = deprecationWarnings[i]; - alert.appendChild(createDom('span', {className: warningBarClassName}, 'DEPRECATION: ' + warning)); + alert.appendChild( + createDom( + 'span', + { className: warningBarClassName }, + 'DEPRECATION: ' + warning + ) + ); } var results = find('.jasmine-results'); @@ -249,13 +325,29 @@ jasmineRequire.HtmlReporter = function(j$) { if (failures.length) { alert.appendChild( - createDom('span', {className: 'jasmine-menu jasmine-bar jasmine-spec-list'}, + createDom( + 'span', + { className: 'jasmine-menu jasmine-bar jasmine-spec-list' }, createDom('span', {}, 'Spec List | '), - createDom('a', {className: 'jasmine-failures-menu', href: '#'}, 'Failures'))); + createDom( + 'a', + { className: 'jasmine-failures-menu', href: '#' }, + 'Failures' + ) + ) + ); alert.appendChild( - createDom('span', {className: 'jasmine-menu jasmine-bar jasmine-failure-list'}, - createDom('a', {className: 'jasmine-spec-list-menu', href: '#'}, 'Spec List'), - createDom('span', {}, ' | Failures '))); + createDom( + 'span', + { className: 'jasmine-menu jasmine-bar jasmine-failure-list' }, + createDom( + 'a', + { className: 'jasmine-spec-list-menu', href: '#' }, + 'Spec List' + ), + createDom('span', {}, ' | Failures ') + ) + ); find('.jasmine-failures-menu').onclick = function() { setMenuModeTo('jasmine-failure-list'); @@ -276,17 +368,30 @@ jasmineRequire.HtmlReporter = function(j$) { return this; function failureDom(result) { - var failure = - createDom('div', {className: 'jasmine-spec-detail jasmine-failed'}, - failureDescription(result, stateBuilder.currentParent), - createDom('div', {className: 'jasmine-messages'}) - ); + var failure = createDom( + 'div', + { className: 'jasmine-spec-detail jasmine-failed' }, + failureDescription(result, stateBuilder.currentParent), + createDom('div', { className: 'jasmine-messages' }) + ); var messages = failure.childNodes[1]; for (var i = 0; i < result.failedExpectations.length; i++) { var expectation = result.failedExpectations[i]; - messages.appendChild(createDom('div', {className: 'jasmine-result-message'}, expectation.message)); - messages.appendChild(createDom('div', {className: 'jasmine-stack-trace'}, expectation.stack)); + messages.appendChild( + createDom( + 'div', + { className: 'jasmine-result-message' }, + expectation.message + ) + ); + messages.appendChild( + createDom( + 'div', + { className: 'jasmine-stack-trace' }, + expectation.stack + ) + ); } return failure; @@ -300,9 +405,20 @@ jasmineRequire.HtmlReporter = function(j$) { continue; } if (resultNode.type === 'suite') { - var suiteListNode = createDom('ul', {className: 'jasmine-suite', id: 'suite-' + resultNode.result.id}, - createDom('li', {className: 'jasmine-suite-detail jasmine-' + resultNode.result.status}, - createDom('a', {href: specHref(resultNode.result)}, resultNode.result.description) + var suiteListNode = createDom( + 'ul', + { className: 'jasmine-suite', id: 'suite-' + resultNode.result.id }, + createDom( + 'li', + { + className: + 'jasmine-suite-detail jasmine-' + resultNode.result.status + }, + createDom( + 'a', + { href: specHref(resultNode.result) }, + resultNode.result.description + ) ) ); @@ -311,22 +427,34 @@ jasmineRequire.HtmlReporter = function(j$) { } if (resultNode.type === 'spec') { if (domParent.getAttribute('class') !== 'jasmine-specs') { - specListNode = createDom('ul', {className: 'jasmine-specs'}); + specListNode = createDom('ul', { className: 'jasmine-specs' }); domParent.appendChild(specListNode); } var specDescription = resultNode.result.description; - if(noExpectations(resultNode.result)) { + if (noExpectations(resultNode.result)) { specDescription = 'SPEC HAS NO EXPECTATIONS ' + specDescription; } - if(resultNode.result.status === 'pending' && resultNode.result.pendingReason !== '') { - specDescription = specDescription + ' PENDING WITH MESSAGE: ' + resultNode.result.pendingReason; + if ( + resultNode.result.status === 'pending' && + resultNode.result.pendingReason !== '' + ) { + specDescription = + specDescription + + ' PENDING WITH MESSAGE: ' + + resultNode.result.pendingReason; } specListNode.appendChild( - createDom('li', { + createDom( + 'li', + { className: 'jasmine-' + resultNode.result.status, id: 'spec-' + resultNode.result.id }, - createDom('a', {href: specHref(resultNode.result)}, specDescription) + createDom( + 'a', + { href: specHref(resultNode.result) }, + specDescription + ) ) ); } @@ -334,37 +462,69 @@ jasmineRequire.HtmlReporter = function(j$) { } function optionsMenu(config) { - var optionsMenuDom = createDom('div', { className: 'jasmine-run-options' }, + var optionsMenuDom = createDom( + 'div', + { className: 'jasmine-run-options' }, createDom('span', { className: 'jasmine-trigger' }, 'Options'), - createDom('div', { className: 'jasmine-payload' }, - createDom('div', { className: 'jasmine-stop-on-failure' }, + createDom( + 'div', + { className: 'jasmine-payload' }, + createDom( + 'div', + { className: 'jasmine-stop-on-failure' }, createDom('input', { className: 'jasmine-fail-fast', id: 'jasmine-fail-fast', type: 'checkbox' }), - createDom('label', { className: 'jasmine-label', 'for': 'jasmine-fail-fast' }, 'stop execution on spec failure')), - createDom('div', { className: 'jasmine-throw-failures' }, + createDom( + 'label', + { className: 'jasmine-label', for: 'jasmine-fail-fast' }, + 'stop execution on spec failure' + ) + ), + createDom( + 'div', + { className: 'jasmine-throw-failures' }, createDom('input', { className: 'jasmine-throw', id: 'jasmine-throw-failures', type: 'checkbox' }), - createDom('label', { className: 'jasmine-label', 'for': 'jasmine-throw-failures' }, 'stop spec on expectation failure')), - createDom('div', { className: 'jasmine-random-order' }, + createDom( + 'label', + { className: 'jasmine-label', for: 'jasmine-throw-failures' }, + 'stop spec on expectation failure' + ) + ), + createDom( + 'div', + { className: 'jasmine-random-order' }, createDom('input', { className: 'jasmine-random', id: 'jasmine-random-order', type: 'checkbox' }), - createDom('label', { className: 'jasmine-label', 'for': 'jasmine-random-order' }, 'run tests in random order')), - createDom('div', { className: 'jasmine-hide-disabled' }, + createDom( + 'label', + { className: 'jasmine-label', for: 'jasmine-random-order' }, + 'run tests in random order' + ) + ), + createDom( + 'div', + { className: 'jasmine-hide-disabled' }, createDom('input', { className: 'jasmine-disabled', id: 'jasmine-hide-disabled', type: 'checkbox' }), - createDom('label', { className: 'jasmine-label', 'for': 'jasmine-hide-disabled' }, 'hide disabled tests')) + createDom( + 'label', + { className: 'jasmine-label', for: 'jasmine-hide-disabled' }, + 'hide disabled tests' + ) + ) ) ); @@ -374,13 +534,17 @@ jasmineRequire.HtmlReporter = function(j$) { navigateWithNewParam('failFast', !config.failFast); }; - var throwCheckbox = optionsMenuDom.querySelector('#jasmine-throw-failures'); + var throwCheckbox = optionsMenuDom.querySelector( + '#jasmine-throw-failures' + ); throwCheckbox.checked = config.oneFailurePerSpec; throwCheckbox.onclick = function() { navigateWithNewParam('throwFailures', !config.oneFailurePerSpec); }; - var randomCheckbox = optionsMenuDom.querySelector('#jasmine-random-order'); + var randomCheckbox = optionsMenuDom.querySelector( + '#jasmine-random-order' + ); randomCheckbox.checked = config.random; randomCheckbox.onclick = function() { navigateWithNewParam('random', !config.random); @@ -398,7 +562,10 @@ jasmineRequire.HtmlReporter = function(j$) { optionsTrigger.onclick = function() { if (isOpen.test(optionsPayload.className)) { - optionsPayload.className = optionsPayload.className.replace(isOpen, ''); + optionsPayload.className = optionsPayload.className.replace( + isOpen, + '' + ); } else { optionsPayload.className += ' jasmine-open'; } @@ -408,14 +575,24 @@ jasmineRequire.HtmlReporter = function(j$) { } function failureDescription(result, suite) { - var wrapper = createDom('div', {className: 'jasmine-description'}, - createDom('a', {title: result.description, href: specHref(result)}, result.description) + var wrapper = createDom( + 'div', + { className: 'jasmine-description' }, + createDom( + 'a', + { title: result.description, href: specHref(result) }, + result.description + ) ); var suiteLink; while (suite && suite.parent) { wrapper.insertBefore(createTextNode(' > '), wrapper.firstChild); - suiteLink = createDom('a', {href: suiteHref(suite)}, suite.result.description); + suiteLink = createDom( + 'a', + { href: suiteHref(suite) }, + suite.result.description + ); wrapper.insertBefore(suiteLink, wrapper.firstChild); suite = suite.parent; @@ -437,7 +614,7 @@ jasmineRequire.HtmlReporter = function(j$) { function addDeprecationWarnings(result) { if (result && result.deprecationWarnings) { - for(var i = 0; i < result.deprecationWarnings.length; i++) { + for (var i = 0; i < result.deprecationWarnings.length; i++) { var warning = result.deprecationWarnings[i].message; if (!j$.util.arrayContains(warning)) { deprecationWarnings.push(warning); @@ -454,7 +631,7 @@ jasmineRequire.HtmlReporter = function(j$) { // return the reporter var oldReporter = find(''); - if(oldReporter) { + if (oldReporter) { getContainer().removeChild(oldReporter); } } @@ -486,7 +663,7 @@ jasmineRequire.HtmlReporter = function(j$) { } function pluralize(singular, count) { - var word = (count == 1 ? singular : singular + 's'); + var word = count == 1 ? singular : singular + 's'; return '' + count + ' ' + word; } @@ -508,8 +685,10 @@ jasmineRequire.HtmlReporter = function(j$) { } function noExpectations(result) { - return (result.failedExpectations.length + result.passedExpectations.length) === 0 && - result.status === 'passed'; + return ( + result.failedExpectations.length + result.passedExpectations.length === + 0 && result.status === 'passed' + ); } function hasActiveSpec(resultNode) { @@ -532,7 +711,10 @@ jasmineRequire.HtmlReporter = function(j$) { jasmineRequire.HtmlSpecFilter = function() { function HtmlSpecFilter(options) { - var filterString = options && options.filterString() && options.filterString().replace(/[-[\]{}()*+?.,\\^$|#\s]/g, '\\$&'); + var filterString = + options && + options.filterString() && + options.filterString().replace(/[-[\]{}()*+?.,\\^$|#\s]/g, '\\$&'); var filterPattern = new RegExp(filterString); this.matches = function(specName) { @@ -569,9 +751,11 @@ jasmineRequire.ResultsNode = function() { jasmineRequire.QueryString = function() { function QueryString(options) { - this.navigateWithNewParam = function(key, value) { - options.getWindowLocation().search = this.fullStringWithNewParam(key, value); + options.getWindowLocation().search = this.fullStringWithNewParam( + key, + value + ); }; this.fullStringWithNewParam = function(key, value) { @@ -589,7 +773,9 @@ jasmineRequire.QueryString = function() { function toQueryString(paramMap) { var qStrPairs = []; for (var prop in paramMap) { - qStrPairs.push(encodeURIComponent(prop) + '=' + encodeURIComponent(paramMap[prop])); + qStrPairs.push( + encodeURIComponent(prop) + '=' + encodeURIComponent(paramMap[prop]) + ); } return '?' + qStrPairs.join('&'); } @@ -613,7 +799,6 @@ jasmineRequire.QueryString = function() { return paramMap; } - } return QueryString; diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 89c7e0c6..3bd8dd93 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -20,11 +20,15 @@ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ -var getJasmineRequireObj = (function (jasmineGlobal) { - /* globals exports, global, module, window */ +// eslint-disable-next-line no-unused-vars +var getJasmineRequireObj = (function(jasmineGlobal) { var jasmineRequire; - if (typeof module !== 'undefined' && module.exports && typeof exports !== 'undefined') { + if ( + typeof module !== 'undefined' && + module.exports && + typeof exports !== 'undefined' + ) { if (typeof global !== 'undefined') { jasmineGlobal = global; } else { @@ -32,7 +36,11 @@ var getJasmineRequireObj = (function (jasmineGlobal) { } jasmineRequire = exports; } else { - if (typeof window !== 'undefined' && typeof window.toString === 'function' && window.toString() === '[object GjsGlobal]') { + if ( + typeof window !== 'undefined' && + typeof window.toString === 'function' && + window.toString() === '[object GjsGlobal]' + ) { jasmineGlobal = window; } jasmineRequire = jasmineGlobal.jasmineRequire = {}; @@ -187,7 +195,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @return {Env} */ j$.getEnv = function(options) { - var env = j$.currentEnv_ = j$.currentEnv_ || new j$.Env(options); + var env = (j$.currentEnv_ = j$.currentEnv_ || new j$.Env(options)); //jasmine. singletons in here (setTimeout blah blah). return env; }; @@ -197,7 +205,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { }; j$.isObject_ = function(value) { - return !j$.util.isUndefined(value) && value !== null && j$.isA_('Object', value); + return ( + !j$.util.isUndefined(value) && value !== null && j$.isA_('Object', value) + ); }; j$.isString_ = function(value) { @@ -217,7 +227,8 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { }; j$.isTypedArray_ = function(value) { - return j$.isA_('Float32Array', value) || + return ( + j$.isA_('Float32Array', value) || j$.isA_('Float64Array', value) || j$.isA_('Int16Array', value) || j$.isA_('Int32Array', value) || @@ -225,7 +236,8 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { j$.isA_('Uint16Array', value) || j$.isA_('Uint32Array', value) || j$.isA_('Uint8Array', value) || - j$.isA_('Uint8ClampedArray', value); + j$.isA_('Uint8ClampedArray', value) + ); }; j$.isA_ = function(typeName, value) { @@ -255,9 +267,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { j$.isDomNode = function(obj) { // Node is a function, because constructors - return typeof jasmineGlobal.Node !== 'undefined' ? - obj instanceof jasmineGlobal.Node : - obj !== null && + return typeof jasmineGlobal.Node !== 'undefined' + ? obj instanceof jasmineGlobal.Node + : obj !== null && typeof obj === 'object' && typeof obj.nodeType === 'number' && typeof obj.nodeName === 'string'; @@ -265,15 +277,25 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { }; j$.isMap = function(obj) { - return typeof jasmineGlobal.Map !== 'undefined' && obj.constructor === jasmineGlobal.Map; + return ( + typeof jasmineGlobal.Map !== 'undefined' && + obj.constructor === jasmineGlobal.Map + ); }; j$.isSet = function(obj) { - return typeof jasmineGlobal.Set !== 'undefined' && obj.constructor === jasmineGlobal.Set; + return ( + typeof jasmineGlobal.Set !== 'undefined' && + obj.constructor === jasmineGlobal.Set + ); }; j$.isPromise = function(obj) { - return typeof jasmineGlobal.Promise !== 'undefined' && !!obj && obj.constructor === jasmineGlobal.Promise; + return ( + typeof jasmineGlobal.Promise !== 'undefined' && + !!obj && + obj.constructor === jasmineGlobal.Promise + ); }; j$.isPromiseLike = function(obj) { @@ -285,7 +307,8 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return func.name; } - var matches = func.toString().match(/^\s*function\s*(\w+)\s*\(/) || + var matches = + func.toString().match(/^\s*function\s*(\w+)\s*\(/) || func.toString().match(/^\s*\[object\s*(\w+)Constructor\]/); return matches ? matches[1] : ''; @@ -318,7 +341,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @name jasmine.truthy * @function */ - j$.truthy = function() { return new j$.Truthy(); }; + j$.truthy = function() { + return new j$.Truthy(); + }; /** * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), @@ -326,7 +351,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @name jasmine.falsy * @function */ - j$.falsy = function() { return new j$.Falsy(); }; + j$.falsy = function() { + return new j$.Falsy(); + }; /** * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), @@ -334,7 +361,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @name jasmine.empty * @function */ - j$.empty = function() { return new j$.Empty(); }; + j$.empty = function() { + return new j$.Empty(); + }; /** * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), @@ -342,7 +371,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @name jasmine.notEmpty * @function */ - j$.notEmpty = function() { return new j$.NotEmpty(); }; + j$.notEmpty = function() { + return new j$.NotEmpty(); + }; /** * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), @@ -392,18 +423,18 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { if (!putativeSpy) { return false; } - return putativeSpy.and instanceof j$.SpyStrategy && - putativeSpy.calls instanceof j$.CallTracker; + return ( + putativeSpy.and instanceof j$.SpyStrategy && + putativeSpy.calls instanceof j$.CallTracker + ); }; }; getJasmineRequireObj().util = function(j$) { - var util = {}; util.inherit = function(childClass, parentClass) { - var Subclass = function() { - }; + var Subclass = function() {}; Subclass.prototype = parentClass.prototype; childClass.prototype = new Subclass(); }; @@ -412,7 +443,8 @@ getJasmineRequireObj().util = function(j$) { if (!str) { return str; } - return str.replace(/&/g, '&') + return str + .replace(/&/g, '&') .replace(//g, '>'); }; @@ -457,7 +489,7 @@ getJasmineRequireObj().util = function(j$) { util.cloneArgs = function(args) { var clonedArgs = []; var argsAsArray = j$.util.argsToArray(args); - for(var i = 0; i < argsAsArray.length; i++) { + for (var i = 0; i < argsAsArray.length; i++) { var str = Object.prototype.toString.apply(argsAsArray[i]), primitives = /^\[object (Boolean|String|RegExp|Number)/; @@ -499,7 +531,7 @@ getJasmineRequireObj().util = function(j$) { return Object.prototype.hasOwnProperty.call(obj, key); }; - util.errorWithStack = function errorWithStack () { + util.errorWithStack = function errorWithStack() { // Don't throw and catch if we don't have to, because it makes it harder // for users to debug their code with exception breakpoints. var error = new Error(); @@ -531,7 +563,7 @@ getJasmineRequireObj().util = function(j$) { return result; }; - }()); + })(); return util; }; @@ -544,13 +576,30 @@ getJasmineRequireObj().Spec = function(j$) { this.id = attrs.id; this.description = attrs.description || ''; this.queueableFn = attrs.queueableFn; - this.beforeAndAfterFns = attrs.beforeAndAfterFns || function() { return {befores: [], afters: []}; }; - this.userContext = attrs.userContext || function() { return {}; }; + this.beforeAndAfterFns = + attrs.beforeAndAfterFns || + function() { + return { befores: [], afters: [] }; + }; + this.userContext = + attrs.userContext || + function() { + return {}; + }; this.onStart = attrs.onStart || function() {}; - this.getSpecName = attrs.getSpecName || function() { return ''; }; - this.expectationResultFactory = attrs.expectationResultFactory || function() { }; + this.getSpecName = + attrs.getSpecName || + function() { + return ''; + }; + this.expectationResultFactory = + attrs.expectationResultFactory || function() {}; this.queueRunnerFactory = attrs.queueRunnerFactory || function() {}; - this.catchingExceptions = attrs.catchingExceptions || function() { return true; }; + this.catchingExceptions = + attrs.catchingExceptions || + function() { + return true; + }; this.throwOnExpectationFailure = !!attrs.throwOnExpectationFailure; this.timer = attrs.timer || j$.noopTimer; @@ -628,12 +677,15 @@ getJasmineRequireObj().Spec = function(j$) { isLeaf: true, queueableFns: regularFns, cleanupFns: fns.afters, - onException: function () { + onException: function() { self.onException.apply(self, arguments); }, onComplete: function() { self.result.duration = self.timer.elapsed(); - onComplete(self.result.status === 'failed' && new j$.StopExecutionError('spec failed')); + onComplete( + self.result.status === 'failed' && + new j$.StopExecutionError('spec failed') + ); }, userContext: this.userContext() }; @@ -659,13 +711,17 @@ getJasmineRequireObj().Spec = function(j$) { return; } - this.addExpectationResult(false, { - matcherName: '', - passed: false, - expected: '', - actual: '', - error: e - }, true); + this.addExpectationResult( + false, + { + matcherName: '', + passed: false, + expected: '', + actual: '', + error: e + }, + true + ); }; Spec.prototype.pend = function(message) { @@ -704,13 +760,16 @@ getJasmineRequireObj().Spec = function(j$) { if (typeof deprecation === 'string') { deprecation = { message: deprecation }; } - this.result.deprecationWarnings.push(this.expectationResultFactory(deprecation)); + this.result.deprecationWarnings.push( + this.expectationResultFactory(deprecation) + ); }; var extractCustomPendingMessage = function(e) { var fullMessage = e.toString(), - boilerplateStart = fullMessage.indexOf(Spec.pendingSpecExceptionMessage), - boilerplateEnd = boilerplateStart + Spec.pendingSpecExceptionMessage.length; + boilerplateStart = fullMessage.indexOf(Spec.pendingSpecExceptionMessage), + boilerplateEnd = + boilerplateStart + Spec.pendingSpecExceptionMessage.length; return fullMessage.substr(boilerplateEnd); }; @@ -718,7 +777,11 @@ getJasmineRequireObj().Spec = function(j$) { Spec.pendingSpecExceptionMessage = '=> marked Pending'; Spec.isPendingSpecException = function(e) { - return !!(e && e.toString && e.toString().indexOf(Spec.pendingSpecExceptionMessage) !== -1); + return !!( + e && + e.toString && + e.toString().indexOf(Spec.pendingSpecExceptionMessage) !== -1 + ); }; return Spec; @@ -734,7 +797,7 @@ if (typeof window == void 0 && typeof exports == 'object') { getJasmineRequireObj().Order = function() { function Order(options) { this.random = 'random' in options ? options.random : true; - var seed = this.seed = options.seed || generateSeed(); + var seed = (this.seed = options.seed || generateSeed()); this.sort = this.random ? randomOrder : naturalOrder; function naturalOrder(items) { @@ -760,17 +823,16 @@ getJasmineRequireObj().Order = function() { function jenkinsHash(key) { var hash, i; - for(hash = i = 0; i < key.length; ++i) { + for (hash = i = 0; i < key.length; ++i) { hash += key.charCodeAt(i); - hash += (hash << 10); - hash ^= (hash >> 6); + hash += hash << 10; + hash ^= hash >> 6; } - hash += (hash << 3); - hash ^= (hash >> 11); - hash += (hash << 15); + hash += hash << 3; + hash ^= hash >> 11; + hash += hash << 15; return hash; } - } return Order; @@ -795,7 +857,13 @@ getJasmineRequireObj().Env = function(j$) { var realSetTimeout = global.setTimeout; var realClearTimeout = global.clearTimeout; var clearStack = j$.getClearStack(global); - this.clock = new j$.Clock(global, function () { return new j$.DelayedFunctionScheduler(); }, new j$.MockDate(global)); + this.clock = new j$.Clock( + global, + function() { + return new j$.DelayedFunctionScheduler(); + }, + new j$.MockDate(global) + ); var runnableResources = {}; @@ -888,7 +956,13 @@ getJasmineRequireObj().Env = function(j$) { if (!options.suppressLoadErrors) { installGlobalErrors(); - globalErrors.pushListener(function(message, filename, lineno, colNo, err) { + globalErrors.pushListener(function( + message, + filename, + lineno, + colNo, + err + ) { topSuite.result.failedExpectations.push({ passed: false, globalErrorType: 'load', @@ -932,11 +1006,15 @@ getJasmineRequireObj().Env = function(j$) { } if (configuration.hasOwnProperty('Promise')) { - if (typeof configuration.Promise.resolve === 'function' && - typeof configuration.Promise.reject === 'function') { + if ( + typeof configuration.Promise.resolve === 'function' && + typeof configuration.Promise.reject === 'function' + ) { customPromise = configuration.Promise; } else { - throw new Error('Custom promise library missing `resolve`/`reject` functions'); + throw new Error( + 'Custom promise library missing `resolve`/`reject` functions' + ); } } }; @@ -957,34 +1035,47 @@ getJasmineRequireObj().Env = function(j$) { Object.defineProperty(this, 'specFilter', { get: function() { - self.deprecated('Getting specFilter directly from Env is deprecated and will be removed in a future version of Jasmine, please check the specFilter option from `configuration`'); + self.deprecated( + 'Getting specFilter directly from Env is deprecated and will be removed in a future version of Jasmine, please check the specFilter option from `configuration`' + ); return config.specFilter; }, set: function(val) { - self.deprecated('Setting specFilter directly on Env is deprecated and will be removed in a future version of Jasmine, please use the specFilter option in `configure`'); + self.deprecated( + 'Setting specFilter directly on Env is deprecated and will be removed in a future version of Jasmine, please use the specFilter option in `configure`' + ); config.specFilter = val; } }); this.addSpyStrategy = function(name, fn) { - if(!currentRunnable()) { - throw new Error('Custom spy strategies must be added in a before function or a spec'); + if (!currentRunnable()) { + throw new Error( + 'Custom spy strategies must be added in a before function or a spec' + ); } runnableResources[currentRunnable().id].customSpyStrategies[name] = fn; }; this.addCustomEqualityTester = function(tester) { - if(!currentRunnable()) { - throw new Error('Custom Equalities must be added in a before function or a spec'); + if (!currentRunnable()) { + throw new Error( + 'Custom Equalities must be added in a before function or a spec' + ); } - runnableResources[currentRunnable().id].customEqualityTesters.push(tester); + runnableResources[currentRunnable().id].customEqualityTesters.push( + tester + ); }; this.addMatchers = function(matchersToAdd) { - if(!currentRunnable()) { - throw new Error('Matchers must be added in a before function or a spec'); + if (!currentRunnable()) { + throw new Error( + 'Matchers must be added in a before function or a spec' + ); } - var customMatchers = runnableResources[currentRunnable().id].customMatchers; + var customMatchers = + runnableResources[currentRunnable().id].customMatchers; for (var matcherName in matchersToAdd) { customMatchers[matcherName] = matchersToAdd[matcherName]; } @@ -1031,19 +1122,28 @@ getJasmineRequireObj().Env = function(j$) { }; var defaultResourcesForRunnable = function(id, parentRunnableId) { - var resources = {spies: [], customEqualityTesters: [], customMatchers: {}, customSpyStrategies: {}}; + var resources = { + spies: [], + customEqualityTesters: [], + customMatchers: {}, + customSpyStrategies: {} + }; - if(runnableResources[parentRunnableId]) { - resources.customEqualityTesters = j$.util.clone(runnableResources[parentRunnableId].customEqualityTesters); - resources.customMatchers = j$.util.clone(runnableResources[parentRunnableId].customMatchers); + if (runnableResources[parentRunnableId]) { + resources.customEqualityTesters = j$.util.clone( + runnableResources[parentRunnableId].customEqualityTesters + ); + resources.customMatchers = j$.util.clone( + runnableResources[parentRunnableId].customMatchers + ); } runnableResources[id] = resources; }; var clearResourcesForRunnable = function(id) { - spyRegistry.clearSpies(); - delete runnableResources[id]; + spyRegistry.clearSpies(); + delete runnableResources[id]; }; var beforeAndAfterFns = function(suite) { @@ -1051,7 +1151,7 @@ getJasmineRequireObj().Env = function(j$) { var befores = [], afters = []; - while(suite) { + while (suite) { befores = befores.concat(suite.beforeFns); afters = afters.concat(suite.afterFns); @@ -1067,7 +1167,7 @@ getJasmineRequireObj().Env = function(j$) { var getSpecName = function(spec, suite) { var fullName = [spec.description], - suiteFullName = suite.getFullName(); + suiteFullName = suite.getFullName(); if (suiteFullName !== '') { fullName.unshift(suiteFullName); @@ -1077,13 +1177,13 @@ getJasmineRequireObj().Env = function(j$) { // TODO: we may just be able to pass in the fn instead of wrapping here var buildExpectationResult = j$.buildExpectationResult, - exceptionFormatter = new j$.ExceptionFormatter(), - expectationResultFactory = function(attrs) { - attrs.messageFormatter = exceptionFormatter.message; - attrs.stackFormatter = exceptionFormatter.stack; + exceptionFormatter = new j$.ExceptionFormatter(), + expectationResultFactory = function(attrs) { + attrs.messageFormatter = exceptionFormatter.message; + attrs.stackFormatter = exceptionFormatter.stack; - return buildExpectationResult(attrs); - }; + return buildExpectationResult(attrs); + }; /** * Sets whether Jasmine should throw an Error when an expectation fails. @@ -1094,12 +1194,16 @@ getJasmineRequireObj().Env = function(j$) { * @deprecated Use the `oneFailurePerSpec` option with {@link Env#configure} */ this.throwOnExpectationFailure = function(value) { - this.deprecated('Setting throwOnExpectationFailure directly on Env is deprecated and will be removed in a future version of Jasmine, please use the oneFailurePerSpec option in `configure`'); - this.configure({oneFailurePerSpec: !!value}); + this.deprecated( + 'Setting throwOnExpectationFailure directly on Env is deprecated and will be removed in a future version of Jasmine, please use the oneFailurePerSpec option in `configure`' + ); + this.configure({ oneFailurePerSpec: !!value }); }; this.throwingExpectationFailures = function() { - this.deprecated('Getting throwingExpectationFailures directly from Env is deprecated and will be removed in a future version of Jasmine, please check the oneFailurePerSpec option from `configuration`'); + this.deprecated( + 'Getting throwingExpectationFailures directly from Env is deprecated and will be removed in a future version of Jasmine, please check the oneFailurePerSpec option from `configuration`' + ); return config.oneFailurePerSpec; }; @@ -1111,12 +1215,16 @@ getJasmineRequireObj().Env = function(j$) { * @deprecated Use the `failFast` option with {@link Env#configure} */ this.stopOnSpecFailure = function(value) { - this.deprecated('Setting stopOnSpecFailure directly is deprecated and will be removed in a future version of Jasmine, please use the failFast option in `configure`'); - this.configure({failFast: !!value}); + this.deprecated( + 'Setting stopOnSpecFailure directly is deprecated and will be removed in a future version of Jasmine, please use the failFast option in `configure`' + ); + this.configure({ failFast: !!value }); }; this.stoppingOnSpecFailure = function() { - this.deprecated('Getting stoppingOnSpecFailure directly from Env is deprecated and will be removed in a future version of Jasmine, please check the failFast option from `configuration`'); + this.deprecated( + 'Getting stoppingOnSpecFailure directly from Env is deprecated and will be removed in a future version of Jasmine, please check the failFast option from `configuration`' + ); return config.failFast; }; @@ -1128,12 +1236,16 @@ getJasmineRequireObj().Env = function(j$) { * @deprecated Use the `random` option with {@link Env#configure} */ this.randomizeTests = function(value) { - this.deprecated('Setting randomizeTests directly is deprecated and will be removed in a future version of Jasmine, please use the random option in `configure`'); + this.deprecated( + 'Setting randomizeTests directly is deprecated and will be removed in a future version of Jasmine, please use the random option in `configure`' + ); config.random = !!value; }; this.randomTests = function() { - this.deprecated('Getting randomTests directly from Env is deprecated and will be removed in a future version of Jasmine, please check the random option from `configuration`'); + this.deprecated( + 'Getting randomTests directly from Env is deprecated and will be removed in a future version of Jasmine, please check the random option from `configuration`' + ); return config.random; }; @@ -1145,7 +1257,9 @@ getJasmineRequireObj().Env = function(j$) { * @deprecated Use the `seed` option with {@link Env#configure} */ this.seed = function(value) { - this.deprecated('Setting seed directly is deprecated and will be removed in a future version of Jasmine, please use the seed option in `configure`'); + this.deprecated( + 'Setting seed directly is deprecated and will be removed in a future version of Jasmine, please use the seed option in `configure`' + ); if (value) { config.seed = value; } @@ -1153,7 +1267,9 @@ getJasmineRequireObj().Env = function(j$) { }; this.hidingDisabled = function(value) { - this.deprecated('Getting hidingDisabled directly from Env is deprecated and will be removed in a future version of Jasmine, please check the hideDisabled option from `configuration`'); + this.deprecated( + 'Getting hidingDisabled directly from Env is deprecated and will be removed in a future version of Jasmine, please check the hideDisabled option from `configuration`' + ); return config.hideDisabled; }; @@ -1162,14 +1278,19 @@ getJasmineRequireObj().Env = function(j$) { * @function */ this.hideDisabled = function(value) { - this.deprecated('Setting hideDisabled directly is deprecated and will be removed in a future version of Jasmine, please use the hideDisabled option in `configure`'); + this.deprecated( + 'Setting hideDisabled directly is deprecated and will be removed in a future version of Jasmine, please use the hideDisabled option in `configure`' + ); config.hideDisabled = !!value; }; this.deprecated = function(deprecation) { var runnable = currentRunnable() || topSuite; runnable.addDeprecationWarning(deprecation); - if(typeof console !== 'undefined' && typeof console.error === 'function') { + if ( + typeof console !== 'undefined' && + typeof console.error === 'function' + ) { console.error('DEPRECATION:', deprecation); } }; @@ -1182,13 +1303,18 @@ getJasmineRequireObj().Env = function(j$) { failFast = config.failFast; } options.clearStack = options.clearStack || clearStack; - options.timeout = {setTimeout: realSetTimeout, clearTimeout: realClearTimeout}; + options.timeout = { + setTimeout: realSetTimeout, + clearTimeout: realClearTimeout + }; options.fail = self.fail; options.globalErrors = globalErrors; options.completeOnFirstError = failFast; - options.onException = options.onException || function(e) { - (currentRunnable() || topSuite).onException(e); - }; + options.onException = + options.onException || + function(e) { + (currentRunnable() || topSuite).onException(e); + }; options.deprecated = self.deprecated; new j$.QueueRunner(options).execute(args); @@ -1214,78 +1340,80 @@ getJasmineRequireObj().Env = function(j$) { * @interface Reporter * @see custom_reporter */ - var reporter = new j$.ReportDispatcher([ - /** - * `jasmineStarted` is called after all of the specs have been loaded, but just before execution starts. - * @function - * @name Reporter#jasmineStarted - * @param {JasmineStartedInfo} suiteInfo Information about the full Jasmine suite that is being run - * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. - * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. - * @see async - */ - 'jasmineStarted', - /** - * When the entire suite has finished execution `jasmineDone` is called - * @function - * @name Reporter#jasmineDone - * @param {JasmineDoneInfo} suiteInfo Information about the full Jasmine suite that just finished running. - * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. - * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. - * @see async - */ - 'jasmineDone', - /** - * `suiteStarted` is invoked when a `describe` starts to run - * @function - * @name Reporter#suiteStarted - * @param {SuiteResult} result Information about the individual {@link describe} being run - * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. - * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. - * @see async - */ - 'suiteStarted', - /** - * `suiteDone` is invoked when all of the child specs and suites for a given suite have been run - * - * While jasmine doesn't require any specific functions, not defining a `suiteDone` will make it impossible for a reporter to know when a suite has failures in an `afterAll`. - * @function - * @name Reporter#suiteDone - * @param {SuiteResult} result - * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. - * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. - * @see async - */ - 'suiteDone', - /** - * `specStarted` is invoked when an `it` starts to run (including associated `beforeEach` functions) - * @function - * @name Reporter#specStarted - * @param {SpecResult} result Information about the individual {@link it} being run - * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. - * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. - * @see async - */ - 'specStarted', - /** - * `specDone` is invoked when an `it` and its associated `beforeEach` and `afterEach` functions have been run. - * - * While jasmine doesn't require any specific functions, not defining a `specDone` will make it impossible for a reporter to know when a spec has failed. - * @function - * @name Reporter#specDone - * @param {SpecResult} result - * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. - * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. - * @see async - */ - 'specDone' - ], queueRunnerFactory); + var reporter = new j$.ReportDispatcher( + [ + /** + * `jasmineStarted` is called after all of the specs have been loaded, but just before execution starts. + * @function + * @name Reporter#jasmineStarted + * @param {JasmineStartedInfo} suiteInfo Information about the full Jasmine suite that is being run + * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. + * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. + * @see async + */ + 'jasmineStarted', + /** + * When the entire suite has finished execution `jasmineDone` is called + * @function + * @name Reporter#jasmineDone + * @param {JasmineDoneInfo} suiteInfo Information about the full Jasmine suite that just finished running. + * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. + * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. + * @see async + */ + 'jasmineDone', + /** + * `suiteStarted` is invoked when a `describe` starts to run + * @function + * @name Reporter#suiteStarted + * @param {SuiteResult} result Information about the individual {@link describe} being run + * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. + * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. + * @see async + */ + 'suiteStarted', + /** + * `suiteDone` is invoked when all of the child specs and suites for a given suite have been run + * + * While jasmine doesn't require any specific functions, not defining a `suiteDone` will make it impossible for a reporter to know when a suite has failures in an `afterAll`. + * @function + * @name Reporter#suiteDone + * @param {SuiteResult} result + * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. + * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. + * @see async + */ + 'suiteDone', + /** + * `specStarted` is invoked when an `it` starts to run (including associated `beforeEach` functions) + * @function + * @name Reporter#specStarted + * @param {SpecResult} result Information about the individual {@link it} being run + * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. + * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. + * @see async + */ + 'specStarted', + /** + * `specDone` is invoked when an `it` and its associated `beforeEach` and `afterEach` functions have been run. + * + * While jasmine doesn't require any specific functions, not defining a `specDone` will make it impossible for a reporter to know when a spec has failed. + * @function + * @name Reporter#specDone + * @param {SpecResult} result + * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. + * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. + * @see async + */ + 'specDone' + ], + queueRunnerFactory + ); this.execute = function(runnablesToRun) { - var self = this; installGlobalErrors(); - if(!runnablesToRun) { + if (!runnablesToRun) { if (focusedRunnables.length) { runnablesToRun = focusedRunnables; } else { @@ -1330,8 +1458,10 @@ getJasmineRequireObj().Env = function(j$) { } }); - if(!processor.processTree().valid) { - throw new Error('Invalid order: would cause a beforeAll or afterAll to be run multiple times'); + if (!processor.processTree().valid) { + throw new Error( + 'Invalid order: would cause a beforeAll or afterAll to be run multiple times' + ); } /** @@ -1340,47 +1470,53 @@ getJasmineRequireObj().Env = function(j$) { * @property {Int} totalSpecsDefined - The total number of specs defined in this suite. * @property {Order} order - Information about the ordering (random or not) of this execution of the suite. */ - reporter.jasmineStarted({ - totalSpecsDefined: totalSpecsDefined, - order: order - }, function() { - currentlyExecutingSuites.push(topSuite); + reporter.jasmineStarted( + { + totalSpecsDefined: totalSpecsDefined, + order: order + }, + function() { + currentlyExecutingSuites.push(topSuite); - processor.execute(function () { - clearResourcesForRunnable(topSuite.id); - currentlyExecutingSuites.pop(); - var overallStatus, incompleteReason; + processor.execute(function() { + clearResourcesForRunnable(topSuite.id); + currentlyExecutingSuites.pop(); + var overallStatus, incompleteReason; - if (hasFailures || topSuite.result.failedExpectations.length > 0) { - overallStatus = 'failed'; - } else if (focusedRunnables.length > 0) { - overallStatus = 'incomplete'; - incompleteReason = 'fit() or fdescribe() was found'; - } else if (totalSpecsDefined === 0) { - overallStatus = 'incomplete'; - incompleteReason = 'No specs found'; - } else { - overallStatus = 'passed'; - } + if (hasFailures || topSuite.result.failedExpectations.length > 0) { + overallStatus = 'failed'; + } else if (focusedRunnables.length > 0) { + overallStatus = 'incomplete'; + incompleteReason = 'fit() or fdescribe() was found'; + } else if (totalSpecsDefined === 0) { + overallStatus = 'incomplete'; + incompleteReason = 'No specs found'; + } else { + overallStatus = 'passed'; + } - /** - * Information passed to the {@link Reporter#jasmineDone} event. - * @typedef JasmineDoneInfo - * @property {OverallStatus} overallStatus - The overall result of the suite: 'passed', 'failed', or 'incomplete'. - * @property {IncompleteReason} incompleteReason - Explanation of why the suite was incomplete. - * @property {Order} order - Information about the ordering (random or not) of this execution of the suite. - * @property {Expectation[]} failedExpectations - List of expectations that failed in an {@link afterAll} at the global level. - * @property {Expectation[]} deprecationWarnings - List of deprecation warnings that occurred at the global level. - */ - reporter.jasmineDone({ - overallStatus: overallStatus, - incompleteReason: incompleteReason, - order: order, - failedExpectations: topSuite.result.failedExpectations, - deprecationWarnings: topSuite.result.deprecationWarnings - }, function() {}); - }); - }); + /** + * Information passed to the {@link Reporter#jasmineDone} event. + * @typedef JasmineDoneInfo + * @property {OverallStatus} overallStatus - The overall result of the suite: 'passed', 'failed', or 'incomplete'. + * @property {IncompleteReason} incompleteReason - Explanation of why the suite was incomplete. + * @property {Order} order - Information about the ordering (random or not) of this execution of the suite. + * @property {Expectation[]} failedExpectations - List of expectations that failed in an {@link afterAll} at the global level. + * @property {Expectation[]} deprecationWarnings - List of deprecation warnings that occurred at the global level. + */ + reporter.jasmineDone( + { + overallStatus: overallStatus, + incompleteReason: incompleteReason, + order: order, + failedExpectations: topSuite.result.failedExpectations, + deprecationWarnings: topSuite.result.deprecationWarnings + }, + function() {} + ); + }); + } + ); }; /** @@ -1431,8 +1567,10 @@ getJasmineRequireObj().Env = function(j$) { var spyRegistry = new j$.SpyRegistry({ currentSpies: function() { - if(!currentRunnable()) { - throw new Error('Spies must be created in a before function or a spec'); + if (!currentRunnable()) { + throw new Error( + 'Spies must be created in a before function or a spec' + ); } return runnableResources[currentRunnable().id].spies; }, @@ -1472,20 +1610,26 @@ getJasmineRequireObj().Env = function(j$) { var ensureIsFunction = function(fn, caller) { if (!j$.isFunction_(fn)) { - throw new Error(caller + ' expects a function argument; received ' + j$.getType_(fn)); + throw new Error( + caller + ' expects a function argument; received ' + j$.getType_(fn) + ); } }; var ensureIsFunctionOrAsync = function(fn, caller) { if (!j$.isFunction_(fn) && !j$.isAsyncFunction_(fn)) { - throw new Error(caller + ' expects a function argument; received ' + j$.getType_(fn)); + throw new Error( + caller + ' expects a function argument; received ' + j$.getType_(fn) + ); } }; function ensureIsNotNested(method) { var runnable = currentRunnable(); if (runnable !== null && runnable !== undefined) { - throw new Error('\'' + method + '\' should only be used in \'describe\' function'); + throw new Error( + "'" + method + "' should only be used in 'describe' function" + ); } } @@ -1599,7 +1743,9 @@ getJasmineRequireObj().Env = function(j$) { description: description, expectationResultFactory: expectationResultFactory, queueRunnerFactory: queueRunnerFactory, - userContext: function() { return suite.clonedSharedUserContext(); }, + userContext: function() { + return suite.clonedSharedUserContext(); + }, queueableFn: { fn: fn, timeout: timeout || 0 @@ -1666,7 +1812,9 @@ getJasmineRequireObj().Env = function(j$) { this.expect = function(actual) { if (!currentRunnable()) { - throw new Error('\'expect\' was used when there was no current spec, this could be because an asynchronous test timed out'); + throw new Error( + "'expect' was used when there was no current spec, this could be because an asynchronous test timed out" + ); } return currentRunnable().expect(actual); @@ -1674,7 +1822,9 @@ getJasmineRequireObj().Env = function(j$) { this.expectAsync = function(actual) { if (!currentRunnable()) { - throw new Error('\'expectAsync\' was used when there was no current spec, this could be because an asynchronous test timed out'); + throw new Error( + "'expectAsync' was used when there was no current spec, this could be because an asynchronous test timed out" + ); } return currentRunnable().expectAsync(actual); @@ -1719,7 +1869,7 @@ getJasmineRequireObj().Env = function(j$) { this.pending = function(message) { var fullMessage = j$.Spec.pendingSpecExceptionMessage; - if(message) { + if (message) { fullMessage += message; } throw fullMessage; @@ -1727,7 +1877,9 @@ getJasmineRequireObj().Env = function(j$) { this.fail = function(error) { if (!currentRunnable()) { - throw new Error('\'fail\' was used when there was no current spec, this could be because an asynchronous test timed out'); + throw new Error( + "'fail' was used when there was no current spec, this could be because an asynchronous test timed out" + ); } var message = 'Failed'; @@ -1770,7 +1922,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { */ function JsApiReporter(options) { var timer = options.timer || j$.noopTimer, - status = 'loaded'; + status = 'loaded'; this.started = false; this.finished = false; @@ -1880,7 +2032,6 @@ getJasmineRequireObj().JsApiReporter = function(j$) { this.executionTime = function() { return executionTime; }; - } return JsApiReporter; @@ -2165,7 +2316,6 @@ getJasmineRequireObj().Truthy = function(j$) { }; getJasmineRequireObj().CallTracker = function(j$) { - /** * @namespace Spy#calls */ @@ -2174,7 +2324,7 @@ getJasmineRequireObj().CallTracker = function(j$) { var opts = {}; this.track = function(context) { - if(opts.cloneArgs) { + if (opts.cloneArgs) { context.args = j$.util.cloneArgs(context.args); } calls.push(context); @@ -2230,7 +2380,7 @@ getJasmineRequireObj().CallTracker = function(j$) { */ this.allArgs = function() { var callArgs = []; - for(var i = 0; i < calls.length; i++) { + for (var i = 0; i < calls.length; i++) { callArgs.push(calls[i].args); } @@ -2274,7 +2424,6 @@ getJasmineRequireObj().CallTracker = function(j$) { this.saveArgumentsByValue = function() { opts.cloneArgs = true; }; - } return CallTracker; @@ -2285,8 +2434,8 @@ getJasmineRequireObj().clearStack = function(j$) { function messageChannelImpl(global, setTimeout) { var channel = new global.MessageChannel(), - head = {}, - tail = head; + head = {}, + tail = head; var taskRunning = false; channel.port1.onmessage = function() { @@ -2324,7 +2473,7 @@ getJasmineRequireObj().clearStack = function(j$) { var currentCallCount = 0; var realSetTimeout = global.setTimeout; var setTimeoutImpl = function clearStack(fn) { - Function.prototype.apply.apply(realSetTimeout, [global, [fn, 0]]); + Function.prototype.apply.apply(realSetTimeout, [global, [fn, 0]]); }; if (j$.isFunction_(global.setImmediate)) { @@ -2351,9 +2500,11 @@ getJasmineRequireObj().clearStack = function(j$) { }; getJasmineRequireObj().Clock = function() { - /* global process */ - var NODE_JS = typeof process !== 'undefined' && process.versions && typeof process.versions.node === 'string'; + var NODE_JS = + typeof process !== 'undefined' && + process.versions && + typeof process.versions.node === 'string'; /** * _Note:_ Do not construct this directly, Jasmine will make one during booting. You can get the current clock with {@link jasmine.clock}. @@ -2387,8 +2538,10 @@ getJasmineRequireObj().Clock = function() { * @return {Clock} */ self.install = function() { - if(!originalTimingFunctionsIntact()) { - throw new Error('Jasmine Clock was unable to install over custom global timer functions. Is the clock already installed?'); + if (!originalTimingFunctionsIntact()) { + throw new Error( + 'Jasmine Clock was unable to install over custom global timer functions. Is the clock already installed?' + ); } replace(global, fakeTimingFunctions); timer = fakeTimingFunctions; @@ -2440,11 +2593,17 @@ getJasmineRequireObj().Clock = function() { }; self.setTimeout = function(fn, delay, params) { - return Function.prototype.apply.apply(timer.setTimeout, [global, arguments]); + return Function.prototype.apply.apply(timer.setTimeout, [ + global, + arguments + ]); }; self.setInterval = function(fn, delay, params) { - return Function.prototype.apply.apply(timer.setInterval, [global, arguments]); + return Function.prototype.apply.apply(timer.setInterval, [ + global, + arguments + ]); }; self.clearTimeout = function(id) { @@ -2463,19 +2622,25 @@ getJasmineRequireObj().Clock = function() { */ self.tick = function(millis) { if (installed) { - delayedFunctionScheduler.tick(millis, function(millis) { mockDate.tick(millis); }); + delayedFunctionScheduler.tick(millis, function(millis) { + mockDate.tick(millis); + }); } else { - throw new Error('Mock clock is not installed, use jasmine.clock().install()'); + throw new Error( + 'Mock clock is not installed, use jasmine.clock().install()' + ); } }; return self; function originalTimingFunctionsIntact() { - return global.setTimeout === realTimingFunctions.setTimeout && + return ( + global.setTimeout === realTimingFunctions.setTimeout && global.clearTimeout === realTimingFunctions.clearTimeout && global.setInterval === realTimingFunctions.setInterval && - global.clearInterval === realTimingFunctions.clearInterval; + global.clearInterval === realTimingFunctions.clearInterval + ); } function replace(dest, source) { @@ -2486,12 +2651,22 @@ getJasmineRequireObj().Clock = function() { function setTimeout(fn, delay) { if (!NODE_JS) { - return delayedFunctionScheduler.scheduleFunction(fn, delay, argSlice(arguments, 2)); + return delayedFunctionScheduler.scheduleFunction( + fn, + delay, + argSlice(arguments, 2) + ); } var timeout = new FakeTimeout(); - delayedFunctionScheduler.scheduleFunction(fn, delay, argSlice(arguments, 2), false, timeout); + delayedFunctionScheduler.scheduleFunction( + fn, + delay, + argSlice(arguments, 2), + false, + timeout + ); return timeout; } @@ -2502,12 +2677,23 @@ getJasmineRequireObj().Clock = function() { function setInterval(fn, interval) { if (!NODE_JS) { - return delayedFunctionScheduler.scheduleFunction(fn, interval, argSlice(arguments, 2), true); + return delayedFunctionScheduler.scheduleFunction( + fn, + interval, + argSlice(arguments, 2), + true + ); } var timeout = new FakeTimeout(); - delayedFunctionScheduler.scheduleFunction(fn, interval, argSlice(arguments, 2), true, timeout); + delayedFunctionScheduler.scheduleFunction( + fn, + interval, + argSlice(arguments, 2), + true, + timeout + ); return timeout; } @@ -2526,11 +2712,11 @@ getJasmineRequireObj().Clock = function() { */ function FakeTimeout() {} - FakeTimeout.prototype.ref = function () { + FakeTimeout.prototype.ref = function() { return this; }; - FakeTimeout.prototype.unref = function () { + FakeTimeout.prototype.unref = function() { return this; }; @@ -2554,11 +2740,20 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { currentTime = endTime; }; - self.scheduleFunction = function(funcToCall, millis, params, recurring, timeoutKey, runAtMillis) { + self.scheduleFunction = function( + funcToCall, + millis, + params, + recurring, + timeoutKey, + runAtMillis + ) { var f; - if (typeof(funcToCall) === 'string') { + if (typeof funcToCall === 'string') { /* jshint evil: true */ - f = function() { return eval(funcToCall); }; + f = function() { + return eval(funcToCall); + }; /* jshint evil: false */ } else { f = funcToCall; @@ -2566,7 +2761,7 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { millis = millis || 0; timeoutKey = timeoutKey || ++delayedFnCount; - runAtMillis = runAtMillis || (currentTime + millis); + runAtMillis = runAtMillis || currentTime + millis; var funcToSchedule = { runAtMillis: runAtMillis, @@ -2582,7 +2777,7 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { } else { scheduledFunctions[runAtMillis] = [funcToSchedule]; scheduledLookup.push(runAtMillis); - scheduledLookup.sort(function (a, b) { + scheduledLookup.sort(function(a, b) { return a - b; }); } @@ -2595,7 +2790,7 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { for (var runAtMillis in scheduledFunctions) { var funcs = scheduledFunctions[runAtMillis]; - var i = indexOfFirstToPass(funcs, function (func) { + var i = indexOfFirstToPass(funcs, function(func) { return func.timeoutKey === timeoutKey; }); @@ -2631,7 +2826,7 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { function deleteFromLookup(key) { var value = Number(key); - var i = indexOfFirstToPass(scheduledLookup, function (millis) { + var i = indexOfFirstToPass(scheduledLookup, function(millis) { return millis === value; }); @@ -2641,12 +2836,14 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { } function reschedule(scheduledFn) { - self.scheduleFunction(scheduledFn.funcToCall, + self.scheduleFunction( + scheduledFn.funcToCall, scheduledFn.millis, scheduledFn.params, true, scheduledFn.timeoutKey, - scheduledFn.runAtMillis + scheduledFn.millis); + scheduledFn.runAtMillis + scheduledFn.millis + ); } function forEachFunction(funcsToRun, callback) { @@ -2687,11 +2884,13 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { funcToRun.funcToCall.apply(null, funcToRun.params || []); }); deletedKeys = []; - } while (scheduledLookup.length > 0 && - // checking first if we're out of time prevents setTimeout(0) - // scheduled in a funcToRun from forcing an extra iteration - currentTime !== endTime && - scheduledLookup[0] <= endTime); + } while ( + scheduledLookup.length > 0 && + // checking first if we're out of time prevents setTimeout(0) + // scheduled in a funcToRun from forcing an extra iteration + currentTime !== endTime && + scheduledLookup[0] <= endTime + ); // ran out of functions to call, but still time left on the clock if (currentTime !== endTime) { @@ -2713,9 +2912,20 @@ getJasmineRequireObj().errors = function() { ExpectationFailed: ExpectationFailed }; }; -getJasmineRequireObj().ExceptionFormatter = function(j$) { - var ignoredProperties = ['name', 'message', 'stack', 'fileName', 'sourceURL', 'line', 'lineNumber', 'column', 'description', 'jasmineMessage']; +getJasmineRequireObj().ExceptionFormatter = function(j$) { + var ignoredProperties = [ + 'name', + 'message', + 'stack', + 'fileName', + 'sourceURL', + 'line', + 'lineNumber', + 'column', + 'description', + 'jasmineMessage' + ]; function ExceptionFormatter(options) { var jasmineFile = (options && options.jasmineFile) || j$.util.jasmineFile(); @@ -2764,7 +2974,8 @@ getJasmineRequireObj().ExceptionFormatter = function(j$) { function filterJasmine(stackTrace) { var result = [], - jasmineMarker = stackTrace.style === 'webkit' ? '' : ' at '; + jasmineMarker = + stackTrace.style === 'webkit' ? '' : ' at '; stackTrace.frames.forEach(function(frame) { if (frame.file && frame.file !== jasmineFile) { @@ -2806,7 +3017,9 @@ getJasmineRequireObj().ExceptionFormatter = function(j$) { getJasmineRequireObj().Expectation = function(j$) { var promiseForMessage = { - jasmineToString: function() { return 'a promise'; } + jasmineToString: function() { + return 'a promise'; + } }; /** @@ -2818,7 +3031,10 @@ getJasmineRequireObj().Expectation = function(j$) { var customMatchers = options.customMatchers || {}; for (var matcherName in customMatchers) { - this[matcherName] = wrapSyncCompare(matcherName, customMatchers[matcherName]); + this[matcherName] = wrapSyncCompare( + matcherName, + customMatchers[matcherName] + ); } } @@ -2856,7 +3072,9 @@ getJasmineRequireObj().Expectation = function(j$) { this.expector = new j$.Expector(options); if (!global.Promise) { - throw new Error('expectAsync is unavailable because the environment does not support promises.'); + throw new Error( + 'expectAsync is unavailable because the environment does not support promises.' + ); } if (!j$.isPromiseLike(this.expector.actual)) { @@ -2906,9 +3124,11 @@ getJasmineRequireObj().Expectation = function(j$) { // frames that are relevant to the user instead of just parts of Jasmine. var errorForStack = j$.util.errorWithStack(); - return this.expector.compare(name, matcherFactory, arguments).then(function(result) { - self.expector.processResult(result, errorForStack, promiseForMessage); - }); + return this.expector + .compare(name, matcherFactory, arguments) + .then(function(result) { + self.expector.processResult(result, errorForStack, promiseForMessage); + }); }; } @@ -3005,7 +3225,12 @@ getJasmineRequireObj().ExpectationFilterChain = function() { return this.callFirst_('selectComparisonFunc', arguments).result; }; - ExpectationFilterChain.prototype.buildFailureMessage = function(result, matcherName, args, util) { + ExpectationFilterChain.prototype.buildFailureMessage = function( + result, + matcherName, + args, + util + ) { return this.callFirst_('buildFailureMessage', arguments).result; }; @@ -3032,7 +3257,7 @@ getJasmineRequireObj().ExpectationFilterChain = function() { }; } - return {found: false}; + return { found: false }; }; return ExpectationFilterChain; @@ -3060,7 +3285,7 @@ getJasmineRequireObj().buildExpectationResult = function() { passed: options.passed }; - if(!result.passed) { + if (!result.passed) { result.expected = options.expected; result.actual = options.actual; } @@ -3113,7 +3338,11 @@ getJasmineRequireObj().Expector = function(j$) { this.filters = new j$.ExpectationFilterChain(); } - Expector.prototype.instantiateMatcher = function(matcherName, matcherFactory, args) { + Expector.prototype.instantiateMatcher = function( + matcherName, + matcherFactory, + args + ) { this.matcherName = matcherName; this.args = Array.prototype.slice.call(args, 0); this.expected = this.args.slice(0); @@ -3132,7 +3361,13 @@ getJasmineRequireObj().Expector = function(j$) { return ''; } - var msg = this.filters.buildFailureMessage(result, this.matcherName, this.args, this.util, defaultMessage); + var msg = this.filters.buildFailureMessage( + result, + this.matcherName, + this.args, + this.util, + defaultMessage + ); return this.filters.modifyFailureMessage(msg || defaultMessage()); function defaultMessage() { @@ -3150,7 +3385,11 @@ getJasmineRequireObj().Expector = function(j$) { }; Expector.prototype.compare = function(matcherName, matcherFactory, args) { - var matcherCompare = this.instantiateMatcher(matcherName, matcherFactory, args); + var matcherCompare = this.instantiateMatcher( + matcherName, + matcherFactory, + args + ); return matcherCompare.apply(null, this.args); }; @@ -3160,7 +3399,11 @@ getJasmineRequireObj().Expector = function(j$) { return result; }; - Expector.prototype.processResult = function(result, errorForStack, actualOverride) { + Expector.prototype.processResult = function( + result, + errorForStack, + actualOverride + ) { this.args[0] = actualOverride || this.args[0]; var message = this.buildMessage(result); @@ -3168,18 +3411,15 @@ getJasmineRequireObj().Expector = function(j$) { this.expected = this.expected[0]; } - this.addExpectationResult( - result.pass, - { - matcherName: this.matcherName, - passed: result.pass, - message: message, - error: errorForStack ? undefined : result.error, - errorForStack: errorForStack || undefined, - actual: this.actual, - expected: this.expected // TODO: this may need to be arrayified/sliced - } - ); + this.addExpectationResult(result.pass, { + matcherName: this.matcherName, + passed: result.pass, + message: message, + error: errorForStack ? undefined : result.error, + errorForStack: errorForStack || undefined, + actual: this.actual, + expected: this.expected // TODO: this may need to be arrayified/sliced + }); }; return Expector; @@ -3237,7 +3477,10 @@ getJasmineRequireObj().GlobalErrors = function(j$) { var errorTypes = Object.keys(this.originalHandlers); for (var iType = 0; iType < errorTypes.length; iType++) { var errorType = errorTypes[iType]; - global.process.removeListener(errorType, this.jasmineHandlers[errorType]); + global.process.removeListener( + errorType, + this.jasmineHandlers[errorType] + ); for (var i = 0; i < this.originalHandlers[errorType].length; i++) { global.process.on(errorType, this.originalHandlers[errorType][i]); } @@ -3248,7 +3491,11 @@ getJasmineRequireObj().GlobalErrors = function(j$) { }; this.install = function install() { - if (global.process && global.process.listeners && j$.isFunction_(global.process.on)) { + if ( + global.process && + global.process.listeners && + j$.isFunction_(global.process.on) + ) { this.installOne_('uncaughtException', 'Uncaught exception'); this.installOne_('unhandledRejection', 'Unhandled promise rejection'); } else { @@ -5185,7 +5432,7 @@ getJasmineRequireObj().MockDate = function() { return self; function FakeDate() { - switch(arguments.length) { + switch (arguments.length) { case 0: return new GlobalDate(currentTime); case 1: @@ -5195,16 +5442,39 @@ getJasmineRequireObj().MockDate = function() { case 3: return new GlobalDate(arguments[0], arguments[1], arguments[2]); case 4: - return new GlobalDate(arguments[0], arguments[1], arguments[2], arguments[3]); + return new GlobalDate( + arguments[0], + arguments[1], + arguments[2], + arguments[3] + ); case 5: - return new GlobalDate(arguments[0], arguments[1], arguments[2], arguments[3], - arguments[4]); + return new GlobalDate( + arguments[0], + arguments[1], + arguments[2], + arguments[3], + arguments[4] + ); case 6: - return new GlobalDate(arguments[0], arguments[1], arguments[2], arguments[3], - arguments[4], arguments[5]); + return new GlobalDate( + arguments[0], + arguments[1], + arguments[2], + arguments[3], + arguments[4], + arguments[5] + ); default: - return new GlobalDate(arguments[0], arguments[1], arguments[2], arguments[3], - arguments[4], arguments[5], arguments[6]); + return new GlobalDate( + arguments[0], + arguments[1], + arguments[2], + arguments[3], + arguments[4], + arguments[5], + arguments[6] + ); } } @@ -5230,7 +5500,6 @@ getJasmineRequireObj().MockDate = function() { }; getJasmineRequireObj().pp = function(j$) { - function PrettyPrinter() { this.ppNestLevel_ = 0; this.seen = []; @@ -5241,7 +5510,11 @@ getJasmineRequireObj().pp = function(j$) { function hasCustomToString(value) { // value.toString !== Object.prototype.toString if value has no custom toString but is from another context (e.g. // iframe, web worker) - return j$.isFunction_(value.toString) && value.toString !== Object.prototype.toString && (value.toString() !== Object.prototype.toString.call(value)); + return ( + j$.isFunction_(value.toString) && + value.toString !== Object.prototype.toString && + value.toString() !== Object.prototype.toString.call(value) + ); } PrettyPrinter.prototype.format = function(value) { @@ -5251,7 +5524,7 @@ getJasmineRequireObj().pp = function(j$) { this.emitScalar('undefined'); } else if (value === null) { this.emitScalar('null'); - } else if (value === 0 && 1/value === -Infinity) { + } else if (value === 0 && 1 / value === -Infinity) { this.emitScalar('-0'); } else if (value === j$.getGlobal()) { this.emitScalar(''); @@ -5281,10 +5554,19 @@ getJasmineRequireObj().pp = function(j$) { this.emitMap(value); } else if (j$.isTypedArray_(value)) { this.emitTypedArray(value); - } else if (value.toString && typeof value === 'object' && !j$.isArray_(value) && hasCustomToString(value)) { + } else if ( + value.toString && + typeof value === 'object' && + !j$.isArray_(value) && + hasCustomToString(value) + ) { this.emitScalar(value.toString()); } else if (j$.util.arrayContains(this.seen, value)) { - this.emitScalar(''); + this.emitScalar( + '' + ); } else if (j$.isArray_(value) || j$.isA_('Object', value)) { this.seen.push(value); if (j$.isArray_(value)) { @@ -5314,7 +5596,6 @@ getJasmineRequireObj().pp = function(j$) { var getter = obj.__lookupGetter__(prop); return !j$.util.isUndefined(getter) && getter !== null; }; - } var length = Math.min(objKeys.length, j$.MAX_PRETTY_PRINT_ARRAY_LENGTH); for (var i = 0; i < length; i++) { @@ -5330,7 +5611,7 @@ getJasmineRequireObj().pp = function(j$) { }; PrettyPrinter.prototype.emitString = function(value) { - this.append('\'' + value + '\''); + this.append("'" + value + "'"); }; PrettyPrinter.prototype.emitArray = function(array) { @@ -5346,7 +5627,7 @@ getJasmineRequireObj().pp = function(j$) { } this.format(array[i]); } - if(array.length > length) { + if (array.length > length) { this.append(', ...'); } @@ -5362,7 +5643,9 @@ getJasmineRequireObj().pp = function(j$) { self.formatProperty(array, property, isGetter); }); - if (truncated) { this.append(', ...'); } + if (truncated) { + this.append(', ...'); + } this.append(' ]'); }; @@ -5375,7 +5658,7 @@ getJasmineRequireObj().pp = function(j$) { this.append('Set( '); var size = Math.min(set.size, j$.MAX_PRETTY_PRINT_ARRAY_LENGTH); var i = 0; - set.forEach( function( value, key ) { + set.forEach(function(value, key) { if (i >= size) { return; } @@ -5385,7 +5668,7 @@ getJasmineRequireObj().pp = function(j$) { this.format(value); i++; - }, this ); + }, this); if (set.size > size) { this.append(', ...'); } @@ -5400,17 +5683,17 @@ getJasmineRequireObj().pp = function(j$) { this.append('Map( '); var size = Math.min(map.size, j$.MAX_PRETTY_PRINT_ARRAY_LENGTH); var i = 0; - map.forEach( function( value, key ) { + map.forEach(function(value, key) { if (i >= size) { return; } if (i > 0) { this.append(', '); } - this.format([key,value]); + this.format([key, value]); i++; - }, this ); + }, this); if (map.size > size) { this.append(', ...'); } @@ -5419,11 +5702,12 @@ getJasmineRequireObj().pp = function(j$) { PrettyPrinter.prototype.emitObject = function(obj) { var ctor = obj.constructor, - constructorName; + constructorName; - constructorName = typeof ctor === 'function' && obj instanceof ctor ? - j$.fnNameFor(obj.constructor) : - 'null'; + constructorName = + typeof ctor === 'function' && obj instanceof ctor + ? j$.fnNameFor(obj.constructor) + : 'null'; this.append(constructorName); @@ -5445,14 +5729,20 @@ getJasmineRequireObj().pp = function(j$) { self.formatProperty(obj, property, isGetter); }); - if (truncated) { this.append(', ...'); } + if (truncated) { + this.append(', ...'); + } this.append(' })'); }; PrettyPrinter.prototype.emitTypedArray = function(arr) { var constructorName = j$.fnNameFor(arr.constructor), - limitedArray = Array.prototype.slice.call(arr, 0, j$.MAX_PRETTY_PRINT_ARRAY_LENGTH), + limitedArray = Array.prototype.slice.call( + arr, + 0, + j$.MAX_PRETTY_PRINT_ARRAY_LENGTH + ), itemsString = Array.prototype.join.call(limitedArray, ', '); if (limitedArray.length !== arr.length) { @@ -5489,13 +5779,13 @@ getJasmineRequireObj().pp = function(j$) { }; PrettyPrinter.prototype.formatProperty = function(obj, property, isGetter) { - this.append(property); - this.append(': '); - if (isGetter) { - this.append(''); - } else { - this.format(obj[property]); - } + this.append(property); + this.append(': '); + if (isGetter) { + this.append(''); + } else { + this.format(obj[property]); + } }; PrettyPrinter.prototype.append = function(value) { @@ -5514,7 +5804,6 @@ getJasmineRequireObj().pp = function(j$) { } }; - function truncate(s, maxlen) { if (s.length <= maxlen) { return { value: s, truncated: false }; @@ -5525,30 +5814,33 @@ getJasmineRequireObj().pp = function(j$) { } function MaxCharsReachedError() { - this.message = 'Exceeded ' + j$.MAX_PRETTY_PRINT_CHARS + + this.message = + 'Exceeded ' + + j$.MAX_PRETTY_PRINT_CHARS + ' characters while pretty-printing a value'; } MaxCharsReachedError.prototype = new Error(); function keys(obj, isArray) { - var allKeys = Object.keys ? Object.keys(obj) : - (function(o) { + var allKeys = Object.keys + ? Object.keys(obj) + : (function(o) { var keys = []; for (var key in o) { - if (j$.util.has(o, key)) { - keys.push(key); - } + if (j$.util.has(o, key)) { + keys.push(key); + } } return keys; - })(obj); + })(obj); if (!isArray) { return allKeys; } if (allKeys.length === 0) { - return allKeys; + return allKeys; } var extraKeys = []; @@ -5591,16 +5883,26 @@ getJasmineRequireObj().QueueRunner = function(j$) { this.queueableFns = queueableFns.concat(attrs.cleanupFns || []); this.firstCleanupIx = queueableFns.length; this.onComplete = attrs.onComplete || emptyFn; - this.clearStack = attrs.clearStack || function(fn) { fn(); }; + this.clearStack = + attrs.clearStack || + function(fn) { + fn(); + }; this.onException = attrs.onException || emptyFn; this.userContext = attrs.userContext || new j$.UserContext(); - this.timeout = attrs.timeout || {setTimeout: setTimeout, clearTimeout: clearTimeout}; + this.timeout = attrs.timeout || { + setTimeout: setTimeout, + clearTimeout: clearTimeout + }; this.fail = attrs.fail || emptyFn; - this.globalErrors = attrs.globalErrors || { pushListener: emptyFn, popListener: emptyFn }; + this.globalErrors = attrs.globalErrors || { + pushListener: emptyFn, + popListener: emptyFn + }; this.completeOnFirstError = !!attrs.completeOnFirstError; this.errored = false; - if (typeof(this.onComplete) !== 'function') { + if (typeof this.onComplete !== 'function') { throw new Error('invalid onComplete ' + JSON.stringify(this.onComplete)); } this.deprecated = attrs.deprecated; @@ -5624,15 +5926,22 @@ getJasmineRequireObj().QueueRunner = function(j$) { }; QueueRunner.prototype.clearTimeout = function(timeoutId) { - Function.prototype.apply.apply(this.timeout.clearTimeout, [j$.getGlobal(), [timeoutId]]); + Function.prototype.apply.apply(this.timeout.clearTimeout, [ + j$.getGlobal(), + [timeoutId] + ]); }; QueueRunner.prototype.setTimeout = function(fn, timeout) { - return Function.prototype.apply.apply(this.timeout.setTimeout, [j$.getGlobal(), [fn, timeout]]); + return Function.prototype.apply.apply(this.timeout.setTimeout, [ + j$.getGlobal(), + [fn, timeout] + ]); }; QueueRunner.prototype.attempt = function attempt(iterativeIndex) { - var self = this, completedSynchronously = true, + var self = this, + completedSynchronously = true, handleError = function handleError(error) { onException(error); next(error); @@ -5683,8 +5992,12 @@ getJasmineRequireObj().QueueRunner = function(j$) { var timeoutInterval = queueableFn.timeout || j$.DEFAULT_TIMEOUT_INTERVAL; timeoutId = self.setTimeout(function() { var error = new Error( - 'Timeout - Async callback was not invoked within ' + timeoutInterval + 'ms ' + - (queueableFn.timeout ? '(custom timeout)' : '(set by jasmine.DEFAULT_TIMEOUT_INTERVAL)') + 'Timeout - Async callback was not invoked within ' + + timeoutInterval + + 'ms ' + + (queueableFn.timeout + ? '(custom timeout)' + : '(set by jasmine.DEFAULT_TIMEOUT_INTERVAL)') ); onException(error); next(); @@ -5729,8 +6042,11 @@ getJasmineRequireObj().QueueRunner = function(j$) { self = this, iterativeIndex; - - for(iterativeIndex = recursiveIndex; iterativeIndex < length; iterativeIndex++) { + for ( + iterativeIndex = recursiveIndex; + iterativeIndex < length; + iterativeIndex++ + ) { var result = this.attempt(iterativeIndex); if (!result.completedSynchronously) { @@ -5749,7 +6065,6 @@ getJasmineRequireObj().QueueRunner = function(j$) { self.globalErrors.popListener(self.handleFinalError); self.onComplete(self.errored && new StopExecutionError()); }); - }; return QueueRunner; @@ -5757,7 +6072,6 @@ getJasmineRequireObj().QueueRunner = function(j$) { getJasmineRequireObj().ReportDispatcher = function(j$) { function ReportDispatcher(methods, queueRunnerFactory) { - var dispatchedMethods = methods || []; for (var i = 0; i < dispatchedMethods.length; i++) { @@ -5766,7 +6080,7 @@ getJasmineRequireObj().ReportDispatcher = function(j$) { return function() { dispatch(m, arguments); }; - }(method)); + })(method); } var reporters = []; @@ -5788,7 +6102,7 @@ getJasmineRequireObj().ReportDispatcher = function(j$) { function dispatch(method, args) { if (reporters.length === 0 && fallbackReporter !== null) { - reporters.push(fallbackReporter); + reporters.push(fallbackReporter); } var onComplete = args[args.length - 1]; args = j$.util.argsToArray(args).splice(0, args.length - 1); @@ -5814,13 +6128,13 @@ getJasmineRequireObj().ReportDispatcher = function(j$) { var thisArgs = j$.util.cloneArgs(args); if (fn.length <= 1) { fns.push({ - fn: function () { + fn: function() { return fn.apply(reporter, thisArgs); } }); } else { fns.push({ - fn: function (done) { + fn: function(done) { return fn.apply(reporter, thisArgs.concat([done])); } }); @@ -5831,7 +6145,6 @@ getJasmineRequireObj().ReportDispatcher = function(j$) { return ReportDispatcher; }; - getJasmineRequireObj().interface = function(jasmine, env) { var jasmineInterface = { /** @@ -6037,7 +6350,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * @function * @global * @param {String|Error} [error] - Reason for the failure. - */ + */ fail: function() { return env.fail.apply(env, arguments); }, @@ -6167,8 +6480,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { return jasmineInterface; }; -getJasmineRequireObj().Spy = function (j$) { - +getJasmineRequireObj().Spy = function(j$) { var nextOrder = (function() { var order = 0; @@ -6183,21 +6495,21 @@ getJasmineRequireObj().Spy = function (j$) { * @name Spy */ function Spy(name, originalFn, customStrategies, getPromise) { - var numArgs = (typeof originalFn === 'function' ? originalFn.length : 0), - wrapper = makeFunc(numArgs, function () { + var numArgs = typeof originalFn === 'function' ? originalFn.length : 0, + wrapper = makeFunc(numArgs, function() { return spy.apply(this, Array.prototype.slice.call(arguments)); }), strategyDispatcher = new SpyStrategyDispatcher({ name: name, fn: originalFn, - getSpy: function () { + getSpy: function() { return wrapper; }, customStrategies: customStrategies, getPromise: getPromise }), callTracker = new j$.CallTracker(), - spy = function () { + spy = function() { /** * @name Spy.callData * @property {object} object - `this` context for the invocation. @@ -6219,22 +6531,54 @@ getJasmineRequireObj().Spy = function (j$) { function makeFunc(length, fn) { switch (length) { - case 1 : return function (a) { return fn.apply(this, arguments); }; - case 2 : return function (a,b) { return fn.apply(this, arguments); }; - case 3 : return function (a,b,c) { return fn.apply(this, arguments); }; - case 4 : return function (a,b,c,d) { return fn.apply(this, arguments); }; - case 5 : return function (a,b,c,d,e) { return fn.apply(this, arguments); }; - case 6 : return function (a,b,c,d,e,f) { return fn.apply(this, arguments); }; - case 7 : return function (a,b,c,d,e,f,g) { return fn.apply(this, arguments); }; - case 8 : return function (a,b,c,d,e,f,g,h) { return fn.apply(this, arguments); }; - case 9 : return function (a,b,c,d,e,f,g,h,i) { return fn.apply(this, arguments); }; - default : return function () { return fn.apply(this, arguments); }; + case 1: + return function(a) { + return fn.apply(this, arguments); + }; + case 2: + return function(a, b) { + return fn.apply(this, arguments); + }; + case 3: + return function(a, b, c) { + return fn.apply(this, arguments); + }; + case 4: + return function(a, b, c, d) { + return fn.apply(this, arguments); + }; + case 5: + return function(a, b, c, d, e) { + return fn.apply(this, arguments); + }; + case 6: + return function(a, b, c, d, e, f) { + return fn.apply(this, arguments); + }; + case 7: + return function(a, b, c, d, e, f, g) { + return fn.apply(this, arguments); + }; + case 8: + return function(a, b, c, d, e, f, g, h) { + return fn.apply(this, arguments); + }; + case 9: + return function(a, b, c, d, e, f, g, h, i) { + return fn.apply(this, arguments); + }; + default: + return function() { + return fn.apply(this, arguments); + }; } } for (var prop in originalFn) { if (prop === 'and' || prop === 'calls') { - throw new Error('Jasmine spies would overwrite the \'and\' and \'calls\' properties on the object being spied upon'); + throw new Error( + "Jasmine spies would overwrite the 'and' and 'calls' properties on the object being spied upon" + ); } wrapper[prop] = originalFn[prop]; @@ -6281,7 +6625,13 @@ getJasmineRequireObj().Spy = function (j$) { if (!strategy) { if (argsStrategies.any() && !baseStrategy.isConfigured()) { - throw new Error('Spy \'' + strategyArgs.name + '\' received a call with arguments ' + j$.pp(Array.prototype.slice.call(args)) + ' but all configured strategies specify other arguments.'); + throw new Error( + "Spy '" + + strategyArgs.name + + "' received a call with arguments " + + j$.pp(Array.prototype.slice.call(args)) + + ' but all configured strategies specify other arguments.' + ); } else { strategy = baseStrategy; } @@ -6332,7 +6682,6 @@ getJasmineRequireObj().Spy = function (j$) { }; getJasmineRequireObj().SpyFactory = function(j$) { - function SpyFactory(getCustomStrategies, getPromise) { var self = this; @@ -6341,7 +6690,8 @@ getJasmineRequireObj().SpyFactory = function(j$) { }; this.createSpyObj = function(baseName, methodNames) { - var baseNameIsCollection = j$.isObject_(baseName) || j$.isArray_(baseName); + var baseNameIsCollection = + j$.isObject_(baseName) || j$.isArray_(baseName); if (baseNameIsCollection && j$.util.isUndefined(methodNames)) { methodNames = baseName; @@ -6378,15 +6728,21 @@ getJasmineRequireObj().SpyFactory = function(j$) { }; getJasmineRequireObj().SpyRegistry = function(j$) { - var spyOnMsg = j$.formatErrorMsg('', 'spyOn(, )'); - var spyOnPropertyMsg = j$.formatErrorMsg('', 'spyOnProperty(, , [accessType])'); + var spyOnPropertyMsg = j$.formatErrorMsg( + '', + 'spyOnProperty(, , [accessType])' + ); function SpyRegistry(options) { options = options || {}; var global = options.global || j$.getGlobal(); var createSpy = options.createSpy; - var currentSpies = options.currentSpies || function() { return []; }; + var currentSpies = + options.currentSpies || + function() { + return []; + }; this.allowRespy = function(allow) { this.respy = allow; @@ -6396,7 +6752,11 @@ getJasmineRequireObj().SpyRegistry = function(j$) { var getErrorMsg = spyOnMsg; if (j$.util.isUndefined(obj) || obj === null) { - throw new Error(getErrorMsg('could not find an object to spy upon for ' + methodName + '()')); + throw new Error( + getErrorMsg( + 'could not find an object to spy upon for ' + methodName + '()' + ) + ); } if (j$.util.isUndefined(methodName) || methodName === null) { @@ -6407,25 +6767,32 @@ getJasmineRequireObj().SpyRegistry = function(j$) { throw new Error(getErrorMsg(methodName + '() method does not exist')); } - if (obj[methodName] && j$.isSpy(obj[methodName]) ) { + if (obj[methodName] && j$.isSpy(obj[methodName])) { if (this.respy) { return obj[methodName]; - }else { - throw new Error(getErrorMsg(methodName + ' has already been spied upon')); + } else { + throw new Error( + getErrorMsg(methodName + ' has already been spied upon') + ); } } var descriptor = Object.getOwnPropertyDescriptor(obj, methodName); if (descriptor && !(descriptor.writable || descriptor.set)) { - throw new Error(getErrorMsg(methodName + ' is not declared writable or has no setter')); + throw new Error( + getErrorMsg(methodName + ' is not declared writable or has no setter') + ); } var originalMethod = obj[methodName], spiedMethod = createSpy(methodName, originalMethod), restoreStrategy; - if (Object.prototype.hasOwnProperty.call(obj, methodName) || (obj === global && methodName === 'onerror')) { + if ( + Object.prototype.hasOwnProperty.call(obj, methodName) || + (obj === global && methodName === 'onerror') + ) { restoreStrategy = function() { obj[methodName] = originalMethod; }; @@ -6446,13 +6813,19 @@ getJasmineRequireObj().SpyRegistry = function(j$) { return spiedMethod; }; - this.spyOnProperty = function (obj, propertyName, accessType) { + this.spyOnProperty = function(obj, propertyName, accessType) { var getErrorMsg = spyOnPropertyMsg; accessType = accessType || 'get'; if (j$.util.isUndefined(obj)) { - throw new Error(getErrorMsg('spyOn could not find an object to spy upon for ' + propertyName + '')); + throw new Error( + getErrorMsg( + 'spyOn could not find an object to spy upon for ' + + propertyName + + '' + ) + ); } if (j$.util.isUndefined(propertyName)) { @@ -6466,18 +6839,31 @@ getJasmineRequireObj().SpyRegistry = function(j$) { } if (!descriptor.configurable) { - throw new Error(getErrorMsg(propertyName + ' is not declared configurable')); + throw new Error( + getErrorMsg(propertyName + ' is not declared configurable') + ); } - if(!descriptor[accessType]) { - throw new Error(getErrorMsg('Property ' + propertyName + ' does not have access type ' + accessType)); + if (!descriptor[accessType]) { + throw new Error( + getErrorMsg( + 'Property ' + + propertyName + + ' does not have access type ' + + accessType + ) + ); } if (j$.isSpy(descriptor[accessType])) { if (this.respy) { return descriptor[accessType]; } else { - throw new Error(getErrorMsg(propertyName + '#' + accessType + ' has already been spied upon')); + throw new Error( + getErrorMsg( + propertyName + '#' + accessType + ' has already been spied upon' + ) + ); } } @@ -6508,19 +6894,27 @@ getJasmineRequireObj().SpyRegistry = function(j$) { this.spyOnAllFunctions = function(obj) { if (j$.util.isUndefined(obj)) { - throw new Error('spyOnAllFunctions could not find an object to spy upon'); + throw new Error( + 'spyOnAllFunctions could not find an object to spy upon' + ); } var pointer = obj, - props = [], - prop, - descriptor; + props = [], + prop, + descriptor; while (pointer) { for (prop in pointer) { - if (Object.prototype.hasOwnProperty.call(pointer, prop) && pointer[prop] instanceof Function) { + if ( + Object.prototype.hasOwnProperty.call(pointer, prop) && + pointer[prop] instanceof Function + ) { descriptor = Object.getOwnPropertyDescriptor(pointer, prop); - if ((descriptor.writable || descriptor.set) && descriptor.configurable) { + if ( + (descriptor.writable || descriptor.set) && + descriptor.configurable + ) { props.push(prop); } } @@ -6548,7 +6942,6 @@ getJasmineRequireObj().SpyRegistry = function(j$) { }; getJasmineRequireObj().SpyStrategy = function(j$) { - /** * @interface SpyStrategy */ @@ -6568,20 +6961,27 @@ getJasmineRequireObj().SpyStrategy = function(j$) { this.getSpy = options.getSpy || function() {}; this.plan = this._defaultPlan = function() {}; - var k, cs = options.customStrategies || {}; + var k, + cs = options.customStrategies || {}; for (k in cs) { if (j$.util.has(cs, k) && !this[k]) { this[k] = createCustomPlan(cs[k]); } } - var getPromise = (typeof options.getPromise === 'function') ? options.getPromise : function() {}; + var getPromise = + typeof options.getPromise === 'function' + ? options.getPromise + : function() {}; var requirePromise = function(name) { var Promise = getPromise(); if (!Promise) { - throw new Error(name + ' requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`'); + throw new Error( + name + + ' requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`' + ); } return Promise; @@ -6609,7 +7009,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { */ this.rejectWith = function(value) { var Promise = requirePromise('rejectWith'); - var error = (value instanceof Error) ? value : new Error(value); + var error = value instanceof Error ? value : new Error(value); self.plan = function() { return Promise.reject(error); @@ -6671,7 +7071,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { */ SpyStrategy.prototype.returnValues = function() { var values = Array.prototype.slice.call(arguments); - this.plan = function () { + this.plan = function() { return values.shift(); }; return this.getSpy(); @@ -6684,7 +7084,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { * @param {Error|String} something Thing to throw */ SpyStrategy.prototype.throwError = function(something) { - var error = (something instanceof Error) ? something : new Error(something); + var error = something instanceof Error ? something : new Error(something); this.plan = function() { throw error; }; @@ -6698,8 +7098,10 @@ getJasmineRequireObj().SpyStrategy = function(j$) { * @param {Function} fn The function to invoke with the passed parameters. */ SpyStrategy.prototype.callFake = function(fn) { - if(!(j$.isFunction_(fn) || j$.isAsyncFunction_(fn))) { - throw new Error('Argument passed to callFake should be a function, got ' + fn); + if (!(j$.isFunction_(fn) || j$.isAsyncFunction_(fn))) { + throw new Error( + 'Argument passed to callFake should be a function, got ' + fn + ); } this.plan = fn; return this.getSpy(); @@ -6724,9 +7126,9 @@ getJasmineRequireObj().SpyStrategy = function(j$) { getJasmineRequireObj().StackTrace = function(j$) { function StackTrace(error) { - var lines = error.stack - .split('\n') - .filter(function(line) { return line !== ''; }); + var lines = error.stack.split('\n').filter(function(line) { + return line !== ''; + }); var extractResult = extractMessage(error.message, lines); @@ -6745,7 +7147,12 @@ getJasmineRequireObj().StackTrace = function(j$) { // e.g. " at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)" // Note that the "function name" can include a surprisingly large set of // characters, including angle brackets and square brackets. - { re: /^\s*at ([^\)]+) \(([^\)]+)\)$/, fnIx: 1, fileLineColIx: 2, style: 'v8' }, + { + re: /^\s*at ([^\)]+) \(([^\)]+)\)$/, + fnIx: 1, + fileLineColIx: 2, + style: 'v8' + }, // NodeJS alternate form, often mixed in with the Chrome style // e.g. " at /some/path:4320:20 @@ -6754,7 +7161,12 @@ getJasmineRequireObj().StackTrace = function(j$) { // PhantomJS on OS X, Safari, Firefox // e.g. "run@http://localhost:8888/__jasmine__/jasmine.js:4320:27" // or "http://localhost:8888/__jasmine__/jasmine.js:4320:27" - { re: /^(([^@\s]+)@)?([^\s]+)$/, fnIx: 2, fileLineColIx: 3, style: 'webkit' } + { + re: /^(([^@\s]+)@)?([^\s]+)$/, + fnIx: 2, + fileLineColIx: 3, + style: 'webkit' + } ]; // regexes should capture the function name (if any) as group 1 @@ -6765,11 +7177,16 @@ getJasmineRequireObj().StackTrace = function(j$) { var convertedLine = first(framePatterns, function(pattern) { var overallMatch = line.match(pattern.re), fileLineColMatch; - if (!overallMatch) { return null; } + if (!overallMatch) { + return null; + } fileLineColMatch = overallMatch[pattern.fileLineColIx].match( - /^(.*):(\d+):\d+$/); - if (!fileLineColMatch) { return null; } + /^(.*):(\d+):\d+$/ + ); + if (!fileLineColMatch) { + return null; + } style = style || pattern.style; return { @@ -6882,7 +7299,11 @@ getJasmineRequireObj().Suite = function(j$) { Suite.prototype.getFullName = function() { var fullName = []; - for (var parentSuite = this; parentSuite; parentSuite = parentSuite.parentSuite) { + for ( + var parentSuite = this; + parentSuite; + parentSuite = parentSuite.parentSuite + ) { if (parentSuite.parentSuite) { fullName.unshift(parentSuite.description); } @@ -6919,7 +7340,7 @@ getJasmineRequireObj().Suite = function(j$) { }; function removeFns(queueableFns) { - for(var i = 0; i < queueableFns.length; i++) { + for (var i = 0; i < queueableFns.length; i++) { queueableFns[i].fn = null; } } @@ -6958,7 +7379,9 @@ getJasmineRequireObj().Suite = function(j$) { Suite.prototype.sharedUserContext = function() { if (!this.sharedContext) { - this.sharedContext = this.parentSuite ? this.parentSuite.clonedSharedUserContext() : new j$.UserContext(); + this.sharedContext = this.parentSuite + ? this.parentSuite.clonedSharedUserContext() + : new j$.UserContext(); } return this.sharedContext; @@ -6989,11 +7412,11 @@ getJasmineRequireObj().Suite = function(j$) { this.result.failedExpectations.push(failedExpectation); }; - Suite.prototype.addExpectationResult = function () { - if(isFailure(arguments)) { + Suite.prototype.addExpectationResult = function() { + if (isFailure(arguments)) { var data = arguments[1]; this.result.failedExpectations.push(this.expectationResultFactory(data)); - if(this.throwOnExpectationFailure) { + if (this.throwOnExpectationFailure) { throw new j$.errors.ExpectationFailed(); } } @@ -7003,7 +7426,9 @@ getJasmineRequireObj().Suite = function(j$) { if (typeof deprecation === 'string') { deprecation = { message: deprecation }; } - this.result.deprecationWarnings.push(this.expectationResultFactory(deprecation)); + this.result.deprecationWarnings.push( + this.expectationResultFactory(deprecation) + ); }; function isFailure(args) { @@ -7020,7 +7445,9 @@ if (typeof window == void 0 && typeof exports == 'object') { getJasmineRequireObj().Timer = function() { var defaultNow = (function(Date) { - return function() { return new Date().getTime(); }; + return function() { + return new Date().getTime(); + }; })(Date); function Timer(options) { @@ -7044,22 +7471,33 @@ getJasmineRequireObj().Timer = function() { getJasmineRequireObj().noopTimer = function() { return { start: function() {}, - elapsed: function() { return 0; } + elapsed: function() { + return 0; + } }; }; + getJasmineRequireObj().TreeProcessor = function() { function TreeProcessor(attrs) { var tree = attrs.tree, - runnableIds = attrs.runnableIds, - queueRunnerFactory = attrs.queueRunnerFactory, - nodeStart = attrs.nodeStart || function() {}, - nodeComplete = attrs.nodeComplete || function() {}, - orderChildren = attrs.orderChildren || function(node) { return node.children; }, - excludeNode = attrs.excludeNode || function(node) { return false; }, - stats = { valid: true }, - processed = false, - defaultMin = Infinity, - defaultMax = 1 - Infinity; + runnableIds = attrs.runnableIds, + queueRunnerFactory = attrs.queueRunnerFactory, + nodeStart = attrs.nodeStart || function() {}, + nodeComplete = attrs.nodeComplete || function() {}, + orderChildren = + attrs.orderChildren || + function(node) { + return node.children; + }, + excludeNode = + attrs.excludeNode || + function(node) { + return false; + }, + stats = { valid: true }, + processed = false, + defaultMin = Infinity, + defaultMax = 1 - Infinity; this.processTree = function() { processNode(tree, true); @@ -7108,13 +7546,15 @@ getJasmineRequireObj().TreeProcessor = function() { stats[node.id] = { excluded: excluded, willExecute: !excluded && !node.markedPending, - segments: [{ - index: 0, - owner: node, - nodes: [node], - min: startingMin(executableIndex), - max: startingMax(executableIndex) - }] + segments: [ + { + index: 0, + owner: node, + nodes: [node], + min: startingMin(executableIndex), + max: startingMax(executableIndex) + } + ] }; } else { var hasExecutableChild = false; @@ -7156,14 +7596,29 @@ getJasmineRequireObj().TreeProcessor = function() { return executableIndex === undefined ? defaultMax : executableIndex; } - function segmentChildren(node, orderedChildren, nodeStats, executableIndex) { - var currentSegment = { index: 0, owner: node, nodes: [], min: startingMin(executableIndex), max: startingMax(executableIndex) }, - result = [currentSegment], - lastMax = defaultMax, - orderedChildSegments = orderChildSegments(orderedChildren); + function segmentChildren( + node, + orderedChildren, + nodeStats, + executableIndex + ) { + var currentSegment = { + index: 0, + owner: node, + nodes: [], + min: startingMin(executableIndex), + max: startingMax(executableIndex) + }, + result = [currentSegment], + lastMax = defaultMax, + orderedChildSegments = orderChildSegments(orderedChildren); function isSegmentBoundary(minIndex) { - return lastMax !== defaultMax && minIndex !== defaultMin && lastMax < minIndex - 1; + return ( + lastMax !== defaultMax && + minIndex !== defaultMin && + lastMax < minIndex - 1 + ); } for (var i = 0; i < orderedChildSegments.length; i++) { @@ -7172,7 +7627,13 @@ getJasmineRequireObj().TreeProcessor = function() { minIndex = childSegment.min; if (isSegmentBoundary(minIndex)) { - currentSegment = {index: result.length, owner: node, nodes: [], min: defaultMin, max: defaultMax}; + currentSegment = { + index: result.length, + owner: node, + nodes: [], + min: defaultMin, + max: defaultMax + }; result.push(currentSegment); } @@ -7187,11 +7648,11 @@ getJasmineRequireObj().TreeProcessor = function() { function orderChildSegments(children) { var specifiedOrder = [], - unspecifiedOrder = []; + unspecifiedOrder = []; for (var i = 0; i < children.length; i++) { var child = children[i], - segments = stats[child.id].segments; + segments = stats[child.id].segments; for (var j = 0; j < segments.length; j++) { var seg = segments[j]; @@ -7222,7 +7683,7 @@ getJasmineRequireObj().TreeProcessor = function() { }; queueRunnerFactory({ - onComplete: function () { + onComplete: function() { var args = Array.prototype.slice.call(arguments, [0]); node.cleanupBeforeAfter(); nodeComplete(node, node.getResult(), function() { @@ -7231,7 +7692,7 @@ getJasmineRequireObj().TreeProcessor = function() { }, queueableFns: [onStart].concat(wrapChildren(node, segmentNumber)), userContext: node.sharedUserContext(), - onException: function () { + onException: function() { node.onException.apply(node, arguments); } }); @@ -7239,17 +7700,21 @@ getJasmineRequireObj().TreeProcessor = function() { }; } else { return { - fn: function(done) { node.execute(done, stats[node.id].excluded); } + fn: function(done) { + node.execute(done, stats[node.id].excluded); + } }; } } function wrapChildren(node, segmentNumber) { var result = [], - segmentChildren = stats[node.id].segments[segmentNumber].nodes; + segmentChildren = stats[node.id].segments[segmentNumber].nodes; for (var i = 0; i < segmentChildren.length; i++) { - result.push(executeNode(segmentChildren[i].owner, segmentChildren[i].index)); + result.push( + executeNode(segmentChildren[i].owner, segmentChildren[i].index) + ); } if (!stats[node.id].willExecute) { @@ -7264,8 +7729,7 @@ getJasmineRequireObj().TreeProcessor = function() { }; getJasmineRequireObj().UserContext = function(j$) { - function UserContext() { - } + function UserContext() {} UserContext.fromExisting = function(oldContext) { var context = new UserContext(); @@ -7279,7 +7743,7 @@ getJasmineRequireObj().UserContext = function(j$) { return context; }; - return UserContext; + return UserContext; }; getJasmineRequireObj().version = function() { diff --git a/package.json b/package.json index 72ed2916..9cefdc97 100644 --- a/package.json +++ b/package.json @@ -13,28 +13,69 @@ "bdd" ], "scripts": { - "test": "grunt jshint execSpecsInNode" + "pretest": "eslint src/**/*.js spec/**/*.js && prettier --check src/**/*.js spec/**/*.js", + "test": "grunt execSpecsInNode", + "cleanup": "prettier --write src/**/*.js spec/**/*.js" }, "description": "Official packaging of Jasmine's core files for use by Node.js projects.", "homepage": "https://jasmine.github.io", "main": "./lib/jasmine-core.js", "devDependencies": { "ejs": "^2.5.5", + "eslint": "^5.16.0", "express": "^4.16.4", "fast-glob": "^2.2.6", "grunt": "^1.0.4", "grunt-cli": "^1.3.2", "grunt-contrib-compress": "^1.3.0", "grunt-contrib-concat": "^1.0.1", - "grunt-contrib-jshint": "^2.1.0", "grunt-css-url-embed": "^1.11.1", "grunt-sass": "^3.0.2", "jasmine": "^3.4.0", "jsdom": "^15.0.0", "load-grunt-tasks": "^4.0.0", "node-sass": "^4.11.0", + "prettier": "1.17.1", "selenium-webdriver": "^3.6.0", "shelljs": "^0.8.3", "temp": "^0.9.0" + }, + "prettier": { + "singleQuote": true + }, + "eslintConfig": { + "rules": { + "quotes": [ + "error", + "single", + { + "avoidEscape": true + } + ], + "no-unused-vars": [ + "error", + { + "args": "none" + } + ], + "block-spacing": "error", + "comma-dangle": [ + "error", + "never" + ], + "func-call-spacing": [ + "error", + "never" + ], + "key-spacing": "error", + "no-tabs": "error", + "no-trailing-spaces": "error", + "no-whitespace-before-property": "error", + "semi": [ + "error", + "always" + ], + "space-before-blocks": "error" + } } } diff --git a/spec/core/AsyncExpectationSpec.js b/spec/core/AsyncExpectationSpec.js index 906b3081..42fcd544 100644 --- a/spec/core/AsyncExpectationSpec.js +++ b/spec/core/AsyncExpectationSpec.js @@ -1,22 +1,30 @@ describe('AsyncExpectation', function() { beforeEach(function() { - jasmineUnderTest.Expectation.addAsyncCoreMatchers(jasmineUnderTest.asyncMatchers); + jasmineUnderTest.Expectation.addAsyncCoreMatchers( + jasmineUnderTest.asyncMatchers + ); }); describe('Factory', function() { it('throws an Error if promises are not available', function() { - var thenable = {then: function() {}}, - options = {global: {}, actual: thenable} - function f() { jasmineUnderTest.Expectation.asyncFactory(options); } - expect(f).toThrowError('expectAsync is unavailable because the environment does not support promises.'); + var thenable = { then: function() {} }, + options = { global: {}, actual: thenable }; + function f() { + jasmineUnderTest.Expectation.asyncFactory(options); + } + expect(f).toThrowError( + 'expectAsync is unavailable because the environment does not support promises.' + ); }); it('throws an Error if the argument is not a promise', function() { jasmine.getEnv().requirePromises(); function f() { - jasmineUnderTest.Expectation.asyncFactory({actual: 'not a promise'}); + jasmineUnderTest.Expectation.asyncFactory({ actual: 'not a promise' }); } - expect(f).toThrowError('Expected expectAsync to be called with a promise.'); + expect(f).toThrowError( + 'Expected expectAsync to be called with a promise.' + ); }); }); @@ -33,7 +41,8 @@ describe('AsyncExpectation', function() { }); return expectation.not.toBeResolved().then(function() { - expect(addExpectationResult).toHaveBeenCalledWith(false, + expect(addExpectationResult).toHaveBeenCalledWith( + false, jasmine.objectContaining({ passed: false, message: 'Expected a promise not to be resolved.' @@ -54,7 +63,8 @@ describe('AsyncExpectation', function() { }); return expectation.not.toBeResolved().then(function() { - expect(addExpectationResult).toHaveBeenCalledWith(true, + expect(addExpectationResult).toHaveBeenCalledWith( + true, jasmine.objectContaining({ passed: true, message: '' @@ -68,7 +78,6 @@ describe('AsyncExpectation', function() { jasmine.getEnv().requirePromises(); var error = new Error('ExpectationSpec failure'); - var addExpectationResult = jasmine.createSpy('addExpectationResult'), actual = dummyPromise(), expectation = jasmineUnderTest.Expectation.asyncFactory({ @@ -76,22 +85,26 @@ describe('AsyncExpectation', function() { addExpectationResult: addExpectationResult }); - spyOn(expectation, 'toBeResolved') - .and.returnValue(Promise.reject(error)); + spyOn(expectation, 'toBeResolved').and.returnValue(Promise.reject(error)); - return expectation.toBeResolved() - .then( - function() { fail('Expected a rejection'); }, - function(e) { expect(e).toBe(error); } - ); + return expectation.toBeResolved().then( + function() { + fail('Expected a rejection'); + }, + function(e) { + expect(e).toBe(error); + } + ); }); describe('#withContext', function() { - it("prepends the context to the generated failure message", function() { + it('prepends the context to the generated failure message', function() { jasmine.getEnv().requirePromises(); var util = { - buildFailureMessage: function() { return 'failure message'; } + buildFailureMessage: function() { + return 'failure message'; + } }, addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation = jasmineUnderTest.Expectation.asyncFactory({ @@ -100,21 +113,26 @@ describe('AsyncExpectation', function() { util: util }); - return expectation.withContext('Some context').toBeResolved() - .then( - function() { - expect(addExpectationResult).toHaveBeenCalledWith(false, - jasmine.objectContaining({ - message: 'Some context: failure message' - })); - }); + return expectation + .withContext('Some context') + .toBeResolved() + .then(function() { + expect(addExpectationResult).toHaveBeenCalledWith( + false, + jasmine.objectContaining({ + message: 'Some context: failure message' + }) + ); + }); }); - it("prepends the context to a custom failure message", function() { + it('prepends the context to a custom failure message', function() { jasmine.getEnv().requirePromises(); var util = { - buildFailureMessage: function() { return 'failure message'; } + buildFailureMessage: function() { + return 'failure message'; + } }, addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation = jasmineUnderTest.Expectation.asyncFactory({ @@ -123,22 +141,28 @@ describe('AsyncExpectation', function() { util: util }); - return expectation.withContext('Some context').toBeResolvedTo('a') - .then( - function() { - expect(addExpectationResult).toHaveBeenCalledWith(false, - jasmine.objectContaining({ - message: "Some context: Expected a promise to be resolved to 'a' but it was rejected." - })); - }); + return expectation + .withContext('Some context') + .toBeResolvedTo('a') + .then(function() { + expect(addExpectationResult).toHaveBeenCalledWith( + false, + jasmine.objectContaining({ + message: + "Some context: Expected a promise to be resolved to 'a' but it was rejected." + }) + ); + }); }); - it("prepends the context to a custom failure message from a function", function() { + it('prepends the context to a custom failure message from a function', function() { pending('should actually work, but no custom matchers for async yet'); jasmine.getEnv().requirePromises(); var util = { - buildFailureMessage: function() { return 'failure message'; } + buildFailureMessage: function() { + return 'failure message'; + } }, addExpectationResult = jasmine.createSpy('addExpectationResult'), actual = Promise.reject(), @@ -148,17 +172,20 @@ describe('AsyncExpectation', function() { util: util }); - return expectation.withContext('Some context').toBeResolved() - .then( - function() { - expect(addExpectationResult).toHaveBeenCalledWith(false, - jasmine.objectContaining({ - message: 'Some context: msg' - })); - }); + return expectation + .withContext('Some context') + .toBeResolved() + .then(function() { + expect(addExpectationResult).toHaveBeenCalledWith( + false, + jasmine.objectContaining({ + message: 'Some context: msg' + }) + ); + }); }); - it("works with #not", function() { + it('works with #not', function() { jasmine.getEnv().requirePromises(); var addExpectationResult = jasmine.createSpy('addExpectationResult'), @@ -169,17 +196,20 @@ describe('AsyncExpectation', function() { util: jasmineUnderTest.matchersUtil }); - return expectation.withContext('Some context').not.toBeResolved() - .then( - function() { - expect(addExpectationResult).toHaveBeenCalledWith(false, - jasmine.objectContaining({ - message: 'Some context: Expected a promise not to be resolved.' - })); - }); + return expectation + .withContext('Some context') + .not.toBeResolved() + .then(function() { + expect(addExpectationResult).toHaveBeenCalledWith( + false, + jasmine.objectContaining({ + message: 'Some context: Expected a promise not to be resolved.' + }) + ); + }); }); - it("works with #not and a custom message", function() { + it('works with #not and a custom message', function() { jasmine.getEnv().requirePromises(); var addExpectationResult = jasmine.createSpy('addExpectationResult'), @@ -190,19 +220,22 @@ describe('AsyncExpectation', function() { util: jasmineUnderTest.matchersUtil }); - return expectation.withContext('Some context').not.toBeResolvedTo('a') - .then( - function() { - expect(addExpectationResult).toHaveBeenCalledWith(false, - jasmine.objectContaining({ - message: "Some context: Expected a promise not to be resolved to 'a'." - })); - }); + return expectation + .withContext('Some context') + .not.toBeResolvedTo('a') + .then(function() { + expect(addExpectationResult).toHaveBeenCalledWith( + false, + jasmine.objectContaining({ + message: + "Some context: Expected a promise not to be resolved to 'a'." + }) + ); + }); }); }); function dummyPromise() { - return new Promise(function(resolve, reject) { - }); + return new Promise(function(resolve, reject) {}); } }); diff --git a/spec/core/CallTrackerSpec.js b/spec/core/CallTrackerSpec.js index 3fdc8c60..474f674f 100644 --- a/spec/core/CallTrackerSpec.js +++ b/spec/core/CallTrackerSpec.js @@ -1,5 +1,5 @@ -describe("CallTracker", function() { - it("tracks that it was called when executed", function() { +describe('CallTracker', function() { + it('tracks that it was called when executed', function() { var callTracker = new jasmineUnderTest.CallTracker(); expect(callTracker.any()).toBe(false); @@ -9,7 +9,7 @@ describe("CallTracker", function() { expect(callTracker.any()).toBe(true); }); - it("tracks that number of times that it is executed", function() { + it('tracks that number of times that it is executed', function() { var callTracker = new jasmineUnderTest.CallTracker(); expect(callTracker.count()).toEqual(0); @@ -19,52 +19,52 @@ describe("CallTracker", function() { expect(callTracker.count()).toEqual(1); }); - it("tracks the params from each execution", function() { + it('tracks the params from each execution', function() { var callTracker = new jasmineUnderTest.CallTracker(); - callTracker.track({object: void 0, args: []}); - callTracker.track({object: {}, args: [0, "foo"]}); + callTracker.track({ object: void 0, args: [] }); + callTracker.track({ object: {}, args: [0, 'foo'] }); expect(callTracker.argsFor(0)).toEqual([]); - expect(callTracker.argsFor(1)).toEqual([0, "foo"]); + expect(callTracker.argsFor(1)).toEqual([0, 'foo']); }); - it("returns any empty array when there was no call", function() { + it('returns any empty array when there was no call', function() { var callTracker = new jasmineUnderTest.CallTracker(); expect(callTracker.argsFor(0)).toEqual([]); }); - it("allows access for the arguments for all calls", function() { + it('allows access for the arguments for all calls', function() { var callTracker = new jasmineUnderTest.CallTracker(); - callTracker.track({object: {}, args: []}); - callTracker.track({object: {}, args: [0, "foo"]}); + callTracker.track({ object: {}, args: [] }); + callTracker.track({ object: {}, args: [0, 'foo'] }); - expect(callTracker.allArgs()).toEqual([[], [0, "foo"]]); + expect(callTracker.allArgs()).toEqual([[], [0, 'foo']]); }); - it("tracks the context and arguments for each call", function() { + it('tracks the context and arguments for each call', function() { var callTracker = new jasmineUnderTest.CallTracker(); - callTracker.track({object: {}, args: []}); - callTracker.track({object: {}, args: [0, "foo"]}); + callTracker.track({ object: {}, args: [] }); + callTracker.track({ object: {}, args: [0, 'foo'] }); - expect(callTracker.all()[0]).toEqual({object: {}, args: []}); + expect(callTracker.all()[0]).toEqual({ object: {}, args: [] }); - expect(callTracker.all()[1]).toEqual({object: {}, args: [0, "foo"]}); + expect(callTracker.all()[1]).toEqual({ object: {}, args: [0, 'foo'] }); }); - it("simplifies access to the arguments for the last (most recent) call", function() { + it('simplifies access to the arguments for the last (most recent) call', function() { var callTracker = new jasmineUnderTest.CallTracker(); callTracker.track(); - callTracker.track({object: {}, args: [0, "foo"]}); + callTracker.track({ object: {}, args: [0, 'foo'] }); expect(callTracker.mostRecent()).toEqual({ object: {}, - args: [0, "foo"] + args: [0, 'foo'] }); }); @@ -74,12 +74,12 @@ describe("CallTracker", function() { expect(callTracker.mostRecent()).toBeFalsy(); }); - it("simplifies access to the arguments for the first (oldest) call", function() { + it('simplifies access to the arguments for the first (oldest) call', function() { var callTracker = new jasmineUnderTest.CallTracker(); - callTracker.track({object: {}, args: [0, "foo"]}); + callTracker.track({ object: {}, args: [0, 'foo'] }); - expect(callTracker.first()).toEqual({object: {}, args: [0, "foo"]}) + expect(callTracker.first()).toEqual({ object: {}, args: [0, 'foo'] }); }); it("returns a useful falsy value when there isn't a first (oldest) call", function() { @@ -88,12 +88,11 @@ describe("CallTracker", function() { expect(callTracker.first()).toBeFalsy(); }); - - it("allows the tracking to be reset", function() { + it('allows the tracking to be reset', function() { var callTracker = new jasmineUnderTest.CallTracker(); callTracker.track(); - callTracker.track({object: {}, args: [0, "foo"]}); + callTracker.track({ object: {}, args: [0, 'foo'] }); callTracker.reset(); expect(callTracker.any()).toBe(false); @@ -103,14 +102,17 @@ describe("CallTracker", function() { expect(callTracker.mostRecent()).toBeFalsy(); }); - it("allows object arguments to be shallow cloned", function() { + it('allows object arguments to be shallow cloned', function() { var callTracker = new jasmineUnderTest.CallTracker(); callTracker.saveArgumentsByValue(); - var objectArg = {"foo": "bar"}, - arrayArg = ["foo", "bar"]; + var objectArg = { foo: 'bar' }, + arrayArg = ['foo', 'bar']; - callTracker.track({object: {}, args: [objectArg, arrayArg, false, undefined, null, NaN, "", 0, 1.0]}); + callTracker.track({ + object: {}, + args: [objectArg, arrayArg, false, undefined, null, NaN, '', 0, 1.0] + }); expect(callTracker.mostRecent().args[0]).not.toBe(objectArg); expect(callTracker.mostRecent().args[0]).toEqual(objectArg); diff --git a/spec/core/ClearStackSpec.js b/spec/core/ClearStackSpec.js index 854d4478..9592b2d2 100644 --- a/spec/core/ClearStackSpec.js +++ b/spec/core/ClearStackSpec.js @@ -1,17 +1,23 @@ -describe("ClearStack", function() { - it("works in an integrationy way", function(done) { - var clearStack = jasmineUnderTest.getClearStack(jasmineUnderTest.getGlobal()); +describe('ClearStack', function() { + it('works in an integrationy way', function(done) { + var clearStack = jasmineUnderTest.getClearStack( + jasmineUnderTest.getGlobal() + ); clearStack(function() { done(); }); }); - it("uses setImmediate when available", function() { - var setImmediate = jasmine.createSpy('setImmediate').and.callFake(function(fn) { fn() }), - global = { setImmediate: setImmediate }, - clearStack = jasmineUnderTest.getClearStack(global), - called = false; + it('uses setImmediate when available', function() { + var setImmediate = jasmine + .createSpy('setImmediate') + .and.callFake(function(fn) { + fn(); + }), + global = { setImmediate: setImmediate }, + clearStack = jasmineUnderTest.getClearStack(global), + called = false; clearStack(function() { called = true; @@ -21,42 +27,50 @@ describe("ClearStack", function() { expect(setImmediate).toHaveBeenCalled(); }); - it("uses setTimeout instead of setImmediate every 10 calls to make sure we release the CPU", function() { + it('uses setTimeout instead of setImmediate every 10 calls to make sure we release the CPU', function() { var setImmediate = jasmine.createSpy('setImmediate'), - setTimeout = jasmine.createSpy('setTimeout'), - global = { setImmediate: setImmediate, setTimeout: setTimeout }, - clearStack = jasmineUnderTest.getClearStack(global); + setTimeout = jasmine.createSpy('setTimeout'), + global = { setImmediate: setImmediate, setTimeout: setTimeout }, + clearStack = jasmineUnderTest.getClearStack(global); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); expect(setImmediate).toHaveBeenCalled(); expect(setTimeout).not.toHaveBeenCalled(); - clearStack(function() { }); + clearStack(function() {}); expect(setImmediate.calls.count()).toEqual(9); expect(setTimeout.calls.count()).toEqual(1); - clearStack(function() { }); + clearStack(function() {}); expect(setImmediate.calls.count()).toEqual(10); expect(setTimeout.calls.count()).toEqual(1); }); - it("uses MessageChannels when available", function() { + it('uses MessageChannels when available', function() { var fakeChannel = { - port1: {}, - port2: { postMessage: function() { fakeChannel.port1.onmessage(); } } - }, - global = { MessageChannel: function() { return fakeChannel; } }, - clearStack = jasmineUnderTest.getClearStack(global), - called = false; + port1: {}, + port2: { + postMessage: function() { + fakeChannel.port1.onmessage(); + } + } + }, + global = { + MessageChannel: function() { + return fakeChannel; + } + }, + clearStack = jasmineUnderTest.getClearStack(global), + called = false; clearStack(function() { called = true; @@ -65,53 +79,66 @@ describe("ClearStack", function() { expect(called).toBe(true); }); - it("uses setTimeout instead of MessageChannel every 10 calls to make sure we release the CPU", function() { + it('uses setTimeout instead of MessageChannel every 10 calls to make sure we release the CPU', function() { var fakeChannel = { - port1: {}, - port2: { - postMessage: jasmine.createSpy('postMessage').and.callFake(function() { + port1: {}, + port2: { + postMessage: jasmine + .createSpy('postMessage') + .and.callFake(function() { fakeChannel.port1.onmessage(); }) - } + } + }, + setTimeout = jasmine.createSpy('setTimeout'), + global = { + MessageChannel: function() { + return fakeChannel; }, - setTimeout = jasmine.createSpy('setTimeout'), - global = { MessageChannel: function() { return fakeChannel; }, setTimeout: setTimeout }, - clearStack = jasmineUnderTest.getClearStack(global); + setTimeout: setTimeout + }, + clearStack = jasmineUnderTest.getClearStack(global); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); - clearStack(function() { }); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); + clearStack(function() {}); expect(fakeChannel.port2.postMessage).toHaveBeenCalled(); expect(setTimeout).not.toHaveBeenCalled(); - clearStack(function() { }); + clearStack(function() {}); expect(fakeChannel.port2.postMessage.calls.count()).toEqual(9); expect(setTimeout.calls.count()).toEqual(1); - clearStack(function() { }); + clearStack(function() {}); expect(fakeChannel.port2.postMessage.calls.count()).toEqual(10); expect(setTimeout.calls.count()).toEqual(1); }); - it("calls setTimeout when onmessage is called recursively", function() { + it('calls setTimeout when onmessage is called recursively', function() { var fakeChannel = { - port1: {}, - port2: { postMessage: function() { fakeChannel.port1.onmessage(); } } + port1: {}, + port2: { + postMessage: function() { + fakeChannel.port1.onmessage(); + } + } + }, + setTimeout = jasmine.createSpy('setTimeout'), + global = { + MessageChannel: function() { + return fakeChannel; }, - setTimeout = jasmine.createSpy('setTimeout'), - global = { - MessageChannel: function() { return fakeChannel; }, - setTimeout: setTimeout, - }, - clearStack = jasmineUnderTest.getClearStack(global), - fn = jasmine.createSpy("second clearStack function"); + setTimeout: setTimeout + }, + clearStack = jasmineUnderTest.getClearStack(global), + fn = jasmine.createSpy('second clearStack function'); clearStack(function() { clearStack(fn); @@ -121,11 +148,13 @@ describe("ClearStack", function() { expect(setTimeout).toHaveBeenCalledWith(fn, 0); }); - it("falls back to setTimeout", function() { - var setTimeout = jasmine.createSpy('setTimeout').and.callFake(function(fn) { fn() }), - global = { setTimeout: setTimeout }, - clearStack = jasmineUnderTest.getClearStack(global), - called = false; + it('falls back to setTimeout', function() { + var setTimeout = jasmine.createSpy('setTimeout').and.callFake(function(fn) { + fn(); + }), + global = { setTimeout: setTimeout }, + clearStack = jasmineUnderTest.getClearStack(global), + called = false; clearStack(function() { called = true; diff --git a/spec/core/ClockSpec.js b/spec/core/ClockSpec.js index b330b6c7..2aba566b 100644 --- a/spec/core/ClockSpec.js +++ b/spec/core/ClockSpec.js @@ -1,14 +1,29 @@ -describe("Clock", function() { +describe('Clock', function() { + var NODE_JS = + typeof process !== 'undefined' && + process.versions && + typeof process.versions.node === 'string'; - var NODE_JS = typeof process !== 'undefined' && process.versions && typeof process.versions.node === 'string'; - - it("does not replace setTimeout until it is installed", function() { - var fakeSetTimeout = jasmine.createSpy("global setTimeout"), + it('does not replace setTimeout until it is installed', function() { + var fakeSetTimeout = jasmine.createSpy('global setTimeout'), fakeGlobal = { setTimeout: fakeSetTimeout }, - delayedFunctionScheduler = jasmine.createSpyObj("delayedFunctionScheduler", ["scheduleFunction"]), - delayedFn = jasmine.createSpy("delayedFn"), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate); + delayedFunctionScheduler = jasmine.createSpyObj( + 'delayedFunctionScheduler', + ['scheduleFunction'] + ), + delayedFn = jasmine.createSpy('delayedFn'), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); fakeGlobal.setTimeout(delayedFn, 0); @@ -24,35 +39,62 @@ describe("Clock", function() { expect(fakeSetTimeout).not.toHaveBeenCalled(); }); - it("does not replace clearTimeout until it is installed", function() { - var fakeClearTimeout = jasmine.createSpy("global cleartimeout"), + it('does not replace clearTimeout until it is installed', function() { + var fakeClearTimeout = jasmine.createSpy('global cleartimeout'), fakeGlobal = { clearTimeout: fakeClearTimeout }, - delayedFunctionScheduler = jasmine.createSpyObj("delayedFunctionScheduler", ["removeFunctionWithId"]), - delayedFn = jasmine.createSpy("delayedFn"), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate); + delayedFunctionScheduler = jasmine.createSpyObj( + 'delayedFunctionScheduler', + ['removeFunctionWithId'] + ), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); - fakeGlobal.clearTimeout("foo"); + fakeGlobal.clearTimeout('foo'); - expect(fakeClearTimeout).toHaveBeenCalledWith("foo"); - expect(delayedFunctionScheduler.removeFunctionWithId).not.toHaveBeenCalled(); + expect(fakeClearTimeout).toHaveBeenCalledWith('foo'); + expect( + delayedFunctionScheduler.removeFunctionWithId + ).not.toHaveBeenCalled(); fakeClearTimeout.calls.reset(); clock.install(); - fakeGlobal.clearTimeout("foo"); + fakeGlobal.clearTimeout('foo'); expect(delayedFunctionScheduler.removeFunctionWithId).toHaveBeenCalled(); expect(fakeClearTimeout).not.toHaveBeenCalled(); }); - it("does not replace setInterval until it is installed", function() { - var fakeSetInterval = jasmine.createSpy("global setInterval"), + it('does not replace setInterval until it is installed', function() { + var fakeSetInterval = jasmine.createSpy('global setInterval'), fakeGlobal = { setInterval: fakeSetInterval }, - delayedFunctionScheduler = jasmine.createSpyObj("delayedFunctionScheduler", ["scheduleFunction"]), - delayedFn = jasmine.createSpy("delayedFn"), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate); + delayedFunctionScheduler = jasmine.createSpyObj( + 'delayedFunctionScheduler', + ['scheduleFunction'] + ), + delayedFn = jasmine.createSpy('delayedFn'), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); fakeGlobal.setInterval(delayedFn, 0); @@ -68,35 +110,55 @@ describe("Clock", function() { expect(fakeSetInterval).not.toHaveBeenCalled(); }); - it("does not replace clearInterval until it is installed", function() { - var fakeClearInterval = jasmine.createSpy("global clearinterval"), + it('does not replace clearInterval until it is installed', function() { + var fakeClearInterval = jasmine.createSpy('global clearinterval'), fakeGlobal = { clearInterval: fakeClearInterval }, - delayedFunctionScheduler = jasmine.createSpyObj("delayedFunctionScheduler", ["removeFunctionWithId"]), - delayedFn = jasmine.createSpy("delayedFn"), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate); + delayedFunctionScheduler = jasmine.createSpyObj( + 'delayedFunctionScheduler', + ['removeFunctionWithId'] + ), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); - fakeGlobal.clearInterval("foo"); + fakeGlobal.clearInterval('foo'); - expect(fakeClearInterval).toHaveBeenCalledWith("foo"); - expect(delayedFunctionScheduler.removeFunctionWithId).not.toHaveBeenCalled(); + expect(fakeClearInterval).toHaveBeenCalledWith('foo'); + expect( + delayedFunctionScheduler.removeFunctionWithId + ).not.toHaveBeenCalled(); fakeClearInterval.calls.reset(); clock.install(); - fakeGlobal.clearInterval("foo"); + fakeGlobal.clearInterval('foo'); expect(delayedFunctionScheduler.removeFunctionWithId).toHaveBeenCalled(); expect(fakeClearInterval).not.toHaveBeenCalled(); }); - it("does not install if the current setTimeout is not the original function on the global", function() { + it('does not install if the current setTimeout is not the original function on the global', function() { var originalFakeSetTimeout = function() {}, replacedSetTimeout = function() {}, fakeGlobal = { setTimeout: originalFakeSetTimeout }, - delayedFunctionSchedulerFactory = jasmine.createSpy('delayedFunctionSchedulerFactory'), + delayedFunctionSchedulerFactory = jasmine.createSpy( + 'delayedFunctionSchedulerFactory' + ), mockDate = {}, - clock = new jasmineUnderTest.Clock(fakeGlobal, delayedFunctionSchedulerFactory, mockDate); + clock = new jasmineUnderTest.Clock( + fakeGlobal, + delayedFunctionSchedulerFactory, + mockDate + ); fakeGlobal.setTimeout = replacedSetTimeout; @@ -108,13 +170,19 @@ describe("Clock", function() { expect(fakeGlobal.setTimeout).toBe(replacedSetTimeout); }); - it("does not install if the current clearTimeout is not the original function on the global", function() { + it('does not install if the current clearTimeout is not the original function on the global', function() { var originalFakeClearTimeout = function() {}, replacedClearTimeout = function() {}, fakeGlobal = { clearTimeout: originalFakeClearTimeout }, - delayedFunctionSchedulerFactory = jasmine.createSpy('delayedFunctionSchedulerFactory'), + delayedFunctionSchedulerFactory = jasmine.createSpy( + 'delayedFunctionSchedulerFactory' + ), mockDate = {}, - clock = new jasmineUnderTest.Clock(fakeGlobal, delayedFunctionSchedulerFactory, mockDate); + clock = new jasmineUnderTest.Clock( + fakeGlobal, + delayedFunctionSchedulerFactory, + mockDate + ); fakeGlobal.clearTimeout = replacedClearTimeout; @@ -126,13 +194,19 @@ describe("Clock", function() { expect(fakeGlobal.clearTimeout).toBe(replacedClearTimeout); }); - it("does not install if the current setInterval is not the original function on the global", function() { + it('does not install if the current setInterval is not the original function on the global', function() { var originalFakeSetInterval = function() {}, replacedSetInterval = function() {}, fakeGlobal = { setInterval: originalFakeSetInterval }, - delayedFunctionSchedulerFactory = jasmine.createSpy('delayedFunctionSchedulerFactory'), + delayedFunctionSchedulerFactory = jasmine.createSpy( + 'delayedFunctionSchedulerFactory' + ), mockDate = {}, - clock = new jasmineUnderTest.Clock(fakeGlobal, delayedFunctionSchedulerFactory, mockDate); + clock = new jasmineUnderTest.Clock( + fakeGlobal, + delayedFunctionSchedulerFactory, + mockDate + ); fakeGlobal.setInterval = replacedSetInterval; @@ -144,13 +218,19 @@ describe("Clock", function() { expect(fakeGlobal.setInterval).toBe(replacedSetInterval); }); - it("does not install if the current clearInterval is not the original function on the global", function() { + it('does not install if the current clearInterval is not the original function on the global', function() { var originalFakeClearInterval = function() {}, replacedClearInterval = function() {}, fakeGlobal = { clearInterval: originalFakeClearInterval }, - delayedFunctionSchedulerFactory = jasmine.createSpy('delayedFunctionSchedulerFactory'), + delayedFunctionSchedulerFactory = jasmine.createSpy( + 'delayedFunctionSchedulerFactory' + ), mockDate = {}, - clock = new jasmineUnderTest.Clock(fakeGlobal, delayedFunctionSchedulerFactory, mockDate); + clock = new jasmineUnderTest.Clock( + fakeGlobal, + delayedFunctionSchedulerFactory, + mockDate + ); fakeGlobal.clearInterval = replacedClearInterval; @@ -162,58 +242,84 @@ describe("Clock", function() { expect(fakeGlobal.clearInterval).toBe(replacedClearInterval); }); - it("replaces the global timer functions on uninstall", function() { - var fakeSetTimeout = jasmine.createSpy("global setTimeout"), - fakeClearTimeout = jasmine.createSpy("global clearTimeout"), - fakeSetInterval = jasmine.createSpy("global setInterval"), - fakeClearInterval = jasmine.createSpy("global clearInterval"), + it('replaces the global timer functions on uninstall', function() { + var fakeSetTimeout = jasmine.createSpy('global setTimeout'), + fakeClearTimeout = jasmine.createSpy('global clearTimeout'), + fakeSetInterval = jasmine.createSpy('global setInterval'), + fakeClearInterval = jasmine.createSpy('global clearInterval'), fakeGlobal = { setTimeout: fakeSetTimeout, clearTimeout: fakeClearTimeout, setInterval: fakeSetInterval, clearInterval: fakeClearInterval }, - delayedFunctionScheduler = jasmine.createSpyObj("delayedFunctionScheduler", ["scheduleFunction", "reset"]), - delayedFn = jasmine.createSpy("delayedFn"), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate); + delayedFunctionScheduler = jasmine.createSpyObj( + 'delayedFunctionScheduler', + ['scheduleFunction', 'reset'] + ), + delayedFn = jasmine.createSpy('delayedFn'), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); clock.install(); clock.uninstall(); fakeGlobal.setTimeout(delayedFn, 0); - fakeGlobal.clearTimeout("foo"); + fakeGlobal.clearTimeout('foo'); fakeGlobal.setInterval(delayedFn, 10); - fakeGlobal.clearInterval("bar"); + fakeGlobal.clearInterval('bar'); expect(fakeSetTimeout).toHaveBeenCalledWith(delayedFn, 0); - expect(fakeClearTimeout).toHaveBeenCalledWith("foo"); + expect(fakeClearTimeout).toHaveBeenCalledWith('foo'); expect(fakeSetInterval).toHaveBeenCalledWith(delayedFn, 10); - expect(fakeClearInterval).toHaveBeenCalledWith("bar"); + expect(fakeClearInterval).toHaveBeenCalledWith('bar'); expect(delayedFunctionScheduler.scheduleFunction).not.toHaveBeenCalled(); }); - it("can be installed for the duration of a passed in function and uninstalled when done", function() { - var fakeSetTimeout = jasmine.createSpy("global setTimeout"), - fakeClearTimeout = jasmine.createSpy("global clearTimeout"), - fakeSetInterval = jasmine.createSpy("global setInterval"), - fakeClearInterval = jasmine.createSpy("global clearInterval"), + it('can be installed for the duration of a passed in function and uninstalled when done', function() { + var fakeSetTimeout = jasmine.createSpy('global setTimeout'), + fakeClearTimeout = jasmine.createSpy('global clearTimeout'), + fakeSetInterval = jasmine.createSpy('global setInterval'), + fakeClearInterval = jasmine.createSpy('global clearInterval'), fakeGlobal = { setTimeout: fakeSetTimeout, clearTimeout: fakeClearTimeout, setInterval: fakeSetInterval, clearInterval: fakeClearInterval }, - delayedFunctionScheduler = jasmine.createSpyObj("delayedFunctionScheduler", ["scheduleFunction", "reset", "removeFunctionWithId"]), - delayedFn = jasmine.createSpy("delayedFn"), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate), + delayedFunctionScheduler = jasmine.createSpyObj( + 'delayedFunctionScheduler', + ['scheduleFunction', 'reset', 'removeFunctionWithId'] + ), + delayedFn = jasmine.createSpy('delayedFn'), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ), passedFunctionCalled = false; clock.withMock(function() { fakeGlobal.setTimeout(delayedFn, 0); - fakeGlobal.clearTimeout("foo"); + fakeGlobal.clearTimeout('foo'); fakeGlobal.setInterval(delayedFn, 10); - fakeGlobal.clearInterval("bar"); + fakeGlobal.clearInterval('bar'); passedFunctionCalled = true; }); @@ -228,40 +334,53 @@ describe("Clock", function() { delayedFunctionScheduler.scheduleFunction.calls.reset(); fakeGlobal.setTimeout(delayedFn, 0); - fakeGlobal.clearTimeout("foo"); + fakeGlobal.clearTimeout('foo'); fakeGlobal.setInterval(delayedFn, 10); - fakeGlobal.clearInterval("bar"); + fakeGlobal.clearInterval('bar'); expect(fakeSetTimeout).toHaveBeenCalledWith(delayedFn, 0); - expect(fakeClearTimeout).toHaveBeenCalledWith("foo"); + expect(fakeClearTimeout).toHaveBeenCalledWith('foo'); expect(fakeSetInterval).toHaveBeenCalledWith(delayedFn, 10); - expect(fakeClearInterval).toHaveBeenCalledWith("bar"); + expect(fakeClearInterval).toHaveBeenCalledWith('bar'); expect(delayedFunctionScheduler.scheduleFunction).not.toHaveBeenCalled(); }); - it("can be installed for the duration of a passed in function and uninstalled if an error is thrown", function() { - var fakeSetTimeout = jasmine.createSpy("global setTimeout"), - fakeClearTimeout = jasmine.createSpy("global clearTimeout"), - fakeSetInterval = jasmine.createSpy("global setInterval"), - fakeClearInterval = jasmine.createSpy("global clearInterval"), + it('can be installed for the duration of a passed in function and uninstalled if an error is thrown', function() { + var fakeSetTimeout = jasmine.createSpy('global setTimeout'), + fakeClearTimeout = jasmine.createSpy('global clearTimeout'), + fakeSetInterval = jasmine.createSpy('global setInterval'), + fakeClearInterval = jasmine.createSpy('global clearInterval'), fakeGlobal = { setTimeout: fakeSetTimeout, clearTimeout: fakeClearTimeout, setInterval: fakeSetInterval, clearInterval: fakeClearInterval }, - delayedFunctionScheduler = jasmine.createSpyObj("delayedFunctionScheduler", ["scheduleFunction", "reset", "removeFunctionWithId"]), - delayedFn = jasmine.createSpy("delayedFn"), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate), + delayedFunctionScheduler = jasmine.createSpyObj( + 'delayedFunctionScheduler', + ['scheduleFunction', 'reset', 'removeFunctionWithId'] + ), + delayedFn = jasmine.createSpy('delayedFn'), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ), passedFunctionCalled = false; expect(function() { clock.withMock(function() { fakeGlobal.setTimeout(delayedFn, 0); - fakeGlobal.clearTimeout("foo"); + fakeGlobal.clearTimeout('foo'); fakeGlobal.setInterval(delayedFn, 10); - fakeGlobal.clearInterval("bar"); + fakeGlobal.clearInterval('bar'); passedFunctionCalled = true; throw 'oops'; }); @@ -278,25 +397,35 @@ describe("Clock", function() { delayedFunctionScheduler.scheduleFunction.calls.reset(); fakeGlobal.setTimeout(delayedFn, 0); - fakeGlobal.clearTimeout("foo"); + fakeGlobal.clearTimeout('foo'); fakeGlobal.setInterval(delayedFn, 10); - fakeGlobal.clearInterval("bar"); + fakeGlobal.clearInterval('bar'); expect(fakeSetTimeout).toHaveBeenCalledWith(delayedFn, 0); - expect(fakeClearTimeout).toHaveBeenCalledWith("foo"); + expect(fakeClearTimeout).toHaveBeenCalledWith('foo'); expect(fakeSetInterval).toHaveBeenCalledWith(delayedFn, 10); - expect(fakeClearInterval).toHaveBeenCalledWith("bar"); + expect(fakeClearInterval).toHaveBeenCalledWith('bar'); expect(delayedFunctionScheduler.scheduleFunction).not.toHaveBeenCalled(); }); - it("schedules the delayed function (via setTimeout) with the fake timer", function() { + it('schedules the delayed function (via setTimeout) with the fake timer', function() { var fakeSetTimeout = jasmine.createSpy('setTimeout'), scheduleFunction = jasmine.createSpy('scheduleFunction'), delayedFunctionScheduler = { scheduleFunction: scheduleFunction }, fakeGlobal = { setTimeout: fakeSetTimeout }, delayedFn = jasmine.createSpy('delayedFn'), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ), timeout = new clock.FakeTimeout(); clock.install(); @@ -305,21 +434,43 @@ describe("Clock", function() { expect(fakeSetTimeout).not.toHaveBeenCalled(); if (!NODE_JS) { - expect(delayedFunctionScheduler.scheduleFunction).toHaveBeenCalledWith(delayedFn, 0, ['a', 'b']); + expect(delayedFunctionScheduler.scheduleFunction).toHaveBeenCalledWith( + delayedFn, + 0, + ['a', 'b'] + ); } else { - expect(delayedFunctionScheduler.scheduleFunction).toHaveBeenCalledWith(delayedFn, 0, ['a', 'b'], false, timeout); + expect(delayedFunctionScheduler.scheduleFunction).toHaveBeenCalledWith( + delayedFn, + 0, + ['a', 'b'], + false, + timeout + ); } }); - it("returns an id for the delayed function", function() { + it('returns an id for the delayed function', function() { var fakeSetTimeout = jasmine.createSpy('setTimeout'), scheduleId = 123, - scheduleFunction = jasmine.createSpy('scheduleFunction').and.returnValue(scheduleId), - delayedFunctionScheduler = {scheduleFunction: scheduleFunction}, + scheduleFunction = jasmine + .createSpy('scheduleFunction') + .and.returnValue(scheduleId), + delayedFunctionScheduler = { scheduleFunction: scheduleFunction }, fakeGlobal = { setTimeout: fakeSetTimeout }, delayedFn = jasmine.createSpy('delayedFn'), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ), timeout; clock.install(); @@ -332,30 +483,54 @@ describe("Clock", function() { } }); - it("clears the scheduled function with the scheduler", function() { + it('clears the scheduled function with the scheduler', function() { var fakeClearTimeout = jasmine.createSpy('clearTimeout'), - delayedFunctionScheduler = jasmine.createSpyObj('delayedFunctionScheduler', ['removeFunctionWithId']), + delayedFunctionScheduler = jasmine.createSpyObj( + 'delayedFunctionScheduler', + ['removeFunctionWithId'] + ), fakeGlobal = { setTimeout: fakeClearTimeout }, - delayedFn = jasmine.createSpy('delayedFn'), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate); + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); clock.install(); clock.clearTimeout(123); expect(fakeClearTimeout).not.toHaveBeenCalled(); - expect(delayedFunctionScheduler.removeFunctionWithId).toHaveBeenCalledWith(123); + expect(delayedFunctionScheduler.removeFunctionWithId).toHaveBeenCalledWith( + 123 + ); }); - it("schedules the delayed function with the fake timer", function() { + it('schedules the delayed function with the fake timer', function() { var fakeSetInterval = jasmine.createSpy('setInterval'), scheduleFunction = jasmine.createSpy('scheduleFunction'), - delayedFunctionScheduler = {scheduleFunction: scheduleFunction}, + delayedFunctionScheduler = { scheduleFunction: scheduleFunction }, fakeGlobal = { setInterval: fakeSetInterval }, delayedFn = jasmine.createSpy('delayedFn'), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate), - timeout = new clock.FakeTimeout; + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ), + timeout = new clock.FakeTimeout(); clock.install(); clock.setInterval(delayedFn, 0, 'a', 'b'); @@ -363,21 +538,44 @@ describe("Clock", function() { expect(fakeSetInterval).not.toHaveBeenCalled(); if (!NODE_JS) { - expect(delayedFunctionScheduler.scheduleFunction).toHaveBeenCalledWith(delayedFn, 0, ['a', 'b'], true); + expect(delayedFunctionScheduler.scheduleFunction).toHaveBeenCalledWith( + delayedFn, + 0, + ['a', 'b'], + true + ); } else { - expect(delayedFunctionScheduler.scheduleFunction).toHaveBeenCalledWith(delayedFn, 0, ['a', 'b'], true, timeout); + expect(delayedFunctionScheduler.scheduleFunction).toHaveBeenCalledWith( + delayedFn, + 0, + ['a', 'b'], + true, + timeout + ); } }); - it("returns an id for the delayed function", function() { + it('returns an id for the delayed function', function() { var fakeSetInterval = jasmine.createSpy('setInterval'), scheduleId = 123, - scheduleFunction = jasmine.createSpy('scheduleFunction').and.returnValue(scheduleId), - delayedFunctionScheduler = {scheduleFunction: scheduleFunction}, + scheduleFunction = jasmine + .createSpy('scheduleFunction') + .and.returnValue(scheduleId), + delayedFunctionScheduler = { scheduleFunction: scheduleFunction }, fakeGlobal = { setInterval: fakeSetInterval }, delayedFn = jasmine.createSpy('delayedFn'), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ), interval; clock.install(); @@ -390,38 +588,65 @@ describe("Clock", function() { } }); - it("clears the scheduled function with the scheduler", function() { + it('clears the scheduled function with the scheduler', function() { var clearInterval = jasmine.createSpy('clearInterval'), - delayedFunctionScheduler = jasmine.createSpyObj('delayedFunctionScheduler', ['removeFunctionWithId']), + delayedFunctionScheduler = jasmine.createSpyObj( + 'delayedFunctionScheduler', + ['removeFunctionWithId'] + ), fakeGlobal = { setInterval: clearInterval }, - delayedFn = jasmine.createSpy('delayedFn'), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock(fakeGlobal, function () { return delayedFunctionScheduler; }, mockDate); + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + fakeGlobal, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); clock.install(); clock.clearInterval(123); expect(clearInterval).not.toHaveBeenCalled(); - expect(delayedFunctionScheduler.removeFunctionWithId).toHaveBeenCalledWith(123); + expect(delayedFunctionScheduler.removeFunctionWithId).toHaveBeenCalledWith( + 123 + ); }); - it("gives you a friendly reminder if the Clock is not installed and you tick", function() { - var clock = new jasmineUnderTest.Clock({}, jasmine.createSpyObj('delayedFunctionScheduler', ['tick'])); + it('gives you a friendly reminder if the Clock is not installed and you tick', function() { + var clock = new jasmineUnderTest.Clock( + {}, + jasmine.createSpyObj('delayedFunctionScheduler', ['tick']) + ); expect(function() { clock.tick(50); }).toThrow(); }); }); -describe("Clock (acceptance)", function() { - it("can run setTimeouts/setIntervals synchronously", function() { +describe('Clock (acceptance)', function() { + it('can run setTimeouts/setIntervals synchronously', function() { var delayedFn1 = jasmine.createSpy('delayedFn1'), delayedFn2 = jasmine.createSpy('delayedFn2'), delayedFn3 = jasmine.createSpy('delayedFn3'), recurring1 = jasmine.createSpy('recurring1'), delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock({setTimeout: setTimeout}, function () { return delayedFunctionScheduler; }, mockDate); + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + { setTimeout: setTimeout }, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); clock.install(); @@ -464,11 +689,21 @@ describe("Clock (acceptance)", function() { expect(recurring1.calls.count()).toBe(4); }); - it("can clear a previously set timeout", function() { + it('can clear a previously set timeout', function() { var clearedFn = jasmine.createSpy('clearedFn'), delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock({setTimeout: function() {}}, function () { return delayedFunctionScheduler; }, mockDate), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + { setTimeout: function() {} }, + function() { + return delayedFunctionScheduler; + }, + mockDate + ), timeoutId; clock.install(); @@ -485,8 +720,18 @@ describe("Clock (acceptance)", function() { it("can clear a previously set interval using that interval's handler", function() { var spy = jasmine.createSpy('spy'), delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock({setInterval: function() {}}, function () { return delayedFunctionScheduler; }, mockDate), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + { setInterval: function() {} }, + function() { + return delayedFunctionScheduler; + }, + mockDate + ), intervalId; clock.install(); @@ -500,11 +745,21 @@ describe("Clock (acceptance)", function() { expect(spy.calls.count()).toEqual(1); }); - it("correctly schedules functions after the Clock has advanced", function() { + it('correctly schedules functions after the Clock has advanced', function() { var delayedFn1 = jasmine.createSpy('delayedFn1'), delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock({setTimeout: function() {}}, function () { return delayedFunctionScheduler; }, mockDate); + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + { setTimeout: function() {} }, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); clock.install(); @@ -516,14 +771,26 @@ describe("Clock (acceptance)", function() { expect(delayedFn1).toHaveBeenCalled(); }); - it("correctly schedules functions while the Clock is advancing", function() { + it('correctly schedules functions while the Clock is advancing', function() { var delayedFn1 = jasmine.createSpy('delayedFn1'), - delayedFn2 = jasmine.createSpy('delayedFn2'), - delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock({setTimeout: function() {}}, function () { return delayedFunctionScheduler; }, mockDate); + delayedFn2 = jasmine.createSpy('delayedFn2'), + delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + { setTimeout: function() {} }, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); - delayedFn1.and.callFake(function() { clock.setTimeout(delayedFn2, 0); }); + delayedFn1.and.callFake(function() { + clock.setTimeout(delayedFn2, 0); + }); clock.install(); clock.setTimeout(delayedFn1, 5); @@ -535,14 +802,26 @@ describe("Clock (acceptance)", function() { expect(delayedFn2).toHaveBeenCalled(); }); - it("correctly calls functions scheduled while the Clock is advancing", function() { + it('correctly calls functions scheduled while the Clock is advancing', function() { var delayedFn1 = jasmine.createSpy('delayedFn1'), - delayedFn2 = jasmine.createSpy('delayedFn2'), - delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock({setTimeout: function() {}}, function () { return delayedFunctionScheduler; }, mockDate); + delayedFn2 = jasmine.createSpy('delayedFn2'), + delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + { setTimeout: function() {} }, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); - delayedFn1.and.callFake(function() { clock.setTimeout(delayedFn2, 1); }); + delayedFn1.and.callFake(function() { + clock.setTimeout(delayedFn2, 1); + }); clock.install(); clock.setTimeout(delayedFn1, 5); @@ -551,12 +830,22 @@ describe("Clock (acceptance)", function() { expect(delayedFn2).toHaveBeenCalled(); }); - it("correctly schedules functions scheduled while the Clock is advancing but after the Clock is uninstalled", function() { + it('correctly schedules functions scheduled while the Clock is advancing but after the Clock is uninstalled', function() { var delayedFn1 = jasmine.createSpy('delayedFn1'), - delayedFn2 = jasmine.createSpy('delayedFn2'), - delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - mockDate = { install: function() {}, tick: function() {}, uninstall: function() {} }, - clock = new jasmineUnderTest.Clock({setTimeout: function() {}}, function () { return delayedFunctionScheduler; }, mockDate); + delayedFn2 = jasmine.createSpy('delayedFn2'), + delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), + mockDate = { + install: function() {}, + tick: function() {}, + uninstall: function() {} + }, + clock = new jasmineUnderTest.Clock( + { setTimeout: function() {} }, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); delayedFn1.and.callFake(function() { clock.uninstall(); @@ -575,11 +864,17 @@ describe("Clock (acceptance)", function() { expect(delayedFn2).toHaveBeenCalled(); }); - it("does not mock the Date object by default", function() { - var delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - global = {Date: Date}, + it('does not mock the Date object by default', function() { + var delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), + global = { Date: Date }, mockDate = new jasmineUnderTest.MockDate(global), - clock = new jasmineUnderTest.Clock({setTimeout: setTimeout}, function () { return delayedFunctionScheduler; }, mockDate); + clock = new jasmineUnderTest.Clock( + { setTimeout: setTimeout }, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); clock.install(); @@ -592,11 +887,17 @@ describe("Clock (acceptance)", function() { expect(new global.Date().getTime() - now).not.toEqual(50); }); - it("mocks the Date object and sets it to current time", function() { + it('mocks the Date object and sets it to current time', function() { var delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - global = {Date: Date}, + global = { Date: Date }, mockDate = new jasmineUnderTest.MockDate(global), - clock = new jasmineUnderTest.Clock({setTimeout: setTimeout}, function () { return delayedFunctionScheduler; }, mockDate); + clock = new jasmineUnderTest.Clock( + { setTimeout: setTimeout }, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); clock.install().mockDate(); @@ -616,14 +917,19 @@ describe("Clock (acceptance)", function() { expect(timeoutDate - now).toEqual(150); }); - it("mocks the Date object and sets it to a given time", function() { + it('mocks the Date object and sets it to a given time', function() { var delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - global = {Date: Date}, + global = { Date: Date }, mockDate = new jasmineUnderTest.MockDate(global), - clock = new jasmineUnderTest.Clock({setTimeout: setTimeout}, function () { return delayedFunctionScheduler; }, mockDate), + clock = new jasmineUnderTest.Clock( + { setTimeout: setTimeout }, + function() { + return delayedFunctionScheduler; + }, + mockDate + ), baseTime = new Date(2013, 9, 23); - clock.install().mockDate(baseTime); var now = new global.Date().getTime(); @@ -644,17 +950,25 @@ describe("Clock (acceptance)", function() { expect(timeoutDate).toEqual(baseTime.getTime() + 150); }); - it("mocks the Date object and updates the date per delayed function", function () { + it('mocks the Date object and updates the date per delayed function', function() { var delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - global = {Date: Date}, + global = { Date: Date }, mockDate = new jasmineUnderTest.MockDate(global), - clock = new jasmineUnderTest.Clock({setTimeout: setTimeout}, function () { return delayedFunctionScheduler; }, mockDate), + clock = new jasmineUnderTest.Clock( + { setTimeout: setTimeout }, + function() { + return delayedFunctionScheduler; + }, + mockDate + ), baseTime = new Date(); clock.install().mockDate(baseTime); var actualTimes = []; - var pushCurrentTime = function() { actualTimes.push(global.Date().getTime()); }; + var pushCurrentTime = function() { + actualTimes.push(global.Date().getTime()); + }; delayedFunctionScheduler.scheduleFunction(pushCurrentTime); delayedFunctionScheduler.scheduleFunction(pushCurrentTime, 1); delayedFunctionScheduler.scheduleFunction(pushCurrentTime, 3); @@ -668,20 +982,30 @@ describe("Clock (acceptance)", function() { clock.tick(1); expect(global.Date().getTime()).toEqual(baseTime.getTime() + 5); - expect(actualTimes).toEqual([baseTime.getTime(), baseTime.getTime() + 1, baseTime.getTime() + 3]); + expect(actualTimes).toEqual([ + baseTime.getTime(), + baseTime.getTime() + 1, + baseTime.getTime() + 3 + ]); }); - it('correctly clears a scheduled timeout while the Clock is advancing', function () { + it('correctly clears a scheduled timeout while the Clock is advancing', function() { var delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - global = {Date: Date, setTimeout: undefined}, + global = { Date: Date, setTimeout: undefined }, mockDate = new jasmineUnderTest.MockDate(global), - clock = new jasmineUnderTest.Clock(global, function () { return delayedFunctionScheduler; }, mockDate); + clock = new jasmineUnderTest.Clock( + global, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); clock.install(); var timerId2; - global.setTimeout(function () { + global.setTimeout(function() { global.clearTimeout(timerId2); }, 100); @@ -690,16 +1014,22 @@ describe("Clock (acceptance)", function() { clock.tick(100); }); - it('correctly clears a scheduled interval while the Clock is advancing', function () { + it('correctly clears a scheduled interval while the Clock is advancing', function() { var delayedFunctionScheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - global = {Date: Date, setTimeout: undefined}, + global = { Date: Date, setTimeout: undefined }, mockDate = new jasmineUnderTest.MockDate(global), - clock = new jasmineUnderTest.Clock(global, function () { return delayedFunctionScheduler; }, mockDate); + clock = new jasmineUnderTest.Clock( + global, + function() { + return delayedFunctionScheduler; + }, + mockDate + ); clock.install(); var timerId2; - var timerId1 = global.setInterval(function () { + global.setInterval(function() { global.clearInterval(timerId2); }, 100); diff --git a/spec/core/DelayedFunctionSchedulerSpec.js b/spec/core/DelayedFunctionSchedulerSpec.js index f04d8f39..d06a66c1 100644 --- a/spec/core/DelayedFunctionSchedulerSpec.js +++ b/spec/core/DelayedFunctionSchedulerSpec.js @@ -1,5 +1,5 @@ -describe("DelayedFunctionScheduler", function() { - it("schedules a function for later execution", function() { +describe('DelayedFunctionScheduler', function() { + it('schedules a function for later execution', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), fn = jasmine.createSpy('fn'); @@ -12,9 +12,9 @@ describe("DelayedFunctionScheduler", function() { expect(fn).toHaveBeenCalled(); }); - it("schedules a string for later execution", function() { + it('schedules a string for later execution', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), - strfn = "horrible = true;"; + strfn = 'horrible = true;'; scheduler.scheduleFunction(strfn, 0); @@ -23,7 +23,7 @@ describe("DelayedFunctionScheduler", function() { expect(horrible).toEqual(true); }); - it("#tick defaults to 0", function() { + it('#tick defaults to 0', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), fn = jasmine.createSpy('fn'); @@ -36,7 +36,7 @@ describe("DelayedFunctionScheduler", function() { expect(fn).toHaveBeenCalled(); }); - it("defaults delay to 0", function() { + it('defaults delay to 0', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), fn = jasmine.createSpy('fn'); @@ -49,7 +49,7 @@ describe("DelayedFunctionScheduler", function() { expect(fn).toHaveBeenCalled(); }); - it("optionally passes params to scheduled functions", function() { + it('optionally passes params to scheduled functions', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), fn = jasmine.createSpy('fn'); @@ -62,7 +62,7 @@ describe("DelayedFunctionScheduler", function() { expect(fn).toHaveBeenCalledWith('foo', 'bar'); }); - it("scheduled fns can optionally reoccur", function() { + it('scheduled fns can optionally reoccur', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), fn = jasmine.createSpy('fn'); @@ -81,23 +81,20 @@ describe("DelayedFunctionScheduler", function() { scheduler.tick(21); expect(fn.calls.count()).toBe(4); - }); - it("increments scheduled fns ids unless one is passed", function() { + it('increments scheduled fns ids unless one is passed', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(); - expect(scheduler.scheduleFunction(function() { - }, 0)).toBe(1); - expect(scheduler.scheduleFunction(function() { - }, 0)).toBe(2); - expect(scheduler.scheduleFunction(function() { - }, 0, [], false, 123)).toBe(123); - expect(scheduler.scheduleFunction(function() { - }, 0)).toBe(3); + expect(scheduler.scheduleFunction(function() {}, 0)).toBe(1); + expect(scheduler.scheduleFunction(function() {}, 0)).toBe(2); + expect(scheduler.scheduleFunction(function() {}, 0, [], false, 123)).toBe( + 123 + ); + expect(scheduler.scheduleFunction(function() {}, 0)).toBe(3); }); - it("#removeFunctionWithId removes a previously scheduled function with a given id", function() { + it('#removeFunctionWithId removes a previously scheduled function with a given id', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), fn = jasmine.createSpy('fn'), timeoutKey; @@ -113,7 +110,7 @@ describe("DelayedFunctionScheduler", function() { expect(fn).not.toHaveBeenCalled(); }); - it("executes recurring functions interleaved with regular functions in the correct order", function() { + it('executes recurring functions interleaved with regular functions in the correct order', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), fn = jasmine.createSpy('fn'), recurringCallCount = 0, @@ -134,12 +131,12 @@ describe("DelayedFunctionScheduler", function() { expect(fn).toHaveBeenCalled(); }); - it("schedules a function for later execution during a tick", function () { + it('schedules a function for later execution during a tick', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), fn = jasmine.createSpy('fn'), fnDelay = 10; - scheduler.scheduleFunction(function () { + scheduler.scheduleFunction(function() { scheduler.scheduleFunction(fn, fnDelay); }, 0); @@ -150,13 +147,13 @@ describe("DelayedFunctionScheduler", function() { expect(fn).toHaveBeenCalled(); }); - it("#removeFunctionWithId removes a previously scheduled function with a given id during a tick", function () { + it('#removeFunctionWithId removes a previously scheduled function with a given id during a tick', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), fn = jasmine.createSpy('fn'), fnDelay = 10, timeoutKey; - scheduler.scheduleFunction(function () { + scheduler.scheduleFunction(function() { scheduler.removeFunctionWithId(timeoutKey); }, 0); timeoutKey = scheduler.scheduleFunction(fn, fnDelay); @@ -168,7 +165,7 @@ describe("DelayedFunctionScheduler", function() { expect(fn).not.toHaveBeenCalled(); }); - it("executes recurring functions interleaved with regular functions and functions scheduled during a tick in the correct order", function () { + it('executes recurring functions interleaved with regular functions and functions scheduled during a tick in the correct order', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), fn = jasmine.createSpy('fn'), recurringCallCount = 0, @@ -185,7 +182,7 @@ describe("DelayedFunctionScheduler", function() { scheduling = jasmine.createSpy('scheduling').and.callFake(function() { expect(recurring.calls.count()).toBe(3); expect(fn).not.toHaveBeenCalled(); - scheduler.scheduleFunction(innerFn, 10); // 41ms absolute + scheduler.scheduleFunction(innerFn, 10); // 41ms absolute }); scheduler.scheduleFunction(recurring, 10, [], true); @@ -201,7 +198,7 @@ describe("DelayedFunctionScheduler", function() { expect(innerFn).toHaveBeenCalled(); }); - it("executes recurring functions after rescheduling them", function () { + it('executes recurring functions after rescheduling them', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), recurring = function() { expect(scheduler.scheduleFunction).toHaveBeenCalled(); @@ -209,12 +206,12 @@ describe("DelayedFunctionScheduler", function() { scheduler.scheduleFunction(recurring, 10, [], true); - spyOn(scheduler, "scheduleFunction"); + spyOn(scheduler, 'scheduleFunction'); scheduler.tick(10); }); - it("removes functions during a tick that runs the function", function() { + it('removes functions during a tick that runs the function', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), spy = jasmine.createSpy('fn'), spyAndRemove = jasmine.createSpy('fn'), @@ -235,14 +232,14 @@ describe("DelayedFunctionScheduler", function() { expect(spyAndRemove).toHaveBeenCalled(); }); - it("removes functions during the first tick that runs the function", function() { + it('removes functions during the first tick that runs the function', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), fn = jasmine.createSpy('fn'), fnDelay = 10, timeoutKey; timeoutKey = scheduler.scheduleFunction(fn, fnDelay, [], true); - scheduler.scheduleFunction(function () { + scheduler.scheduleFunction(function() { scheduler.removeFunctionWithId(timeoutKey); }, fnDelay); @@ -257,8 +254,7 @@ describe("DelayedFunctionScheduler", function() { it("does not remove a function that hasn't been added yet", function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), fn = jasmine.createSpy('fn'), - fnDelay = 10, - timeoutKey; + fnDelay = 10; scheduler.removeFunctionWithId('foo'); scheduler.scheduleFunction(fn, fnDelay, [], false, 'foo'); @@ -270,17 +266,16 @@ describe("DelayedFunctionScheduler", function() { expect(fn).toHaveBeenCalled(); }); - it("updates the mockDate per scheduled time", function () { + it('updates the mockDate per scheduled time', function() { var scheduler = new jasmineUnderTest.DelayedFunctionScheduler(), tickDate = jasmine.createSpy('tickDate'); - scheduler.scheduleFunction(function() {}); - scheduler.scheduleFunction(function() {}, 1); + scheduler.scheduleFunction(function() {}); + scheduler.scheduleFunction(function() {}, 1); - scheduler.tick(1, tickDate); + scheduler.tick(1, tickDate); - expect(tickDate).toHaveBeenCalledWith(0); - expect(tickDate).toHaveBeenCalledWith(1); - }) + expect(tickDate).toHaveBeenCalledWith(0); + expect(tickDate).toHaveBeenCalledWith(1); + }); }); - diff --git a/spec/core/EnvSpec.js b/spec/core/EnvSpec.js index 0cdad2cd..72c8d979 100644 --- a/spec/core/EnvSpec.js +++ b/spec/core/EnvSpec.js @@ -1,54 +1,63 @@ // TODO: Fix these unit tests! -describe("Env", function() { +describe('Env', function() { var env; beforeEach(function() { env = new jasmineUnderTest.Env(); }); - describe("#pending", function() { - it("throws the Pending Spec exception", function() { + describe('#pending', function() { + it('throws the Pending Spec exception', function() { expect(function() { env.pending(); }).toThrow(jasmineUnderTest.Spec.pendingSpecExceptionMessage); }); - it("throws the Pending Spec exception with a custom message", function() { + it('throws the Pending Spec exception with a custom message', function() { expect(function() { env.pending('custom message'); - }).toThrow(jasmineUnderTest.Spec.pendingSpecExceptionMessage + 'custom message'); + }).toThrow( + jasmineUnderTest.Spec.pendingSpecExceptionMessage + 'custom message' + ); }); }); - describe("#topSuite", function() { - it("returns the Jasmine top suite for users to traverse the spec tree", function() { + describe('#topSuite', function() { + it('returns the Jasmine top suite for users to traverse the spec tree', function() { var suite = env.topSuite(); expect(suite.description).toEqual('Jasmine__TopLevel__Suite'); }); }); it('can configure specs to throw errors on expectation failures', function() { - env.configure({oneFailurePerSpec: true}); + env.configure({ oneFailurePerSpec: true }); spyOn(jasmineUnderTest, 'Spec'); env.it('foo', function() {}); - expect(jasmineUnderTest.Spec).toHaveBeenCalledWith(jasmine.objectContaining({ - throwOnExpectationFailure: true - })); + expect(jasmineUnderTest.Spec).toHaveBeenCalledWith( + jasmine.objectContaining({ + throwOnExpectationFailure: true + }) + ); }); it('can configure suites to throw errors on expectation failures', function() { - env.configure({oneFailurePerSpec: true}); + env.configure({ oneFailurePerSpec: true }); spyOn(jasmineUnderTest, 'Suite'); env.describe('foo', function() {}); - expect(jasmineUnderTest.Suite).toHaveBeenCalledWith(jasmine.objectContaining({ - throwOnExpectationFailure: true - })); + expect(jasmineUnderTest.Suite).toHaveBeenCalledWith( + jasmine.objectContaining({ + throwOnExpectationFailure: true + }) + ); }); describe('promise library', function() { it('can be configured with a custom library', function() { - var myLibrary = { resolve: jasmine.createSpy(), reject: jasmine.createSpy() }; + var myLibrary = { + resolve: jasmine.createSpy(), + reject: jasmine.createSpy() + }; env.configure({ Promise: myLibrary }); }); @@ -57,28 +66,34 @@ describe("Env", function() { expect(function() { env.configure({ Promise: myLibrary }); - }).toThrowError('Custom promise library missing `resolve`/`reject` functions'); + }).toThrowError( + 'Custom promise library missing `resolve`/`reject` functions' + ); }); }); it('defaults to multiple failures for specs', function() { spyOn(jasmineUnderTest, 'Spec'); - env.it('bar', function() {}); - expect(jasmineUnderTest.Spec).toHaveBeenCalledWith(jasmine.objectContaining({ - throwOnExpectationFailure: false - })); + env.it('bar', function() {}); + expect(jasmineUnderTest.Spec).toHaveBeenCalledWith( + jasmine.objectContaining({ + throwOnExpectationFailure: false + }) + ); }); it('defaults to multiple failures for suites', function() { spyOn(jasmineUnderTest, 'Suite'); env.describe('foo', function() {}); - expect(jasmineUnderTest.Suite).toHaveBeenCalledWith(jasmine.objectContaining({ - throwOnExpectationFailure: false - })); + expect(jasmineUnderTest.Suite).toHaveBeenCalledWith( + jasmine.objectContaining({ + throwOnExpectationFailure: false + }) + ); }); - describe('#describe', function () { - it("throws an error when given arguments", function() { + describe('#describe', function() { + it('throws an error when given arguments', function() { expect(function() { env.describe('done method', function(done) {}); }).toThrowError('describe does not expect any arguments'); @@ -92,29 +107,41 @@ describe("Env", function() { // anything other than a function throws an error. expect(function() { env.describe('undefined arg', undefined); - }).toThrowError(/describe expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/); + }).toThrowError( + /describe expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/ + ); expect(function() { env.describe('null arg', null); - }).toThrowError(/describe expects a function argument; received \[object (Null|DOMWindow|Object)\]/); + }).toThrowError( + /describe expects a function argument; received \[object (Null|DOMWindow|Object)\]/ + ); expect(function() { env.describe('array arg', []); - }).toThrowError('describe expects a function argument; received [object Array]'); + }).toThrowError( + 'describe expects a function argument; received [object Array]' + ); expect(function() { env.describe('object arg', {}); - }).toThrowError('describe expects a function argument; received [object Object]'); + }).toThrowError( + 'describe expects a function argument; received [object Object]' + ); expect(function() { env.describe('fn arg', function() {}); - }).not.toThrowError('describe expects a function argument; received [object Function]'); + }).not.toThrowError( + 'describe expects a function argument; received [object Function]' + ); }); }); - describe('#it', function () { + describe('#it', function() { it('throws an error when it receives a non-fn argument', function() { expect(function() { env.it('undefined arg', null); - }).toThrowError(/it expects a function argument; received \[object (Null|DOMWindow|Object)\]/); + }).toThrowError( + /it expects a function argument; received \[object (Null|DOMWindow|Object)\]/ + ); }); it('does not throw when it is not given a fn argument', function() { @@ -144,7 +171,9 @@ describe("Env", function() { it('throws an error when it receives a non-fn argument', function() { expect(function() { env.xit('undefined arg', null); - }).toThrowError(/xit expects a function argument; received \[object (Null|DOMWindow|Object)\]/); + }).toThrowError( + /xit expects a function argument; received \[object (Null|DOMWindow|Object)\]/ + ); }); it('does not throw when it is not given a fn argument', function() { @@ -161,19 +190,23 @@ describe("Env", function() { }); }); - describe('#fit', function () { + describe('#fit', function() { it('throws an error when it receives a non-fn argument', function() { expect(function() { env.fit('undefined arg', undefined); - }).toThrowError(/fit expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/); + }).toThrowError( + /fit expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/ + ); }); }); - describe('#beforeEach', function () { + describe('#beforeEach', function() { it('throws an error when it receives a non-fn argument', function() { expect(function() { env.beforeEach(undefined); - }).toThrowError(/beforeEach expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/); + }).toThrowError( + /beforeEach expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/ + ); }); it('accepts an async function', function() { @@ -184,11 +217,13 @@ describe("Env", function() { }); }); - describe('#beforeAll', function () { + describe('#beforeAll', function() { it('throws an error when it receives a non-fn argument', function() { expect(function() { env.beforeAll(undefined); - }).toThrowError(/beforeAll expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/); + }).toThrowError( + /beforeAll expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/ + ); }); it('accepts an async function', function() { @@ -199,11 +234,13 @@ describe("Env", function() { }); }); - describe('#afterEach', function () { + describe('#afterEach', function() { it('throws an error when it receives a non-fn argument', function() { expect(function() { env.afterEach(undefined); - }).toThrowError(/afterEach expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/); + }).toThrowError( + /afterEach expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/ + ); }); it('accepts an async function', function() { @@ -214,11 +251,13 @@ describe("Env", function() { }); }); - describe('#afterAll', function () { + describe('#afterAll', function() { it('throws an error when it receives a non-fn argument', function() { expect(function() { env.afterAll(undefined); - }).toThrowError(/afterAll expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/); + }).toThrowError( + /afterAll expects a function argument; received \[object (Undefined|DOMWindow|Object)\]/ + ); }); it('accepts an async function', function() { @@ -231,7 +270,11 @@ describe("Env", function() { describe('when not constructed with suppressLoadErrors: true', function() { it('installs a global error handler on construction', function() { - var globalErrors = jasmine.createSpyObj('globalErrors', ['install', 'pushListener', 'popListener']); + var globalErrors = jasmine.createSpyObj('globalErrors', [ + 'install', + 'pushListener', + 'popListener' + ]); spyOn(jasmineUnderTest, 'GlobalErrors').and.returnValue(globalErrors); new jasmineUnderTest.Env(); expect(globalErrors.install).toHaveBeenCalled(); @@ -240,9 +283,13 @@ describe("Env", function() { describe('when constructed with suppressLoadErrors: true', function() { it('does not install a global error handler until execute is called', function() { - var globalErrors = jasmine.createSpyObj('globalErrors', ['install', 'pushListener', 'popListener']); + var globalErrors = jasmine.createSpyObj('globalErrors', [ + 'install', + 'pushListener', + 'popListener' + ]); spyOn(jasmineUnderTest, 'GlobalErrors').and.returnValue(globalErrors); - env = new jasmineUnderTest.Env({suppressLoadErrors: true}); + env = new jasmineUnderTest.Env({ suppressLoadErrors: true }); expect(globalErrors.install).not.toHaveBeenCalled(); env.execute(); expect(globalErrors.install).toHaveBeenCalled(); diff --git a/spec/core/ExceptionFormatterSpec.js b/spec/core/ExceptionFormatterSpec.js index 40316190..2242cf27 100644 --- a/spec/core/ExceptionFormatterSpec.js +++ b/spec/core/ExceptionFormatterSpec.js @@ -1,5 +1,5 @@ -describe("ExceptionFormatter", function() { - describe("#message", function() { +describe('ExceptionFormatter', function() { + describe('#message', function() { it('formats Firefox exception messages', function() { var sampleFirefoxException = { fileName: 'foo.js', @@ -10,7 +10,9 @@ describe("ExceptionFormatter", function() { exceptionFormatter = new jasmineUnderTest.ExceptionFormatter(), message = exceptionFormatter.message(sampleFirefoxException); - expect(message).toEqual('A Classic Mistake: you got your foo in my bar in foo.js (line 1978)'); + expect(message).toEqual( + 'A Classic Mistake: you got your foo in my bar in foo.js (line 1978)' + ); }); it('formats Webkit exception messages', function() { @@ -23,7 +25,9 @@ describe("ExceptionFormatter", function() { exceptionFormatter = new jasmineUnderTest.ExceptionFormatter(), message = exceptionFormatter.message(sampleWebkitException); - expect(message).toEqual('A Classic Mistake: you got your foo in my bar in foo.js (line 1978)'); + expect(message).toEqual( + 'A Classic Mistake: you got your foo in my bar in foo.js (line 1978)' + ); }); it('formats V8 exception messages', function() { @@ -38,10 +42,10 @@ describe("ExceptionFormatter", function() { }); it('formats unnamed exceptions with message', function() { - var unnamedError = {message: 'This is an unnamed error message.'}; + var unnamedError = { message: 'This is an unnamed error message.' }; var exceptionFormatter = new jasmineUnderTest.ExceptionFormatter(), - message = exceptionFormatter.message(unnamedError); + message = exceptionFormatter.message(unnamedError); expect(message).toEqual('This is an unnamed error message.'); }); @@ -54,32 +58,39 @@ describe("ExceptionFormatter", function() { var emptyError = new EmptyError(); var exceptionFormatter = new jasmineUnderTest.ExceptionFormatter(), - message = exceptionFormatter.message(emptyError); + message = exceptionFormatter.message(emptyError); expect(message).toEqual('[EmptyError] thrown'); }); it("formats thrown exceptions that aren't errors", function() { - var thrown = "crazy error", - exceptionFormatter = new jasmineUnderTest.ExceptionFormatter(), - message = exceptionFormatter.message(thrown); + var thrown = 'crazy error', + exceptionFormatter = new jasmineUnderTest.ExceptionFormatter(), + message = exceptionFormatter.message(thrown); - expect(message).toEqual("crazy error thrown"); + expect(message).toEqual('crazy error thrown'); }); }); - describe("#stack", function() { - it("formats stack traces", function() { + describe('#stack', function() { + it('formats stack traces', function() { var error; - try { throw new Error("an error") } catch(e) { error = e; } + try { + throw new Error('an error'); + } catch (e) { + error = e; + } - expect(new jasmineUnderTest.ExceptionFormatter().stack(error)).toMatch(/ExceptionFormatterSpec\.js.*\d+/) + expect(new jasmineUnderTest.ExceptionFormatter().stack(error)).toMatch( + /ExceptionFormatterSpec\.js.*\d+/ + ); }); - it("filters Jasmine stack frames from V8 style traces", function() { + it('filters Jasmine stack frames from V8 style traces', function() { var error = { message: 'nope', - stack: 'Error: nope\n' + + stack: + 'Error: nope\n' + ' at fn1 (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)\n' + ' at fn2 (http://localhost:8888/__jasmine__/jasmine.js:4320:20)\n' + ' at fn3 (http://localhost:8888/__jasmine__/jasmine.js:4320:20)\n' + @@ -89,16 +100,18 @@ describe("ExceptionFormatter", function() { jasmineFile: 'http://localhost:8888/__jasmine__/jasmine.js' }); var result = subject.stack(error); - expect(result).toEqual('Error: nope\n' + + expect(result).toEqual( + 'Error: nope\n' + ' at fn1 (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)\n' + ' at \n' + ' at fn4 (http://localhost:8888/__spec__/core/UtilSpec.js:110:19)' ); }); - it("filters Jasmine stack frames from Webkit style traces", function() { + it('filters Jasmine stack frames from Webkit style traces', function() { var error = { - stack: 'http://localhost:8888/__spec__/core/UtilSpec.js:115:28\n' + + stack: + 'http://localhost:8888/__spec__/core/UtilSpec.js:115:28\n' + 'fn1@http://localhost:8888/__jasmine__/jasmine.js:4320:27\n' + 'fn2@http://localhost:8888/__jasmine__/jasmine.js:4320:27\n' + 'http://localhost:8888/__spec__/core/UtilSpec.js:115:28' @@ -114,9 +127,13 @@ describe("ExceptionFormatter", function() { ); }); - it("filters Jasmine stack frames in this environment", function() { + it('filters Jasmine stack frames in this environment', function() { var error, i; - try { throw new Error("an error"); } catch(e) { error = e; } + try { + throw new Error('an error'); + } catch (e) { + error = e; + } var subject = new jasmineUnderTest.ExceptionFormatter({ jasmineFile: jasmine.util.jasmineFile() }); @@ -136,9 +153,14 @@ describe("ExceptionFormatter", function() { } }); - it("handles multiline error messages in this environment", function() { - var error, i, msg = "an error\nwith two lines"; - try { throw new Error(msg); } catch(e) { error = e; } + it('handles multiline error messages in this environment', function() { + var error, + msg = 'an error\nwith two lines'; + try { + throw new Error(msg); + } catch (e) { + error = e; + } if (error.stack.indexOf(msg) === -1) { pending("Stack traces don't have messages in this environment"); @@ -155,19 +177,22 @@ describe("ExceptionFormatter", function() { expect(lines[3]).toMatch(//); }); - it("returns null if no Error provided", function() { + it('returns null if no Error provided', function() { expect(new jasmineUnderTest.ExceptionFormatter().stack()).toBeNull(); }); - it("includes error properties in stack", function() { + it('includes error properties in stack', function() { var error; - try { throw new Error("an error") } catch(e) { error = e; } + try { + throw new Error('an error'); + } catch (e) { + error = e; + } error.someProperty = 'hello there'; var result = new jasmineUnderTest.ExceptionFormatter().stack(error); expect(result).toMatch(/error properties:.*someProperty.*hello there/); }); - }); }); diff --git a/spec/core/ExceptionsSpec.js b/spec/core/ExceptionsSpec.js index e0a141a6..538c682d 100644 --- a/spec/core/ExceptionsSpec.js +++ b/spec/core/ExceptionsSpec.js @@ -7,11 +7,17 @@ describe('Exceptions:', function() { it('should handle exceptions thrown, but continue', function(done) { var secondTest = jasmine.createSpy('second test'); - env.describe('Suite for handles exceptions', function () { - env.it('should be a test that fails because it throws an exception', function() { - throw new Error(); - }); - env.it('should be a passing test that runs after exceptions are thrown from a async test', secondTest); + env.describe('Suite for handles exceptions', function() { + env.it( + 'should be a test that fails because it throws an exception', + function() { + throw new Error(); + } + ); + env.it( + 'should be a passing test that runs after exceptions are thrown from a async test', + secondTest + ); }); var expectations = function() { @@ -23,14 +29,14 @@ describe('Exceptions:', function() { env.execute(); }); - it("should handle exceptions thrown directly in top-level describe blocks and continue", function(done) { - var secondDescribe = jasmine.createSpy("second describe"); - env.describe("a suite that throws an exception", function () { - env.it("is a test that should pass", function () { + it('should handle exceptions thrown directly in top-level describe blocks and continue', function(done) { + var secondDescribe = jasmine.createSpy('second describe'); + env.describe('a suite that throws an exception', function() { + env.it('is a test that should pass', function() { this.expect(true).toEqual(true); }); - throw new Error("top level error"); + throw new Error('top level error'); }); env.describe("a suite that doesn't throw an exception", secondDescribe); @@ -43,4 +49,3 @@ describe('Exceptions:', function() { env.execute(); }); }); - diff --git a/spec/core/ExpectationFilterChainSpec.js b/spec/core/ExpectationFilterChainSpec.js index 195fbe27..911f6b30 100644 --- a/spec/core/ExpectationFilterChainSpec.js +++ b/spec/core/ExpectationFilterChainSpec.js @@ -6,7 +6,7 @@ describe('ExpectationFilterChain', function() { orig = new jasmineUnderTest.ExpectationFilterChain({ modifyFailureMessage: first }), - added = orig.addFilter({selectComparisonFunc: second}); + added = orig.addFilter({ selectComparisonFunc: second }); added.modifyFailureMessage(); expect(first).toHaveBeenCalled(); @@ -18,7 +18,7 @@ describe('ExpectationFilterChain', function() { var orig = new jasmineUnderTest.ExpectationFilterChain({}), f = jasmine.createSpy('f'); - orig.addFilter({selectComparisonFunc: f}); + orig.addFilter({ selectComparisonFunc: f }); orig.selectComparisonFunc(); expect(f).not.toHaveBeenCalled(); @@ -39,8 +39,8 @@ describe('ExpectationFilterChain', function() { var first = jasmine.createSpy('first').and.returnValue('first'), second = jasmine.createSpy('second').and.returnValue('second'), chain = new jasmineUnderTest.ExpectationFilterChain() - .addFilter({selectComparisonFunc: first}) - .addFilter({selectComparisonFunc: second}), + .addFilter({ selectComparisonFunc: first }) + .addFilter({ selectComparisonFunc: second }), matcher = {}, result; @@ -67,17 +67,27 @@ describe('ExpectationFilterChain', function() { var first = jasmine.createSpy('first').and.returnValue('first'), second = jasmine.createSpy('second').and.returnValue('second'), chain = new jasmineUnderTest.ExpectationFilterChain() - .addFilter({buildFailureMessage: first}) - .addFilter({buildFailureMessage: second}), - matcherResult = {pass: false}, + .addFilter({ buildFailureMessage: first }) + .addFilter({ buildFailureMessage: second }), + matcherResult = { pass: false }, matcherName = 'foo', args = [], util = {}, result; - result = chain.buildFailureMessage(matcherResult, matcherName, args, util); + result = chain.buildFailureMessage( + matcherResult, + matcherName, + args, + util + ); - expect(first).toHaveBeenCalledWith(matcherResult, matcherName, args, util); + expect(first).toHaveBeenCalledWith( + matcherResult, + matcherName, + args, + util + ); expect(second).not.toHaveBeenCalled(); expect(result).toEqual('first'); }); @@ -98,8 +108,8 @@ describe('ExpectationFilterChain', function() { var first = jasmine.createSpy('first').and.returnValue('first'), second = jasmine.createSpy('second').and.returnValue('second'), chain = new jasmineUnderTest.ExpectationFilterChain() - .addFilter({modifyFailureMessage: first}) - .addFilter({modifyFailureMessage: second}), + .addFilter({ modifyFailureMessage: first }) + .addFilter({ modifyFailureMessage: second }), result; result = chain.modifyFailureMessage('original'); diff --git a/spec/core/ExpectationResultSpec.js b/spec/core/ExpectationResultSpec.js index 53d2c7e3..d9af2322 100644 --- a/spec/core/ExpectationResultSpec.js +++ b/spec/core/ExpectationResultSpec.js @@ -1,76 +1,93 @@ -describe("buildExpectationResult", function() { - it("defaults to passed", function() { - var result = jasmineUnderTest.buildExpectationResult({passed: 'some-value'}); +describe('buildExpectationResult', function() { + it('defaults to passed', function() { + var result = jasmineUnderTest.buildExpectationResult({ + passed: 'some-value' + }); expect(result.passed).toBe('some-value'); }); - it("message defaults to Passed for passing specs", function() { - var result = jasmineUnderTest.buildExpectationResult({passed: true, message: 'some-value'}); + it('message defaults to Passed for passing specs', function() { + var result = jasmineUnderTest.buildExpectationResult({ + passed: true, + message: 'some-value' + }); expect(result.message).toBe('Passed.'); }); - it("message returns the message for failing expectations", function() { - var result = jasmineUnderTest.buildExpectationResult({passed: false, message: 'some-value'}); + it('message returns the message for failing expectations', function() { + var result = jasmineUnderTest.buildExpectationResult({ + passed: false, + message: 'some-value' + }); expect(result.message).toBe('some-value'); }); - it("delegates message formatting to the provided formatter if there was an Error", function() { - var fakeError = {message: 'foo'}, - messageFormatter = jasmine.createSpy("exception message formatter").and.returnValue(fakeError.message); + it('delegates message formatting to the provided formatter if there was an Error', function() { + var fakeError = { message: 'foo' }, + messageFormatter = jasmine + .createSpy('exception message formatter') + .and.returnValue(fakeError.message); - var result = jasmineUnderTest.buildExpectationResult( - { - passed: false, - error: fakeError, - messageFormatter: messageFormatter - }); + var result = jasmineUnderTest.buildExpectationResult({ + passed: false, + error: fakeError, + messageFormatter: messageFormatter + }); expect(messageFormatter).toHaveBeenCalledWith(fakeError); expect(result.message).toEqual('foo'); }); - it("delegates stack formatting to the provided formatter if there was an Error", function() { - var fakeError = {stack: 'foo'}, - stackFormatter = jasmine.createSpy("stack formatter").and.returnValue(fakeError.stack); + it('delegates stack formatting to the provided formatter if there was an Error', function() { + var fakeError = { stack: 'foo' }, + stackFormatter = jasmine + .createSpy('stack formatter') + .and.returnValue(fakeError.stack); - var result = jasmineUnderTest.buildExpectationResult( - { - passed: false, - error: fakeError, - stackFormatter: stackFormatter - }); + var result = jasmineUnderTest.buildExpectationResult({ + passed: false, + error: fakeError, + stackFormatter: stackFormatter + }); expect(stackFormatter).toHaveBeenCalledWith(fakeError); expect(result.stack).toEqual('foo'); }); - it("delegates stack formatting to the provided formatter if there was a provided errorForStack", function() { - var fakeError = {stack: 'foo'}, - stackFormatter = jasmine.createSpy("stack formatter").and.returnValue(fakeError.stack); + it('delegates stack formatting to the provided formatter if there was a provided errorForStack', function() { + var fakeError = { stack: 'foo' }, + stackFormatter = jasmine + .createSpy('stack formatter') + .and.returnValue(fakeError.stack); - var result = jasmineUnderTest.buildExpectationResult( - { - passed: false, - errorForStack: fakeError, - stackFormatter: stackFormatter - }); + var result = jasmineUnderTest.buildExpectationResult({ + passed: false, + errorForStack: fakeError, + stackFormatter: stackFormatter + }); expect(stackFormatter).toHaveBeenCalledWith(fakeError); expect(result.stack).toEqual('foo'); }); - it("matcherName returns passed matcherName", function() { - var result = jasmineUnderTest.buildExpectationResult({matcherName: 'some-value'}); + it('matcherName returns passed matcherName', function() { + var result = jasmineUnderTest.buildExpectationResult({ + matcherName: 'some-value' + }); expect(result.matcherName).toBe('some-value'); }); - it("expected returns passed expected", function() { - var result = jasmineUnderTest.buildExpectationResult({expected: 'some-value'}); + it('expected returns passed expected', function() { + var result = jasmineUnderTest.buildExpectationResult({ + expected: 'some-value' + }); expect(result.expected).toBe('some-value'); }); - it("actual returns passed actual", function() { - var result = jasmineUnderTest.buildExpectationResult({actual: 'some-value'}); + it('actual returns passed actual', function() { + var result = jasmineUnderTest.buildExpectationResult({ + actual: 'some-value' + }); expect(result.actual).toBe('some-value'); }); }); diff --git a/spec/core/ExpectationSpec.js b/spec/core/ExpectationSpec.js index 72a4426f..45f69eb5 100644 --- a/spec/core/ExpectationSpec.js +++ b/spec/core/ExpectationSpec.js @@ -1,5 +1,5 @@ -describe("Expectation", function() { - it("makes custom matchers available to this expectation", function() { +describe('Expectation', function() { + it('makes custom matchers available to this expectation', function() { var matchers = { toFoo: function() {}, toBar: function() {} @@ -14,7 +14,7 @@ describe("Expectation", function() { expect(expectation.toBar).toBeDefined(); }); - it(".addCoreMatchers makes matchers available to any expectation", function() { + it('.addCoreMatchers makes matchers available to any expectation', function() { var coreMatchers = { toQuux: function() {} }, @@ -28,8 +28,12 @@ describe("Expectation", function() { }); it("wraps matchers's compare functions, passing in matcher dependencies", function() { - var fakeCompare = function() { return { pass: true }; }, - matcherFactory = jasmine.createSpy("matcher").and.returnValue({ compare: fakeCompare }), + var fakeCompare = function() { + return { pass: true }; + }, + matcherFactory = jasmine + .createSpy('matcher') + .and.returnValue({ compare: fakeCompare }), matchers = { toFoo: matcherFactory }, @@ -37,24 +41,26 @@ describe("Expectation", function() { buildFailureMessage: jasmine.createSpy('buildFailureMessage') }, customEqualityTesters = ['a'], - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation; expectation = jasmineUnderTest.Expectation.factory({ util: util, customMatchers: matchers, customEqualityTesters: customEqualityTesters, - actual: "an actual", + actual: 'an actual', addExpectationResult: addExpectationResult }); - expectation.toFoo("hello"); + expectation.toFoo('hello'); - expect(matcherFactory).toHaveBeenCalledWith(util, customEqualityTesters) + expect(matcherFactory).toHaveBeenCalledWith(util, customEqualityTesters); }); it("wraps matchers's compare functions, passing the actual and expected", function() { - var fakeCompare = jasmine.createSpy('fake-compare').and.returnValue({pass: true}), + var fakeCompare = jasmine + .createSpy('fake-compare') + .and.returnValue({ pass: true }), matchers = { toFoo: function() { return { @@ -65,259 +71,270 @@ describe("Expectation", function() { util = { buildFailureMessage: jasmine.createSpy('buildFailureMessage') }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation; expectation = jasmineUnderTest.Expectation.factory({ util: util, customMatchers: matchers, - actual: "an actual", + actual: 'an actual', addExpectationResult: addExpectationResult }); - expectation.toFoo("hello"); + expectation.toFoo('hello'); - expect(fakeCompare).toHaveBeenCalledWith("an actual", "hello"); + expect(fakeCompare).toHaveBeenCalledWith('an actual', 'hello'); }); - it("reports a passing result to the spec when the comparison passes", function() { + it('reports a passing result to the spec when the comparison passes', function() { var matchers = { toFoo: function() { return { - compare: function() { return { pass: true }; } + compare: function() { + return { pass: true }; + } }; } }, util = { buildFailureMessage: jasmine.createSpy('buildFailureMessage') }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation; expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, util: util, - actual: "an actual", + actual: 'an actual', addExpectationResult: addExpectationResult }); - expectation.toFoo("hello"); + expectation.toFoo('hello'); expect(addExpectationResult).toHaveBeenCalledWith(true, { - matcherName: "toFoo", + matcherName: 'toFoo', passed: true, - message: "", + message: '', error: undefined, - expected: "hello", - actual: "an actual", + expected: 'hello', + actual: 'an actual', errorForStack: undefined }); }); - it("reports a failing result to the spec when the comparison fails", function() { + it('reports a failing result to the spec when the comparison fails', function() { var matchers = { toFoo: function() { return { - compare: function() { return { pass: false }; } + compare: function() { + return { pass: false }; + } }; } }, util = { - buildFailureMessage: function() { return ""; } + buildFailureMessage: function() { + return ''; + } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation; expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, util: util, - actual: "an actual", + actual: 'an actual', addExpectationResult: addExpectationResult }); - expectation.toFoo("hello"); + expectation.toFoo('hello'); expect(addExpectationResult).toHaveBeenCalledWith(false, { - matcherName: "toFoo", + matcherName: 'toFoo', passed: false, - expected: "hello", - actual: "an actual", - message: "", + expected: 'hello', + actual: 'an actual', + message: '', error: undefined, errorForStack: undefined }); }); - it("reports a failing result and a custom fail message to the spec when the comparison fails", function() { + it('reports a failing result and a custom fail message to the spec when the comparison fails', function() { var matchers = { toFoo: function() { return { compare: function() { return { pass: false, - message: "I am a custom message" + message: 'I am a custom message' }; } }; } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation; expectation = jasmineUnderTest.Expectation.factory({ - actual: "an actual", + actual: 'an actual', customMatchers: matchers, addExpectationResult: addExpectationResult }); - expectation.toFoo("hello"); + expectation.toFoo('hello'); expect(addExpectationResult).toHaveBeenCalledWith(false, { - matcherName: "toFoo", + matcherName: 'toFoo', passed: false, - expected: "hello", - actual: "an actual", - message: "I am a custom message", + expected: 'hello', + actual: 'an actual', + message: 'I am a custom message', error: undefined, errorForStack: undefined }); }); - it("reports a failing result with a custom fail message function to the spec when the comparison fails", function() { + it('reports a failing result with a custom fail message function to the spec when the comparison fails', function() { var matchers = { toFoo: function() { return { compare: function() { return { pass: false, - message: function() { return "I am a custom message"; } + message: function() { + return 'I am a custom message'; + } }; } }; } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation; expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - actual: "an actual", + actual: 'an actual', addExpectationResult: addExpectationResult }); - expectation.toFoo("hello"); + expectation.toFoo('hello'); expect(addExpectationResult).toHaveBeenCalledWith(false, { - matcherName: "toFoo", + matcherName: 'toFoo', passed: false, - expected: "hello", - actual: "an actual", - message: "I am a custom message", + expected: 'hello', + actual: 'an actual', + message: 'I am a custom message', error: undefined, errorForStack: undefined }); }); - it("reports a passing result to the spec when the comparison fails for a negative expectation", function() { + it('reports a passing result to the spec when the comparison fails for a negative expectation', function() { var matchers = { toFoo: function() { return { - compare: function() { return { pass: false }; } + compare: function() { + return { pass: false }; + } }; } }, - util = { - buildFailureMessage: function() { return ""; } - }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), - actual = "an actual", + addExpectationResult = jasmine.createSpy('addExpectationResult'), + actual = 'an actual', expectation; expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - actual: "an actual", + actual: 'an actual', addExpectationResult: addExpectationResult }).not; - expectation.toFoo("hello"); + expectation.toFoo('hello'); expect(addExpectationResult).toHaveBeenCalledWith(true, { - matcherName: "toFoo", + matcherName: 'toFoo', passed: true, - message: "", + message: '', error: undefined, - expected: "hello", + expected: 'hello', actual: actual, errorForStack: undefined }); }); - it("reports a failing result to the spec when the comparison passes for a negative expectation", function() { + it('reports a failing result to the spec when the comparison passes for a negative expectation', function() { var matchers = { toFoo: function() { return { - compare: function() { return { pass: true }; } + compare: function() { + return { pass: true }; + } }; } }, util = { - buildFailureMessage: function() { return "default message"; } + buildFailureMessage: function() { + return 'default message'; + } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), - actual = "an actual", + addExpectationResult = jasmine.createSpy('addExpectationResult'), + actual = 'an actual', expectation; expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - actual: "an actual", + actual: 'an actual', util: util, - addExpectationResult: addExpectationResult, + addExpectationResult: addExpectationResult }).not; - expectation.toFoo("hello"); + expectation.toFoo('hello'); expect(addExpectationResult).toHaveBeenCalledWith(false, { - matcherName: "toFoo", + matcherName: 'toFoo', passed: false, - expected: "hello", + expected: 'hello', actual: actual, - message: "default message", + message: 'default message', error: undefined, errorForStack: undefined }); }); - it("reports a failing result and a custom fail message to the spec when the comparison passes for a negative expectation", function() { + it('reports a failing result and a custom fail message to the spec when the comparison passes for a negative expectation', function() { var matchers = { toFoo: function() { return { compare: function() { return { pass: true, - message: "I am a custom message" + message: 'I am a custom message' }; } }; } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), - actual = "an actual", + addExpectationResult = jasmine.createSpy('addExpectationResult'), + actual = 'an actual', expectation; expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - actual: "an actual", + actual: 'an actual', addExpectationResult: addExpectationResult }).not; - expectation.toFoo("hello"); + expectation.toFoo('hello'); expect(addExpectationResult).toHaveBeenCalledWith(false, { - matcherName: "toFoo", + matcherName: 'toFoo', passed: false, - expected: "hello", + expected: 'hello', actual: actual, - message: "I am a custom message", + message: 'I am a custom message', error: undefined, errorForStack: undefined }); @@ -327,29 +344,33 @@ describe("Expectation", function() { var matchers = { toFoo: function() { return { - compare: function() { return { pass: true }; }, - negativeCompare: function() { return { pass: true }; } + compare: function() { + return { pass: true }; + }, + negativeCompare: function() { + return { pass: true }; + } }; } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), - actual = "an actual", + addExpectationResult = jasmine.createSpy('addExpectationResult'), + actual = 'an actual', expectation; expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - actual: "an actual", + actual: 'an actual', addExpectationResult: addExpectationResult }).not; - expectation.toFoo("hello"); + expectation.toFoo('hello'); expect(addExpectationResult).toHaveBeenCalledWith(true, { - matcherName: "toFoo", + matcherName: 'toFoo', passed: true, - expected: "hello", + expected: 'hello', actual: actual, - message: "", + message: '', error: undefined, errorForStack: undefined }); @@ -359,7 +380,9 @@ describe("Expectation", function() { var matchers = { toFoo: function() { return { - compare: function() { return { pass: true }; }, + compare: function() { + return { pass: true }; + }, negativeCompare: function() { return { pass: false, @@ -369,22 +392,22 @@ describe("Expectation", function() { }; } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), - actual = "an actual", + addExpectationResult = jasmine.createSpy('addExpectationResult'), + actual = 'an actual', expectation; expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - actual: "an actual", - addExpectationResult: addExpectationResult, + actual: 'an actual', + addExpectationResult: addExpectationResult }).not; - expectation.toFoo("hello"); + expectation.toFoo('hello'); expect(addExpectationResult).toHaveBeenCalledWith(false, { - matcherName: "toFoo", + matcherName: 'toFoo', passed: false, - expected: "hello", + expected: 'hello', actual: actual, message: "I'm a custom message", error: undefined, @@ -392,254 +415,272 @@ describe("Expectation", function() { }); }); - it("reports a custom error message to the spec", function() { - var customError = new Error("I am a custom error"); + it('reports a custom error message to the spec', function() { + var customError = new Error('I am a custom error'); var matchers = { toFoo: function() { return { compare: function() { return { pass: false, - message: "I am a custom message", + message: 'I am a custom message', error: customError }; } }; } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation; expectation = jasmineUnderTest.Expectation.factory({ - actual: "an actual", + actual: 'an actual', customMatchers: matchers, addExpectationResult: addExpectationResult }); - expectation.toFoo("hello"); + expectation.toFoo('hello'); expect(addExpectationResult).toHaveBeenCalledWith(false, { - matcherName: "toFoo", + matcherName: 'toFoo', passed: false, - expected: "hello", - actual: "an actual", - message: "I am a custom message", + expected: 'hello', + actual: 'an actual', + message: 'I am a custom message', error: customError, errorForStack: undefined }); }); it("reports a custom message to the spec when a 'not' comparison fails", function() { - var customError = new Error("I am a custom error"); + var customError = new Error('I am a custom error'); var matchers = { toFoo: function() { return { compare: function() { return { pass: true, - message: "I am a custom message", + message: 'I am a custom message', error: customError }; } }; } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation; expectation = jasmineUnderTest.Expectation.factory({ - actual: "an actual", + actual: 'an actual', customMatchers: matchers, addExpectationResult: addExpectationResult }).not; - expectation.toFoo("hello"); + expectation.toFoo('hello'); expect(addExpectationResult).toHaveBeenCalledWith(false, { - matcherName: "toFoo", + matcherName: 'toFoo', passed: false, - expected: "hello", - actual: "an actual", - message: "I am a custom message", + expected: 'hello', + actual: 'an actual', + message: 'I am a custom message', error: customError, errorForStack: undefined }); }); it("reports a custom message func to the spec when a 'not' comparison fails", function() { - var customError = new Error("I am a custom error"); + var customError = new Error('I am a custom error'); var matchers = { toFoo: function() { return { compare: function() { return { pass: true, - message: function() { return "I am a custom message"; }, + message: function() { + return 'I am a custom message'; + }, error: customError }; } }; } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation; expectation = jasmineUnderTest.Expectation.factory({ - actual: "an actual", + actual: 'an actual', customMatchers: matchers, addExpectationResult: addExpectationResult }).not; - expectation.toFoo("hello"); + expectation.toFoo('hello'); expect(addExpectationResult).toHaveBeenCalledWith(false, { - matcherName: "toFoo", + matcherName: 'toFoo', passed: false, - expected: "hello", - actual: "an actual", - message: "I am a custom message", + expected: 'hello', + actual: 'an actual', + message: 'I am a custom message', error: customError, errorForStack: undefined }); }); - describe("#withContext", function() { - it("prepends the context to the generated failure message", function() { + describe('#withContext', function() { + it('prepends the context to the generated failure message', function() { var matchers = { toFoo: function() { return { - compare: function() { return { pass: false }; } + compare: function() { + return { pass: false }; + } }; } }, util = { - buildFailureMessage: function() { return "failure message"; } + buildFailureMessage: function() { + return 'failure message'; + } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, util: util, - actual: "an actual", + actual: 'an actual', addExpectationResult: addExpectationResult }); - expectation.withContext("Some context").toFoo("hello"); + expectation.withContext('Some context').toFoo('hello'); - expect(addExpectationResult).toHaveBeenCalledWith(false, + expect(addExpectationResult).toHaveBeenCalledWith( + false, jasmine.objectContaining({ - message: "Some context: failure message" + message: 'Some context: failure message' }) ); }); - it("prepends the context to a custom failure message", function() { + it('prepends the context to a custom failure message', function() { var matchers = { toFoo: function() { return { - compare: function() { return { pass: false, message: "msg" }; } + compare: function() { + return { pass: false, message: 'msg' }; + } }; } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - actual: "an actual", + actual: 'an actual', addExpectationResult: addExpectationResult }); - expectation.withContext("Some context").toFoo("hello"); + expectation.withContext('Some context').toFoo('hello'); - expect(addExpectationResult).toHaveBeenCalledWith(false, + expect(addExpectationResult).toHaveBeenCalledWith( + false, jasmine.objectContaining({ - message: "Some context: msg" + message: 'Some context: msg' }) ); }); - it("prepends the context to a custom failure message from a function", function() { + it('prepends the context to a custom failure message from a function', function() { var matchers = { toFoo: function() { return { compare: function() { return { pass: false, - message: function() { return "msg"; } + message: function() { + return 'msg'; + } }; } }; } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - actual: "an actual", + actual: 'an actual', addExpectationResult: addExpectationResult }); - expectation.withContext("Some context").toFoo("hello"); + expectation.withContext('Some context').toFoo('hello'); - expect(addExpectationResult).toHaveBeenCalledWith(false, + expect(addExpectationResult).toHaveBeenCalledWith( + false, jasmine.objectContaining({ - message: "Some context: msg" + message: 'Some context: msg' }) ); }); - it("works with #not", function() { + it('works with #not', function() { var matchers = { toFoo: function() { return { - compare: function() { return { pass: true }; } + compare: function() { + return { pass: true }; + } }; } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, util: jasmineUnderTest.matchersUtil, - actual: "an actual", + actual: 'an actual', addExpectationResult: addExpectationResult }); - expectation.withContext("Some context").not.toFoo(); + expectation.withContext('Some context').not.toFoo(); - expect(addExpectationResult).toHaveBeenCalledWith(false, + expect(addExpectationResult).toHaveBeenCalledWith( + false, jasmine.objectContaining({ message: "Some context: Expected 'an actual' not to foo." }) ); }); - it("works with #not and a custom message", function() { - var customError = new Error("I am a custom error"); + it('works with #not and a custom message', function() { + var customError = new Error('I am a custom error'); var matchers = { toFoo: function() { return { compare: function() { return { pass: true, - message: function() { return "I am a custom message"; }, + message: function() { + return 'I am a custom message'; + }, error: customError }; } }; } }, - addExpectationResult = jasmine.createSpy("addExpectationResult"), + addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation = jasmineUnderTest.Expectation.factory({ - actual: "an actual", + actual: 'an actual', customMatchers: matchers, addExpectationResult: addExpectationResult }); - expectation.withContext("Some context").not.toFoo("hello"); + expectation.withContext('Some context').not.toFoo('hello'); - expect(addExpectationResult).toHaveBeenCalledWith(false, + expect(addExpectationResult).toHaveBeenCalledWith( + false, jasmine.objectContaining({ - message: "Some context: I am a custom message", + message: 'Some context: I am a custom message' }) ); }); }); }); - diff --git a/spec/core/GlobalErrorsSpec.js b/spec/core/GlobalErrorsSpec.js index 1d26185d..9ff19891 100644 --- a/spec/core/GlobalErrorsSpec.js +++ b/spec/core/GlobalErrorsSpec.js @@ -1,8 +1,8 @@ -describe("GlobalErrors", function() { - it("calls the added handler on error", function() { +describe('GlobalErrors', function() { + it('calls the added handler on error', function() { var fakeGlobal = { onerror: null }, - handler = jasmine.createSpy('errorHandler'), - errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); + handler = jasmine.createSpy('errorHandler'), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); errors.install(); errors.pushListener(handler); @@ -12,11 +12,11 @@ describe("GlobalErrors", function() { expect(handler).toHaveBeenCalledWith('foo'); }); - it("only calls the most recent handler", function() { + it('only calls the most recent handler', function() { var fakeGlobal = { onerror: null }, - handler1 = jasmine.createSpy('errorHandler1'), - handler2 = jasmine.createSpy('errorHandler2'), - errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); + handler1 = jasmine.createSpy('errorHandler1'), + handler2 = jasmine.createSpy('errorHandler2'), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); errors.install(); errors.pushListener(handler1); @@ -28,11 +28,11 @@ describe("GlobalErrors", function() { expect(handler2).toHaveBeenCalledWith('foo'); }); - it("calls previous handlers when one is removed", function() { + it('calls previous handlers when one is removed', function() { var fakeGlobal = { onerror: null }, - handler1 = jasmine.createSpy('errorHandler1'), - handler2 = jasmine.createSpy('errorHandler2'), - errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); + handler1 = jasmine.createSpy('errorHandler1'), + handler2 = jasmine.createSpy('errorHandler2'), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); errors.install(); errors.pushListener(handler1); @@ -46,10 +46,10 @@ describe("GlobalErrors", function() { expect(handler2).not.toHaveBeenCalled(); }); - it("uninstalls itself, putting back a previous callback", function() { + it('uninstalls itself, putting back a previous callback', function() { var originalCallback = jasmine.createSpy('error'), - fakeGlobal = { onerror: originalCallback }, - errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); + fakeGlobal = { onerror: originalCallback }, + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); expect(fakeGlobal.onerror).toBe(originalCallback); @@ -62,10 +62,10 @@ describe("GlobalErrors", function() { expect(fakeGlobal.onerror).toBe(originalCallback); }); - it("rethrows the original error when there is no handler", function() { - var fakeGlobal = { }, - errors = new jasmineUnderTest.GlobalErrors(fakeGlobal), - originalError = new Error('nope'); + it('rethrows the original error when there is no handler', function() { + var fakeGlobal = {}, + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal), + originalError = new Error('nope'); errors.install(); @@ -78,22 +78,31 @@ describe("GlobalErrors", function() { errors.uninstall(); }); - it("reports uncaughtException in node.js", function() { + it('reports uncaughtException in node.js', function() { var fakeGlobal = { - process: { - on: jasmine.createSpy('process.on'), - removeListener: jasmine.createSpy('process.removeListener'), - listeners: jasmine.createSpy('process.listeners').and.returnValue(['foo']), - removeAllListeners: jasmine.createSpy('process.removeAllListeners') - } - }, - handler = jasmine.createSpy('errorHandler'), - errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); + process: { + on: jasmine.createSpy('process.on'), + removeListener: jasmine.createSpy('process.removeListener'), + listeners: jasmine + .createSpy('process.listeners') + .and.returnValue(['foo']), + removeAllListeners: jasmine.createSpy('process.removeAllListeners') + } + }, + handler = jasmine.createSpy('errorHandler'), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); errors.install(); - expect(fakeGlobal.process.on).toHaveBeenCalledWith('uncaughtException', jasmine.any(Function)); - expect(fakeGlobal.process.listeners).toHaveBeenCalledWith('uncaughtException'); - expect(fakeGlobal.process.removeAllListeners).toHaveBeenCalledWith('uncaughtException'); + expect(fakeGlobal.process.on).toHaveBeenCalledWith( + 'uncaughtException', + jasmine.any(Function) + ); + expect(fakeGlobal.process.listeners).toHaveBeenCalledWith( + 'uncaughtException' + ); + expect(fakeGlobal.process.removeAllListeners).toHaveBeenCalledWith( + 'uncaughtException' + ); errors.pushListener(handler); @@ -101,30 +110,47 @@ describe("GlobalErrors", function() { addedListener(new Error('bar')); expect(handler).toHaveBeenCalledWith(new Error('bar')); - expect(handler.calls.argsFor(0)[0].jasmineMessage).toBe('Uncaught exception: Error: bar'); + expect(handler.calls.argsFor(0)[0].jasmineMessage).toBe( + 'Uncaught exception: Error: bar' + ); errors.uninstall(); - expect(fakeGlobal.process.removeListener).toHaveBeenCalledWith('uncaughtException', addedListener); - expect(fakeGlobal.process.on).toHaveBeenCalledWith('uncaughtException', 'foo'); + expect(fakeGlobal.process.removeListener).toHaveBeenCalledWith( + 'uncaughtException', + addedListener + ); + expect(fakeGlobal.process.on).toHaveBeenCalledWith( + 'uncaughtException', + 'foo' + ); }); - it("reports unhandledRejection in node.js", function() { + it('reports unhandledRejection in node.js', function() { var fakeGlobal = { - process: { - on: jasmine.createSpy('process.on'), - removeListener: jasmine.createSpy('process.removeListener'), - listeners: jasmine.createSpy('process.listeners').and.returnValue(['foo']), - removeAllListeners: jasmine.createSpy('process.removeAllListeners') - } - }, - handler = jasmine.createSpy('errorHandler'), - errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); + process: { + on: jasmine.createSpy('process.on'), + removeListener: jasmine.createSpy('process.removeListener'), + listeners: jasmine + .createSpy('process.listeners') + .and.returnValue(['foo']), + removeAllListeners: jasmine.createSpy('process.removeAllListeners') + } + }, + handler = jasmine.createSpy('errorHandler'), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); errors.install(); - expect(fakeGlobal.process.on).toHaveBeenCalledWith('unhandledRejection', jasmine.any(Function)); - expect(fakeGlobal.process.listeners).toHaveBeenCalledWith('unhandledRejection'); - expect(fakeGlobal.process.removeAllListeners).toHaveBeenCalledWith('unhandledRejection'); + expect(fakeGlobal.process.on).toHaveBeenCalledWith( + 'unhandledRejection', + jasmine.any(Function) + ); + expect(fakeGlobal.process.listeners).toHaveBeenCalledWith( + 'unhandledRejection' + ); + expect(fakeGlobal.process.removeAllListeners).toHaveBeenCalledWith( + 'unhandledRejection' + ); errors.pushListener(handler); @@ -132,11 +158,19 @@ describe("GlobalErrors", function() { addedListener(new Error('bar')); expect(handler).toHaveBeenCalledWith(new Error('bar')); - expect(handler.calls.argsFor(0)[0].jasmineMessage).toBe('Unhandled promise rejection: Error: bar'); + expect(handler.calls.argsFor(0)[0].jasmineMessage).toBe( + 'Unhandled promise rejection: Error: bar' + ); errors.uninstall(); - expect(fakeGlobal.process.removeListener).toHaveBeenCalledWith('unhandledRejection', addedListener); - expect(fakeGlobal.process.on).toHaveBeenCalledWith('unhandledRejection', 'foo'); + expect(fakeGlobal.process.removeListener).toHaveBeenCalledWith( + 'unhandledRejection', + addedListener + ); + expect(fakeGlobal.process.on).toHaveBeenCalledWith( + 'unhandledRejection', + 'foo' + ); }); }); diff --git a/spec/core/JsApiReporterSpec.js b/spec/core/JsApiReporterSpec.js index 7a8cf2fb..2dcbdcff 100644 --- a/spec/core/JsApiReporterSpec.js +++ b/spec/core/JsApiReporterSpec.js @@ -2,86 +2,81 @@ xdescribe('JsApiReporter (integration specs)', function() { describe('results', function() { var reporter, spec1, spec2; var env; - var suite, nestedSuite, nestedSpec; beforeEach(function() { env = new jasmineUnderTest.Env(); - suite = env.describe("top-level suite", function() { - spec1 = env.it("spec 1", function() { + env.describe('top-level suite', function() { + spec1 = env.it('spec 1', function() { this.expect(true).toEqual(true); - }); - spec2 = env.it("spec 2", function() { + spec2 = env.it('spec 2', function() { this.expect(true).toEqual(false); }); - nestedSuite = env.describe("nested suite", function() { - nestedSpec = env.it("nested spec", function() { + env.describe('nested suite', function() { + env.it('nested spec', function() { expect(true).toEqual(true); }); }); - }); reporter = new jasmineUnderTest.JsApiReporter({}); env.addReporter(reporter); env.execute(); - }); it('results() should return a hash of all results, indexed by spec id', function() { - var expectedSpec1Results = { - result: "passed" - }, - expectedSpec2Results = { - result: "failed" - }; expect(reporter.results()[spec1.id].result).toEqual('passed'); expect(reporter.results()[spec2.id].result).toEqual('failed'); }); - it("should return nested suites as children of their parents", function() { + it('should return nested suites as children of their parents', function() { expect(reporter.suites()).toEqual([ - { id: 0, name: 'top-level suite', type: 'suite', + { + id: 0, + name: 'top-level suite', + type: 'suite', children: [ - { id: 0, name: 'spec 1', type: 'spec', children: [ ] }, - { id: 1, name: 'spec 2', type: 'spec', children: [ ] }, - { id: 1, name: 'nested suite', type: 'suite', + { id: 0, name: 'spec 1', type: 'spec', children: [] }, + { id: 1, name: 'spec 2', type: 'spec', children: [] }, + { + id: 1, + name: 'nested suite', + type: 'suite', children: [ - { id: 2, name: 'nested spec', type: 'spec', children: [ ] } + { id: 2, name: 'nested spec', type: 'spec', children: [] } ] - }, + } ] } ]); }); - describe("#summarizeResult_", function() { - it("should summarize a passing result", function() { + describe('#summarizeResult_', function() { + it('should summarize a passing result', function() { var result = reporter.results()[spec1.id]; var summarizedResult = reporter.summarizeResult_(result); expect(summarizedResult.result).toEqual('passed'); expect(summarizedResult.messages.length).toEqual(0); }); - it("should have a stack trace for failing specs", function() { + it('should have a stack trace for failing specs', function() { var result = reporter.results()[spec2.id]; var summarizedResult = reporter.summarizeResult_(result); expect(summarizedResult.result).toEqual('failed'); - expect(summarizedResult.messages[0].trace.stack).toEqual(result.messages[0].trace.stack); + expect(summarizedResult.messages[0].trace.stack).toEqual( + result.messages[0].trace.stack + ); }); - }); }); }); - -describe("JsApiReporter", function() { - - it("knows when a full environment is started", function() { +describe('JsApiReporter', function() { + it('knows when a full environment is started', function() { var reporter = new jasmineUnderTest.JsApiReporter({}); expect(reporter.started).toBe(false); @@ -93,7 +88,7 @@ describe("JsApiReporter", function() { expect(reporter.finished).toBe(false); }); - it("knows when a full environment is done", function() { + it('knows when a full environment is done', function() { var reporter = new jasmineUnderTest.JsApiReporter({}); expect(reporter.started).toBe(false); @@ -127,58 +122,60 @@ describe("JsApiReporter", function() { expect(reporter.status()).toEqual('done'); }); - it("tracks a suite", function() { + it('tracks a suite', function() { var reporter = new jasmineUnderTest.JsApiReporter({}); reporter.suiteStarted({ id: 123, - description: "A suite" + description: 'A suite' }); var suites = reporter.suites(); - expect(suites).toEqual({123: {id: 123, description: "A suite"}}); + expect(suites).toEqual({ 123: { id: 123, description: 'A suite' } }); reporter.suiteDone({ id: 123, - description: "A suite", + description: 'A suite', status: 'passed' }); - expect(suites).toEqual({123: {id: 123, description: "A suite", status: 'passed'}}); + expect(suites).toEqual({ + 123: { id: 123, description: 'A suite', status: 'passed' } + }); }); - describe("#specResults", function() { + describe('#specResults', function() { var reporter, specResult1, specResult2; beforeEach(function() { reporter = new jasmineUnderTest.JsApiReporter({}); specResult1 = { id: 1, - description: "A spec" + description: 'A spec' }; specResult2 = { id: 2, - description: "Another spec" + description: 'Another spec' }; reporter.specDone(specResult1); reporter.specDone(specResult2); }); - it("should return a slice of results", function() { + it('should return a slice of results', function() { expect(reporter.specResults(0, 1)).toEqual([specResult1]); expect(reporter.specResults(1, 1)).toEqual([specResult2]); }); - describe("when the results do not exist", function() { - it("should return a slice of shorter length", function() { + describe('when the results do not exist', function() { + it('should return a slice of shorter length', function() { expect(reporter.specResults(0, 3)).toEqual([specResult1, specResult2]); expect(reporter.specResults(2, 3)).toEqual([]); }); }); }); - describe("#suiteResults", function(){ + describe('#suiteResults', function() { var reporter, suiteResult1, suiteResult2; beforeEach(function() { reporter = new jasmineUnderTest.JsApiReporter({}); @@ -200,37 +197,37 @@ describe("JsApiReporter", function() { reporter.suiteDone(suiteResult2); }); - it('should not include suite starts', function(){ - expect(reporter.suiteResults(0,3).length).toEqual(2); + it('should not include suite starts', function() { + expect(reporter.suiteResults(0, 3).length).toEqual(2); }); - it("should return a slice of results", function() { + it('should return a slice of results', function() { expect(reporter.suiteResults(0, 1)).toEqual([suiteResult1]); expect(reporter.suiteResults(1, 1)).toEqual([suiteResult2]); }); - it("returns nothing for out of bounds indices", function() { + it('returns nothing for out of bounds indices', function() { expect(reporter.suiteResults(0, 3)).toEqual([suiteResult1, suiteResult2]); expect(reporter.suiteResults(2, 3)).toEqual([]); }); }); - describe("#executionTime", function() { - it("should start the timer when jasmine starts", function() { + describe('#executionTime', function() { + it('should start the timer when jasmine starts', function() { var timerSpy = jasmine.createSpyObj('timer', ['start', 'elapsed']), - reporter = new jasmineUnderTest.JsApiReporter({ - timer: timerSpy - }); + reporter = new jasmineUnderTest.JsApiReporter({ + timer: timerSpy + }); reporter.jasmineStarted(); expect(timerSpy.start).toHaveBeenCalled(); }); - it("should return the time it took the specs to run, in ms", function() { + it('should return the time it took the specs to run, in ms', function() { var timerSpy = jasmine.createSpyObj('timer', ['start', 'elapsed']), - reporter = new jasmineUnderTest.JsApiReporter({ - timer: timerSpy - }); + reporter = new jasmineUnderTest.JsApiReporter({ + timer: timerSpy + }); timerSpy.elapsed.and.returnValue(1000); reporter.jasmineDone(); @@ -238,11 +235,11 @@ describe("JsApiReporter", function() { }); describe("when the specs haven't finished being run", function() { - it("should return undefined", function() { + it('should return undefined', function() { var timerSpy = jasmine.createSpyObj('timer', ['start', 'elapsed']), - reporter = new jasmineUnderTest.JsApiReporter({ - timer: timerSpy - }); + reporter = new jasmineUnderTest.JsApiReporter({ + timer: timerSpy + }); expect(reporter.executionTime()).toBeUndefined(); }); @@ -252,8 +249,8 @@ describe("JsApiReporter", function() { describe('#runDetails', function() { it('should have details about the run', function() { var reporter = new jasmineUnderTest.JsApiReporter({}); - reporter.jasmineDone({some: {run: 'details'}}); - expect(reporter.runDetails).toEqual({some: {run: 'details'}}); + reporter.jasmineDone({ some: { run: 'details' } }); + expect(reporter.runDetails).toEqual({ some: { run: 'details' } }); }); }); }); diff --git a/spec/core/MockDateSpec.js b/spec/core/MockDateSpec.js index cc4ae816..6f6f88df 100644 --- a/spec/core/MockDateSpec.js +++ b/spec/core/MockDateSpec.js @@ -1,5 +1,5 @@ -describe("FakeDate", function() { - it("does not fail if no global date is found", function() { +describe('FakeDate', function() { + it('does not fail if no global date is found', function() { var fakeGlobal = {}, mockDate = new jasmineUnderTest.MockDate(fakeGlobal); @@ -10,11 +10,11 @@ describe("FakeDate", function() { }).not.toThrow(); }); - it("replaces the global Date when it is installed", function() { - var globalDate = jasmine.createSpy("global Date").and.callFake(function() { + it('replaces the global Date when it is installed', function() { + var globalDate = jasmine.createSpy('global Date').and.callFake(function() { return { getTime: function() {} - } + }; }), fakeGlobal = { Date: globalDate }, mockDate = new jasmineUnderTest.MockDate(fakeGlobal); @@ -25,11 +25,11 @@ describe("FakeDate", function() { expect(fakeGlobal.Date).not.toEqual(globalDate); }); - it("replaces the global Date on uninstall", function() { - var globalDate = jasmine.createSpy("global Date").and.callFake(function() { + it('replaces the global Date on uninstall', function() { + var globalDate = jasmine.createSpy('global Date').and.callFake(function() { return { getTime: function() {} - } + }; }), fakeGlobal = { Date: globalDate }, mockDate = new jasmineUnderTest.MockDate(fakeGlobal); @@ -40,13 +40,13 @@ describe("FakeDate", function() { expect(fakeGlobal.Date).toEqual(globalDate); }); - it("takes the current time as the base when installing without parameters", function() { - var globalDate = jasmine.createSpy("global Date").and.callFake(function() { + it('takes the current time as the base when installing without parameters', function() { + var globalDate = jasmine.createSpy('global Date').and.callFake(function() { return { getTime: function() { return 1000; } - } + }; }), fakeGlobal = { Date: globalDate }, mockDate = new jasmineUnderTest.MockDate(fakeGlobal); @@ -58,7 +58,7 @@ describe("FakeDate", function() { expect(globalDate).toHaveBeenCalledWith(1000); }); - it("can accept a date as time base when installing", function() { + it('can accept a date as time base when installing', function() { var fakeGlobal = { Date: Date }, mockDate = new jasmineUnderTest.MockDate(fakeGlobal), baseDate = new Date(); @@ -69,7 +69,7 @@ describe("FakeDate", function() { expect(new fakeGlobal.Date().getTime()).toEqual(123); }); - it("makes real dates", function() { + it('makes real dates', function() { var fakeGlobal = { Date: Date }, mockDate = new jasmineUnderTest.MockDate(fakeGlobal); @@ -78,13 +78,13 @@ describe("FakeDate", function() { expect(new fakeGlobal.Date() instanceof fakeGlobal.Date).toBe(true); }); - it("fakes current time when using Date.now()", function() { - var globalDate = jasmine.createSpy("global Date").and.callFake(function() { + it('fakes current time when using Date.now()', function() { + var globalDate = jasmine.createSpy('global Date').and.callFake(function() { return { getTime: function() { return 1000; } - } + }; }), fakeGlobal = { Date: globalDate }; @@ -97,28 +97,30 @@ describe("FakeDate", function() { }); it("does not stub Date.now() if it doesn't already exist", function() { - var globalDate = jasmine.createSpy("global Date").and.callFake(function() { + var globalDate = jasmine.createSpy('global Date').and.callFake(function() { return { getTime: function() { return 1000; } - } + }; }), fakeGlobal = { Date: globalDate }, mockDate = new jasmineUnderTest.MockDate(fakeGlobal); mockDate.install(); - expect(fakeGlobal.Date.now).toThrowError("Browser does not support Date.now()"); + expect(fakeGlobal.Date.now).toThrowError( + 'Browser does not support Date.now()' + ); }); - it("makes time passes using tick", function() { - var globalDate = jasmine.createSpy("global Date").and.callFake(function() { + it('makes time passes using tick', function() { + var globalDate = jasmine.createSpy('global Date').and.callFake(function() { return { getTime: function() { return 1000; } - } + }; }), fakeGlobal = { Date: globalDate }; @@ -136,13 +138,13 @@ describe("FakeDate", function() { expect(fakeGlobal.Date.now()).toEqual(2100); }); - it("allows to increase 0 milliseconds using tick", function() { - var globalDate = jasmine.createSpy("global Date").and.callFake(function() { + it('allows to increase 0 milliseconds using tick', function() { + var globalDate = jasmine.createSpy('global Date').and.callFake(function() { return { getTime: function() { return 1000; } - } + }; }), fakeGlobal = { Date: globalDate }; @@ -158,14 +160,16 @@ describe("FakeDate", function() { expect(fakeGlobal.Date.now()).toEqual(1000); }); - it("allows creation of a Date in a different time than the mocked time", function() { + it('allows creation of a Date in a different time than the mocked time', function() { var fakeGlobal = { Date: Date }, mockDate = new jasmineUnderTest.MockDate(fakeGlobal); mockDate.install(); var otherDate = new fakeGlobal.Date(2013, 9, 23, 0, 0, 1, 0); - expect(otherDate.getTime()).toEqual(new Date(2013, 9, 23, 0, 0, 1, 0).getTime()); + expect(otherDate.getTime()).toEqual( + new Date(2013, 9, 23, 0, 0, 1, 0).getTime() + ); }); it("allows creation of a Date that isn't fully specified", function() { @@ -189,7 +193,7 @@ describe("FakeDate", function() { expect(otherDate.getTime()).toEqual(now); }); - it("copies all Date properties to the mocked date", function() { + it('copies all Date properties to the mocked date', function() { var fakeGlobal = { Date: Date }, mockDate = new jasmineUnderTest.MockDate(fakeGlobal); diff --git a/spec/core/PrettyPrintSpec.js b/spec/core/PrettyPrintSpec.js index b62d191d..0e3c48ad 100644 --- a/spec/core/PrettyPrintSpec.js +++ b/spec/core/PrettyPrintSpec.js @@ -1,29 +1,29 @@ -describe("jasmineUnderTest.pp", function () { - it("should wrap strings in single quotes", function() { - expect(jasmineUnderTest.pp("some string")).toEqual("'some string'"); +describe('jasmineUnderTest.pp', function() { + it('should wrap strings in single quotes', function() { + expect(jasmineUnderTest.pp('some string')).toEqual("'some string'"); expect(jasmineUnderTest.pp("som' string")).toEqual("'som' string'"); }); - it("should stringify primitives properly", function() { - expect(jasmineUnderTest.pp(true)).toEqual("true"); - expect(jasmineUnderTest.pp(false)).toEqual("false"); - expect(jasmineUnderTest.pp(null)).toEqual("null"); - expect(jasmineUnderTest.pp(jasmine.undefined)).toEqual("undefined"); - expect(jasmineUnderTest.pp(3)).toEqual("3"); - expect(jasmineUnderTest.pp(-3.14)).toEqual("-3.14"); - expect(jasmineUnderTest.pp(-0)).toEqual("-0"); + it('should stringify primitives properly', function() { + expect(jasmineUnderTest.pp(true)).toEqual('true'); + expect(jasmineUnderTest.pp(false)).toEqual('false'); + expect(jasmineUnderTest.pp(null)).toEqual('null'); + expect(jasmineUnderTest.pp(jasmine.undefined)).toEqual('undefined'); + expect(jasmineUnderTest.pp(3)).toEqual('3'); + expect(jasmineUnderTest.pp(-3.14)).toEqual('-3.14'); + expect(jasmineUnderTest.pp(-0)).toEqual('-0'); }); describe('stringify sets', function() { - it("should stringify sets properly", function() { + it('should stringify sets properly', function() { jasmine.getEnv().requireFunctioningSets(); var set = new Set(); set.add(1); set.add(2); - expect(jasmineUnderTest.pp(set)).toEqual("Set( 1, 2 )"); + expect(jasmineUnderTest.pp(set)).toEqual('Set( 1, 2 )'); }); - it("should truncate sets with more elements than jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH", function() { + it('should truncate sets with more elements than jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH', function() { jasmine.getEnv().requireFunctioningSets(); var originalMaxSize = jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH; @@ -37,112 +37,137 @@ describe("jasmineUnderTest.pp", function () { } finally { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = originalMaxSize; } - }) + }); }); describe('stringify maps', function() { - it("should stringify maps properly", function() { + it('should stringify maps properly', function() { jasmine.getEnv().requireFunctioningMaps(); var map = new Map(); - map.set(1,2); - expect(jasmineUnderTest.pp(map)).toEqual("Map( [ 1, 2 ] )"); + map.set(1, 2); + expect(jasmineUnderTest.pp(map)).toEqual('Map( [ 1, 2 ] )'); }); - it("should truncate maps with more elements than jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH", function() { + it('should truncate maps with more elements than jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH', function() { jasmine.getEnv().requireFunctioningMaps(); var originalMaxSize = jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH; try { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = 2; var map = new Map(); - map.set("a",1); - map.set("b",2); - map.set("c",3); - expect(jasmineUnderTest.pp(map)).toEqual("Map( [ 'a', 1 ], [ 'b', 2 ], ... )"); + map.set('a', 1); + map.set('b', 2); + map.set('c', 3); + expect(jasmineUnderTest.pp(map)).toEqual( + "Map( [ 'a', 1 ], [ 'b', 2 ], ... )" + ); } finally { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = originalMaxSize; } - }) + }); }); - describe('stringify arrays', function() { - it("should stringify arrays properly", function() { - expect(jasmineUnderTest.pp([1, 2])).toEqual("[ 1, 2 ]"); - expect(jasmineUnderTest.pp([1, 'foo', {}, jasmine.undefined, null])).toEqual("[ 1, 'foo', Object({ }), undefined, null ]"); + it('should stringify arrays properly', function() { + expect(jasmineUnderTest.pp([1, 2])).toEqual('[ 1, 2 ]'); + expect( + jasmineUnderTest.pp([1, 'foo', {}, jasmine.undefined, null]) + ).toEqual("[ 1, 'foo', Object({ }), undefined, null ]"); }); - it("should truncate arrays that are longer than jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH", function() { + it('should truncate arrays that are longer than jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH', function() { var originalMaxLength = jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH; var array = [1, 2, 3]; try { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = 2; - expect(jasmineUnderTest.pp(array)).toEqual("[ 1, 2, ... ]"); + expect(jasmineUnderTest.pp(array)).toEqual('[ 1, 2, ... ]'); } finally { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = originalMaxLength; } }); - it("should stringify arrays with properties properly", function() { + it('should stringify arrays with properties properly', function() { var arr = [1, 2]; arr.foo = 'bar'; arr.baz = {}; - expect(jasmineUnderTest.pp(arr)).toEqual("[ 1, 2, foo: 'bar', baz: Object({ }) ]"); + expect(jasmineUnderTest.pp(arr)).toEqual( + "[ 1, 2, foo: 'bar', baz: Object({ }) ]" + ); }); - it("should stringify empty arrays with properties properly", function() { + it('should stringify empty arrays with properties properly', function() { var empty = []; empty.foo = 'bar'; empty.baz = {}; - expect(jasmineUnderTest.pp(empty)).toEqual("[ foo: 'bar', baz: Object({ }) ]"); + expect(jasmineUnderTest.pp(empty)).toEqual( + "[ foo: 'bar', baz: Object({ }) ]" + ); }); - it("should stringify long arrays with properties properly", function() { + it('should stringify long arrays with properties properly', function() { var originalMaxLength = jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH; - var long = [1,2,3]; + var long = [1, 2, 3]; long.foo = 'bar'; long.baz = {}; try { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = 2; - expect(jasmineUnderTest.pp(long)).toEqual("[ 1, 2, ..., foo: 'bar', baz: Object({ }) ]"); + expect(jasmineUnderTest.pp(long)).toEqual( + "[ 1, 2, ..., foo: 'bar', baz: Object({ }) ]" + ); } finally { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = originalMaxLength; } }); - it("should indicate circular array references", function() { + it('should indicate circular array references', function() { var array1 = [1, 2]; var array2 = [array1]; array1.push(array2); - expect(jasmineUnderTest.pp(array1)).toEqual("[ 1, 2, [ ] ]"); + expect(jasmineUnderTest.pp(array1)).toEqual( + '[ 1, 2, [ ] ]' + ); }); - it("should not indicate circular references incorrectly", function() { - var array = [ [1] ]; - expect(jasmineUnderTest.pp(array)).toEqual("[ [ 1 ] ]"); + it('should not indicate circular references incorrectly', function() { + var array = [[1]]; + expect(jasmineUnderTest.pp(array)).toEqual('[ [ 1 ] ]'); }); }); - it("should stringify objects properly", function() { - expect(jasmineUnderTest.pp({foo: 'bar'})).toEqual("Object({ foo: 'bar' })"); - expect(jasmineUnderTest.pp({foo:'bar', baz:3, nullValue: null, undefinedValue: jasmine.undefined})).toEqual("Object({ foo: 'bar', baz: 3, nullValue: null, undefinedValue: undefined })"); - expect(jasmineUnderTest.pp({foo: function () { - }, bar: [1, 2, 3]})).toEqual("Object({ foo: Function, bar: [ 1, 2, 3 ] })"); + it('should stringify objects properly', function() { + expect(jasmineUnderTest.pp({ foo: 'bar' })).toEqual( + "Object({ foo: 'bar' })" + ); + expect( + jasmineUnderTest.pp({ + foo: 'bar', + baz: 3, + nullValue: null, + undefinedValue: jasmine.undefined + }) + ).toEqual( + "Object({ foo: 'bar', baz: 3, nullValue: null, undefinedValue: undefined })" + ); + expect(jasmineUnderTest.pp({ foo: function() {}, bar: [1, 2, 3] })).toEqual( + 'Object({ foo: Function, bar: [ 1, 2, 3 ] })' + ); }); - it("should stringify objects that almost look like DOM nodes", function() { - expect(jasmineUnderTest.pp({nodeType: 1})).toEqual("Object({ nodeType: 1 })"); + it('should stringify objects that almost look like DOM nodes', function() { + expect(jasmineUnderTest.pp({ nodeType: 1 })).toEqual( + 'Object({ nodeType: 1 })' + ); }); - it("should truncate objects with too many keys", function () { + it('should truncate objects with too many keys', function() { var originalMaxLength = jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH; - var long = {a: 1, b: 2, c: 3}; + var long = { a: 1, b: 2, c: 3 }; try { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = 2; - expect(jasmineUnderTest.pp(long)).toEqual("Object({ a: 1, b: 2, ... })"); + expect(jasmineUnderTest.pp(long)).toEqual('Object({ a: 1, b: 2, ... })'); } finally { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = originalMaxLength; } @@ -159,86 +184,119 @@ describe("jasmineUnderTest.pp", function () { } } - it("should truncate outputs that are too long", function() { - var big = [ - { a: 1, b: "a long string" }, - {} - ]; + it('should truncate outputs that are too long', function() { + var big = [{ a: 1, b: 'a long string' }, {}]; withMaxChars(34, function() { - expect(jasmineUnderTest.pp(big)).toEqual("[ Object({ a: 1, b: 'a long st ..."); + expect(jasmineUnderTest.pp(big)).toEqual( + "[ Object({ a: 1, b: 'a long st ..." + ); }); }); - it("should not serialize more objects after hitting MAX_PRETTY_PRINT_CHARS", function() { - var a = { jasmineToString: function() { return 'object a'; } }, - b = { jasmineToString: function() { return 'object b'; } }, - c = { jasmineToString: jasmine.createSpy('c jasmineToString').and.returnValue('') }, - d = { jasmineToString: jasmine.createSpy('d jasmineToString').and.returnValue('') }; + it('should not serialize more objects after hitting MAX_PRETTY_PRINT_CHARS', function() { + var a = { + jasmineToString: function() { + return 'object a'; + } + }, + b = { + jasmineToString: function() { + return 'object b'; + } + }, + c = { + jasmineToString: jasmine + .createSpy('c jasmineToString') + .and.returnValue('') + }, + d = { + jasmineToString: jasmine + .createSpy('d jasmineToString') + .and.returnValue('') + }; withMaxChars(30, function() { - jasmineUnderTest.pp([{a: a, b: b, c: c}, d]); + jasmineUnderTest.pp([{ a: a, b: b, c: c }, d]); expect(c.jasmineToString).not.toHaveBeenCalled(); expect(d.jasmineToString).not.toHaveBeenCalled(); }); }); it("should print 'null' as the constructor of an object with its own constructor property", function() { - expect(jasmineUnderTest.pp({constructor: function() {}})).toContain("null({"); - expect(jasmineUnderTest.pp({constructor: 'foo'})).toContain("null({"); + expect(jasmineUnderTest.pp({ constructor: function() {} })).toContain( + 'null({' + ); + expect(jasmineUnderTest.pp({ constructor: 'foo' })).toContain('null({'); }); - it("should not include inherited properties when stringifying an object", function() { + it('should not include inherited properties when stringifying an object', function() { var SomeClass = function SomeClass() {}; - SomeClass.prototype.foo = "inherited foo"; + SomeClass.prototype.foo = 'inherited foo'; var instance = new SomeClass(); - instance.bar = "my own bar"; - expect(jasmineUnderTest.pp(instance)).toEqual("SomeClass({ bar: 'my own bar' })"); + instance.bar = 'my own bar'; + expect(jasmineUnderTest.pp(instance)).toEqual( + "SomeClass({ bar: 'my own bar' })" + ); }); - it("should not recurse objects and arrays more deeply than jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH", function() { + it('should not recurse objects and arrays more deeply than jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH', function() { var originalMaxDepth = jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH; - var nestedObject = { level1: { level2: { level3: { level4: "leaf" } } } }; - var nestedArray = [1, [2, [3, [4, "leaf"]]]]; + var nestedObject = { level1: { level2: { level3: { level4: 'leaf' } } } }; + var nestedArray = [1, [2, [3, [4, 'leaf']]]]; try { jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH = 2; - expect(jasmineUnderTest.pp(nestedObject)).toEqual("Object({ level1: Object({ level2: Object }) })"); - expect(jasmineUnderTest.pp(nestedArray)).toEqual("[ 1, [ 2, Array ] ]"); + expect(jasmineUnderTest.pp(nestedObject)).toEqual( + 'Object({ level1: Object({ level2: Object }) })' + ); + expect(jasmineUnderTest.pp(nestedArray)).toEqual('[ 1, [ 2, Array ] ]'); jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH = 3; - expect(jasmineUnderTest.pp(nestedObject)).toEqual("Object({ level1: Object({ level2: Object({ level3: Object }) }) })"); - expect(jasmineUnderTest.pp(nestedArray)).toEqual("[ 1, [ 2, [ 3, Array ] ] ]"); + expect(jasmineUnderTest.pp(nestedObject)).toEqual( + 'Object({ level1: Object({ level2: Object({ level3: Object }) }) })' + ); + expect(jasmineUnderTest.pp(nestedArray)).toEqual( + '[ 1, [ 2, [ 3, Array ] ] ]' + ); jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH = 4; - expect(jasmineUnderTest.pp(nestedObject)).toEqual("Object({ level1: Object({ level2: Object({ level3: Object({ level4: 'leaf' }) }) }) })"); - expect(jasmineUnderTest.pp(nestedArray)).toEqual("[ 1, [ 2, [ 3, [ 4, 'leaf' ] ] ] ]"); + expect(jasmineUnderTest.pp(nestedObject)).toEqual( + "Object({ level1: Object({ level2: Object({ level3: Object({ level4: 'leaf' }) }) }) })" + ); + expect(jasmineUnderTest.pp(nestedArray)).toEqual( + "[ 1, [ 2, [ 3, [ 4, 'leaf' ] ] ] ]" + ); } finally { jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH = originalMaxDepth; } }); - it("should stringify immutable circular objects", function(){ - if(Object.freeze){ - var frozenObject = {foo: {bar: 'baz'}}; + it('should stringify immutable circular objects', function() { + if (Object.freeze) { + var frozenObject = { foo: { bar: 'baz' } }; frozenObject.circular = frozenObject; frozenObject = Object.freeze(frozenObject); - expect(jasmineUnderTest.pp(frozenObject)).toEqual("Object({ foo: Object({ bar: 'baz' }), circular: })"); + expect(jasmineUnderTest.pp(frozenObject)).toEqual( + "Object({ foo: Object({ bar: 'baz' }), circular: })" + ); } }); - it("should stringify RegExp objects properly", function() { - expect(jasmineUnderTest.pp(/x|y|z/)).toEqual("/x|y|z/"); + it('should stringify RegExp objects properly', function() { + expect(jasmineUnderTest.pp(/x|y|z/)).toEqual('/x|y|z/'); }); - it("should indicate circular object references", function() { - var sampleValue = {foo: 'hello'}; + it('should indicate circular object references', function() { + var sampleValue = { foo: 'hello' }; sampleValue.nested = sampleValue; - expect(jasmineUnderTest.pp(sampleValue)).toEqual("Object({ foo: 'hello', nested: })"); + expect(jasmineUnderTest.pp(sampleValue)).toEqual( + "Object({ foo: 'hello', nested: })" + ); }); - it("should indicate getters on objects as such", function() { - var sampleValue = {id: 1}; + it('should indicate getters on objects as such', function() { + var sampleValue = { id: 1 }; if (sampleValue.__defineGetter__) { //not supported in IE! sampleValue.__defineGetter__('calculatedValue', function() { @@ -246,53 +304,64 @@ describe("jasmineUnderTest.pp", function () { }); } if (sampleValue.__defineGetter__) { - expect(jasmineUnderTest.pp(sampleValue)).toEqual("Object({ id: 1, calculatedValue: })"); - } - else { - expect(jasmineUnderTest.pp(sampleValue)).toEqual("Object({ id: 1 })"); + expect(jasmineUnderTest.pp(sampleValue)).toEqual( + 'Object({ id: 1, calculatedValue: })' + ); + } else { + expect(jasmineUnderTest.pp(sampleValue)).toEqual('Object({ id: 1 })'); } }); it('should not do HTML escaping of strings', function() { - expect(jasmineUnderTest.pp('some html string &', false)).toEqual('\'some html string &\''); + expect(jasmineUnderTest.pp('some html string &', false)).toEqual( + "'some html string &'" + ); }); - it("should abbreviate the global (usually window) object", function() { - expect(jasmineUnderTest.pp(jasmine.getGlobal())).toEqual(""); + it('should abbreviate the global (usually window) object', function() { + expect(jasmineUnderTest.pp(jasmine.getGlobal())).toEqual(''); }); - it("should stringify Date objects properly", function() { + it('should stringify Date objects properly', function() { var now = new Date(); - expect(jasmineUnderTest.pp(now)).toEqual("Date(" + now.toString() + ")"); + expect(jasmineUnderTest.pp(now)).toEqual('Date(' + now.toString() + ')'); }); - it("should stringify spy objects properly", function() { + it('should stringify spy objects properly', function() { var TestObject = { - someFunction: function() {} - }, - env = new jasmineUnderTest.Env(); + someFunction: function() {} + }, + env = new jasmineUnderTest.Env(); var spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() {return [];}, + currentSpies: function() { + return []; + }, createSpy: function(name, originalFn) { return jasmineUnderTest.Spy(name, originalFn); } }); spyRegistry.spyOn(TestObject, 'someFunction'); - expect(jasmineUnderTest.pp(TestObject.someFunction)).toEqual("spy on someFunction"); + expect(jasmineUnderTest.pp(TestObject.someFunction)).toEqual( + 'spy on someFunction' + ); - expect(jasmineUnderTest.pp(env.createSpy("something"))).toEqual("spy on something"); + expect(jasmineUnderTest.pp(env.createSpy('something'))).toEqual( + 'spy on something' + ); }); - it("should stringify spyOn toString properly", function() { + it('should stringify spyOn toString properly', function() { var TestObject = { - someFunction: function() {} - }, - env = new jasmineUnderTest.Env(); + someFunction: function() {} + }, + env = new jasmineUnderTest.Env(); var spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() {return [];}, + currentSpies: function() { + return []; + }, createSpy: function(name, originalFn) { return jasmineUnderTest.Spy(name, originalFn); } @@ -301,59 +370,73 @@ describe("jasmineUnderTest.pp", function () { spyRegistry.spyOn(TestObject, 'toString'); var testSpyObj = env.createSpyObj('TheClassName', ['toString']); - expect(jasmineUnderTest.pp(testSpyObj)).toEqual("spy on TheClassName.toString"); + expect(jasmineUnderTest.pp(testSpyObj)).toEqual( + 'spy on TheClassName.toString' + ); }); - it("should stringify objects that implement jasmineToString", function () { + it('should stringify objects that implement jasmineToString', function() { var obj = { - jasmineToString: function () { return "strung"; } + jasmineToString: function() { + return 'strung'; + } }; - expect(jasmineUnderTest.pp(obj)).toEqual("strung"); + expect(jasmineUnderTest.pp(obj)).toEqual('strung'); }); - it("should stringify objects that implement custom toString", function () { + it('should stringify objects that implement custom toString', function() { var obj = { - toString: function () { return "my toString"; } + toString: function() { + return 'my toString'; + } }; - expect(jasmineUnderTest.pp(obj)).toEqual("my toString"); + expect(jasmineUnderTest.pp(obj)).toEqual('my toString'); // Simulate object from another global context (e.g. an iframe or Web Worker) that does not actually have a custom // toString despite obj.toString !== Object.prototype.toString var objFromOtherContext = { foo: 'bar', - toString: function () { return Object.prototype.toString.call(this); } + toString: function() { + return Object.prototype.toString.call(this); + } }; - expect(jasmineUnderTest.pp(objFromOtherContext)).toEqual("Object({ foo: 'bar', toString: Function })"); + expect(jasmineUnderTest.pp(objFromOtherContext)).toEqual( + "Object({ foo: 'bar', toString: Function })" + ); }); it("should stringify objects have have a toString that isn't a function", function() { var obj = { - toString: "foo" + toString: 'foo' }; expect(jasmineUnderTest.pp(obj)).toEqual("Object({ toString: 'foo' })"); }); - it("should stringify objects from anonymous constructors with custom toString", function () { - var MyAnonymousConstructor = (function() { return function () {}; })(); - MyAnonymousConstructor.toString = function () { return ''; }; + it('should stringify objects from anonymous constructors with custom toString', function() { + var MyAnonymousConstructor = (function() { + return function() {}; + })(); + MyAnonymousConstructor.toString = function() { + return ''; + }; var a = new MyAnonymousConstructor(); - expect(jasmineUnderTest.pp(a)).toEqual("({ })"); + expect(jasmineUnderTest.pp(a)).toEqual('({ })'); }); - it("should handle objects with null prototype", function() { + it('should handle objects with null prototype', function() { var obj = Object.create(null); obj.foo = 'bar'; expect(jasmineUnderTest.pp(obj)).toEqual("null({ foo: 'bar' })"); }); - it("should gracefully handle objects with invalid toString implementations", function () { + it('should gracefully handle objects with invalid toString implementations', function() { var obj = { foo: { toString: function() { @@ -374,9 +457,11 @@ describe("jasmineUnderTest.pp", function () { // Valid: an actual number baz: 3, // Valid: an actual Error object - qux: new Error("bar") + qux: new Error('bar') }; - expect(jasmineUnderTest.pp(obj)).toEqual("Object({ foo: [object Number], bar: [object Object], baz: 3, qux: Error: bar })"); + expect(jasmineUnderTest.pp(obj)).toEqual( + 'Object({ foo: [object Number], bar: [object Object], baz: 3, qux: Error: bar })' + ); }); }); diff --git a/spec/core/QueueRunnerSpec.js b/spec/core/QueueRunnerSpec.js index 632565ba..e0b4c23c 100644 --- a/spec/core/QueueRunnerSpec.js +++ b/spec/core/QueueRunnerSpec.js @@ -1,5 +1,4 @@ -describe("QueueRunner", function() { - +describe('QueueRunner', function() { it("runs all the functions it's passed", function() { var calls = [], queueableFn1 = { fn: jasmine.createSpy('fn1') }, @@ -19,7 +18,7 @@ describe("QueueRunner", function() { expect(calls).toEqual(['fn1', 'fn2']); }); - it("runs cleanup functions after the others", function() { + it('runs cleanup functions after the others', function() { var calls = [], queueableFn1 = { fn: jasmine.createSpy('fn1') }, queueableFn2 = { fn: jasmine.createSpy('fn2') }, @@ -41,12 +40,17 @@ describe("QueueRunner", function() { it("calls each function with a consistent 'this'-- an empty object", function() { var queueableFn1 = { fn: jasmine.createSpy('fn1') }, - queueableFn2 = { fn: jasmine.createSpy('fn2') }, - queueableFn3 = { fn: function(done) { asyncContext = this; done(); } }, - queueRunner = new jasmineUnderTest.QueueRunner({ - queueableFns: [queueableFn1, queueableFn2, queueableFn3] - }), - asyncContext; + queueableFn2 = { fn: jasmine.createSpy('fn2') }, + queueableFn3 = { + fn: function(done) { + asyncContext = this; + done(); + } + }, + queueRunner = new jasmineUnderTest.QueueRunner({ + queueableFns: [queueableFn1, queueableFn2, queueableFn3] + }), + asyncContext; queueRunner.execute(); @@ -56,7 +60,7 @@ describe("QueueRunner", function() { expect(asyncContext).toBe(context); }); - describe("with an asynchronous function", function() { + describe('with an asynchronous function', function() { beforeEach(function() { jasmine.clock().install(); }); @@ -65,7 +69,7 @@ describe("QueueRunner", function() { jasmine.clock().uninstall(); }); - it("supports asynchronous functions, only advancing to next function after a done() callback", function() { + it('supports asynchronous functions, only advancing to next function after a done() callback', function() { //TODO: it would be nice if spy arity could match the fake, so we could do something like: //createSpy('asyncfn').and.callFake(function(done) {}); @@ -73,18 +77,24 @@ describe("QueueRunner", function() { beforeCallback = jasmine.createSpy('beforeCallback'), fnCallback = jasmine.createSpy('fnCallback'), afterCallback = jasmine.createSpy('afterCallback'), - queueableFn1 = { fn: function(done) { - beforeCallback(); - setTimeout(done, 100); - } }, - queueableFn2 = { fn: function(done) { - fnCallback(); - setTimeout(done, 100); - } }, - queueableFn3 = { fn: function(done) { - afterCallback(); - setTimeout(done, 100); - } }, + queueableFn1 = { + fn: function(done) { + beforeCallback(); + setTimeout(done, 100); + } + }, + queueableFn2 = { + fn: function(done) { + fnCallback(); + setTimeout(done, 100); + } + }, + queueableFn3 = { + fn: function(done) { + afterCallback(); + setTimeout(done, 100); + } + }, queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [queueableFn1, queueableFn2, queueableFn3], onComplete: onComplete @@ -113,10 +123,14 @@ describe("QueueRunner", function() { expect(onComplete).toHaveBeenCalled(); }); - it("explicitly fails an async function with a provided fail function and moves to the next function", function() { - var queueableFn1 = { fn: function(done) { - setTimeout(function() { done.fail('foo'); }, 100); - } }, + it('explicitly fails an async function with a provided fail function and moves to the next function', function() { + var queueableFn1 = { + fn: function(done) { + setTimeout(function() { + done.fail('foo'); + }, 100); + } + }, queueableFn2 = { fn: jasmine.createSpy('fn2') }, failFn = jasmine.createSpy('fail'), queueRunner = new jasmineUnderTest.QueueRunner({ @@ -135,11 +149,15 @@ describe("QueueRunner", function() { expect(queueableFn2.fn).toHaveBeenCalled(); }); - it("explicitly fails an async function when next is called with an Error and moves to the next function", function() { + it('explicitly fails an async function when next is called with an Error and moves to the next function', function() { var err = new Error('foo'), - queueableFn1 = { fn: function(done) { - setTimeout(function() { done(err); }, 100); - } }, + queueableFn1 = { + fn: function(done) { + setTimeout(function() { + done(err); + }, 100); + } + }, queueableFn2 = { fn: jasmine.createSpy('fn2') }, failFn = jasmine.createSpy('fail'), queueRunner = new jasmineUnderTest.QueueRunner({ @@ -158,11 +176,15 @@ describe("QueueRunner", function() { expect(queueableFn2.fn).toHaveBeenCalled(); }); - it("does not cause an explicit fail if execution is being stopped", function() { + it('does not cause an explicit fail if execution is being stopped', function() { var err = new jasmineUnderTest.StopExecutionError('foo'), - queueableFn1 = { fn: function(done) { - setTimeout(function() { done(err); }, 100); - } }, + queueableFn1 = { + fn: function(done) { + setTimeout(function() { + done(err); + }, 100); + } + }, queueableFn2 = { fn: jasmine.createSpy('fn2') }, failFn = jasmine.createSpy('fail'), queueRunner = new jasmineUnderTest.QueueRunner({ @@ -183,7 +205,7 @@ describe("QueueRunner", function() { it("sets a timeout if requested for asynchronous functions so they don't go on forever", function() { var timeout = 3, - beforeFn = { fn: function(done) { }, type: 'before', timeout: timeout }, + beforeFn = { fn: function(done) {}, type: 'before', timeout: timeout }, queueableFn = { fn: jasmine.createSpy('fn'), type: 'queueable' }, onComplete = jasmine.createSpy('onComplete'), onException = jasmine.createSpy('onException'), @@ -203,15 +225,15 @@ describe("QueueRunner", function() { expect(onComplete).toHaveBeenCalled(); }); - it("by default does not set a timeout for asynchronous functions", function() { - var beforeFn = { fn: function(done) { } }, + it('by default does not set a timeout for asynchronous functions', function() { + var beforeFn = { fn: function(done) {} }, queueableFn = { fn: jasmine.createSpy('fn') }, onComplete = jasmine.createSpy('onComplete'), onException = jasmine.createSpy('onException'), queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [beforeFn, queueableFn], onComplete: onComplete, - onException: onException, + onException: onException }); queueRunner.execute(); @@ -224,8 +246,12 @@ describe("QueueRunner", function() { expect(onComplete).not.toHaveBeenCalled(); }); - it("clears the timeout when an async function throws an exception, to prevent additional exception reporting", function() { - var queueableFn = { fn: function(done) { throw new Error("error!"); } }, + it('clears the timeout when an async function throws an exception, to prevent additional exception reporting', function() { + var queueableFn = { + fn: function(done) { + throw new Error('error!'); + } + }, onComplete = jasmine.createSpy('onComplete'), onException = jasmine.createSpy('onException'), queueRunner = new jasmineUnderTest.QueueRunner({ @@ -243,8 +269,12 @@ describe("QueueRunner", function() { expect(onException.calls.count()).toEqual(1); }); - it("clears the timeout when the done callback is called", function() { - var queueableFn = { fn: function(done) { done(); } }, + it('clears the timeout when the done callback is called', function() { + var queueableFn = { + fn: function(done) { + done(); + } + }, onComplete = jasmine.createSpy('onComplete'), onException = jasmine.createSpy('onException'), queueRunner = new jasmineUnderTest.QueueRunner({ @@ -262,8 +292,13 @@ describe("QueueRunner", function() { expect(onException).not.toHaveBeenCalled(); }); - it("only moves to the next spec the first time you call done", function() { - var queueableFn = { fn: function(done) {done(); done();} }, + it('only moves to the next spec the first time you call done', function() { + var queueableFn = { + fn: function(done) { + done(); + done(); + } + }, nextQueueableFn = { fn: jasmine.createSpy('nextFn') }, queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [queueableFn, nextQueueableFn] @@ -274,27 +309,31 @@ describe("QueueRunner", function() { expect(nextQueueableFn.fn.calls.count()).toEqual(1); }); - it("does not move to the next spec if done is called after an exception has ended the spec", function() { - var queueableFn = { fn: function(done) { - setTimeout(done, 1); - throw new Error('error!'); - } }, - nextQueueableFn = { fn: jasmine.createSpy('nextFn') }, - queueRunner = new jasmineUnderTest.QueueRunner({ - queueableFns: [queueableFn, nextQueueableFn] - }); + it('does not move to the next spec if done is called after an exception has ended the spec', function() { + var queueableFn = { + fn: function(done) { + setTimeout(done, 1); + throw new Error('error!'); + } + }, + nextQueueableFn = { fn: jasmine.createSpy('nextFn') }, + queueRunner = new jasmineUnderTest.QueueRunner({ + queueableFns: [queueableFn, nextQueueableFn] + }); queueRunner.execute(); jasmine.clock().tick(1); expect(nextQueueableFn.fn.calls.count()).toEqual(1); }); - it("should return a null when you call done", function () { + it('should return a null when you call done', function() { // Some promises want handlers to return anything but undefined to help catch "forgotten returns". var doneReturn, - queueableFn = { fn: function(done) { - doneReturn = done(); - } }, + queueableFn = { + fn: function(done) { + doneReturn = done(); + } + }, queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [queueableFn] }); @@ -303,24 +342,36 @@ describe("QueueRunner", function() { expect(doneReturn).toBe(null); }); - it("continues running functions when an exception is thrown in async code without timing out", function() { - var queueableFn = { fn: function(done) { throwAsync(); }, timeout: 1 }, - nextQueueableFn = { fn: jasmine.createSpy("nextFunction") }, + it('continues running functions when an exception is thrown in async code without timing out', function() { + var queueableFn = { + fn: function(done) { + throwAsync(); + }, + timeout: 1 + }, + nextQueueableFn = { fn: jasmine.createSpy('nextFunction') }, onException = jasmine.createSpy('onException'), - globalErrors = { pushListener: jasmine.createSpy('pushListener'), popListener: jasmine.createSpy('popListener') }, + globalErrors = { + pushListener: jasmine.createSpy('pushListener'), + popListener: jasmine.createSpy('popListener') + }, queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [queueableFn, nextQueueableFn], onException: onException, globalErrors: globalErrors }), throwAsync = function() { - globalErrors.pushListener.calls.mostRecent().args[0](new Error('foo')); + globalErrors.pushListener.calls + .mostRecent() + .args[0](new Error('foo')); jasmine.clock().tick(2); }; nextQueueableFn.fn.and.callFake(function() { // should remove the same function that was added - expect(globalErrors.popListener).toHaveBeenCalledWith(globalErrors.pushListener.calls.argsFor(1)[0]); + expect(globalErrors.popListener).toHaveBeenCalledWith( + globalErrors.pushListener.calls.argsFor(1)[0] + ); }); queueRunner.execute(); @@ -335,28 +386,37 @@ describe("QueueRunner", function() { } }; } - expect(onException).not.toHaveBeenCalledWith(errorWithMessage(/DEFAULT_TIMEOUT_INTERVAL/)); + expect(onException).not.toHaveBeenCalledWith( + errorWithMessage(/DEFAULT_TIMEOUT_INTERVAL/) + ); expect(onException).toHaveBeenCalledWith(errorWithMessage(/^foo$/)); expect(nextQueueableFn.fn).toHaveBeenCalled(); }); - it("handles exceptions thrown while waiting for the stack to clear", function() { - var queueableFn = { fn: function(done) { done() } }, - global = {}, - errorListeners = [], - globalErrors = { - pushListener: function(f) { errorListeners.push(f); }, - popListener: function() { errorListeners.pop(); } - }, - clearStack = jasmine.createSpy('clearStack'), - onException = jasmine.createSpy('onException'), - queueRunner = new jasmineUnderTest.QueueRunner({ - queueableFns: [queueableFn], - globalErrors: globalErrors, - clearStack: clearStack, - onException: onException - }), - error = new Error('nope'); + it('handles exceptions thrown while waiting for the stack to clear', function() { + var queueableFn = { + fn: function(done) { + done(); + } + }, + errorListeners = [], + globalErrors = { + pushListener: function(f) { + errorListeners.push(f); + }, + popListener: function() { + errorListeners.pop(); + } + }, + clearStack = jasmine.createSpy('clearStack'), + onException = jasmine.createSpy('onException'), + queueRunner = new jasmineUnderTest.QueueRunner({ + queueableFns: [queueableFn], + globalErrors: globalErrors, + clearStack: clearStack, + onException: onException + }), + error = new Error('nope'); queueRunner.execute(); jasmine.clock().tick(); @@ -368,7 +428,7 @@ describe("QueueRunner", function() { }); }); - describe("with a function that returns a promise", function() { + describe('with a function that returns a promise', function() { function StubPromise() {} StubPromise.prototype.then = function(resolve, reject) { @@ -384,28 +444,32 @@ describe("QueueRunner", function() { jasmine.clock().uninstall(); }); - it("runs the function asynchronously, advancing once the promise is settled", function() { + it('runs the function asynchronously, advancing once the promise is settled', function() { var onComplete = jasmine.createSpy('onComplete'), - fnCallback = jasmine.createSpy('fnCallback'), + fnCallback = jasmine.createSpy('fnCallback'), p1 = new StubPromise(), p2 = new StubPromise(), - queueableFn1 = { fn: function() { - setTimeout(function() { - p1.resolveHandler(); - }, 100); - return p1; - } }; - queueableFn2 = { fn: function() { + queueableFn1 = { + fn: function() { + setTimeout(function() { + p1.resolveHandler(); + }, 100); + return p1; + } + }; + (queueableFn2 = { + fn: function() { fnCallback(); setTimeout(function() { p2.resolveHandler(); }, 100); return p2; - } }, - queueRunner = new jasmineUnderTest.QueueRunner({ + } + }), + (queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [queueableFn1, queueableFn2], onComplete: onComplete - }); + })); queueRunner.execute(); expect(fnCallback).not.toHaveBeenCalled(); @@ -421,16 +485,17 @@ describe("QueueRunner", function() { expect(onComplete).toHaveBeenCalled(); }); - it("handles a rejected promise like an unhandled exception", function() { + it('handles a rejected promise like an unhandled exception', function() { var promise = new StubPromise(), - queueableFn1 = { fn: function() { - setTimeout(function() { - promise.rejectHandler('foo') - }, 100); - return promise; - } }, + queueableFn1 = { + fn: function() { + setTimeout(function() { + promise.rejectHandler('foo'); + }, 100); + return promise; + } + }, queueableFn2 = { fn: jasmine.createSpy('fn2') }, - failFn = jasmine.createSpy('fail'), onExceptionCallback = jasmine.createSpy('on exception callback'), queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [queueableFn1, queueableFn2], @@ -449,11 +514,13 @@ describe("QueueRunner", function() { }); }); - it("calls exception handlers when an exception is thrown in a fn", function() { - var queueableFn = { type: 'queueable', - fn: function() { - throw new Error('fake error'); - } }, + it('calls exception handlers when an exception is thrown in a fn', function() { + var queueableFn = { + type: 'queueable', + fn: function() { + throw new Error('fake error'); + } + }, onExceptionCallback = jasmine.createSpy('on exception callback'), queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [queueableFn], @@ -465,9 +532,13 @@ describe("QueueRunner", function() { expect(onExceptionCallback).toHaveBeenCalledWith(jasmine.any(Error)); }); - it("continues running the functions even after an exception is thrown in an async spec", function() { - var queueableFn = { fn: function(done) { throw new Error("error"); } }, - nextQueueableFn = { fn: jasmine.createSpy("nextFunction") }, + it('continues running the functions even after an exception is thrown in an async spec', function() { + var queueableFn = { + fn: function(done) { + throw new Error('error'); + } + }, + nextQueueableFn = { fn: jasmine.createSpy('nextFunction') }, queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [queueableFn, nextQueueableFn] }); @@ -476,12 +547,16 @@ describe("QueueRunner", function() { expect(nextQueueableFn.fn).toHaveBeenCalled(); }); - describe("When configured to complete on first error", function() { - it("skips to cleanup functions on the first exception", function() { - var queueableFn = { fn: function() { throw new Error("error"); } }, - nextQueueableFn = { fn: jasmine.createSpy("nextFunction") }, - cleanupFn = { fn: jasmine.createSpy("cleanup") }, - onComplete = jasmine.createSpy("onComplete"), + describe('When configured to complete on first error', function() { + it('skips to cleanup functions on the first exception', function() { + var queueableFn = { + fn: function() { + throw new Error('error'); + } + }, + nextQueueableFn = { fn: jasmine.createSpy('nextFunction') }, + cleanupFn = { fn: jasmine.createSpy('cleanup') }, + onComplete = jasmine.createSpy('onComplete'), queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [queueableFn, nextQueueableFn], cleanupFns: [cleanupFn], @@ -492,13 +567,19 @@ describe("QueueRunner", function() { queueRunner.execute(); expect(nextQueueableFn.fn).not.toHaveBeenCalled(); expect(cleanupFn.fn).toHaveBeenCalled(); - expect(onComplete).toHaveBeenCalledWith(jasmine.any(jasmineUnderTest.StopExecutionError)); + expect(onComplete).toHaveBeenCalledWith( + jasmine.any(jasmineUnderTest.StopExecutionError) + ); }); - it("does not skip when a cleanup function throws", function() { - var queueableFn = { fn: function() { } }, - cleanupFn1 = { fn: function() { throw new Error("error"); } }, - cleanupFn2 = { fn: jasmine.createSpy("cleanupFn2") }, + it('does not skip when a cleanup function throws', function() { + var queueableFn = { fn: function() {} }, + cleanupFn1 = { + fn: function() { + throw new Error('error'); + } + }, + cleanupFn2 = { fn: jasmine.createSpy('cleanupFn2') }, queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [queueableFn], cleanupFns: [cleanupFn1, cleanupFn2], @@ -509,7 +590,7 @@ describe("QueueRunner", function() { expect(cleanupFn2.fn).toHaveBeenCalled(); }); - describe("with an asynchronous function", function() { + describe('with an asynchronous function', function() { beforeEach(function() { jasmine.clock().install(); }); @@ -518,21 +599,24 @@ describe("QueueRunner", function() { jasmine.clock().uninstall(); }); - - it("skips to cleanup functions on the first exception", function() { + it('skips to cleanup functions on the first exception', function() { var errorListeners = [], queueableFn = { fn: function(done) {} }, nextQueueableFn = { fn: jasmine.createSpy('nextFunction') }, cleanupFn = { fn: jasmine.createSpy('cleanup') }, queueRunner = new jasmineUnderTest.QueueRunner({ globalErrors: { - pushListener: function(f) { errorListeners.push(f); }, - popListener: function() { errorListeners.pop(); }, + pushListener: function(f) { + errorListeners.push(f); + }, + popListener: function() { + errorListeners.pop(); + } }, queueableFns: [queueableFn, nextQueueableFn], cleanupFns: [cleanupFn], - completeOnFirstError: true, - }); + completeOnFirstError: true + }); queueRunner.execute(); errorListeners[errorListeners.length - 1](new Error('error')); @@ -540,17 +624,19 @@ describe("QueueRunner", function() { expect(cleanupFn.fn).toHaveBeenCalled(); }); - it("skips to cleanup functions when next.fail is called", function() { - var queueableFn = { fn: function(done) { - done.fail('nope'); - } }, + it('skips to cleanup functions when next.fail is called', function() { + var queueableFn = { + fn: function(done) { + done.fail('nope'); + } + }, nextQueueableFn = { fn: jasmine.createSpy('nextFunction') }, cleanupFn = { fn: jasmine.createSpy('cleanup') }, queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [queueableFn, nextQueueableFn], cleanupFns: [cleanupFn], - completeOnFirstError: true, - }); + completeOnFirstError: true + }); queueRunner.execute(); jasmine.clock().tick(); @@ -558,17 +644,19 @@ describe("QueueRunner", function() { expect(cleanupFn.fn).toHaveBeenCalled(); }); - it("skips to cleanup functions when next is called with an Error", function() { - var queueableFn = { fn: function(done) { - done(new Error('nope')); - } }, + it('skips to cleanup functions when next is called with an Error', function() { + var queueableFn = { + fn: function(done) { + done(new Error('nope')); + } + }, nextQueueableFn = { fn: jasmine.createSpy('nextFunction') }, cleanupFn = { fn: jasmine.createSpy('cleanup') }, queueRunner = new jasmineUnderTest.QueueRunner({ queueableFns: [queueableFn, nextQueueableFn], cleanupFns: [cleanupFn], - completeOnFirstError: true, - }); + completeOnFirstError: true + }); queueRunner.execute(); jasmine.clock().tick(); @@ -578,7 +666,7 @@ describe("QueueRunner", function() { }); }); - it("calls a provided complete callback when done", function() { + it('calls a provided complete callback when done', function() { var queueableFn = { fn: jasmine.createSpy('fn') }, completeCallback = jasmine.createSpy('completeCallback'), queueRunner = new jasmineUnderTest.QueueRunner({ @@ -591,7 +679,7 @@ describe("QueueRunner", function() { expect(completeCallback).toHaveBeenCalled(); }); - describe("clearing the stack", function() { + describe('clearing the stack', function() { beforeEach(function() { jasmine.clock().install(); }); @@ -600,18 +688,24 @@ describe("QueueRunner", function() { jasmine.clock().uninstall(); }); - it("calls a provided stack clearing function when done", function() { - var asyncFn = { fn: function(done) { done() } }, - afterFn = { fn: jasmine.createSpy('afterFn') }, - completeCallback = jasmine.createSpy('completeCallback'), - clearStack = jasmine.createSpy('clearStack'), - queueRunner = new jasmineUnderTest.QueueRunner({ - queueableFns: [asyncFn, afterFn], - clearStack: clearStack, - onComplete: completeCallback - }); + it('calls a provided stack clearing function when done', function() { + var asyncFn = { + fn: function(done) { + done(); + } + }, + afterFn = { fn: jasmine.createSpy('afterFn') }, + completeCallback = jasmine.createSpy('completeCallback'), + clearStack = jasmine.createSpy('clearStack'), + queueRunner = new jasmineUnderTest.QueueRunner({ + queueableFns: [asyncFn, afterFn], + clearStack: clearStack, + onComplete: completeCallback + }); - clearStack.and.callFake(function(fn) { fn(); }); + clearStack.and.callFake(function(fn) { + fn(); + }); queueRunner.execute(); jasmine.clock().tick(); @@ -633,9 +727,7 @@ describe("QueueRunner", function() { }); it('runs the functions on the scope of a UserContext', function() { - var calls = [], - context; - + var context; this.fn.and.callFake(function() { context = this; }); @@ -659,8 +751,7 @@ describe("QueueRunner", function() { }); it('runs the functions on the scope of a UserContext', function() { - var calls = [], - context; + var context; this.fn.and.callFake(function() { context = this; }); diff --git a/spec/core/ReportDispatcherSpec.js b/spec/core/ReportDispatcherSpec.js index 87511ab7..2b569844 100644 --- a/spec/core/ReportDispatcherSpec.js +++ b/spec/core/ReportDispatcherSpec.js @@ -1,16 +1,22 @@ -describe("ReportDispatcher", function() { - - it("builds an interface of requested methods", function() { - var dispatcher = new jasmineUnderTest.ReportDispatcher(['foo', 'bar', 'baz']); +describe('ReportDispatcher', function() { + it('builds an interface of requested methods', function() { + var dispatcher = new jasmineUnderTest.ReportDispatcher([ + 'foo', + 'bar', + 'baz' + ]); expect(dispatcher.foo).toBeDefined(); expect(dispatcher.bar).toBeDefined(); expect(dispatcher.baz).toBeDefined(); }); - it("dispatches requested methods to added reporters", function() { + it('dispatches requested methods to added reporters', function() { var queueRunnerFactory = jasmine.createSpy('queueRunner'), - dispatcher = new jasmineUnderTest.ReportDispatcher(['foo', 'bar'], queueRunnerFactory), + dispatcher = new jasmineUnderTest.ReportDispatcher( + ['foo', 'bar'], + queueRunnerFactory + ), reporter = jasmine.createSpyObj('reporter', ['foo', 'bar']), anotherReporter = jasmine.createSpyObj('reporter', ['foo', 'bar']), completeCallback = jasmine.createSpy('complete'); @@ -20,10 +26,15 @@ describe("ReportDispatcher", function() { dispatcher.foo(123, 456, completeCallback); - expect(queueRunnerFactory).toHaveBeenCalledWith(jasmine.objectContaining({ - queueableFns: [{fn: jasmine.any(Function)}, {fn: jasmine.any(Function)}], - isReporter: true - })); + expect(queueRunnerFactory).toHaveBeenCalledWith( + jasmine.objectContaining({ + queueableFns: [ + { fn: jasmine.any(Function) }, + { fn: jasmine.any(Function) } + ], + isReporter: true + }) + ); var fns = queueRunnerFactory.calls.mostRecent().args[0].queueableFns; fns[0].fn(); @@ -38,10 +49,15 @@ describe("ReportDispatcher", function() { dispatcher.bar('a', 'b', completeCallback); - expect(queueRunnerFactory).toHaveBeenCalledWith(jasmine.objectContaining({ - queueableFns: [{fn: jasmine.any(Function)}, {fn: jasmine.any(Function)}], - isReporter: true - })); + expect(queueRunnerFactory).toHaveBeenCalledWith( + jasmine.objectContaining({ + queueableFns: [ + { fn: jasmine.any(Function) }, + { fn: jasmine.any(Function) } + ], + isReporter: true + }) + ); fns = queueRunnerFactory.calls.mostRecent().args[0].queueableFns; fns[0].fn(); @@ -53,39 +69,52 @@ describe("ReportDispatcher", function() { it("does not dispatch to a reporter if the reporter doesn't accept the method", function() { var queueRunnerFactory = jasmine.createSpy('queueRunner'), - dispatcher = new jasmineUnderTest.ReportDispatcher(['foo'], queueRunnerFactory), + dispatcher = new jasmineUnderTest.ReportDispatcher( + ['foo'], + queueRunnerFactory + ), reporter = jasmine.createSpyObj('reporter', ['baz']); dispatcher.addReporter(reporter); dispatcher.foo(123, 456); - expect(queueRunnerFactory).toHaveBeenCalledWith(jasmine.objectContaining({ - queueableFns: [] - })); + expect(queueRunnerFactory).toHaveBeenCalledWith( + jasmine.objectContaining({ + queueableFns: [] + }) + ); }); it("allows providing a fallback reporter in case there's no other reporter", function() { var queueRunnerFactory = jasmine.createSpy('queueRunner'), - dispatcher = new jasmineUnderTest.ReportDispatcher(['foo', 'bar'], queueRunnerFactory), + dispatcher = new jasmineUnderTest.ReportDispatcher( + ['foo', 'bar'], + queueRunnerFactory + ), reporter = jasmine.createSpyObj('reporter', ['foo', 'bar']), completeCallback = jasmine.createSpy('complete'); dispatcher.provideFallbackReporter(reporter); dispatcher.foo(123, 456, completeCallback); - expect(queueRunnerFactory).toHaveBeenCalledWith(jasmine.objectContaining({ - queueableFns: [{fn: jasmine.any(Function)}], - isReporter: true - })); + expect(queueRunnerFactory).toHaveBeenCalledWith( + jasmine.objectContaining({ + queueableFns: [{ fn: jasmine.any(Function) }], + isReporter: true + }) + ); var fns = queueRunnerFactory.calls.mostRecent().args[0].queueableFns; fns[0].fn(); expect(reporter.foo).toHaveBeenCalledWith(123, 456); }); - it("does not call fallback reporting methods when another reporter is provided", function() { + it('does not call fallback reporting methods when another reporter is provided', function() { var queueRunnerFactory = jasmine.createSpy('queueRunner'), - dispatcher = new jasmineUnderTest.ReportDispatcher(['foo', 'bar'], queueRunnerFactory), + dispatcher = new jasmineUnderTest.ReportDispatcher( + ['foo', 'bar'], + queueRunnerFactory + ), reporter = jasmine.createSpyObj('reporter', ['foo', 'bar']), fallbackReporter = jasmine.createSpyObj('otherReporter', ['foo', 'bar']), completeCallback = jasmine.createSpy('complete'); @@ -94,10 +123,12 @@ describe("ReportDispatcher", function() { dispatcher.addReporter(reporter); dispatcher.foo(123, 456, completeCallback); - expect(queueRunnerFactory).toHaveBeenCalledWith(jasmine.objectContaining({ - queueableFns: [{fn: jasmine.any(Function)}], - isReporter: true - })); + expect(queueRunnerFactory).toHaveBeenCalledWith( + jasmine.objectContaining({ + queueableFns: [{ fn: jasmine.any(Function) }], + isReporter: true + }) + ); var fns = queueRunnerFactory.calls.mostRecent().args[0].queueableFns; fns[0].fn(); @@ -105,19 +136,24 @@ describe("ReportDispatcher", function() { expect(fallbackReporter.foo).not.toHaveBeenCalledWith(123, 456); }); - it("allows registered reporters to be cleared", function() { + it('allows registered reporters to be cleared', function() { var queueRunnerFactory = jasmine.createSpy('queueRunner'), - dispatcher = new jasmineUnderTest.ReportDispatcher(['foo', 'bar'], queueRunnerFactory), - reporter1 = jasmine.createSpyObj('reporter1', ['foo', 'bar']), - reporter2 = jasmine.createSpyObj('reporter2', ['foo', 'bar']), + dispatcher = new jasmineUnderTest.ReportDispatcher( + ['foo', 'bar'], + queueRunnerFactory + ), + reporter1 = jasmine.createSpyObj('reporter1', ['foo', 'bar']), + reporter2 = jasmine.createSpyObj('reporter2', ['foo', 'bar']), completeCallback = jasmine.createSpy('complete'); dispatcher.addReporter(reporter1); dispatcher.foo(123, completeCallback); - expect(queueRunnerFactory).toHaveBeenCalledWith(jasmine.objectContaining({ - queueableFns: [{fn: jasmine.any(Function)}], - isReporter: true - })); + expect(queueRunnerFactory).toHaveBeenCalledWith( + jasmine.objectContaining({ + queueableFns: [{ fn: jasmine.any(Function) }], + isReporter: true + }) + ); var fns = queueRunnerFactory.calls.mostRecent().args[0].queueableFns; fns[0].fn(); @@ -127,10 +163,12 @@ describe("ReportDispatcher", function() { dispatcher.addReporter(reporter2); dispatcher.bar(456, completeCallback); - expect(queueRunnerFactory).toHaveBeenCalledWith(jasmine.objectContaining({ - queueableFns: [{fn: jasmine.any(Function)}], - isReporter: true - })); + expect(queueRunnerFactory).toHaveBeenCalledWith( + jasmine.objectContaining({ + queueableFns: [{ fn: jasmine.any(Function) }], + isReporter: true + }) + ); fns = queueRunnerFactory.calls.mostRecent().args[0].queueableFns; fns[0].fn(); diff --git a/spec/core/SpecSpec.js b/spec/core/SpecSpec.js index 1191f7c3..8219a1cd 100644 --- a/spec/core/SpecSpec.js +++ b/spec/core/SpecSpec.js @@ -1,25 +1,30 @@ -describe("Spec", function() { - - it("#isPendingSpecException returns true for a pending spec exception", function() { +describe('Spec', function() { + it('#isPendingSpecException returns true for a pending spec exception', function() { var e = new Error(jasmineUnderTest.Spec.pendingSpecExceptionMessage); expect(jasmineUnderTest.Spec.isPendingSpecException(e)).toBe(true); }); - it("#isPendingSpecException returns true for a pending spec exception (even when FF bug is present)", function() { + it('#isPendingSpecException returns true for a pending spec exception (even when FF bug is present)', function() { var fakeError = { - toString: function() { return "Error: " + jasmineUnderTest.Spec.pendingSpecExceptionMessage; } + toString: function() { + return 'Error: ' + jasmineUnderTest.Spec.pendingSpecExceptionMessage; + } }; expect(jasmineUnderTest.Spec.isPendingSpecException(fakeError)).toBe(true); }); - it("#isPendingSpecException returns true for a pending spec exception with a custom message", function() { - expect(jasmineUnderTest.Spec.isPendingSpecException(jasmineUnderTest.Spec.pendingSpecExceptionMessage + 'foo')).toBe(true); + it('#isPendingSpecException returns true for a pending spec exception with a custom message', function() { + expect( + jasmineUnderTest.Spec.isPendingSpecException( + jasmineUnderTest.Spec.pendingSpecExceptionMessage + 'foo' + ) + ).toBe(true); }); - it("#isPendingSpecException returns false for not a pending spec exception", function() { - var e = new Error("foo"); + it('#isPendingSpecException returns false for not a pending spec exception', function() { + var e = new Error('foo'); expect(jasmineUnderTest.Spec.isPendingSpecException(e)).toBe(false); }); @@ -28,7 +33,7 @@ describe("Spec", function() { expect(jasmineUnderTest.Spec.isPendingSpecException(void 0)).toBe(false); }); - it("delegates execution to a QueueRunner", function() { + it('delegates execution to a QueueRunner', function() { var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner'), spec = new jasmineUnderTest.Spec({ description: 'my test', @@ -42,7 +47,7 @@ describe("Spec", function() { expect(fakeQueueRunner).toHaveBeenCalled(); }); - it("should call the start callback on execution", function() { + it('should call the start callback on execution', function() { var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner'), startCallback = jasmine.createSpy('startCallback'), spec = new jasmineUnderTest.Spec({ @@ -64,18 +69,22 @@ describe("Spec", function() { expect(startCallback.calls.first().object).toEqual(spec); }); - it("should call the start callback on execution but before any befores are called", function() { + it('should call the start callback on execution but before any befores are called', function() { var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner'), beforesWereCalled = false, - startCallback = jasmine.createSpy('start-callback').and.callFake(function() { - expect(beforesWereCalled).toBe(false); - }), + startCallback = jasmine + .createSpy('start-callback') + .and.callFake(function() { + expect(beforesWereCalled).toBe(false); + }), spec = new jasmineUnderTest.Spec({ queueableFn: { fn: function() {} }, beforeFns: function() { - return [function() { - beforesWereCalled = true - }] + return [ + function() { + beforesWereCalled = true; + } + ]; }, onStart: startCallback, queueRunnerFactory: fakeQueueRunner @@ -87,18 +96,20 @@ describe("Spec", function() { expect(startCallback).toHaveBeenCalled(); }); - it("provides all before fns and after fns to be run", function() { + it('provides all before fns and after fns to be run', function() { var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner'), before = jasmine.createSpy('before'), after = jasmine.createSpy('after'), - queueableFn = { fn: jasmine.createSpy('test body').and.callFake(function() { - expect(before).toHaveBeenCalled(); - expect(after).not.toHaveBeenCalled(); - }) }, + queueableFn = { + fn: jasmine.createSpy('test body').and.callFake(function() { + expect(before).toHaveBeenCalled(); + expect(after).not.toHaveBeenCalled(); + }) + }, spec = new jasmineUnderTest.Spec({ queueableFn: queueableFn, beforeAndAfterFns: function() { - return {befores: [before], afters: [after]} + return { befores: [before], afters: [after] }; }, queueRunnerFactory: fakeQueueRunner }); @@ -106,8 +117,12 @@ describe("Spec", function() { spec.execute(); var options = fakeQueueRunner.calls.mostRecent().args[0]; - expect(options.queueableFns).toEqual([{fn: jasmine.any(Function)}, before, queueableFn]); - expect(options.cleanupFns).toEqual([after, {fn: jasmine.any(Function)}]); + expect(options.queueableFns).toEqual([ + { fn: jasmine.any(Function) }, + before, + queueableFn + ]); + expect(options.cleanupFns).toEqual([after, { fn: jasmine.any(Function) }]); }); it("tells the queue runner that it's a leaf node", function() { @@ -115,21 +130,22 @@ describe("Spec", function() { spec = new jasmineUnderTest.Spec({ queueableFn: { fn: function() {} }, beforeAndAfterFns: function() { - return {befores: [], afters: []} + return { befores: [], afters: [] }; }, queueRunnerFactory: fakeQueueRunner }); spec.execute(); - expect(fakeQueueRunner).toHaveBeenCalledWith(jasmine.objectContaining({ - isLeaf: true - })); + expect(fakeQueueRunner).toHaveBeenCalledWith( + jasmine.objectContaining({ + isLeaf: true + }) + ); }); - it("is marked pending if created without a function body", function() { + it('is marked pending if created without a function body', function() { var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner'), - startCallback = jasmine.createSpy('startCallback'), resultCallback = jasmine.createSpy('resultCallback'), spec = new jasmineUnderTest.Spec({ @@ -142,13 +158,13 @@ describe("Spec", function() { expect(spec.status()).toBe('pending'); }); - it("can be excluded at execution time by a parent", function() { + it('can be excluded at execution time by a parent', function() { var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner'), startCallback = jasmine.createSpy('startCallback'), specBody = jasmine.createSpy('specBody'), resultCallback = jasmine.createSpy('resultCallback'), spec = new jasmineUnderTest.Spec({ - onStart:startCallback, + onStart: startCallback, queueableFn: { fn: specBody }, resultCallback: resultCallback, queueRunnerFactory: fakeQueueRunner @@ -156,11 +172,13 @@ describe("Spec", function() { spec.execute('cally-back', true); - expect(fakeQueueRunner).toHaveBeenCalledWith(jasmine.objectContaining({ - onComplete: jasmine.any(Function), - queueableFns: [{fn: jasmine.any(Function)}], - cleanupFns: [{fn: jasmine.any(Function)}] - })); + expect(fakeQueueRunner).toHaveBeenCalledWith( + jasmine.objectContaining({ + onComplete: jasmine.any(Function), + queueableFns: [{ fn: jasmine.any(Function) }], + cleanupFns: [{ fn: jasmine.any(Function) }] + }) + ); expect(specBody).not.toHaveBeenCalled(); var args = fakeQueueRunner.calls.mostRecent().args[0]; @@ -172,16 +190,16 @@ describe("Spec", function() { expect(spec.result.status).toBe('excluded'); }); - it("can be marked pending, but still calls callbacks when executed", function() { + it('can be marked pending, but still calls callbacks when executed', function() { var fakeQueueRunner = jasmine.createSpy('fakeQueueRunner'), startCallback = jasmine.createSpy('startCallback'), resultCallback = jasmine.createSpy('resultCallback'), spec = new jasmineUnderTest.Spec({ onStart: startCallback, resultCallback: resultCallback, - description: "with a spec", + description: 'with a spec', getSpecName: function() { - return "a suite with a spec" + return 'a suite with a spec'; }, queueRunnerFactory: fakeQueueRunner, queueableFn: { fn: null } @@ -199,26 +217,33 @@ describe("Spec", function() { args.queueableFns[0].fn(); expect(startCallback).toHaveBeenCalled(); args.cleanupFns[0].fn('things'); - expect(resultCallback).toHaveBeenCalledWith({ - id: spec.id, - status: 'pending', - description: 'with a spec', - fullName: 'a suite with a spec', - failedExpectations: [], - passedExpectations: [], - deprecationWarnings: [], - pendingReason: '', - duration: null, - }, 'things'); + expect(resultCallback).toHaveBeenCalledWith( + { + id: spec.id, + status: 'pending', + description: 'with a spec', + fullName: 'a suite with a spec', + failedExpectations: [], + passedExpectations: [], + deprecationWarnings: [], + pendingReason: '', + duration: null + }, + 'things' + ); }); - it("should call the done callback on execution complete", function() { + it('should call the done callback on execution complete', function() { var done = jasmine.createSpy('done callback'), spec = new jasmineUnderTest.Spec({ queueableFn: { fn: function() {} }, - catchExceptions: function() { return false; }, + catchExceptions: function() { + return false; + }, resultCallback: function() {}, - queueRunnerFactory: function(attrs) { attrs.onComplete(); } + queueRunnerFactory: function(attrs) { + attrs.onComplete(); + } }); spec.execute(done); @@ -226,11 +251,13 @@ describe("Spec", function() { expect(done).toHaveBeenCalled(); }); - it("should call the done callback with an error if the spec is failed", function() { + it('should call the done callback with an error if the spec is failed', function() { var done = jasmine.createSpy('done callback'), spec = new jasmineUnderTest.Spec({ queueableFn: { fn: function() {} }, - catchExceptions: function() { return false; }, + catchExceptions: function() { + return false; + }, resultCallback: function() {}, queueRunnerFactory: function(attrs) { spec.result.status = 'failed'; @@ -240,49 +267,61 @@ describe("Spec", function() { spec.execute(done); - expect(done).toHaveBeenCalledWith(jasmine.any(jasmineUnderTest.StopExecutionError)); + expect(done).toHaveBeenCalledWith( + jasmine.any(jasmineUnderTest.StopExecutionError) + ); }); - it("should report the duration of the test", function() { + it('should report the duration of the test', function() { var done = jasmine.createSpy('done callback'), - timer = jasmine.createSpyObj('timer', {'start': null, elapsed: 77000}), + timer = jasmine.createSpyObj('timer', { start: null, elapsed: 77000 }), spec = new jasmineUnderTest.Spec({ - queueableFn: { fn: jasmine.createSpy("spec body")}, - catchExceptions: function() { return false; }, + queueableFn: { fn: jasmine.createSpy('spec body') }, + catchExceptions: function() { + return false; + }, resultCallback: function() {}, queueRunnerFactory: function(attrs) { attrs.onComplete(); }, - timer: timer, + timer: timer }); spec.execute(done); expect(spec.result.duration).toBe(77000); }); - it("#status returns passing by default", function() { - var spec = new jasmineUnderTest.Spec({queueableFn: { fn: jasmine.createSpy("spec body")} }); + it('#status returns passing by default', function() { + var spec = new jasmineUnderTest.Spec({ + queueableFn: { fn: jasmine.createSpy('spec body') } + }); expect(spec.status()).toBe('passed'); }); - it("#status returns passed if all expectations in the spec have passed", function() { - var spec = new jasmineUnderTest.Spec({queueableFn: { fn: jasmine.createSpy("spec body")} }); + it('#status returns passed if all expectations in the spec have passed', function() { + var spec = new jasmineUnderTest.Spec({ + queueableFn: { fn: jasmine.createSpy('spec body') } + }); spec.addExpectationResult(true); expect(spec.status()).toBe('passed'); }); - it("#status returns failed if any expectations in the spec have failed", function() { - var spec = new jasmineUnderTest.Spec({queueableFn: { fn: jasmine.createSpy("spec body") } }); + it('#status returns failed if any expectations in the spec have failed', function() { + var spec = new jasmineUnderTest.Spec({ + queueableFn: { fn: jasmine.createSpy('spec body') } + }); spec.addExpectationResult(true); spec.addExpectationResult(false); expect(spec.status()).toBe('failed'); }); - it("keeps track of passed and failed expectations", function() { + it('keeps track of passed and failed expectations', function() { var fakeQueueRunner = jasmine.createSpy('queueRunner'), resultCallback = jasmine.createSpy('resultCallback'), spec = new jasmineUnderTest.Spec({ - queueableFn: { fn: jasmine.createSpy("spec body") }, - expectationResultFactory: function (data) { return data; }, + queueableFn: { fn: jasmine.createSpy('spec body') }, + expectationResultFactory: function(data) { + return data; + }, queueRunnerFactory: fakeQueueRunner, resultCallback: resultCallback }); @@ -292,8 +331,12 @@ describe("Spec", function() { spec.execute(); fakeQueueRunner.calls.mostRecent().args[0].cleanupFns[0].fn(); - expect(resultCallback.calls.first().args[0].passedExpectations).toEqual(['expectation1']); - expect(resultCallback.calls.first().args[0].failedExpectations).toEqual(['expectation2']); + expect(resultCallback.calls.first().args[0].passedExpectations).toEqual([ + 'expectation1' + ]); + expect(resultCallback.calls.first().args[0].failedExpectations).toEqual([ + 'expectation2' + ]); }); it("throws an ExpectationFailed error upon receiving a failed expectation when 'throwOnExpectationFailure' is set", function() { @@ -301,7 +344,9 @@ describe("Spec", function() { resultCallback = jasmine.createSpy('resultCallback'), spec = new jasmineUnderTest.Spec({ queueableFn: { fn: function() {} }, - expectationResultFactory: function(data) { return data; }, + expectationResultFactory: function(data) { + return data; + }, queueRunnerFactory: fakeQueueRunner, resultCallback: resultCallback, throwOnExpectationFailure: true @@ -309,22 +354,30 @@ describe("Spec", function() { spec.addExpectationResult(true, 'passed'); expect(function() { - spec.addExpectationResult(false, 'failed') + spec.addExpectationResult(false, 'failed'); }).toThrowError(jasmineUnderTest.errors.ExpectationFailed); spec.execute(); fakeQueueRunner.calls.mostRecent().args[0].cleanupFns[0].fn(); - expect(resultCallback.calls.first().args[0].passedExpectations).toEqual(['passed']); - expect(resultCallback.calls.first().args[0].failedExpectations).toEqual(['failed']); + expect(resultCallback.calls.first().args[0].passedExpectations).toEqual([ + 'passed' + ]); + expect(resultCallback.calls.first().args[0].failedExpectations).toEqual([ + 'failed' + ]); }); - it("does not throw an ExpectationFailed error when handling an error", function() { + it('does not throw an ExpectationFailed error when handling an error', function() { var resultCallback = jasmine.createSpy('resultCallback'), spec = new jasmineUnderTest.Spec({ queueableFn: { fn: function() {} }, - expectationResultFactory: function(data) { return data; }, - queueRunnerFactory: function(attrs) { attrs.onComplete(); }, + expectationResultFactory: function(data) { + return data; + }, + queueRunnerFactory: function(attrs) { + attrs.onComplete(); + }, resultCallback: resultCallback, throwOnExpectationFailure: true }); @@ -332,8 +385,10 @@ describe("Spec", function() { spec.onException('failing exception'); }); - it("can return its full name", function() { - var specNameSpy = jasmine.createSpy('specNameSpy').and.returnValue('expected val'); + it('can return its full name', function() { + var specNameSpy = jasmine + .createSpy('specNameSpy') + .and.returnValue('expected val'); var spec = new jasmineUnderTest.Spec({ getSpecName: specNameSpy, @@ -344,48 +399,57 @@ describe("Spec", function() { expect(specNameSpy.calls.mostRecent().args[0].id).toEqual(spec.id); }); - describe("when a spec is marked pending during execution", function() { - it("should mark the spec as pending", function() { + describe('when a spec is marked pending during execution', function() { + it('should mark the spec as pending', function() { var fakeQueueRunner = function(opts) { - opts.onException(new Error(jasmineUnderTest.Spec.pendingSpecExceptionMessage)); + opts.onException( + new Error(jasmineUnderTest.Spec.pendingSpecExceptionMessage) + ); }, spec = new jasmineUnderTest.Spec({ description: 'my test', id: 'some-id', - queueableFn: { fn: function() { } }, + queueableFn: { fn: function() {} }, queueRunnerFactory: fakeQueueRunner }); spec.execute(); - expect(spec.status()).toEqual("pending"); + expect(spec.status()).toEqual('pending'); expect(spec.result.pendingReason).toEqual(''); }); - it("should set the pendingReason", function() { + it('should set the pendingReason', function() { var fakeQueueRunner = function(opts) { - opts.onException(new Error(jasmineUnderTest.Spec.pendingSpecExceptionMessage + 'custom message')); + opts.onException( + new Error( + jasmineUnderTest.Spec.pendingSpecExceptionMessage + + 'custom message' + ) + ); }, spec = new jasmineUnderTest.Spec({ description: 'my test', id: 'some-id', - queueableFn: { fn: function() { } }, + queueableFn: { fn: function() {} }, queueRunnerFactory: fakeQueueRunner }); spec.execute(); - expect(spec.status()).toEqual("pending"); + expect(spec.status()).toEqual('pending'); expect(spec.result.pendingReason).toEqual('custom message'); }); }); - it("should log a failure when handling an exception", function() { + it('should log a failure when handling an exception', function() { var fakeQueueRunner = jasmine.createSpy('queueRunner'), resultCallback = jasmine.createSpy('resultCallback'), spec = new jasmineUnderTest.Spec({ queueableFn: { fn: function() {} }, - expectationResultFactory: function(data) { return data; }, + expectationResultFactory: function(data) { + return data; + }, queueRunnerFactory: fakeQueueRunner, resultCallback: resultCallback }); @@ -395,21 +459,25 @@ describe("Spec", function() { var args = fakeQueueRunner.calls.mostRecent().args[0]; args.cleanupFns[0].fn(); - expect(resultCallback.calls.first().args[0].failedExpectations).toEqual([{ - error: 'foo', - matcherName: '', - passed: false, - expected: '', - actual: '' - }]); + expect(resultCallback.calls.first().args[0].failedExpectations).toEqual([ + { + error: 'foo', + matcherName: '', + passed: false, + expected: '', + actual: '' + } + ]); }); - it("should not log an additional failure when handling an ExpectationFailed error", function() { + it('should not log an additional failure when handling an ExpectationFailed error', function() { var fakeQueueRunner = jasmine.createSpy('queueRunner'), resultCallback = jasmine.createSpy('resultCallback'), spec = new jasmineUnderTest.Spec({ queueableFn: { fn: function() {} }, - expectationResultFactory: function(data) { return data; }, + expectationResultFactory: function(data) { + return data; + }, queueRunnerFactory: fakeQueueRunner, resultCallback: resultCallback }); diff --git a/spec/core/SpyRegistrySpec.js b/spec/core/SpyRegistrySpec.js index dcf414a2..f3c81a47 100644 --- a/spec/core/SpyRegistrySpec.js +++ b/spec/core/SpyRegistrySpec.js @@ -1,33 +1,35 @@ -describe("SpyRegistry", function() { +describe('SpyRegistry', function() { function createSpy(name, originalFn) { return jasmineUnderTest.Spy(name, originalFn); } - describe("#spyOn", function() { - it("checks for the existence of the object", function() { - var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: createSpy}); + describe('#spyOn', function() { + it('checks for the existence of the object', function() { + var spyRegistry = new jasmineUnderTest.SpyRegistry({ + createSpy: createSpy + }); expect(function() { spyRegistry.spyOn(void 0, 'pants'); }).toThrowError(/could not find an object/); }); - it("checks that a method name was passed", function() { + it('checks that a method name was passed', function() { var spyRegistry = new jasmineUnderTest.SpyRegistry(), subject = {}; - expect(function() { - spyRegistry.spyOn(subject); - }).toThrowError(/No method name supplied/); + expect(function() { + spyRegistry.spyOn(subject); + }).toThrowError(/No method name supplied/); }); - it("checks that the object is not `null`", function() { + it('checks that the object is not `null`', function() { var spyRegistry = new jasmineUnderTest.SpyRegistry(); expect(function() { spyRegistry.spyOn(null, 'pants'); }).toThrowError(/could not find an object/); }); - it("checks that the method name is not `null`", function() { + it('checks that the method name is not `null`', function() { var spyRegistry = new jasmineUnderTest.SpyRegistry(), subject = {}; @@ -36,7 +38,7 @@ describe("SpyRegistry", function() { }).toThrowError(/No method name supplied/); }); - it("checks for the existence of the method", function() { + it('checks for the existence of the method', function() { var spyRegistry = new jasmineUnderTest.SpyRegistry(), subject = {}; @@ -45,10 +47,12 @@ describe("SpyRegistry", function() { }).toThrowError(/method does not exist/); }); - it("checks if it has already been spied upon", function() { + it('checks if it has already been spied upon', function() { var spies = [], spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() { return spies; }, + currentSpies: function() { + return spies; + }, createSpy: createSpy }), subject = { spiedFunc: function() {} }; @@ -60,7 +64,7 @@ describe("SpyRegistry", function() { }).toThrowError(/has already been spied upon/); }); - it("checks if it can be spied upon", function() { + it('checks if it can be spied upon', function() { var scope = {}; function myFunc() { @@ -74,7 +78,11 @@ describe("SpyRegistry", function() { }); var spies = [], - spyRegistry = new jasmineUnderTest.SpyRegistry({currentSpies: function() { return spies; }}), + spyRegistry = new jasmineUnderTest.SpyRegistry({ + currentSpies: function() { + return spies; + } + }), subject = { spiedFunc: scope.myFunc }; expect(function() { @@ -86,35 +94,43 @@ describe("SpyRegistry", function() { }).not.toThrowError(/is not declared writable or has no setter/); }); - it("overrides the method on the object and returns the spy", function() { + it('overrides the method on the object and returns the spy', function() { var originalFunctionWasCalled = false, - spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: createSpy}), - subject = { spiedFunc: function() { originalFunctionWasCalled = true; } }; + spyRegistry = new jasmineUnderTest.SpyRegistry({ + createSpy: createSpy + }), + subject = { + spiedFunc: function() { + originalFunctionWasCalled = true; + } + }; var spy = spyRegistry.spyOn(subject, 'spiedFunc'); expect(subject.spiedFunc).toEqual(spy); + subject.spiedFunc(); + expect(originalFunctionWasCalled).toBe(false); }); }); - describe("#spyOnProperty", function() { - it("checks for the existence of the object", function() { + describe('#spyOnProperty', function() { + it('checks for the existence of the object', function() { var spyRegistry = new jasmineUnderTest.SpyRegistry(); expect(function() { spyRegistry.spyOnProperty(void 0, 'pants'); }).toThrowError(/could not find an object/); }); - it("checks that a property name was passed", function() { + it('checks that a property name was passed', function() { var spyRegistry = new jasmineUnderTest.SpyRegistry(), subject = {}; - expect(function() { - spyRegistry.spyOnProperty(subject); - }).toThrowError(/No property name supplied/); + expect(function() { + spyRegistry.spyOnProperty(subject); + }).toThrowError(/No property name supplied/); }); - it("checks for the existence of the method", function() { + it('checks for the existence of the method', function() { var spyRegistry = new jasmineUnderTest.SpyRegistry(), subject = {}; @@ -123,12 +139,14 @@ describe("SpyRegistry", function() { }).toThrowError(/property does not exist/); }); - it("checks for the existence of access type", function() { + it('checks for the existence of access type', function() { var spyRegistry = new jasmineUnderTest.SpyRegistry(), subject = {}; Object.defineProperty(subject, 'pants', { - get: function() { return 1; }, + get: function() { + return 1; + }, configurable: true }); @@ -137,7 +155,7 @@ describe("SpyRegistry", function() { }).toThrowError(/does not have access type/); }); - it("checks if it can be spied upon", function() { + it('checks if it can be spied upon', function() { var subject = {}; Object.defineProperty(subject, 'myProp', { @@ -160,50 +178,64 @@ describe("SpyRegistry", function() { }).not.toThrowError(/is not declared configurable/); }); - it("overrides the property getter on the object and returns the spy", function() { - var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: createSpy}), + it('overrides the property getter on the object and returns the spy', function() { + var spyRegistry = new jasmineUnderTest.SpyRegistry({ + createSpy: createSpy + }), subject = {}, returnValue = 1; Object.defineProperty(subject, 'spiedProperty', { - get: function() { return returnValue; }, + get: function() { + return returnValue; + }, configurable: true }); expect(subject.spiedProperty).toEqual(returnValue); var spy = spyRegistry.spyOnProperty(subject, 'spiedProperty'); - var getter = Object.getOwnPropertyDescriptor(subject, 'spiedProperty').get; + var getter = Object.getOwnPropertyDescriptor(subject, 'spiedProperty') + .get; expect(getter).toEqual(spy); expect(subject.spiedProperty).toBeUndefined(); }); - it("overrides the property setter on the object and returns the spy", function() { - var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: createSpy}), + it('overrides the property setter on the object and returns the spy', function() { + var spyRegistry = new jasmineUnderTest.SpyRegistry({ + createSpy: createSpy + }), subject = {}, returnValue = 1; Object.defineProperty(subject, 'spiedProperty', { - get: function() { return returnValue; }, + get: function() { + return returnValue; + }, set: function() {}, configurable: true }); var spy = spyRegistry.spyOnProperty(subject, 'spiedProperty', 'set'); - var setter = Object.getOwnPropertyDescriptor(subject, 'spiedProperty').set; + var setter = Object.getOwnPropertyDescriptor(subject, 'spiedProperty') + .set; expect(subject.spiedProperty).toEqual(returnValue); expect(setter).toEqual(spy); }); - describe("when the property is already spied upon", function() { - it("throws an error if respy is not allowed", function() { - var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: createSpy}), + describe('when the property is already spied upon', function() { + it('throws an error if respy is not allowed', function() { + var spyRegistry = new jasmineUnderTest.SpyRegistry({ + createSpy: createSpy + }), subject = {}; Object.defineProperty(subject, 'spiedProp', { - get: function() { return 1; }, + get: function() { + return 1; + }, configurable: true }); @@ -214,37 +246,49 @@ describe("SpyRegistry", function() { }).toThrowError(/spiedProp#get has already been spied upon/); }); - it("returns the original spy if respy is allowed", function() { - var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: createSpy}), + it('returns the original spy if respy is allowed', function() { + var spyRegistry = new jasmineUnderTest.SpyRegistry({ + createSpy: createSpy + }), subject = {}; spyRegistry.allowRespy(true); Object.defineProperty(subject, 'spiedProp', { - get: function() { return 1; }, + get: function() { + return 1; + }, configurable: true }); var originalSpy = spyRegistry.spyOnProperty(subject, 'spiedProp'); - expect(spyRegistry.spyOnProperty(subject, 'spiedProp')).toBe(originalSpy); + expect(spyRegistry.spyOnProperty(subject, 'spiedProp')).toBe( + originalSpy + ); }); }); }); - describe("#spyOnAllFunctions", function() { - it("checks for the existence of the object", function() { + describe('#spyOnAllFunctions', function() { + it('checks for the existence of the object', function() { var spyRegistry = new jasmineUnderTest.SpyRegistry(); expect(function() { spyRegistry.spyOnAllFunctions(void 0); }).toThrowError(/spyOnAllFunctions could not find an object to spy upon/); }); - it("overrides all writable and configurable functions of the object and its parents", function() { - var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: function() { - return 'I am a spy'; - }}); - var createNoop = function() { return function() { /**/}; }; + it('overrides all writable and configurable functions of the object and its parents', function() { + var spyRegistry = new jasmineUnderTest.SpyRegistry({ + createSpy: function() { + return 'I am a spy'; + } + }); + var createNoop = function() { + return function() { + /**/ + }; + }; var noop1 = createNoop(); var noop2 = createNoop(); var noop3 = createNoop(); @@ -270,7 +314,7 @@ describe("SpyRegistry", function() { var _spied3 = noop3; Object.defineProperty(subject, 'spied3', { configurable: true, - set: function (val) { + set: function(val) { _spied3 = val; }, get: function() { @@ -293,7 +337,9 @@ describe("SpyRegistry", function() { }); Object.defineProperty(subject, 'notSpied4', { configurable: false, - set: function(val) { /**/ }, + set: function(val) { + /**/ + }, get: function() { return noop4; }, @@ -322,13 +368,15 @@ describe("SpyRegistry", function() { expect(spiedObject).toBe(subject); }); - it("overrides prototype methods on the object", function() { - var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: function() { - return 'I am a spy'; - }}); + it('overrides prototype methods on the object', function() { + var spyRegistry = new jasmineUnderTest.SpyRegistry({ + createSpy: function() { + return 'I am a spy'; + } + }); - var noop1 = function() { }; - var noop2 = function() { }; + var noop1 = function() {}; + var noop2 = function() {}; var MyClass = function() { this.spied1 = noop1; @@ -343,12 +391,14 @@ describe("SpyRegistry", function() { expect(MyClass.prototype.spied2).toBe(noop2); }); - it("does not override non-enumerable properties (like Object.prototype methods)", function() { - var spyRegistry = new jasmineUnderTest.SpyRegistry({createSpy: function() { - return 'I am a spy'; - }}); + it('does not override non-enumerable properties (like Object.prototype methods)', function() { + var spyRegistry = new jasmineUnderTest.SpyRegistry({ + createSpy: function() { + return 'I am a spy'; + } + }); var subject = { - spied1: function() { } + spied1: function() {} }; spyRegistry.spyOnAllFunctions(subject); @@ -359,11 +409,13 @@ describe("SpyRegistry", function() { }); }); - describe("#clearSpies", function() { - it("restores the original functions on the spied-upon objects", function() { + describe('#clearSpies', function() { + it('restores the original functions on the spied-upon objects', function() { var spies = [], spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() { return spies; }, + currentSpies: function() { + return spies; + }, createSpy: createSpy }), originalFunction = function() {}, @@ -375,10 +427,12 @@ describe("SpyRegistry", function() { expect(subject.spiedFunc).toBe(originalFunction); }); - it("restores the original functions, even when that spy has been replace and re-spied upon", function() { + it('restores the original functions, even when that spy has been replace and re-spied upon', function() { var spies = [], spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() { return spies; }, + currentSpies: function() { + return spies; + }, createSpy: createSpy }), originalFunction = function() {}, @@ -400,11 +454,13 @@ describe("SpyRegistry", function() { it("does not add a property that the spied-upon object didn't originally have", function() { var spies = [], spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() { return spies; }, + currentSpies: function() { + return spies; + }, createSpy: createSpy }), originalFunction = function() {}, - subjectParent = {spiedFunc: originalFunction}; + subjectParent = { spiedFunc: originalFunction }; var subject = Object.create(subjectParent); @@ -417,14 +473,16 @@ describe("SpyRegistry", function() { expect(subject.spiedFunc).toBe(originalFunction); }); - it("restores the original function when it\'s inherited and cannot be deleted", function() { + it("restores the original function when it's inherited and cannot be deleted", function() { var spies = [], spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() { return spies; }, + currentSpies: function() { + return spies; + }, createSpy: createSpy }), originalFunction = function() {}, - subjectParent = {spiedFunc: originalFunction}; + subjectParent = { spiedFunc: originalFunction }; var subject = Object.create(subjectParent); @@ -440,15 +498,16 @@ describe("SpyRegistry", function() { expect(jasmineUnderTest.isSpy(subject.spiedFunc)).toBe(false); }); - it("restores window.onerror by overwriting, not deleting", function() { - function FakeWindow() { - } + it('restores window.onerror by overwriting, not deleting', function() { + function FakeWindow() {} FakeWindow.prototype.onerror = function() {}; var spies = [], global = new FakeWindow(), spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() { return spies; }, + currentSpies: function() { + return spies; + }, createSpy: createSpy, global: global }); @@ -460,50 +519,58 @@ describe("SpyRegistry", function() { }); }); - describe('spying on properties', function() { - it("restores the original properties on the spied-upon objects", function() { - var spies = [], - spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() { return spies; }, - createSpy: createSpy - }), - originalReturn = 1, - subject = {}; + describe('spying on properties', function() { + it('restores the original properties on the spied-upon objects', function() { + var spies = [], + spyRegistry = new jasmineUnderTest.SpyRegistry({ + currentSpies: function() { + return spies; + }, + createSpy: createSpy + }), + originalReturn = 1, + subject = {}; - Object.defineProperty(subject, 'spiedProp', { - get: function() { return originalReturn; }, - configurable: true - }); - - spyRegistry.spyOnProperty(subject, 'spiedProp'); - spyRegistry.clearSpies(); - - expect(subject.spiedProp).toBe(originalReturn); + Object.defineProperty(subject, 'spiedProp', { + get: function() { + return originalReturn; + }, + configurable: true }); - it("does not add a property that the spied-upon object didn't originally have", function() { - var spies = [], - spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() { return spies; }, - createSpy: createSpy - }), - originalReturn = 1, - subjectParent = {}; + spyRegistry.spyOnProperty(subject, 'spiedProp'); + spyRegistry.clearSpies(); - Object.defineProperty(subjectParent, 'spiedProp', { - get: function() { return originalReturn; }, - configurable: true - }); - - var subject = Object.create(subjectParent); - - expect(subject.hasOwnProperty('spiedProp')).toBe(false); - - spyRegistry.spyOnProperty(subject, 'spiedProp'); - spyRegistry.clearSpies(); - - expect(subject.hasOwnProperty('spiedProp')).toBe(false); - expect(subject.spiedProp).toBe(originalReturn); - }); + expect(subject.spiedProp).toBe(originalReturn); }); + + it("does not add a property that the spied-upon object didn't originally have", function() { + var spies = [], + spyRegistry = new jasmineUnderTest.SpyRegistry({ + currentSpies: function() { + return spies; + }, + createSpy: createSpy + }), + originalReturn = 1, + subjectParent = {}; + + Object.defineProperty(subjectParent, 'spiedProp', { + get: function() { + return originalReturn; + }, + configurable: true + }); + + var subject = Object.create(subjectParent); + + expect(subject.hasOwnProperty('spiedProp')).toBe(false); + + spyRegistry.spyOnProperty(subject, 'spiedProp'); + spyRegistry.clearSpies(); + + expect(subject.hasOwnProperty('spiedProp')).toBe(false); + expect(subject.spiedProp).toBe(originalReturn); + }); + }); }); diff --git a/spec/core/SpySpec.js b/spec/core/SpySpec.js index 04734e2f..fd7dc4e6 100644 --- a/spec/core/SpySpec.js +++ b/spec/core/SpySpec.js @@ -1,64 +1,78 @@ -describe('Spies', function () { +describe('Spies', function() { var env; beforeEach(function() { env = new jasmineUnderTest.Env(); }); - describe("createSpy", function() { + describe('createSpy', function() { var TestClass; beforeEach(function() { TestClass = function() {}; TestClass.prototype.someFunction = function() {}; - TestClass.prototype.someFunction.bob = "test"; + TestClass.prototype.someFunction.bob = 'test'; }); - it("preserves the properties of the spied function", function() { - var spy = env.createSpy(TestClass.prototype, TestClass.prototype.someFunction); + it('preserves the properties of the spied function', function() { + var spy = env.createSpy( + TestClass.prototype, + TestClass.prototype.someFunction + ); - expect(spy.bob).toEqual("test"); + expect(spy.bob).toEqual('test'); }); - it("should allow you to omit the name argument and only pass the originalFn argument", function() { + it('should allow you to omit the name argument and only pass the originalFn argument', function() { var fn = function test() {}; var spy = env.createSpy(fn); // IE doesn't do `.name` - if (fn.name === "test") { - expect(spy.and.identity).toEqual("test"); + if (fn.name === 'test') { + expect(spy.and.identity).toEqual('test'); } else { - expect(spy.and.identity).toEqual("unknown"); + expect(spy.and.identity).toEqual('unknown'); } - }) + }); - it("warns the user that we intend to overwrite an existing property", function() { - TestClass.prototype.someFunction.and = "turkey"; + it('warns the user that we intend to overwrite an existing property', function() { + TestClass.prototype.someFunction.and = 'turkey'; expect(function() { env.createSpy(TestClass.prototype, TestClass.prototype.someFunction); - }).toThrowError("Jasmine spies would overwrite the 'and' and 'calls' properties on the object being spied upon"); + }).toThrowError( + "Jasmine spies would overwrite the 'and' and 'calls' properties on the object being spied upon" + ); }); - it("adds a spyStrategy and callTracker to the spy", function() { - var spy = env.createSpy(TestClass.prototype, TestClass.prototype.someFunction); + it('adds a spyStrategy and callTracker to the spy', function() { + var spy = env.createSpy( + TestClass.prototype, + TestClass.prototype.someFunction + ); expect(spy.and).toEqual(jasmine.any(jasmineUnderTest.SpyStrategy)); expect(spy.calls).toEqual(jasmine.any(jasmineUnderTest.CallTracker)); }); - it("tracks the argument of calls", function () { - var spy = env.createSpy(TestClass.prototype, TestClass.prototype.someFunction); - var trackSpy = spyOn(spy.calls, "track"); + it('tracks the argument of calls', function() { + var spy = env.createSpy( + TestClass.prototype, + TestClass.prototype.someFunction + ); + var trackSpy = spyOn(spy.calls, 'track'); - spy("arg"); + spy('arg'); - expect(trackSpy.calls.mostRecent().args[0].args).toEqual(["arg"]); + expect(trackSpy.calls.mostRecent().args[0].args).toEqual(['arg']); }); - it("tracks the context of calls", function () { - var spy = env.createSpy(TestClass.prototype, TestClass.prototype.someFunction); - var trackSpy = spyOn(spy.calls, "track"); + it('tracks the context of calls', function() { + var spy = env.createSpy( + TestClass.prototype, + TestClass.prototype.someFunction + ); + var trackSpy = spyOn(spy.calls, 'track'); var contextObject = { spyMethod: spy }; contextObject.spyMethod(); @@ -66,39 +80,47 @@ describe('Spies', function () { expect(trackSpy.calls.mostRecent().args[0].object).toEqual(contextObject); }); - it("tracks the return value of calls", function () { - var spy = env.createSpy(TestClass.prototype, TestClass.prototype.someFunction); - var trackSpy = spyOn(spy.calls, "track"); + it('tracks the return value of calls', function() { + var spy = env.createSpy( + TestClass.prototype, + TestClass.prototype.someFunction + ); + var trackSpy = spyOn(spy.calls, 'track'); - spy.and.returnValue("return value"); + spy.and.returnValue('return value'); spy(); - expect(trackSpy.calls.mostRecent().args[0].returnValue).toEqual("return value"); + expect(trackSpy.calls.mostRecent().args[0].returnValue).toEqual( + 'return value' + ); }); - it("preserves arity of original function", function () { + it('preserves arity of original function', function() { var functions = [ - function nullary () {}, - function unary (arg) {}, - function binary (arg1, arg2) {}, - function ternary (arg1, arg2, arg3) {}, - function quaternary (arg1, arg2, arg3, arg4) {}, - function quinary (arg1, arg2, arg3, arg4, arg5) {}, - function senary (arg1, arg2, arg3, arg4, arg5, arg6) {} + function nullary() {}, + function unary(arg) {}, + function binary(arg1, arg2) {}, + function ternary(arg1, arg2, arg3) {}, + function quaternary(arg1, arg2, arg3, arg4) {}, + function quinary(arg1, arg2, arg3, arg4, arg5) {}, + function senary(arg1, arg2, arg3, arg4, arg5, arg6) {} ]; for (var arity = 0; arity < functions.length; arity++) { var someFunction = functions[arity], - spy = env.createSpy(someFunction.name, someFunction); + spy = env.createSpy(someFunction.name, someFunction); expect(spy.length).toEqual(arity); } }); }); - describe("createSpyObj", function() { - it("should create an object with spy methods and corresponding return values when you call jasmine.createSpyObj() with an object", function () { - var spyObj = env.createSpyObj('BaseName', {'method1': 42, 'method2': 'special sauce' }); + describe('createSpyObj', function() { + it('should create an object with spy methods and corresponding return values when you call jasmine.createSpyObj() with an object', function() { + var spyObj = env.createSpyObj('BaseName', { + method1: 42, + method2: 'special sauce' + }); expect(spyObj.method1()).toEqual(42); expect(spyObj.method1.and.identity).toEqual('BaseName.method1'); @@ -107,43 +129,54 @@ describe('Spies', function () { expect(spyObj.method2.and.identity).toEqual('BaseName.method2'); }); - - it("should create an object with a bunch of spy methods when you call jasmine.createSpyObj()", function() { + it('should create an object with a bunch of spy methods when you call jasmine.createSpyObj()', function() { var spyObj = env.createSpyObj('BaseName', ['method1', 'method2']); - expect(spyObj).toEqual({ method1: jasmine.any(Function), method2: jasmine.any(Function)}); + expect(spyObj).toEqual({ + method1: jasmine.any(Function), + method2: jasmine.any(Function) + }); expect(spyObj.method1.and.identity).toEqual('BaseName.method1'); expect(spyObj.method2.and.identity).toEqual('BaseName.method2'); }); - it("should allow you to omit the baseName", function() { + it('should allow you to omit the baseName', function() { var spyObj = env.createSpyObj(['method1', 'method2']); - expect(spyObj).toEqual({ method1: jasmine.any(Function), method2: jasmine.any(Function)}); + expect(spyObj).toEqual({ + method1: jasmine.any(Function), + method2: jasmine.any(Function) + }); expect(spyObj.method1.and.identity).toEqual('unknown.method1'); expect(spyObj.method2.and.identity).toEqual('unknown.method2'); }); - it("should throw if you do not pass an array or object argument", function() { + it('should throw if you do not pass an array or object argument', function() { expect(function() { env.createSpyObj('BaseName'); - }).toThrow("createSpyObj requires a non-empty array or object of method names to create spies for"); + }).toThrow( + 'createSpyObj requires a non-empty array or object of method names to create spies for' + ); }); - it("should throw if you pass an empty array argument", function() { + it('should throw if you pass an empty array argument', function() { expect(function() { env.createSpyObj('BaseName', []); - }).toThrow("createSpyObj requires a non-empty array or object of method names to create spies for"); + }).toThrow( + 'createSpyObj requires a non-empty array or object of method names to create spies for' + ); }); - it("should throw if you pass an empty object argument", function() { + it('should throw if you pass an empty object argument', function() { expect(function() { env.createSpyObj('BaseName', {}); - }).toThrow("createSpyObj requires a non-empty array or object of method names to create spies for"); + }).toThrow( + 'createSpyObj requires a non-empty array or object of method names to create spies for' + ); }); }); - it("can use different strategies for different arguments", function() { + it('can use different strategies for different arguments', function() { var spy = env.createSpy('foo'); spy.and.returnValue(42); spy.withArgs('baz', 'grault').and.returnValue(-1); @@ -155,7 +188,7 @@ describe('Spies', function () { expect(spy('baz', 'grault', 'waldo')).toEqual(42); }); - it("uses custom equality testers when selecting a strategy", function() { + it('uses custom equality testers when selecting a strategy', function() { var spy = env.createSpy('foo'); spy.and.returnValue(42); spy.withArgs(jasmineUnderTest.any(String)).and.returnValue(-1); @@ -164,7 +197,7 @@ describe('Spies', function () { expect(spy({})).toEqual(42); }); - it("can reconfigure an argument-specific strategy", function() { + it('can reconfigure an argument-specific strategy', function() { var spy = env.createSpy('foo'); spy.withArgs('foo').and.returnValue(42); spy.withArgs('foo').and.returnValue(17); @@ -176,14 +209,19 @@ describe('Spies', function () { jasmine.getEnv().requirePromises(); var spy = env.createSpy('foo').and.resolveWith(42); - spy().then(function(result) { - expect(result).toEqual(42); - done(); - }).catch(done.fail); + spy() + .then(function(result) { + expect(result).toEqual(42); + done(); + }) + .catch(done.fail); }); it('works with a custom Promise library', function() { - var customPromise = { resolve: jasmine.createSpy(), reject: jasmine.createSpy() }; + var customPromise = { + resolve: jasmine.createSpy(), + reject: jasmine.createSpy() + }; customPromise.resolve.and.returnValue('resolved'); env.configure({ Promise: customPromise }); @@ -193,8 +231,8 @@ describe('Spies', function () { }); }); - describe("when withArgs is used without a base strategy", function() { - it("uses the matching strategy", function() { + describe('when withArgs is used without a base strategy', function() { + it('uses the matching strategy', function() { var spy = env.createSpy('foo'); spy.withArgs('baz').and.returnValue(-1); @@ -205,7 +243,11 @@ describe('Spies', function () { var spy = env.createSpy('foo'); spy.withArgs('bar').and.returnValue(-1); - expect(function() { spy('baz', {qux: 42}); }).toThrowError('Spy \'foo\' received a call with arguments [ \'baz\', Object({ qux: 42 }) ] but all configured strategies specify other arguments.'); + expect(function() { + spy('baz', { qux: 42 }); + }).toThrowError( + "Spy 'foo' received a call with arguments [ 'baz', Object({ qux: 42 }) ] but all configured strategies specify other arguments." + ); }); }); }); diff --git a/spec/core/SpyStrategySpec.js b/spec/core/SpyStrategySpec.js index 709c268b..ae2679ac 100644 --- a/spec/core/SpyStrategySpec.js +++ b/spec/core/SpyStrategySpec.js @@ -1,20 +1,19 @@ -describe("SpyStrategy", function() { - - it("defaults its name to unknown", function() { +describe('SpyStrategy', function() { + it('defaults its name to unknown', function() { var spyStrategy = new jasmineUnderTest.SpyStrategy(); - expect(spyStrategy.identity).toEqual("unknown"); + expect(spyStrategy.identity).toEqual('unknown'); }); - it("takes a name", function() { - var spyStrategy = new jasmineUnderTest.SpyStrategy({name: "foo"}); + it('takes a name', function() { + var spyStrategy = new jasmineUnderTest.SpyStrategy({ name: 'foo' }); - expect(spyStrategy.identity).toEqual("foo"); + expect(spyStrategy.identity).toEqual('foo'); }); - it("stubs an original function, if provided", function() { - var originalFn = jasmine.createSpy("original"), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); + it('stubs an original function, if provided', function() { + var originalFn = jasmine.createSpy('original'), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }); spyStrategy.exec(); @@ -22,22 +21,22 @@ describe("SpyStrategy", function() { }); it("allows an original function to be called, passed through the params and returns it's value", function() { - var originalFn = jasmine.createSpy("original").and.returnValue(42), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}), - returnValue; + var originalFn = jasmine.createSpy('original').and.returnValue(42), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }), + returnValue; spyStrategy.callThrough(); - returnValue = spyStrategy.exec(null, ["foo"]); + returnValue = spyStrategy.exec(null, ['foo']); expect(originalFn).toHaveBeenCalled(); - expect(originalFn.calls.mostRecent().args).toEqual(["foo"]); + expect(originalFn.calls.mostRecent().args).toEqual(['foo']); expect(returnValue).toEqual(42); }); - it("can return a specified value when executed", function() { - var originalFn = jasmine.createSpy("original"), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}), - returnValue; + it('can return a specified value when executed', function() { + var originalFn = jasmine.createSpy('original'), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }), + returnValue; spyStrategy.returnValue(17); returnValue = spyStrategy.exec(); @@ -46,9 +45,9 @@ describe("SpyStrategy", function() { expect(returnValue).toEqual(17); }); - it("can return specified values in order specified when executed", function() { - var originalFn = jasmine.createSpy("original"), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); + it('can return specified values in order specified when executed', function() { + var originalFn = jasmine.createSpy('original'), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }); spyStrategy.returnValues('value1', 'value2', 'value3'); @@ -59,31 +58,35 @@ describe("SpyStrategy", function() { expect(originalFn).not.toHaveBeenCalled(); }); - it("allows an exception to be thrown when executed", function() { - var originalFn = jasmine.createSpy("original"), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); + it('allows an exception to be thrown when executed', function() { + var originalFn = jasmine.createSpy('original'), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }); - spyStrategy.throwError(new TypeError("bar")); + spyStrategy.throwError(new TypeError('bar')); - expect(function() { spyStrategy.exec(); }).toThrowError(TypeError, "bar"); + expect(function() { + spyStrategy.exec(); + }).toThrowError(TypeError, 'bar'); expect(originalFn).not.toHaveBeenCalled(); }); - it("allows a non-Error to be thrown, wrapping it into an exception when executed", function() { - var originalFn = jasmine.createSpy("original"), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); + it('allows a non-Error to be thrown, wrapping it into an exception when executed', function() { + var originalFn = jasmine.createSpy('original'), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }); - spyStrategy.throwError("bar"); + spyStrategy.throwError('bar'); - expect(function() { spyStrategy.exec(); }).toThrowError(Error, "bar"); + expect(function() { + spyStrategy.exec(); + }).toThrowError(Error, 'bar'); expect(originalFn).not.toHaveBeenCalled(); }); - it("allows a fake function to be called instead", function() { - var originalFn = jasmine.createSpy("original"), - fakeFn = jasmine.createSpy("fake").and.returnValue(67), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}), - returnValue; + it('allows a fake function to be called instead', function() { + var originalFn = jasmine.createSpy('original'), + fakeFn = jasmine.createSpy('fake').and.returnValue(67), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }), + returnValue; spyStrategy.callFake(fakeFn); returnValue = spyStrategy.exec(); @@ -92,92 +95,128 @@ describe("SpyStrategy", function() { expect(returnValue).toEqual(67); }); - it("allows a fake async function to be called instead", function(done) { + it('allows a fake async function to be called instead', function(done) { jasmine.getEnv().requireAsyncAwait(); - var originalFn = jasmine.createSpy("original"), - fakeFn = jasmine.createSpy("fake").and.callFake(eval("async () => { return 67; }")), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}), - returnValue; + var originalFn = jasmine.createSpy('original'), + fakeFn = jasmine + .createSpy('fake') + .and.callFake(eval('async () => { return 67; }')), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }); spyStrategy.callFake(fakeFn); - spyStrategy.exec().then(function (returnValue) { - expect(originalFn).not.toHaveBeenCalled(); - expect(fakeFn).toHaveBeenCalled(); - expect(returnValue).toEqual(67); - done(); - }).catch(function (err) { - done.fail(err); - }) + spyStrategy + .exec() + .then(function(returnValue) { + expect(originalFn).not.toHaveBeenCalled(); + expect(fakeFn).toHaveBeenCalled(); + expect(returnValue).toEqual(67); + done(); + }) + .catch(function(err) { + done.fail(err); + }); }); - describe("#resolveWith", function() { - it("allows a resolved promise to be returned", function(done) { + describe('#resolveWith', function() { + it('allows a resolved promise to be returned', function(done) { jasmine.getEnv().requirePromises(); - var originalFn = jasmine.createSpy("original"), - getPromise = function() { return Promise; }, - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn, getPromise: getPromise}); + var originalFn = jasmine.createSpy('original'), + getPromise = function() { + return Promise; + }, + spyStrategy = new jasmineUnderTest.SpyStrategy({ + fn: originalFn, + getPromise: getPromise + }); spyStrategy.resolveWith(37); - spyStrategy.exec().then(function (returnValue) { - expect(returnValue).toEqual(37); - done(); - }).catch(done.fail); + spyStrategy + .exec() + .then(function(returnValue) { + expect(returnValue).toEqual(37); + done(); + }) + .catch(done.fail); }); - it("fails if promises are not available", function() { - var originalFn = jasmine.createSpy("original"), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); + it('fails if promises are not available', function() { + var originalFn = jasmine.createSpy('original'), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }); expect(function() { spyStrategy.resolveWith(37); - }).toThrowError('resolveWith requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`'); + }).toThrowError( + 'resolveWith requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`' + ); }); }); - describe("#rejectWith", function() { - it("allows a rejected promise to be returned", function(done) { + describe('#rejectWith', function() { + it('allows a rejected promise to be returned', function(done) { jasmine.getEnv().requirePromises(); - var originalFn = jasmine.createSpy("original"), - getPromise = function() { return Promise; }, - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn, getPromise: getPromise}); + var originalFn = jasmine.createSpy('original'), + getPromise = function() { + return Promise; + }, + spyStrategy = new jasmineUnderTest.SpyStrategy({ + fn: originalFn, + getPromise: getPromise + }); spyStrategy.rejectWith(new Error('oops')); - spyStrategy.exec().then(done.fail).catch(function (error) { - expect(error).toEqual(new Error('oops')); - done(); - }).catch(done.fail); + spyStrategy + .exec() + .then(done.fail) + .catch(function(error) { + expect(error).toEqual(new Error('oops')); + done(); + }) + .catch(done.fail); }); - it("allows a non-Error to be rejected, wrapping it in an exception when executed", function(done) { + it('allows a non-Error to be rejected, wrapping it in an exception when executed', function(done) { jasmine.getEnv().requirePromises(); - var originalFn = jasmine.createSpy("original"), - getPromise = function() { return Promise; }, - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn, getPromise: getPromise}); + var originalFn = jasmine.createSpy('original'), + getPromise = function() { + return Promise; + }, + spyStrategy = new jasmineUnderTest.SpyStrategy({ + fn: originalFn, + getPromise: getPromise + }); spyStrategy.rejectWith('oops'); - spyStrategy.exec().then(done.fail).catch(function (error) { - expect(error).toEqual(new Error('oops')); - done(); - }).catch(done.fail); + spyStrategy + .exec() + .then(done.fail) + .catch(function(error) { + expect(error).toEqual(new Error('oops')); + done(); + }) + .catch(done.fail); }); - it("fails if promises are not available", function() { - var originalFn = jasmine.createSpy("original"), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}); + it('fails if promises are not available', function() { + var originalFn = jasmine.createSpy('original'), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }); expect(function() { spyStrategy.rejectWith(new Error('oops')); - }).toThrowError('rejectWith requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`'); + }).toThrowError( + 'rejectWith requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`' + ); }); }); - it("allows a custom strategy to be used", function() { - var plan = jasmine.createSpy('custom strategy') + it('allows a custom strategy to be used', function() { + var plan = jasmine + .createSpy('custom strategy') .and.returnValue('custom strategy result'), - customStrategy = jasmine.createSpy('custom strategy') + customStrategy = jasmine + .createSpy('custom strategy') .and.returnValue(plan), originalFn = jasmine.createSpy('original'), spyStrategy = new jasmineUnderTest.SpyStrategy({ @@ -189,8 +228,9 @@ describe("SpyStrategy", function() { spyStrategy.doSomething(1, 2, 3); expect(customStrategy).toHaveBeenCalledWith(1, 2, 3); - expect(spyStrategy.exec(null, ['some', 'args'])) - .toEqual('custom strategy result'); + expect(spyStrategy.exec(null, ['some', 'args'])).toEqual( + 'custom strategy result' + ); expect(plan).toHaveBeenCalledWith('some', 'args'); }); @@ -199,46 +239,49 @@ describe("SpyStrategy", function() { spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn, customStrategies: { - doSomething: function() { return 'not a function' } + doSomething: function() { + return 'not a function'; + } } }); - expect(function() { spyStrategy.doSomething(1, 2, 3) }).toThrowError('Spy strategy must return a function'); + expect(function() { + spyStrategy.doSomething(1, 2, 3); + }).toThrowError('Spy strategy must return a function'); }); - it("does not allow custom strategies to overwrite existing methods", function() { + it('does not allow custom strategies to overwrite existing methods', function() { var spyStrategy = new jasmineUnderTest.SpyStrategy({ - fn: function() {}, - customStrategies: { - exec: function() {} - } - }); + fn: function() {}, + customStrategies: { + exec: function() {} + } + }); expect(spyStrategy.exec).toBe(jasmineUnderTest.SpyStrategy.prototype.exec); }); it('throws an error when a non-function is passed to callFake strategy', function() { var originalFn = jasmine.createSpy('original'), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}), - invalidFakes = [5, 'foo', {}, true, false, null, void 0, new Date(), /.*/]; + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }); spyOn(jasmineUnderTest, 'isFunction_').and.returnValue(false); spyOn(jasmineUnderTest, 'isAsyncFunction_').and.returnValue(false); - expect(function () { + expect(function() { spyStrategy.callFake(function() {}); }).toThrowError(/^Argument passed to callFake should be a function, got/); - expect(function () { + expect(function() { spyStrategy.callFake(function() {}); }).toThrowError(/^Argument passed to callFake should be a function, got/); }); - it("allows a return to plan stubbing after another strategy", function() { - var originalFn = jasmine.createSpy("original"), - fakeFn = jasmine.createSpy("fake").and.returnValue(67), - spyStrategy = new jasmineUnderTest.SpyStrategy({fn: originalFn}), - returnValue; + it('allows a return to plan stubbing after another strategy', function() { + var originalFn = jasmine.createSpy('original'), + fakeFn = jasmine.createSpy('fake').and.returnValue(67), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }), + returnValue; spyStrategy.callFake(fakeFn); returnValue = spyStrategy.exec(); @@ -252,10 +295,10 @@ describe("SpyStrategy", function() { expect(returnValue).toEqual(void 0); }); - it("returns the spy after changing the strategy", function(){ + it('returns the spy after changing the strategy', function() { var spy = {}, - spyFn = jasmine.createSpy('spyFn').and.returnValue(spy), - spyStrategy = new jasmineUnderTest.SpyStrategy({getSpy: spyFn}); + spyFn = jasmine.createSpy('spyFn').and.returnValue(spy), + spyStrategy = new jasmineUnderTest.SpyStrategy({ getSpy: spyFn }); expect(spyStrategy.callThrough()).toBe(spy); expect(spyStrategy.returnValue()).toBe(spy); diff --git a/spec/core/StackTraceSpec.js b/spec/core/StackTraceSpec.js index dd8023f4..9cbffe33 100644 --- a/spec/core/StackTraceSpec.js +++ b/spec/core/StackTraceSpec.js @@ -1,5 +1,5 @@ -describe("StackTrace", function() { - it("understands Chrome/IE/Edge style traces", function() { +describe('StackTrace', function() { + it('understands Chrome/IE/Edge style traces', function() { var error = { message: 'nope', stack: @@ -14,13 +14,15 @@ describe("StackTrace", function() { expect(result.style).toEqual('v8'); expect(result.frames).toEqual([ { - raw: ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)', + raw: + ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)', func: 'UserContext.', file: 'http://localhost:8888/__spec__/core/UtilSpec.js', line: 115 }, { - raw: ' at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)', + raw: + ' at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)', func: 'QueueRunner.run', file: 'http://localhost:8888/__jasmine__/jasmine.js', line: 4320 @@ -28,7 +30,7 @@ describe("StackTrace", function() { ]); }); - it("understands Chrome/IE/Edge style traces with multiline messages", function() { + it('understands Chrome/IE/Edge style traces with multiline messages', function() { var error = { message: 'line 1\nline 2', stack: @@ -40,14 +42,16 @@ describe("StackTrace", function() { var result = new jasmineUnderTest.StackTrace(error); expect(result.message).toEqual('Error: line 1\nline 2'); - var rawFrames = result.frames.map(function(f) { return f.raw; }); + var rawFrames = result.frames.map(function(f) { + return f.raw; + }); expect(rawFrames).toEqual([ ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)', - ' at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)', + ' at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)' ]); }); - it("understands Node style traces", function() { + it('understands Node style traces', function() { var error = { message: 'nope', stack: @@ -69,13 +73,15 @@ describe("StackTrace", function() { line: 4255 }, { - raw: ' at QueueRunner.complete [as onComplete] (/somewhere/jasmine/lib/jasmine-core/jasmine.js:579:9)', + raw: + ' at QueueRunner.complete [as onComplete] (/somewhere/jasmine/lib/jasmine-core/jasmine.js:579:9)', func: 'QueueRunner.complete [as onComplete]', file: '/somewhere/jasmine/lib/jasmine-core/jasmine.js', line: 579 }, { - raw: ' at Immediate. (/somewhere/jasmine/lib/jasmine-core/jasmine.js:4314:12)', + raw: + ' at Immediate. (/somewhere/jasmine/lib/jasmine-core/jasmine.js:4314:12)', func: 'Immediate.', file: '/somewhere/jasmine/lib/jasmine-core/jasmine.js', line: 4314 @@ -89,7 +95,7 @@ describe("StackTrace", function() { ]); }); - it("understands Safari/Firefox/Phantom-OS X style traces", function() { + it('understands Safari/Firefox/Phantom-OS X style traces', function() { var error = { message: 'nope', stack: @@ -116,22 +122,20 @@ describe("StackTrace", function() { ]); }); - it("does not mistake gibberish for Safari/Firefox/Phantom-OS X style traces", function() { + it('does not mistake gibberish for Safari/Firefox/Phantom-OS X style traces', function() { var error = { message: 'nope', stack: 'randomcharsnotincludingwhitespace' }; var result = new jasmineUnderTest.StackTrace(error); expect(result.style).toBeNull(); - expect(result.frames).toEqual([ - { raw: error.stack } - ]); + expect(result.frames).toEqual([{ raw: error.stack }]); }); - it("understands Phantom-Linux style traces", function() { + it('understands Phantom-Linux style traces', function() { var error = { message: 'nope', - stack: + stack: ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)\n' + ' at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)' }; @@ -142,13 +146,15 @@ describe("StackTrace", function() { expect(result.style).toEqual('v8'); expect(result.frames).toEqual([ { - raw: ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)', + raw: + ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)', func: 'UserContext.', file: 'http://localhost:8888/__spec__/core/UtilSpec.js', line: 115 }, { - raw: ' at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)', + raw: + ' at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)', func: 'QueueRunner.run', file: 'http://localhost:8888/__jasmine__/jasmine.js', line: 4320 @@ -156,7 +162,7 @@ describe("StackTrace", function() { ]); }); - it("ignores blank lines", function() { + it('ignores blank lines', function() { var error = { message: 'nope', stack: @@ -167,7 +173,8 @@ describe("StackTrace", function() { expect(result.frames).toEqual([ { - raw: ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)', + raw: + ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)', func: 'UserContext.', file: 'http://localhost:8888/__spec__/core/UtilSpec.js', line: 115 @@ -188,7 +195,8 @@ describe("StackTrace", function() { expect(result.style).toEqual('v8'); expect(result.frames).toEqual([ { - raw: ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)', + raw: + ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)', func: 'UserContext.', file: 'http://localhost:8888/__spec__/core/UtilSpec.js', line: 115 @@ -197,7 +205,8 @@ describe("StackTrace", function() { raw: ' but this is quite unexpected' }, { - raw: ' at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)', + raw: + ' at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)', func: 'QueueRunner.run', file: 'http://localhost:8888/__jasmine__/jasmine.js', line: 4320 diff --git a/spec/core/SuiteSpec.js b/spec/core/SuiteSpec.js index 1739259e..8470bad7 100644 --- a/spec/core/SuiteSpec.js +++ b/spec/core/SuiteSpec.js @@ -1,47 +1,46 @@ -describe("Suite", function() { - - it("keeps its id", function() { +describe('Suite', function() { + it('keeps its id', function() { var env = new jasmineUnderTest.Env(), suite = new jasmineUnderTest.Suite({ env: env, id: 456, - description: "I am a suite" + description: 'I am a suite' }); expect(suite.id).toEqual(456); }); - it("returns blank full name for top level suite", function() { + it('returns blank full name for top level suite', function() { var env = new jasmineUnderTest.Env(), suite = new jasmineUnderTest.Suite({ env: env, - description: "I am a suite" + description: 'I am a suite' }); - expect(suite.getFullName()).toEqual(""); + expect(suite.getFullName()).toEqual(''); }); - it("returns its full name when it has parent suites", function() { + it('returns its full name when it has parent suites', function() { var env = new jasmineUnderTest.Env(), parentSuite = new jasmineUnderTest.Suite({ env: env, - description: "I am a parent suite", + description: 'I am a parent suite', parentSuite: jasmine.createSpy('pretend top level suite') }), suite = new jasmineUnderTest.Suite({ env: env, - description: "I am a suite", + description: 'I am a suite', parentSuite: parentSuite }); - expect(suite.getFullName()).toEqual("I am a parent suite I am a suite"); + expect(suite.getFullName()).toEqual('I am a parent suite I am a suite'); }); - it("adds before functions in order of needed execution", function() { + it('adds before functions in order of needed execution', function() { var env = new jasmineUnderTest.Env(), suite = new jasmineUnderTest.Suite({ env: env, - description: "I am a suite" + description: 'I am a suite' }), outerBefore = jasmine.createSpy('outerBeforeEach'), innerBefore = jasmine.createSpy('insideBeforeEach'); @@ -52,11 +51,11 @@ describe("Suite", function() { expect(suite.beforeFns).toEqual([innerBefore, outerBefore]); }); - it("adds after functions in order of needed execution", function() { + it('adds after functions in order of needed execution', function() { var env = new jasmineUnderTest.Env(), suite = new jasmineUnderTest.Suite({ env: env, - description: "I am a suite" + description: 'I am a suite' }), outerAfter = jasmine.createSpy('outerAfterEach'), innerAfter = jasmine.createSpy('insideAfterEach'); @@ -69,29 +68,33 @@ describe("Suite", function() { it('has a status of failed if any expectations have failed', function() { var suite = new jasmineUnderTest.Suite({ - expectationResultFactory: function() { return 'hi'; } + expectationResultFactory: function() { + return 'hi'; + } }); suite.addExpectationResult(false); expect(suite.status()).toBe('failed'); }); - it("retrieves a result with updated status", function() { + it('retrieves a result with updated status', function() { var suite = new jasmineUnderTest.Suite({}); expect(suite.getResult().status).toBe('passed'); }); - it("retrieves a result with pending status", function() { + it('retrieves a result with pending status', function() { var suite = new jasmineUnderTest.Suite({}); suite.pend(); expect(suite.getResult().status).toBe('pending'); }); - it("throws an ExpectationFailed when receiving a failed expectation when throwOnExpectationFailure is set", function() { + it('throws an ExpectationFailed when receiving a failed expectation when throwOnExpectationFailure is set', function() { var suite = new jasmineUnderTest.Suite({ - expectationResultFactory: function(data) { return data; }, + expectationResultFactory: function(data) { + return data; + }, throwOnExpectationFailure: true }); @@ -103,7 +106,7 @@ describe("Suite", function() { expect(suite.result.failedExpectations).toEqual(['failed']); }); - it("does not add an additional failure when an expectation fails", function(){ + it('does not add an additional failure when an expectation fails', function() { var suite = new jasmineUnderTest.Suite({}); suite.onException(new jasmineUnderTest.errors.ExpectationFailed()); @@ -111,17 +114,17 @@ describe("Suite", function() { expect(suite.getResult().failedExpectations).toEqual([]); }); - it("calls timer to compute duration", function(){ - var env = new jasmineUnderTest.Env(), + it('calls timer to compute duration', function() { + var env = new jasmineUnderTest.Env(), suite = new jasmineUnderTest.Suite({ env: env, id: 456, - description: "I am a suite", - timer: jasmine.createSpyObj('timer', {'start': null, elapsed: 77000}), + description: 'I am a suite', + timer: jasmine.createSpyObj('timer', { start: null, elapsed: 77000 }) }); - suite.startTimer(); - suite.endTimer(); - expect(suite.getResult().duration).toEqual(77000); + suite.startTimer(); + suite.endTimer(); + expect(suite.getResult().duration).toEqual(77000); }); describe('#sharedUserContext', function() { @@ -130,7 +133,9 @@ describe("Suite", function() { }); it('returns a UserContext', function() { - expect(this.suite.sharedUserContext().constructor).toBe(jasmineUnderTest.UserContext); + expect(this.suite.sharedUserContext().constructor).toBe( + jasmineUnderTest.UserContext + ); }); }); }); diff --git a/spec/core/TimerSpec.js b/spec/core/TimerSpec.js index 96d8352a..f733f0d9 100644 --- a/spec/core/TimerSpec.js +++ b/spec/core/TimerSpec.js @@ -1,7 +1,7 @@ -describe("Timer", function() { - it("reports the time elapsed", function() { +describe('Timer', function() { + it('reports the time elapsed', function() { var fakeNow = jasmine.createSpy('fake Date.now'), - timer = new jasmineUnderTest.Timer({now: fakeNow}); + timer = new jasmineUnderTest.Timer({ now: fakeNow }); fakeNow.and.returnValue(100); timer.start(); @@ -11,7 +11,7 @@ describe("Timer", function() { expect(timer.elapsed()).toEqual(100); }); - describe("when date is stubbed, perhaps by other testing helpers", function() { + describe('when date is stubbed, perhaps by other testing helpers', function() { var origDate = Date; beforeEach(function() { Date = jasmine.createSpy('date spy'); @@ -21,7 +21,7 @@ describe("Timer", function() { Date = origDate; }); - it("does not throw even though Date was taken away", function() { + it('does not throw even though Date was taken away', function() { var timer = new jasmineUnderTest.Timer(); expect(timer.start).not.toThrow(); diff --git a/spec/core/TreeProcessorSpec.js b/spec/core/TreeProcessorSpec.js index 2e8a9ca8..18f4267f 100644 --- a/spec/core/TreeProcessorSpec.js +++ b/spec/core/TreeProcessorSpec.js @@ -1,5 +1,6 @@ -describe("TreeProcessor", function() { - var nodeNumber = 0, leafNumber = 0; +describe('TreeProcessor', function() { + var nodeNumber = 0, + leafNumber = 0; function Node(attrs) { attrs = attrs || {}; @@ -15,7 +16,7 @@ describe("TreeProcessor", function() { this.getResult = jasmine.createSpy(this.id + '#execute'); this.beforeAllFns = attrs.beforeAllFns || []; this.afterAllFns = attrs.afterAllFns || []; - this.cleanupBeforeAfter = function() { }; + this.cleanupBeforeAfter = function() {}; } function Leaf(attrs) { @@ -25,10 +26,13 @@ describe("TreeProcessor", function() { this.execute = jasmine.createSpy(this.id + '#execute'); } - it("processes a single leaf", function() { + it('processes a single leaf', function() { var leaf = new Leaf(), - processor = new jasmineUnderTest.TreeProcessor({ tree: leaf, runnableIds: [leaf.id] }), - result = processor.processTree(); + processor = new jasmineUnderTest.TreeProcessor({ + tree: leaf, + runnableIds: [leaf.id] + }), + result = processor.processTree(); expect(result.valid).toBe(true); @@ -39,10 +43,13 @@ describe("TreeProcessor", function() { }); }); - it("processes a single pending leaf", function() { + it('processes a single pending leaf', function() { var leaf = new Leaf({ markedPending: true }), - processor = new jasmineUnderTest.TreeProcessor({ tree: leaf, runnableIds: [leaf.id] }), - result = processor.processTree(); + processor = new jasmineUnderTest.TreeProcessor({ + tree: leaf, + runnableIds: [leaf.id] + }), + result = processor.processTree(); expect(result.valid).toBe(true); @@ -53,10 +60,13 @@ describe("TreeProcessor", function() { }); }); - it("processes a single non-specified leaf", function() { + it('processes a single non-specified leaf', function() { var leaf = new Leaf(), - processor = new jasmineUnderTest.TreeProcessor({ tree: leaf, runnableIds: [] }), - result = processor.processTree(); + processor = new jasmineUnderTest.TreeProcessor({ + tree: leaf, + runnableIds: [] + }), + result = processor.processTree(); expect(result.valid).toBe(true); @@ -67,14 +77,16 @@ describe("TreeProcessor", function() { }); }); - it("processes a single excluded leaf", function() { + it('processes a single excluded leaf', function() { var leaf = new Leaf(), - processor = new jasmineUnderTest.TreeProcessor({ - tree: leaf, - runnableIds: [leaf.id], - excludeNode: function(node) { return true; } - }), - result = processor.processTree(); + processor = new jasmineUnderTest.TreeProcessor({ + tree: leaf, + runnableIds: [leaf.id], + excludeNode: function(node) { + return true; + } + }), + result = processor.processTree(); expect(result.valid).toBe(true); @@ -85,11 +97,14 @@ describe("TreeProcessor", function() { }); }); - it("processes a tree with a single leaf with the root specified", function() { + it('processes a tree with a single leaf with the root specified', function() { var leaf = new Leaf(), - parent = new Node({ children: [leaf] }), - processor = new jasmineUnderTest.TreeProcessor({ tree: parent, runnableIds: [parent.id] }), - result = processor.processTree(); + parent = new Node({ children: [leaf] }), + processor = new jasmineUnderTest.TreeProcessor({ + tree: parent, + runnableIds: [parent.id] + }), + result = processor.processTree(); expect(result.valid).toBe(true); @@ -106,11 +121,14 @@ describe("TreeProcessor", function() { }); }); - it("processes a tree with a single pending leaf, with the root specified", function() { + it('processes a tree with a single pending leaf, with the root specified', function() { var leaf = new Leaf({ markedPending: true }), - parent = new Node({ children: [leaf] }), - processor = new jasmineUnderTest.TreeProcessor({ tree: parent, runnableIds: [parent.id] }), - result = processor.processTree(); + parent = new Node({ children: [leaf] }), + processor = new jasmineUnderTest.TreeProcessor({ + tree: parent, + runnableIds: [parent.id] + }), + result = processor.processTree(); expect(result.valid).toBe(true); @@ -127,17 +145,26 @@ describe("TreeProcessor", function() { }); }); - it("processes a complicated tree with the root specified", function() { + it('processes a complicated tree with the root specified', function() { var pendingLeaf = new Leaf({ markedPending: true }), - executableLeaf = new Leaf({ markedPending: false }), - parent = new Node({ children: [pendingLeaf, executableLeaf] }), - childless = new Node(), - childOfPending = new Leaf({ markedPending: true }), - pendingNode = new Node({ markedPending: true, children: [childOfPending] }), - parentOfPendings = new Node({ markedPending: false, children: [childless, pendingNode] }), - root = new Node({ children: [parent, parentOfPendings] }), - processor = new jasmineUnderTest.TreeProcessor({ tree: root, runnableIds: [root.id] }), - result = processor.processTree(); + executableLeaf = new Leaf({ markedPending: false }), + parent = new Node({ children: [pendingLeaf, executableLeaf] }), + childless = new Node(), + childOfPending = new Leaf({ markedPending: true }), + pendingNode = new Node({ + markedPending: true, + children: [childOfPending] + }), + parentOfPendings = new Node({ + markedPending: false, + children: [childless, pendingNode] + }), + root = new Node({ children: [parent, parentOfPendings] }), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [root.id] + }), + result = processor.processTree(); expect(result.valid).toBe(true); @@ -190,58 +217,73 @@ describe("TreeProcessor", function() { }); }); - it("marks the run order invalid if it would re-enter a node that does not allow re-entry", function() { + it('marks the run order invalid if it would re-enter a node that does not allow re-entry', function() { var leaf1 = new Leaf(), - leaf2 = new Leaf(), - leaf3 = new Leaf(), - reentered = new Node({ noReenter: true, children: [leaf1, leaf2] }), - root = new Node({ children: [reentered, leaf3] }), - processor = new jasmineUnderTest.TreeProcessor({ tree: root, runnableIds: [leaf1.id, leaf3.id, leaf2.id] }), - result = processor.processTree(); + leaf2 = new Leaf(), + leaf3 = new Leaf(), + reentered = new Node({ noReenter: true, children: [leaf1, leaf2] }), + root = new Node({ children: [reentered, leaf3] }), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [leaf1.id, leaf3.id, leaf2.id] + }), + result = processor.processTree(); expect(result).toEqual({ valid: false }); }); - it("marks the run order valid if a node being re-entered allows re-entry", function() { + it('marks the run order valid if a node being re-entered allows re-entry', function() { var leaf1 = new Leaf(), - leaf2 = new Leaf(), - leaf3 = new Leaf(), - reentered = new Node({ children: [leaf1, leaf2] }), - root = new Node({ children: [reentered, leaf3] }), - processor = new jasmineUnderTest.TreeProcessor({ tree: root, runnableIds: [leaf1.id, leaf3.id, leaf2.id] }), - result = processor.processTree(); + leaf2 = new Leaf(), + leaf3 = new Leaf(), + reentered = new Node({ children: [leaf1, leaf2] }), + root = new Node({ children: [reentered, leaf3] }), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [leaf1.id, leaf3.id, leaf2.id] + }), + result = processor.processTree(); expect(result.valid).toBe(true); }); it("marks the run order valid if a node which can't be re-entered is only entered once", function() { var leaf1 = new Leaf(), - leaf2 = new Leaf(), - leaf3 = new Leaf(), - noReentry = new Node({ noReenter: true }), - root = new Node({ children: [noReentry] }), - processor = new jasmineUnderTest.TreeProcessor({ tree: root, runnableIds: [leaf2.id, leaf1.id, leaf3.id] }), - result = processor.processTree(); + leaf2 = new Leaf(), + leaf3 = new Leaf(), + noReentry = new Node({ noReenter: true }), + root = new Node({ children: [noReentry] }), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [leaf2.id, leaf1.id, leaf3.id] + }), + result = processor.processTree(); expect(result.valid).toBe(true); }); it("marks the run order valid if a node which can't be re-entered is run directly", function() { - var leaf1 = new Leaf(), - noReentry = new Node({ noReenter: true }), - root = new Node({ children: [noReentry] }), - processor = new jasmineUnderTest.TreeProcessor({ tree: root, runnableIds: [root.id] }), - result = processor.processTree(); + var noReentry = new Node({ noReenter: true }), + root = new Node({ children: [noReentry] }), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [root.id] + }), + result = processor.processTree(); expect(result.valid).toBe(true); }); - it("runs a single leaf", function() { + it('runs a single leaf', function() { var leaf = new Leaf(), - node = new Node({ children: [leaf], userContext: { root: 'context' } }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ tree: node, runnableIds: [leaf.id], queueRunnerFactory: queueRunner }), - treeComplete = jasmine.createSpy('treeComplete'); + node = new Node({ children: [leaf], userContext: { root: 'context' } }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: node, + runnableIds: [leaf.id], + queueRunnerFactory: queueRunner + }), + treeComplete = jasmine.createSpy('treeComplete'); processor.execute(treeComplete); @@ -257,21 +299,21 @@ describe("TreeProcessor", function() { expect(leaf.execute).toHaveBeenCalledWith('foo', false); }); - it("runs a node with no children", function() { + it('runs a node with no children', function() { var node = new Node({ userContext: { node: 'context' } }), - root = new Node({ children: [node], userContext: { root: 'context' } }), - nodeStart = jasmine.createSpy('nodeStart'), - nodeComplete = jasmine.createSpy('nodeComplete'), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [node.id], - nodeStart: nodeStart, - nodeComplete: nodeComplete, - queueRunnerFactory: queueRunner - }), - treeComplete = jasmine.createSpy('treeComplete'), - nodeDone = jasmine.createSpy('nodeDone'); + root = new Node({ children: [node], userContext: { root: 'context' } }), + nodeStart = jasmine.createSpy('nodeStart'), + nodeComplete = jasmine.createSpy('nodeComplete'), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [node.id], + nodeStart: nodeStart, + nodeComplete: nodeComplete, + queueRunnerFactory: queueRunner + }), + treeComplete = jasmine.createSpy('treeComplete'), + nodeDone = jasmine.createSpy('nodeDone'); processor.execute(treeComplete); @@ -297,22 +339,26 @@ describe("TreeProcessor", function() { node.getResult.and.returnValue({ my: 'result' }); queueRunner.calls.mostRecent().args[0].onComplete(); - expect(nodeComplete).toHaveBeenCalledWith(node, { my: 'result' }, jasmine.any(Function)); + expect(nodeComplete).toHaveBeenCalledWith( + node, + { my: 'result' }, + jasmine.any(Function) + ); }); - it("runs a node with children", function() { + it('runs a node with children', function() { var leaf1 = new Leaf(), - leaf2 = new Leaf(), - node = new Node({ children: [leaf1, leaf2] }), - root = new Node({ children: [node] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [node.id], - queueRunnerFactory: queueRunner - }), - treeComplete = jasmine.createSpy('treeComplete'), - nodeDone = jasmine.createSpy('nodeDone'); + leaf2 = new Leaf(), + node = new Node({ children: [leaf1, leaf2] }), + root = new Node({ children: [node] }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [node.id], + queueRunnerFactory: queueRunner + }), + treeComplete = jasmine.createSpy('treeComplete'), + nodeDone = jasmine.createSpy('nodeDone'); processor.execute(treeComplete); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -328,20 +374,20 @@ describe("TreeProcessor", function() { expect(leaf2.execute).toHaveBeenCalledWith('bar', false); }); - it("cascades errors up the tree", function() { + it('cascades errors up the tree', function() { var leaf = new Leaf(), - node = new Node({ children: [leaf] }), - root = new Node({ children: [node] }), - queueRunner = jasmine.createSpy('queueRunner'), - nodeComplete = jasmine.createSpy('nodeComplete'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [node.id], - nodeComplete: nodeComplete, - queueRunnerFactory: queueRunner - }), - treeComplete = jasmine.createSpy('treeComplete'), - nodeDone = jasmine.createSpy('nodeDone'); + node = new Node({ children: [leaf] }), + root = new Node({ children: [node] }), + queueRunner = jasmine.createSpy('queueRunner'), + nodeComplete = jasmine.createSpy('nodeComplete'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [node.id], + nodeComplete: nodeComplete, + queueRunnerFactory: queueRunner + }), + treeComplete = jasmine.createSpy('treeComplete'), + nodeDone = jasmine.createSpy('nodeDone'); processor.execute(treeComplete); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -359,22 +405,22 @@ describe("TreeProcessor", function() { expect(nodeDone).toHaveBeenCalledWith('things'); }); - it("runs an excluded node with leaf", function() { + it('runs an excluded node with leaf', function() { var leaf1 = new Leaf(), - node = new Node({ children: [leaf1] }), - root = new Node({ children: [node] }), - queueRunner = jasmine.createSpy('queueRunner'), - nodeStart = jasmine.createSpy('nodeStart'), - nodeComplete = jasmine.createSpy('nodeComplete'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [], - queueRunnerFactory: queueRunner, - nodeStart: nodeStart, - nodeComplete: nodeComplete - }), - treeComplete = jasmine.createSpy('treeComplete'), - nodeDone = jasmine.createSpy('nodeDone'); + node = new Node({ children: [leaf1] }), + root = new Node({ children: [node] }), + queueRunner = jasmine.createSpy('queueRunner'), + nodeStart = jasmine.createSpy('nodeStart'), + nodeComplete = jasmine.createSpy('nodeComplete'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [], + queueRunnerFactory: queueRunner, + nodeStart: nodeStart, + nodeComplete: nodeComplete + }), + treeComplete = jasmine.createSpy('treeComplete'), + nodeDone = jasmine.createSpy('nodeDone'); processor.execute(treeComplete); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -392,24 +438,28 @@ describe("TreeProcessor", function() { node.getResult.and.returnValue({ im: 'disabled' }); queueRunner.calls.mostRecent().args[0].onComplete(); - expect(nodeComplete).toHaveBeenCalledWith(node, { im: 'disabled' }, jasmine.any(Function)); + expect(nodeComplete).toHaveBeenCalledWith( + node, + { im: 'disabled' }, + jasmine.any(Function) + ); }); - it("runs beforeAlls for a node with children", function() { + it('runs beforeAlls for a node with children', function() { var leaf = new Leaf(), - node = new Node({ - children: [leaf], - beforeAllFns: ['beforeAll1', 'beforeAll2'] - }), - root = new Node({ children: [node] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [node.id], - queueRunnerFactory: queueRunner - }), - treeComplete = jasmine.createSpy('treeComplete'), - nodeDone = jasmine.createSpy('nodeDone'); + node = new Node({ + children: [leaf], + beforeAllFns: ['beforeAll1', 'beforeAll2'] + }), + root = new Node({ children: [node] }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [node.id], + queueRunnerFactory: queueRunner + }), + treeComplete = jasmine.createSpy('treeComplete'), + nodeDone = jasmine.createSpy('nodeDone'); processor.execute(treeComplete); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -417,24 +467,29 @@ describe("TreeProcessor", function() { queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; - expect(queueableFns).toEqual([{ fn: jasmine.any(Function) }, 'beforeAll1', 'beforeAll2', { fn: jasmine.any(Function) }]); + expect(queueableFns).toEqual([ + { fn: jasmine.any(Function) }, + 'beforeAll1', + 'beforeAll2', + { fn: jasmine.any(Function) } + ]); }); - it("runs afterAlls for a node with children", function() { + it('runs afterAlls for a node with children', function() { var leaf = new Leaf(), - node = new Node({ - children: [leaf], - afterAllFns: ['afterAll1', 'afterAll2'] - }), - root = new Node({ children: [node] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [node.id], - queueRunnerFactory: queueRunner - }), - treeComplete = jasmine.createSpy('treeComplete'), - nodeDone = jasmine.createSpy('nodeDone'); + node = new Node({ + children: [leaf], + afterAllFns: ['afterAll1', 'afterAll2'] + }), + root = new Node({ children: [node] }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [node.id], + queueRunnerFactory: queueRunner + }), + treeComplete = jasmine.createSpy('treeComplete'), + nodeDone = jasmine.createSpy('nodeDone'); processor.execute(treeComplete); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -442,23 +497,28 @@ describe("TreeProcessor", function() { queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; - expect(queueableFns).toEqual([{ fn: jasmine.any(Function) }, { fn: jasmine.any(Function) }, 'afterAll1', 'afterAll2']); + expect(queueableFns).toEqual([ + { fn: jasmine.any(Function) }, + { fn: jasmine.any(Function) }, + 'afterAll1', + 'afterAll2' + ]); }); - it("does not run beforeAlls or afterAlls for a node with no children", function() { + it('does not run beforeAlls or afterAlls for a node with no children', function() { var node = new Node({ - beforeAllFns: ['before'], - afterAllFns: ['after'] - }), - root = new Node({ children: [node] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [node.id], - queueRunnerFactory: queueRunner - }), - treeComplete = jasmine.createSpy('treeComplete'), - nodeDone = jasmine.createSpy('nodeDone'); + beforeAllFns: ['before'], + afterAllFns: ['after'] + }), + root = new Node({ children: [node] }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [node.id], + queueRunnerFactory: queueRunner + }), + treeComplete = jasmine.createSpy('treeComplete'), + nodeDone = jasmine.createSpy('nodeDone'); processor.execute(treeComplete); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -466,26 +526,26 @@ describe("TreeProcessor", function() { queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; - expect(queueableFns).toEqual([{fn: jasmine.any(Function)}]); + expect(queueableFns).toEqual([{ fn: jasmine.any(Function) }]); }); - it("does not run beforeAlls or afterAlls for a node with only pending children", function() { + it('does not run beforeAlls or afterAlls for a node with only pending children', function() { var leaf = new Leaf({ markedPending: true }), - node = new Node({ - children: [leaf], - beforeAllFns: ['before'], - afterAllFns: ['after'], - markedPending: false - }), - root = new Node({ children: [node] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [node.id], - queueRunnerFactory: queueRunner - }), - treeComplete = jasmine.createSpy('treeComplete'), - nodeDone = jasmine.createSpy('nodeDone'); + node = new Node({ + children: [leaf], + beforeAllFns: ['before'], + afterAllFns: ['after'], + markedPending: false + }), + root = new Node({ children: [node] }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [node.id], + queueRunnerFactory: queueRunner + }), + treeComplete = jasmine.createSpy('treeComplete'), + nodeDone = jasmine.createSpy('nodeDone'); processor.execute(treeComplete); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -493,20 +553,23 @@ describe("TreeProcessor", function() { queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; - expect(queueableFns).toEqual([{ fn: jasmine.any(Function) }, { fn: jasmine.any(Function) }]); + expect(queueableFns).toEqual([ + { fn: jasmine.any(Function) }, + { fn: jasmine.any(Function) } + ]); }); - it("runs leaves in the order specified", function() { + it('runs leaves in the order specified', function() { var leaf1 = new Leaf(), - leaf2 = new Leaf(), - root = new Node({ children: [leaf1, leaf2] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [leaf2.id, leaf1.id], - queueRunnerFactory: queueRunner - }), - treeComplete = jasmine.createSpy('treeComplete'); + leaf2 = new Leaf(), + root = new Node({ children: [leaf1, leaf2] }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [leaf2.id, leaf1.id], + queueRunnerFactory: queueRunner + }), + treeComplete = jasmine.createSpy('treeComplete'); processor.execute(treeComplete); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -520,17 +583,17 @@ describe("TreeProcessor", function() { expect(leaf1.execute).toHaveBeenCalled(); }); - it("runs specified leaves before non-specified leaves within a parent node", function() { + it('runs specified leaves before non-specified leaves within a parent node', function() { var specified = new Leaf(), - nonSpecified = new Leaf(), - root = new Node({ children: [nonSpecified, specified] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [specified.id], - queueRunnerFactory: queueRunner - }), - treeComplete = jasmine.createSpy('treeComplete'); + nonSpecified = new Leaf(), + root = new Node({ children: [nonSpecified, specified] }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [specified.id], + queueRunnerFactory: queueRunner + }), + treeComplete = jasmine.createSpy('treeComplete'); processor.execute(treeComplete); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -544,17 +607,17 @@ describe("TreeProcessor", function() { expect(nonSpecified.execute).toHaveBeenCalledWith(undefined, true); }); - it("runs nodes and leaves with a specified order", function() { + it('runs nodes and leaves with a specified order', function() { var specifiedLeaf = new Leaf(), - childLeaf = new Leaf(), - specifiedNode = new Node({ children: [childLeaf] }), - root = new Node({ children: [specifiedLeaf, specifiedNode] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [specifiedNode.id, specifiedLeaf.id], - queueRunnerFactory: queueRunner - }); + childLeaf = new Leaf(), + specifiedNode = new Node({ children: [childLeaf] }), + root = new Node({ children: [specifiedLeaf, specifiedNode] }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [specifiedNode.id, specifiedLeaf.id], + queueRunnerFactory: queueRunner + }); processor.execute(); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -571,20 +634,20 @@ describe("TreeProcessor", function() { expect(specifiedLeaf.execute).toHaveBeenCalled(); }); - it("runs a node multiple times if the order specified leaves and re-enters it", function() { + it('runs a node multiple times if the order specified leaves and re-enters it', function() { var leaf1 = new Leaf(), - leaf2 = new Leaf(), - leaf3 = new Leaf(), - leaf4 = new Leaf(), - leaf5 = new Leaf(), - reentered = new Node({ children: [leaf1, leaf2, leaf3] }), - root = new Node({ children: [reentered, leaf4, leaf5] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [leaf1.id, leaf4.id, leaf2.id, leaf5.id, leaf3.id], - queueRunnerFactory: queueRunner - }); + leaf2 = new Leaf(), + leaf3 = new Leaf(), + leaf4 = new Leaf(), + leaf5 = new Leaf(), + reentered = new Node({ children: [leaf1, leaf2, leaf3] }), + root = new Node({ children: [reentered, leaf4, leaf5] }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [leaf1.id, leaf4.id, leaf2.id, leaf5.id, leaf3.id], + queueRunnerFactory: queueRunner + }); processor.execute(); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -614,21 +677,21 @@ describe("TreeProcessor", function() { expect(leaf3.execute).toHaveBeenCalled(); }); - it("runs a parent of a node with segments correctly", function() { + it('runs a parent of a node with segments correctly', function() { var leaf1 = new Leaf(), - leaf2 = new Leaf(), - leaf3 = new Leaf(), - leaf4 = new Leaf(), - leaf5 = new Leaf(), - parent = new Node({ children: [leaf1, leaf2, leaf3] }), - grandparent = new Node({ children: [parent] }), - root = new Node({ children: [grandparent, leaf4, leaf5] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [leaf1.id, leaf4.id, leaf2.id, leaf5.id, leaf3.id], - queueRunnerFactory: queueRunner - }); + leaf2 = new Leaf(), + leaf3 = new Leaf(), + leaf4 = new Leaf(), + leaf5 = new Leaf(), + parent = new Node({ children: [leaf1, leaf2, leaf3] }), + grandparent = new Node({ children: [parent] }), + root = new Node({ children: [grandparent, leaf4, leaf5] }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [leaf1.id, leaf4.id, leaf2.id, leaf5.id, leaf3.id], + queueRunnerFactory: queueRunner + }); processor.execute(); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -671,18 +734,18 @@ describe("TreeProcessor", function() { expect(leaf3.execute).toHaveBeenCalled(); }); - it("runs nodes in the order they were declared", function() { + it('runs nodes in the order they were declared', function() { var leaf1 = new Leaf(), - leaf2 = new Leaf(), - leaf3 = new Leaf(), - parent = new Node({ children: [leaf2, leaf3] }), - root = new Node({ children: [leaf1, parent] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [root.id], - queueRunnerFactory: queueRunner - }); + leaf2 = new Leaf(), + leaf3 = new Leaf(), + parent = new Node({ children: [leaf2, leaf3] }), + root = new Node({ children: [leaf1, parent] }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [root.id], + queueRunnerFactory: queueRunner + }); processor.execute(); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -702,25 +765,39 @@ describe("TreeProcessor", function() { expect(leaf3.execute).toHaveBeenCalled(); }); - it("runs large segments of nodes in the order they were declared", function() { + it('runs large segments of nodes in the order they were declared', function() { var leaf1 = new Leaf(), - leaf2 = new Leaf(), - leaf3 = new Leaf(), - leaf4 = new Leaf(), - leaf5 = new Leaf(), - leaf6 = new Leaf(), - leaf7 = new Leaf(), - leaf8 = new Leaf(), - leaf9 = new Leaf(), - leaf10 = new Leaf(), - leaf11 = new Leaf(), - root = new Node({ children: [leaf1, leaf2, leaf3, leaf4, leaf5, leaf6, leaf7, leaf8, leaf9, leaf10, leaf11] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [root.id], - queueRunnerFactory: queueRunner - }); + leaf2 = new Leaf(), + leaf3 = new Leaf(), + leaf4 = new Leaf(), + leaf5 = new Leaf(), + leaf6 = new Leaf(), + leaf7 = new Leaf(), + leaf8 = new Leaf(), + leaf9 = new Leaf(), + leaf10 = new Leaf(), + leaf11 = new Leaf(), + root = new Node({ + children: [ + leaf1, + leaf2, + leaf3, + leaf4, + leaf5, + leaf6, + leaf7, + leaf8, + leaf9, + leaf10, + leaf11 + ] + }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [root.id], + queueRunnerFactory: queueRunner + }); processor.execute(); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -760,29 +837,43 @@ describe("TreeProcessor", function() { expect(leaf11.execute).toHaveBeenCalled(); }); - it("runs nodes in a custom order when orderChildren is overridden", function() { + it('runs nodes in a custom order when orderChildren is overridden', function() { var leaf1 = new Leaf(), - leaf2 = new Leaf(), - leaf3 = new Leaf(), - leaf4 = new Leaf(), - leaf5 = new Leaf(), - leaf6 = new Leaf(), - leaf7 = new Leaf(), - leaf8 = new Leaf(), - leaf9 = new Leaf(), - leaf10 = new Leaf(), - leaf11 = new Leaf(), - root = new Node({ children: [leaf1, leaf2, leaf3, leaf4, leaf5, leaf6, leaf7, leaf8, leaf9, leaf10, leaf11] }), - queueRunner = jasmine.createSpy('queueRunner'), - processor = new jasmineUnderTest.TreeProcessor({ - tree: root, - runnableIds: [root.id], - queueRunnerFactory: queueRunner, - orderChildren: function(node) { - var children = node.children.slice(); - return children.reverse(); - } - }); + leaf2 = new Leaf(), + leaf3 = new Leaf(), + leaf4 = new Leaf(), + leaf5 = new Leaf(), + leaf6 = new Leaf(), + leaf7 = new Leaf(), + leaf8 = new Leaf(), + leaf9 = new Leaf(), + leaf10 = new Leaf(), + leaf11 = new Leaf(), + root = new Node({ + children: [ + leaf1, + leaf2, + leaf3, + leaf4, + leaf5, + leaf6, + leaf7, + leaf8, + leaf9, + leaf10, + leaf11 + ] + }), + queueRunner = jasmine.createSpy('queueRunner'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [root.id], + queueRunnerFactory: queueRunner, + orderChildren: function(node) { + var children = node.children.slice(); + return children.reverse(); + } + }); processor.execute(); var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; @@ -820,6 +911,5 @@ describe("TreeProcessor", function() { queueableFns[10].fn(); expect(leaf1.execute).toHaveBeenCalled(); - }); }); diff --git a/spec/core/UserContextSpec.js b/spec/core/UserContextSpec.js index ff71c84d..d8e90f69 100644 --- a/spec/core/UserContextSpec.js +++ b/spec/core/UserContextSpec.js @@ -1,7 +1,7 @@ -describe("UserContext", function() { - it("Behaves just like an plain object", function() { +describe('UserContext', function() { + it('Behaves just like an plain object', function() { var context = new jasmineUnderTest.UserContext(), - properties = []; + properties = []; for (var prop in context) { if (obj.hasOwnProperty(prop)) { @@ -51,4 +51,3 @@ describe("UserContext", function() { }); }); }); - diff --git a/spec/core/UtilSpec.js b/spec/core/UtilSpec.js index a097dc30..759ef8ce 100644 --- a/spec/core/UtilSpec.js +++ b/spec/core/UtilSpec.js @@ -1,11 +1,11 @@ -describe("jasmineUnderTest.util", function() { - describe("isArray_", function() { - it("should return true if the argument is an array", function() { +describe('jasmineUnderTest.util', function() { + describe('isArray_', function() { + it('should return true if the argument is an array', function() { expect(jasmineUnderTest.isArray_([])).toBe(true); expect(jasmineUnderTest.isArray_(['a'])).toBe(true); }); - it("should return false if the argument is not an array", function() { + it('should return false if the argument is not an array', function() { expect(jasmineUnderTest.isArray_(undefined)).toBe(false); expect(jasmineUnderTest.isArray_({})).toBe(false); expect(jasmineUnderTest.isArray_(function() {})).toBe(false); @@ -15,13 +15,13 @@ describe("jasmineUnderTest.util", function() { }); }); - describe("isObject_", function() { - it("should return true if the argument is an object", function() { + describe('isObject_', function() { + it('should return true if the argument is an object', function() { expect(jasmineUnderTest.isObject_({})).toBe(true); - expect(jasmineUnderTest.isObject_({an: "object"})).toBe(true); + expect(jasmineUnderTest.isObject_({ an: 'object' })).toBe(true); }); - it("should return false if the argument is not an object", function() { + it('should return false if the argument is not an object', function() { expect(jasmineUnderTest.isObject_(undefined)).toBe(false); expect(jasmineUnderTest.isObject_([])).toBe(false); expect(jasmineUnderTest.isObject_(function() {})).toBe(false); @@ -31,128 +31,126 @@ describe("jasmineUnderTest.util", function() { }); }); - describe("promise utils", function () { + describe('promise utils', function() { + var mockNativePromise, mockPromiseLikeObject; - var mockNativePromise, - mockPromiseLikeObject; + var mockPromiseLike = function() { + this.then = function() {}; + }; - var mockPromiseLike = function () {this.then = function () {};}; - - beforeEach(function () { + beforeEach(function() { jasmine.getEnv().requirePromises(); - mockNativePromise = new Promise(function (res, rej) {}); + mockNativePromise = new Promise(function(res, rej) {}); mockPromiseLikeObject = new mockPromiseLike(); }); - describe("isPromise", function () { - - it("should return true when passed a native promise", function () { + describe('isPromise', function() { + it('should return true when passed a native promise', function() { expect(jasmineUnderTest.isPromise(mockNativePromise)).toBe(true); }); - it("should return false for promise like objects", function () { + it('should return false for promise like objects', function() { expect(jasmineUnderTest.isPromise(mockPromiseLikeObject)).toBe(false); }); - it("should return false for strings", function () { - expect(jasmineUnderTest.isPromise("hello")).toBe(false); + it('should return false for strings', function() { + expect(jasmineUnderTest.isPromise('hello')).toBe(false); }); - it("should return false for numbers", function () { + it('should return false for numbers', function() { expect(jasmineUnderTest.isPromise(3)).toBe(false); }); - it("should return false for null", function () { + it('should return false for null', function() { expect(jasmineUnderTest.isPromise(null)).toBe(false); }); - it("should return false for undefined", function () { + it('should return false for undefined', function() { expect(jasmineUnderTest.isPromise(undefined)).toBe(false); }); - it("should return false for arrays", function () { + it('should return false for arrays', function() { expect(jasmineUnderTest.isPromise([])).toBe(false); }); - it("should return false for objects", function () { + it('should return false for objects', function() { expect(jasmineUnderTest.isPromise({})).toBe(false); }); - it("should return false for boolean values", function () { + it('should return false for boolean values', function() { expect(jasmineUnderTest.isPromise(true)).toBe(false); }); - }); - describe("isPromiseLike", function () { - - it("should return true when passed a native promise", function () { + describe('isPromiseLike', function() { + it('should return true when passed a native promise', function() { expect(jasmineUnderTest.isPromiseLike(mockNativePromise)).toBe(true); }); - it("should return true for promise like objects", function () { - expect(jasmineUnderTest.isPromiseLike(mockPromiseLikeObject)).toBe(true); + it('should return true for promise like objects', function() { + expect(jasmineUnderTest.isPromiseLike(mockPromiseLikeObject)).toBe( + true + ); }); - it("should return false if then is not a function", function () { - expect(jasmineUnderTest.isPromiseLike({then:{its:"Not a function :O"}})).toBe(false); + it('should return false if then is not a function', function() { + expect( + jasmineUnderTest.isPromiseLike({ then: { its: 'Not a function :O' } }) + ).toBe(false); }); - it("should return false for strings", function () { - expect(jasmineUnderTest.isPromiseLike("hello")).toBe(false); + it('should return false for strings', function() { + expect(jasmineUnderTest.isPromiseLike('hello')).toBe(false); }); - it("should return false for numbers", function () { + it('should return false for numbers', function() { expect(jasmineUnderTest.isPromiseLike(3)).toBe(false); }); - it("should return false for null", function () { + it('should return false for null', function() { expect(jasmineUnderTest.isPromiseLike(null)).toBe(false); }); - it("should return false for undefined", function () { + it('should return false for undefined', function() { expect(jasmineUnderTest.isPromiseLike(undefined)).toBe(false); }); - it("should return false for arrays", function () { + it('should return false for arrays', function() { expect(jasmineUnderTest.isPromiseLike([])).toBe(false); }); - it("should return false for objects", function () { + it('should return false for objects', function() { expect(jasmineUnderTest.isPromiseLike({})).toBe(false); }); - it("should return false for boolean values", function () { + it('should return false for boolean values', function() { expect(jasmineUnderTest.isPromiseLike(true)).toBe(false); }); - }); - }); - describe("isUndefined", function() { - it("reports if a variable is defined", function() { + describe('isUndefined', function() { + it('reports if a variable is defined', function() { var a; expect(jasmineUnderTest.util.isUndefined(a)).toBe(true); expect(jasmineUnderTest.util.isUndefined(undefined)).toBe(true); - var undefined = "diz be undefined yo"; + var undefined = 'diz be undefined yo'; expect(jasmineUnderTest.util.isUndefined(undefined)).toBe(false); }); }); - describe("getPropertyDescriptor", function() { - it("get property descriptor from object", function() { - var obj = {prop: 1}, + describe('getPropertyDescriptor', function() { + it('get property descriptor from object', function() { + var obj = { prop: 1 }, actual = jasmineUnderTest.util.getPropertyDescriptor(obj, 'prop'), expected = Object.getOwnPropertyDescriptor(obj, 'prop'); expect(actual).toEqual(expected); }); - it("get property descriptor from object property", function() { - var proto = {prop: 1}, - obj = Object.create(proto), + it('get property descriptor from object property', function() { + var proto = { prop: 1 }, actual = jasmineUnderTest.util.getPropertyDescriptor(proto, 'prop'), expected = Object.getOwnPropertyDescriptor(proto, 'prop'); @@ -160,8 +158,8 @@ describe("jasmineUnderTest.util", function() { }); }); - describe("objectDifference", function() { - it("given two objects A and B, returns the properties in A not present in B", function() { + describe('objectDifference', function() { + it('given two objects A and B, returns the properties in A not present in B', function() { var a = { foo: 3, bar: 4, @@ -173,10 +171,13 @@ describe("jasmineUnderTest.util", function() { quux: 7 }; - expect(jasmineUnderTest.util.objectDifference(a, b)).toEqual({foo: 3, baz: 5}) + expect(jasmineUnderTest.util.objectDifference(a, b)).toEqual({ + foo: 3, + baz: 5 + }); }); - it("only looks at own properties of both objects", function() { + it('only looks at own properties of both objects', function() { function Foo() {} Foo.prototype.x = 1; @@ -188,13 +189,13 @@ describe("jasmineUnderTest.util", function() { var b = new Foo(); b.y = 2; - expect(jasmineUnderTest.util.objectDifference(a, b)).toEqual({x: 1}); - expect(jasmineUnderTest.util.objectDifference(b, a)).toEqual({y: 2}); + expect(jasmineUnderTest.util.objectDifference(a, b)).toEqual({ x: 1 }); + expect(jasmineUnderTest.util.objectDifference(b, a)).toEqual({ y: 2 }); }); }); - describe("jasmineFile", function() { - it("returns the file containing jasmine.util", function() { + describe('jasmineFile', function() { + it('returns the file containing jasmine.util', function() { // Chrome sometimes reports foo.js as foo.js/, so tolerate // a trailing slash if present. expect(jasmineUnderTest.util.jasmineFile()).toMatch(/util.js\/?$/); diff --git a/spec/core/baseSpec.js b/spec/core/baseSpec.js index 7f17265b..07f94e19 100644 --- a/spec/core/baseSpec.js +++ b/spec/core/baseSpec.js @@ -1,6 +1,6 @@ describe('base helpers', function() { describe('isError_', function() { - it("correctly handles WebSocket events", function(done) { + it('correctly handles WebSocket events', function(done) { if (typeof jasmine.getGlobal().WebSocket === 'undefined') { done(); return; @@ -10,9 +10,11 @@ describe('base helpers', function() { var sock = new WebSocket('ws://localhost'); var event; sock.onerror = function(e) { - event = e + event = e; + }; + return function() { + return event; }; - return function() { return event }; })(); var left = 20; @@ -20,6 +22,7 @@ describe('base helpers', function() { if (obj() || left === 0) { var result = jasmineUnderTest.isError_(obj()); expect(result).toBe(false); + clearInterval(int); done(); } else { left--; diff --git a/spec/core/formatErrorMsgSpec.js b/spec/core/formatErrorMsgSpec.js index 12812443..a85665e9 100644 --- a/spec/core/formatErrorMsgSpec.js +++ b/spec/core/formatErrorMsgSpec.js @@ -1,4 +1,4 @@ -describe('formatErrorMsg', function () { +describe('formatErrorMsg', function() { it('should format an error with a domain', function() { var formator = jasmineUnderTest.formatErrorMsg('api'); expect(formator('message')).toBe('api : message'); diff --git a/spec/helpers/BrowserFlags.js b/spec/helpers/BrowserFlags.js index 9cf630e7..248fc274 100644 --- a/spec/helpers/BrowserFlags.js +++ b/spec/helpers/BrowserFlags.js @@ -1,7 +1,9 @@ (function(env) { function browserVersion(matchFn) { var userAgent = jasmine.getGlobal().navigator.userAgent; - if (!userAgent) { return void 0; } + if (!userAgent) { + return void 0; + } var match = matchFn(userAgent); @@ -11,5 +13,4 @@ env.firefoxVersion = browserVersion(function(userAgent) { return /Firefox\/([0-9]{0,})/.exec(userAgent); }); - })(jasmine.getEnv()); diff --git a/spec/helpers/asyncAwait.js b/spec/helpers/asyncAwait.js index 866d9526..9cdead0d 100644 --- a/spec/helpers/asyncAwait.js +++ b/spec/helpers/asyncAwait.js @@ -1,7 +1,7 @@ (function(env) { function getAsyncCtor() { try { - eval("var func = async function(){};"); + eval('var func = async function(){};'); } catch (e) { return null; } @@ -15,13 +15,12 @@ env.makeAsyncAwaitFunction = function() { var AsyncFunction = getAsyncCtor(); - return new AsyncFunction(""); + return new AsyncFunction(''); }; env.requireAsyncAwait = function() { if (!hasAsyncAwaitSupport()) { - env.pending("Environment does not support async/await functions"); + env.pending('Environment does not support async/await functions'); } }; })(jasmine.getEnv()); - diff --git a/spec/helpers/checkForMap.js b/spec/helpers/checkForMap.js index 697d5738..64e32cdc 100644 --- a/spec/helpers/checkForMap.js +++ b/spec/helpers/checkForMap.js @@ -1,37 +1,46 @@ (function(env) { function hasFunctioningMaps() { - if (typeof Map === 'undefined') { return false; } + if (typeof Map === 'undefined') { + return false; + } try { var s = new Map(); - s.set('a',1); - s.set('b',2); + s.set('a', 1); + s.set('b', 2); - if (s.size !== 2) { return false; } - if (s.has('a') !== true) { return false; } + if (s.size !== 2) { + return false; + } + if (s.has('a') !== true) { + return false; + } var iterations = 0; var ifForEachWorking = true; s.forEach(function(value, key, map) { ifForEachWorking = ifForEachWorking && map === s; - if (key==='a') { - ifForEachWorking = ifForEachWorking && value===1; + if (key === 'a') { + ifForEachWorking = ifForEachWorking && value === 1; } iterations++; }); - if (iterations !== 2) { return false; } - if (ifForEachWorking !== true) { return false; } + if (iterations !== 2) { + return false; + } + if (ifForEachWorking !== true) { + return false; + } return true; - } catch(e) { + } catch (e) { return false; } } env.requireFunctioningMaps = function() { if (!hasFunctioningMaps()) { - env.pending("Browser has incomplete or missing support for Maps"); + env.pending('Browser has incomplete or missing support for Maps'); } }; - })(jasmine.getEnv()); diff --git a/spec/helpers/checkForSet.js b/spec/helpers/checkForSet.js index d12e847b..1be8de45 100644 --- a/spec/helpers/checkForSet.js +++ b/spec/helpers/checkForSet.js @@ -1,41 +1,50 @@ (function(env) { function hasFunctioningSets() { - if (typeof Set === 'undefined') { return false; } + if (typeof Set === 'undefined') { + return false; + } try { var s = new Set(); s.add(1); s.add(2); - if (s.size !== 2) { return false; } - if (s.has(1) !== true) { return false; } + if (s.size !== 2) { + return false; + } + if (s.has(1) !== true) { + return false; + } var iterations = 0; var isForEachWorking = true; s.forEach(function(value, key, set) { isForEachWorking = isForEachWorking && set === s; - if (iterations===0) { - isForEachWorking = isForEachWorking && (key===value) && value===1; - } else if (iterations===1) { - isForEachWorking = isForEachWorking && (key===value) && value===2; + if (iterations === 0) { + isForEachWorking = isForEachWorking && key === value && value === 1; + } else if (iterations === 1) { + isForEachWorking = isForEachWorking && key === value && value === 2; } iterations++; }); - if (iterations !== 2) { return false; } - if (isForEachWorking !== true) { return false; } + if (iterations !== 2) { + return false; + } + if (isForEachWorking !== true) { + return false; + } return true; - } catch(e) { + } catch (e) { return false; } } env.requireFunctioningSets = function() { if (!hasFunctioningSets()) { - env.pending("Browser has incomplete or missing support for Sets"); + env.pending('Browser has incomplete or missing support for Sets'); } }; - })(jasmine.getEnv()); diff --git a/spec/helpers/checkForSymbol.js b/spec/helpers/checkForSymbol.js index 93e414ee..c1ed5415 100644 --- a/spec/helpers/checkForSymbol.js +++ b/spec/helpers/checkForSymbol.js @@ -21,8 +21,7 @@ env.requireFunctioningSymbols = function() { if (!hasFunctioningSymbols()) { - env.pending("Browser has incomplete or missing support for Symbols"); + env.pending('Browser has incomplete or missing support for Symbols'); } }; - })(jasmine.getEnv()); diff --git a/spec/helpers/checkForTypedArrays.js b/spec/helpers/checkForTypedArrays.js index ddbdcc9f..3b5d6b35 100644 --- a/spec/helpers/checkForTypedArrays.js +++ b/spec/helpers/checkForTypedArrays.js @@ -1,20 +1,23 @@ (function(env) { function hasFunctioningTypedArrays() { - if (typeof Uint32Array === 'undefined') { return false; } + if (typeof Uint32Array === 'undefined') { + return false; + } try { var a = new Uint32Array([1, 2, 3]); - if (a.length !== 3) { return false; } + if (a.length !== 3) { + return false; + } return true; - } catch(e) { + } catch (e) { return false; } } env.requireFunctioningTypedArrays = function() { if (!hasFunctioningTypedArrays()) { - env.pending("Browser has incomplete or missing support for typed arrays"); + env.pending('Browser has incomplete or missing support for typed arrays'); } }; - })(jasmine.getEnv()); diff --git a/spec/helpers/integrationMatchers.js b/spec/helpers/integrationMatchers.js index 8b524946..694ccd6e 100644 --- a/spec/helpers/integrationMatchers.js +++ b/spec/helpers/integrationMatchers.js @@ -1,10 +1,15 @@ (function(env) { env.registerIntegrationMatchers = function() { jasmine.addMatchers({ - toHaveFailedExpectationsForRunnable: function (util, customeEqualityTesters) { + toHaveFailedExpectationsForRunnable: function( + util, + customeEqualityTesters + ) { return { - compare: function (actual, fullName, expectedFailures) { - var foundRunnable = false, expectations = true, foundFailures = []; + compare: function(actual, fullName, expectedFailures) { + var foundRunnable = false, + expectations = true, + foundFailures = []; for (var i = 0; i < actual.calls.count(); i++) { var args = actual.calls.argsFor(i)[0]; @@ -19,8 +24,12 @@ var failure = foundFailures[j]; var expectedFailure = expectedFailures[j]; - if (Object.prototype.toString.call(expectedFailure) === '[object RegExp]') { - expectations = expectations && expectedFailure.test(failure); + if ( + Object.prototype.toString.call(expectedFailure) === + '[object RegExp]' + ) { + expectations = + expectations && expectedFailure.test(failure); } else { expectations = expectations && failure === expectedFailure; } @@ -31,8 +40,14 @@ return { pass: foundRunnable && expectations, - message: !foundRunnable ? 'The runnable "' + fullName + '" never finished' : - 'Expected runnable "' + fullName + '" to have failures ' + jasmine.pp(expectedFailures) + ' but it had ' + jasmine.pp(foundFailures) + message: !foundRunnable + ? 'The runnable "' + fullName + '" never finished' + : 'Expected runnable "' + + fullName + + '" to have failures ' + + jasmine.pp(expectedFailures) + + ' but it had ' + + jasmine.pp(foundFailures) }; } }; @@ -40,4 +55,3 @@ }); }; })(jasmine.getEnv()); - diff --git a/spec/helpers/nodeDefineJasmineUnderTest.js b/spec/helpers/nodeDefineJasmineUnderTest.js index 119265af..739c20af 100644 --- a/spec/helpers/nodeDefineJasmineUnderTest.js +++ b/spec/helpers/nodeDefineJasmineUnderTest.js @@ -1,21 +1,19 @@ (function() { - var path = require("path"), - fg = require("fast-glob"); + var path = require('path'), + fg = require('fast-glob'); - var jasmineUnderTestRequire = require(path.join(__dirname, "../../src/core/requireCore.js")); + var jasmineUnderTestRequire = require(path.join( + __dirname, + '../../src/core/requireCore.js' + )); - global.getJasmineRequireObj = function () { + global.getJasmineRequireObj = function() { return jasmineUnderTestRequire; }; - function extend(destination, source) { - for (var property in source) destination[property] = source[property]; - return destination; - } - function getSourceFiles() { var src_files = ['core/**/*.js', 'version.js'].map(function(file) { - return path.join(__dirname, "../../", 'src/', file); + return path.join(__dirname, '../../', 'src/', file); }); fg.sync(src_files).forEach(function(resolvedFile) { @@ -24,5 +22,7 @@ } getSourceFiles(); - global.jasmineUnderTest = jasmineUnderTestRequire.core(jasmineUnderTestRequire); + global.jasmineUnderTest = jasmineUnderTestRequire.core( + jasmineUnderTestRequire + ); })(); diff --git a/spec/helpers/promises.js b/spec/helpers/promises.js index 76c6c024..a194af0c 100644 --- a/spec/helpers/promises.js +++ b/spec/helpers/promises.js @@ -1,8 +1,7 @@ (function(env) { env.requirePromises = function() { if (typeof Promise !== 'function') { - env.pending("Environment does not support promises"); + env.pending('Environment does not support promises'); } }; })(jasmine.getEnv()); - diff --git a/spec/html/HtmlReporterSpec.js b/spec/html/HtmlReporterSpec.js index 8b40139c..a8790f87 100644 --- a/spec/html/HtmlReporterSpec.js +++ b/spec/html/HtmlReporterSpec.js @@ -1,178 +1,244 @@ -describe("HtmlReporter", function() { - it("builds the initial DOM elements, including the title banner", function() { +describe('HtmlReporter', function() { + it('builds the initial DOM elements, including the title banner', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { return container; }, + container = document.createElement('div'), + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); // Main top-level elements - expect(container.querySelector("div.jasmine_html-reporter")).toBeTruthy(); - expect(container.querySelector("div.jasmine-banner")).toBeTruthy(); - expect(container.querySelector("div.jasmine-alert")).toBeTruthy(); - expect(container.querySelector("div.jasmine-results")).toBeTruthy(); + expect(container.querySelector('div.jasmine_html-reporter')).toBeTruthy(); + expect(container.querySelector('div.jasmine-banner')).toBeTruthy(); + expect(container.querySelector('div.jasmine-alert')).toBeTruthy(); + expect(container.querySelector('div.jasmine-results')).toBeTruthy(); - expect(container.querySelector("ul.jasmine-symbol-summary")).toBeTruthy(); + expect(container.querySelector('ul.jasmine-symbol-summary')).toBeTruthy(); // title banner - var banner = container.querySelector(".jasmine-banner"); + var banner = container.querySelector('.jasmine-banner'); - var title = banner.querySelector("a.jasmine-title"); + var title = banner.querySelector('a.jasmine-title'); expect(title.getAttribute('href')).toEqual('http://jasmine.github.io/'); expect(title.getAttribute('target')).toEqual('_blank'); - var version = banner.querySelector(".jasmine-version"); + var version = banner.querySelector('.jasmine-version'); expect(version.textContent).toEqual(jasmineUnderTest.version); }); - it("builds a single reporter even if initialized multiple times", function() { + it('builds a single reporter even if initialized multiple times', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { return container; }, + container = document.createElement('div'), + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); reporter.initialize(); reporter.initialize(); - expect(container.querySelectorAll("div.jasmine_html-reporter").length).toEqual(1); + expect( + container.querySelectorAll('div.jasmine_html-reporter').length + ).toEqual(1); }); - it("starts the timer when jasmine begins", function() { + it('starts the timer when jasmine begins', function() { var env = new jasmine.Env(), - startTimerSpy = jasmine.createSpy("start-timer-spy"), - reporter = new jasmineUnderTest.HtmlReporter({ - env: env, - createElement: function() { return document.createElement.apply(document, arguments); }, - timer: { start: startTimerSpy } - }); + startTimerSpy = jasmine.createSpy('start-timer-spy'), + reporter = new jasmineUnderTest.HtmlReporter({ + env: env, + createElement: function() { + return document.createElement.apply(document, arguments); + }, + timer: { start: startTimerSpy } + }); reporter.jasmineStarted({}); expect(startTimerSpy).toHaveBeenCalled(); }); - describe("when a spec is done", function() { - it("logs errors to the console and prints a special symbol if it is an empty spec", function() { - if (typeof console === "undefined") { - console = { error: function(){} }; + describe('when a spec is done', function() { + it('logs errors to the console and prints a special symbol if it is an empty spec', function() { + if (typeof console === 'undefined') { + console = { error: function() {} }; } var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), - getContainer = function() {return container;}, - reporter = new jasmineUnderTest.HtmlReporter({ - env: env, - getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } - }); + container = document.createElement('div'), + getContainer = function() { + return container; + }, + reporter = new jasmineUnderTest.HtmlReporter({ + env: env, + getContainer: getContainer, + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } + }); spyOn(console, 'error'); reporter.initialize(); reporter.specDone({ - status: "passed", + status: 'passed', fullName: 'Some Name', passedExpectations: [], failedExpectations: [] }); - expect(console.error).toHaveBeenCalledWith("Spec \'Some Name\' has no expectations."); + expect(console.error).toHaveBeenCalledWith( + "Spec 'Some Name' has no expectations." + ); var specEl = container.querySelector('.jasmine-symbol-summary li'); - expect(specEl.getAttribute("class")).toEqual("jasmine-empty"); + expect(specEl.getAttribute('class')).toEqual('jasmine-empty'); }); - it("reports the status symbol of a excluded spec", function() { + it('reports the status symbol of a excluded spec', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { return container; }, + container = document.createElement('div'), + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); - reporter.specDone({id: 789, status: "excluded", fullName: "symbols should have titles", passedExpectations: [], failedExpectations: []}); + reporter.specDone({ + id: 789, + status: 'excluded', + fullName: 'symbols should have titles', + passedExpectations: [], + failedExpectations: [] + }); var specEl = container.querySelector('.jasmine-symbol-summary li'); - expect(specEl.getAttribute("class")).toEqual("jasmine-excluded"); - expect(specEl.getAttribute("id")).toEqual("spec_789"); - expect(specEl.getAttribute("title")).toEqual("symbols should have titles"); + expect(specEl.getAttribute('class')).toEqual('jasmine-excluded'); + expect(specEl.getAttribute('id')).toEqual('spec_789'); + expect(specEl.getAttribute('title')).toEqual( + 'symbols should have titles' + ); }); - it("reports the status symbol of a pending spec", function() { + it('reports the status symbol of a pending spec', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { return container; }, + container = document.createElement('div'), + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); - reporter.specDone({id: 789, status: "pending", passedExpectations: [], failedExpectations: []}); + reporter.specDone({ + id: 789, + status: 'pending', + passedExpectations: [], + failedExpectations: [] + }); var specEl = container.querySelector('.jasmine-symbol-summary li'); - expect(specEl.getAttribute("class")).toEqual("jasmine-pending"); - expect(specEl.getAttribute("id")).toEqual("spec_789"); + expect(specEl.getAttribute('class')).toEqual('jasmine-pending'); + expect(specEl.getAttribute('id')).toEqual('spec_789'); }); - it("reports the status symbol of a passing spec", function() { + it('reports the status symbol of a passing spec', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { return container; }, + container = document.createElement('div'), + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); - reporter.specDone({id: 123, status: "passed", passedExpectations: [{passed: true}], failedExpectations: []}); + reporter.specDone({ + id: 123, + status: 'passed', + passedExpectations: [{ passed: true }], + failedExpectations: [] + }); - var statuses = container.querySelector(".jasmine-symbol-summary"); - var specEl = statuses.querySelector("li"); - expect(specEl.getAttribute("class")).toEqual("jasmine-passed"); - expect(specEl.getAttribute("id")).toEqual("spec_123"); + var statuses = container.querySelector('.jasmine-symbol-summary'); + var specEl = statuses.querySelector('li'); + expect(specEl.getAttribute('class')).toEqual('jasmine-passed'); + expect(specEl.getAttribute('id')).toEqual('spec_123'); }); - it("reports the status symbol of a failing spec", function() { + it('reports the status symbol of a failing spec', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { return container; }, + container = document.createElement('div'), + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); reporter.specDone({ id: 345, - status: "failed", + status: 'failed', failedExpectations: [], passedExpectations: [] }); - var specEl = container.querySelector(".jasmine-symbol-summary li"); - expect(specEl.getAttribute("class")).toEqual("jasmine-failed"); - expect(specEl.getAttribute("id")).toEqual("spec_345"); + var specEl = container.querySelector('.jasmine-symbol-summary li'); + expect(specEl.getAttribute('class')).toEqual('jasmine-failed'); + expect(specEl.getAttribute('id')).toEqual('spec_345'); }); }); @@ -180,12 +246,18 @@ describe("HtmlReporter", function() { it('displays the messages in their own alert bars', function() { var env = new jasmineUnderTest.Env(), container = document.createElement('div'), - getContainer = function() { return container; }, + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); @@ -207,37 +279,49 @@ describe("HtmlReporter", function() { failedExpectations: [] }); - var alertBars = container.querySelectorAll(".jasmine-alert .jasmine-bar"); + var alertBars = container.querySelectorAll('.jasmine-alert .jasmine-bar'); expect(alertBars.length).toEqual(4); expect(alertBars[1].innerHTML).toMatch(/spec deprecation/); - expect(alertBars[1].getAttribute("class")).toEqual('jasmine-bar jasmine-warning'); + expect(alertBars[1].getAttribute('class')).toEqual( + 'jasmine-bar jasmine-warning' + ); expect(alertBars[2].innerHTML).toMatch(/suite deprecation/); expect(alertBars[3].innerHTML).toMatch(/global deprecation/); }); }); - describe("when Jasmine is done", function() { - it("adds a warning to the link title of specs that have no expectations", function() { + describe('when Jasmine is done', function() { + it('adds a warning to the link title of specs that have no expectations', function() { if (!window.console) { - window.console = { error: function(){} }; + window.console = { error: function() {} }; } var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), - getContainer = function() {return container;}, - reporter = new jasmineUnderTest.HtmlReporter({ - env: env, - getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } - }); + container = document.createElement('div'), + getContainer = function() { + return container; + }, + reporter = new jasmineUnderTest.HtmlReporter({ + env: env, + getContainer: getContainer, + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } + }); spyOn(console, 'error'); reporter.initialize(); reporter.jasmineStarted({}); - reporter.suiteStarted({id: 1}); - reporter.specStarted({id: 1, passedExpectations: [], failedExpectations: []}); + reporter.suiteStarted({ id: 1 }); + reporter.specStarted({ + id: 1, + passedExpectations: [], + failedExpectations: [] + }); reporter.specDone({ id: 1, status: 'passed', @@ -245,7 +329,7 @@ describe("HtmlReporter", function() { passedExpectations: [], failedExpectations: [] }); - reporter.suiteDone({id: 1}); + reporter.suiteDone({ id: 1 }); reporter.jasmineDone({}); var summary = container.querySelector('.jasmine-summary'); @@ -256,16 +340,22 @@ describe("HtmlReporter", function() { expect(specLink.innerHTML).toMatch(/SPEC HAS NO EXPECTATIONS/); }); - it("reports the run time", function() { + it('reports the run time', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), timer = jasmine.createSpyObj('timer', ['start', 'elapsed']), - getContainer = function() { return container; }, + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); }, + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + }, timer: timer }); @@ -276,54 +366,64 @@ describe("HtmlReporter", function() { timer.elapsed.and.returnValue(100); reporter.jasmineDone({}); - var duration = container.querySelector(".jasmine-alert .jasmine-duration"); + var duration = container.querySelector( + '.jasmine-alert .jasmine-duration' + ); expect(duration.innerHTML).toMatch(/finished in 0.1s/); }); - it("reports the suite and spec names with status", function() { + it('reports the suite and spec names with status', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { return container; }, + container = document.createElement('div'), + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); }, - addToExistingQueryString: function(key, value) { return "?foo=bar&" + key + "=" + value; } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + }, + addToExistingQueryString: function(key, value) { + return '?foo=bar&' + key + '=' + value; + } }); reporter.initialize(); reporter.jasmineStarted({}); reporter.suiteStarted({ id: 1, - description: "A Suite", - fullName: "A Suite" + description: 'A Suite', + fullName: 'A Suite' }); var specResult = { id: 123, - description: "with a spec", - fullName: "A Suite with a spec", - status: "passed", + description: 'with a spec', + fullName: 'A Suite with a spec', + status: 'passed', failedExpectations: [], - passedExpectations: [{passed: true}] + passedExpectations: [{ passed: true }] }; reporter.specStarted(specResult); reporter.specDone(specResult); reporter.suiteStarted({ id: 2, - description: "inner suite", - fullName: "A Suite inner suite" + description: 'inner suite', + fullName: 'A Suite inner suite' }); var specResult = { id: 124, - description: "with another spec", - fullName: "A Suite inner suite with another spec", - status: "passed", + description: 'with another spec', + fullName: 'A Suite inner suite with another spec', + status: 'passed', failedExpectations: [], - passedExpectations: [{passed: true}] + passedExpectations: [{ passed: true }] }; reporter.specStarted(specResult); reporter.specDone(specResult); @@ -331,15 +431,15 @@ describe("HtmlReporter", function() { reporter.suiteDone({ id: 2, status: 'things', - description: "inner suite", - fullName: "A Suite inner suite" + description: 'inner suite', + fullName: 'A Suite inner suite' }); specResult = { id: 209, - description: "with a failing spec", - fullName: "A Suite inner with a failing spec", - status: "failed", + description: 'with a failing spec', + fullName: 'A Suite inner with a failing spec', + status: 'failed', failedExpectations: [{}], passedExpectations: [] }; @@ -349,12 +449,12 @@ describe("HtmlReporter", function() { reporter.suiteDone({ id: 1, status: 'things', - description: "A Suite", - fullName: "A Suite" + description: 'A Suite', + fullName: 'A Suite' }); reporter.jasmineDone({}); - var summary = container.querySelector(".jasmine-summary"); + var summary = container.querySelector('.jasmine-summary'); expect(summary.childNodes.length).toEqual(1); @@ -364,28 +464,35 @@ describe("HtmlReporter", function() { var classes = []; for (var i = 0; i < outerSuite.childNodes.length; i++) { var node = outerSuite.childNodes[i]; - classes.push(node.getAttribute("class")); + classes.push(node.getAttribute('class')); } - expect(classes).toEqual(["jasmine-suite-detail jasmine-things", "jasmine-specs", "jasmine-suite", "jasmine-specs"]); + expect(classes).toEqual([ + 'jasmine-suite-detail jasmine-things', + 'jasmine-specs', + 'jasmine-suite', + 'jasmine-specs' + ]); var suiteDetail = outerSuite.childNodes[0]; var suiteLink = suiteDetail.childNodes[0]; - expect(suiteLink.innerHTML).toEqual("A Suite"); - expect(suiteLink.getAttribute('href')).toEqual("?foo=bar&spec=A Suite"); + expect(suiteLink.innerHTML).toEqual('A Suite'); + expect(suiteLink.getAttribute('href')).toEqual('?foo=bar&spec=A Suite'); var specs = outerSuite.childNodes[1]; var spec = specs.childNodes[0]; - expect(spec.getAttribute("class")).toEqual("jasmine-passed"); - expect(spec.getAttribute("id")).toEqual("spec-123"); + expect(spec.getAttribute('class')).toEqual('jasmine-passed'); + expect(spec.getAttribute('id')).toEqual('spec-123'); var specLink = spec.childNodes[0]; - expect(specLink.innerHTML).toEqual("with a spec"); - expect(specLink.getAttribute("href")).toEqual("?foo=bar&spec=A Suite with a spec"); + expect(specLink.innerHTML).toEqual('with a spec'); + expect(specLink.getAttribute('href')).toEqual( + '?foo=bar&spec=A Suite with a spec' + ); }); - it("has an options menu", function() { + it('has an options menu', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), getContainer = function() { return container; }, @@ -403,8 +510,12 @@ describe("HtmlReporter", function() { reporter.initialize(); reporter.jasmineDone({}); - var trigger = container.querySelector('.jasmine-run-options .jasmine-trigger'), - payload = container.querySelector('.jasmine-run-options .jasmine-payload'); + var trigger = container.querySelector( + '.jasmine-run-options .jasmine-trigger' + ), + payload = container.querySelector( + '.jasmine-run-options .jasmine-payload' + ); expect(payload).not.toHaveClass('jasmine-open'); @@ -417,69 +528,100 @@ describe("HtmlReporter", function() { expect(payload).not.toHaveClass('jasmine-open'); }); - describe("when there are global errors", function() { - it("displays the exceptions in their own alert bars", function(){ + describe('when there are global errors', function() { + it('displays the exceptions in their own alert bars', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { return container; }, + container = document.createElement('div'), + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); reporter.jasmineStarted({}); - reporter.jasmineDone({ failedExpectations: [ - { message: 'Global After All Failure', globalErrorType: 'afterAll' }, + reporter.jasmineDone({ + failedExpectations: [ + { + message: 'Global After All Failure', + globalErrorType: 'afterAll' + }, { message: 'Your JS is borken', globalErrorType: 'load' } - ] }); + ] + }); - var alertBars = container.querySelectorAll(".jasmine-alert .jasmine-bar"); + var alertBars = container.querySelectorAll( + '.jasmine-alert .jasmine-bar' + ); expect(alertBars.length).toEqual(3); - expect(alertBars[1].getAttribute("class")).toEqual('jasmine-bar jasmine-errored'); - expect(alertBars[1].innerHTML).toMatch(/AfterAll Global After All Failure/); - expect(alertBars[2].innerHTML).toMatch(/Error during loading: Your JS is borken/); + expect(alertBars[1].getAttribute('class')).toEqual( + 'jasmine-bar jasmine-errored' + ); + expect(alertBars[1].innerHTML).toMatch( + /AfterAll Global After All Failure/ + ); + expect(alertBars[2].innerHTML).toMatch( + /Error during loading: Your JS is borken/ + ); expect(alertBars[2].innerHTML).not.toMatch(/line/); }); - it("displays file and line information if available", function() { + it('displays file and line information if available', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { return container; }, + container = document.createElement('div'), + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); reporter.jasmineStarted({}); - reporter.jasmineDone({ failedExpectations: [ + reporter.jasmineDone({ + failedExpectations: [ { message: 'Your JS is borken', globalErrorType: 'load', filename: 'some/file.js', lineno: 42 } - ] }); + ] + }); - var alertBars = container.querySelectorAll(".jasmine-alert .jasmine-bar"); + var alertBars = container.querySelectorAll( + '.jasmine-alert .jasmine-bar' + ); expect(alertBars.length).toEqual(2); - expect(alertBars[1].innerHTML).toMatch(/Error during loading: Your JS is borken in some\/file.js line 42/); + expect(alertBars[1].innerHTML).toMatch( + /Error during loading: Your JS is borken in some\/file.js line 42/ + ); }); }); - describe("UI for stop on spec failure", function() { - it("should be unchecked for full execution", function() { + describe('UI for stop on spec failure', function() { + it('should be unchecked for full execution', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), getContainer = function() { return container; }, @@ -497,13 +639,13 @@ describe("HtmlReporter", function() { reporter.initialize(); reporter.jasmineDone({}); - var stopOnFailureUI = container.querySelector(".jasmine-fail-fast"); + var stopOnFailureUI = container.querySelector('.jasmine-fail-fast'); expect(stopOnFailureUI.checked).toBe(false); }); - it("should be checked if stopping short", function() { + it('should be checked if stopping short', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), getContainer = function() { return container; }, @@ -518,18 +660,18 @@ describe("HtmlReporter", function() { } }); - env.configure({failFast: true}); + env.configure({ failFast: true }); reporter.initialize(); reporter.jasmineDone({}); - var stopOnFailureUI = container.querySelector(".jasmine-fail-fast"); + var stopOnFailureUI = container.querySelector('.jasmine-fail-fast'); expect(stopOnFailureUI.checked).toBe(true); }); - it("should navigate and turn the setting on", function() { + it('should navigate and turn the setting on', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), navigationHandler = jasmine.createSpy('navigate'), getContainer = function() { return container; @@ -549,15 +691,15 @@ describe("HtmlReporter", function() { reporter.initialize(); reporter.jasmineDone({}); - var stopOnFailureUI = container.querySelector(".jasmine-fail-fast"); + var stopOnFailureUI = container.querySelector('.jasmine-fail-fast'); stopOnFailureUI.click(); expect(navigationHandler).toHaveBeenCalledWith('failFast', true); }); - it("should navigate and turn the setting off", function() { + it('should navigate and turn the setting off', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), navigationHandler = jasmine.createSpy('navigate'), getContainer = function() { return container; @@ -574,22 +716,22 @@ describe("HtmlReporter", function() { } }); - env.configure({failFast: true}); + env.configure({ failFast: true }); reporter.initialize(); reporter.jasmineDone({}); - var stopOnFailureUI = container.querySelector(".jasmine-fail-fast"); + var stopOnFailureUI = container.querySelector('.jasmine-fail-fast'); stopOnFailureUI.click(); expect(navigationHandler).toHaveBeenCalledWith('failFast', false); }); }); - describe("UI for throwing errors on expectation failures", function() { - it("should be unchecked if not throwing", function() { + describe('UI for throwing errors on expectation failures', function() { + it('should be unchecked if not throwing', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), getContainer = function() { return container; }, @@ -607,13 +749,13 @@ describe("HtmlReporter", function() { reporter.initialize(); reporter.jasmineDone({}); - var throwingExpectationsUI = container.querySelector(".jasmine-throw"); + var throwingExpectationsUI = container.querySelector('.jasmine-throw'); expect(throwingExpectationsUI.checked).toBe(false); }); - it("should be checked if throwing", function() { + it('should be checked if throwing', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), getContainer = function() { return container; }, @@ -628,18 +770,18 @@ describe("HtmlReporter", function() { } }); - env.configure({oneFailurePerSpec: true}); + env.configure({ oneFailurePerSpec: true }); reporter.initialize(); reporter.jasmineDone({}); - var throwingExpectationsUI = container.querySelector(".jasmine-throw"); + var throwingExpectationsUI = container.querySelector('.jasmine-throw'); expect(throwingExpectationsUI.checked).toBe(true); }); - it("should navigate and change the setting to on", function() { + it('should navigate and change the setting to on', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), navigateHandler = jasmine.createSpy('navigate'), getContainer = function() { return container; @@ -659,15 +801,15 @@ describe("HtmlReporter", function() { reporter.initialize(); reporter.jasmineDone({}); - var throwingExpectationsUI = container.querySelector(".jasmine-throw"); + var throwingExpectationsUI = container.querySelector('.jasmine-throw'); throwingExpectationsUI.click(); expect(navigateHandler).toHaveBeenCalledWith('throwFailures', true); }); - it("should navigate and change the setting to off", function() { + it('should navigate and change the setting to off', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), navigateHandler = jasmine.createSpy('navigate'), getContainer = function() { return container; @@ -684,21 +826,21 @@ describe("HtmlReporter", function() { } }); - env.configure({oneFailurePerSpec: true}); + env.configure({ oneFailurePerSpec: true }); reporter.initialize(); reporter.jasmineDone({}); - var throwingExpectationsUI = container.querySelector(".jasmine-throw"); + var throwingExpectationsUI = container.querySelector('.jasmine-throw'); throwingExpectationsUI.click(); expect(navigateHandler).toHaveBeenCalledWith('throwFailures', false); }); }); - describe("UI for hiding disabled specs", function() { - it("should be unchecked if not hiding disabled specs", function() { + describe('UI for hiding disabled specs', function() { + it('should be unchecked if not hiding disabled specs', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), getContainer = function() { return container; }, @@ -713,17 +855,17 @@ describe("HtmlReporter", function() { } }); - env.configure({hideDisabled: false}); + env.configure({ hideDisabled: false }); reporter.initialize(); reporter.jasmineDone({}); - var disabledUI = container.querySelector(".jasmine-disabled"); + var disabledUI = container.querySelector('.jasmine-disabled'); expect(disabledUI.checked).toBe(false); }); - it("should be checked if hiding disabled", function() { + it('should be checked if hiding disabled', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), getContainer = function() { return container; }, @@ -738,43 +880,17 @@ describe("HtmlReporter", function() { } }); - env.configure({hideDisabled: true}); + env.configure({ hideDisabled: true }); reporter.initialize(); reporter.jasmineDone({}); - var disabledUI = container.querySelector(".jasmine-disabled"); + var disabledUI = container.querySelector('.jasmine-disabled'); expect(disabledUI.checked).toBe(true); }); - it("should not display specs that have been disabled", function() { + it('should not display specs that have been disabled', function() { var env = new jasmineUnderTest.Env(), container = document.createElement('div'), - getContainer = function() {return container;}, - reporter = new jasmineUnderTest.HtmlReporter({ - env: env, - getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } - }); - - env.configure({hideDisabled: true}); - reporter.initialize(); - reporter.specDone({ - id: 789, - status: "excluded", - fullName: "symbols should have titles", - passedExpectations: [], - failedExpectations: [] - }); - - var specEl = container.querySelector('.jasmine-symbol-summary li'); - expect(specEl.getAttribute("class")).toEqual("jasmine-excluded-no-display"); - }); - }); - describe("UI for running tests in random order", function() { - it("should be unchecked if not randomizing", function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), getContainer = function() { return container; }, @@ -789,17 +905,51 @@ describe("HtmlReporter", function() { } }); - env.configure({random: false}); + env.configure({ hideDisabled: true }); + reporter.initialize(); + reporter.specDone({ + id: 789, + status: 'excluded', + fullName: 'symbols should have titles', + passedExpectations: [], + failedExpectations: [] + }); + + var specEl = container.querySelector('.jasmine-symbol-summary li'); + expect(specEl.getAttribute('class')).toEqual( + 'jasmine-excluded-no-display' + ); + }); + }); + describe('UI for running tests in random order', function() { + it('should be unchecked if not randomizing', function() { + var env = new jasmineUnderTest.Env(), + container = document.createElement('div'), + getContainer = function() { + return container; + }, + reporter = new jasmineUnderTest.HtmlReporter({ + env: env, + getContainer: getContainer, + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } + }); + + env.configure({ random: false }); reporter.initialize(); reporter.jasmineDone({}); - var randomUI = container.querySelector(".jasmine-random"); + var randomUI = container.querySelector('.jasmine-random'); expect(randomUI.checked).toBe(false); }); - it("should be checked if randomizing", function() { + it('should be checked if randomizing', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), getContainer = function() { return container; }, @@ -814,17 +964,17 @@ describe("HtmlReporter", function() { } }); - env.configure({random: true}); + env.configure({ random: true }); reporter.initialize(); reporter.jasmineDone({}); - var randomUI = container.querySelector(".jasmine-random"); + var randomUI = container.querySelector('.jasmine-random'); expect(randomUI.checked).toBe(true); }); - it("should navigate and change the setting to on", function() { + it('should navigate and change the setting to on', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), navigateHandler = jasmine.createSpy('navigate'), getContainer = function() { return container; @@ -841,19 +991,19 @@ describe("HtmlReporter", function() { } }); - env.configure({random: false}); + env.configure({ random: false }); reporter.initialize(); reporter.jasmineDone({}); - var randomUI = container.querySelector(".jasmine-random"); + var randomUI = container.querySelector('.jasmine-random'); randomUI.click(); expect(navigateHandler).toHaveBeenCalledWith('random', true); }); - it("should navigate and change the setting to off", function() { + it('should navigate and change the setting to off', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), navigateHandler = jasmine.createSpy('navigate'), getContainer = function() { return container; @@ -870,32 +1020,32 @@ describe("HtmlReporter", function() { } }); - env.configure({random: true}); + env.configure({ random: true }); reporter.initialize(); reporter.jasmineDone({}); - var randomUI = container.querySelector(".jasmine-random"); + var randomUI = container.querySelector('.jasmine-random'); randomUI.click(); expect(navigateHandler).toHaveBeenCalledWith('random', false); }); - it("should show the seed bar if randomizing", function() { + it('should show the seed bar if randomizing', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { - return container; + container = document.createElement('div'), + getContainer = function() { + return container; + }, + reporter = new jasmineUnderTest.HtmlReporter({ + env: env, + getContainer: getContainer, + createElement: function() { + return document.createElement.apply(document, arguments); }, - reporter = new jasmineUnderTest.HtmlReporter({ - env: env, - getContainer: getContainer, - createElement: function() { - return document.createElement.apply(document, arguments); - }, - createTextNode: function() { - return document.createTextNode.apply(document, arguments); - } - }); + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } + }); reporter.initialize(); reporter.jasmineDone({ @@ -905,132 +1055,154 @@ describe("HtmlReporter", function() { } }); - var seedBar = container.querySelector(".jasmine-seed-bar"); + var seedBar = container.querySelector('.jasmine-seed-bar'); expect(seedBar.textContent).toBe(', randomized with seed 424242'); - var seedLink = container.querySelector(".jasmine-seed-bar a"); + var seedLink = container.querySelector('.jasmine-seed-bar a'); expect(seedLink.getAttribute('href')).toBe('?seed=424242'); }); - it("should not show the current seed bar if not randomizing", function() { + it('should not show the current seed bar if not randomizing', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { - return container; + container = document.createElement('div'), + getContainer = function() { + return container; + }, + reporter = new jasmineUnderTest.HtmlReporter({ + env: env, + getContainer: getContainer, + createElement: function() { + return document.createElement.apply(document, arguments); }, - reporter = new jasmineUnderTest.HtmlReporter({ - env: env, - getContainer: getContainer, - createElement: function() { - return document.createElement.apply(document, arguments); - }, - createTextNode: function() { - return document.createTextNode.apply(document, arguments); - } - }); + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } + }); reporter.initialize(); reporter.jasmineDone({}); - var seedBar = container.querySelector(".jasmine-seed-bar"); + var seedBar = container.querySelector('.jasmine-seed-bar'); expect(seedBar).toBeNull(); }); - it("should include non-spec query params in the jasmine-skipped link when present", function(){ + it('should include non-spec query params in the jasmine-skipped link when present', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), + container = document.createElement('div'), reporter = new jasmineUnderTest.HtmlReporter({ env: env, - getContainer: function() { return container; }, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); }, - addToExistingQueryString: function(key, value) { return "?foo=bar&" + key + "=" + value; } + getContainer: function() { + return container; + }, + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + }, + addToExistingQueryString: function(key, value) { + return '?foo=bar&' + key + '=' + value; + } }); reporter.initialize(); reporter.jasmineStarted({ totalSpecsDefined: 1 }); reporter.jasmineDone({ order: { random: true } }); - var skippedLink = container.querySelector(".jasmine-skipped a"); + var skippedLink = container.querySelector('.jasmine-skipped a'); expect(skippedLink.getAttribute('href')).toEqual('?foo=bar&spec='); }); }); - describe("and all specs pass", function() { - var env, container, reporter; + describe('and all specs pass', function() { + var env, container; beforeEach(function() { env = new jasmineUnderTest.Env(); - container = document.createElement("div"); - var getContainer = function() { return container; }, + container = document.createElement('div'); + var getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); reporter.jasmineStarted({ totalSpecsDefined: 2 }); reporter.specDone({ id: 123, - description: "with a spec", - fullName: "A Suite with a spec", - status: "passed", - passedExpectations: [{passed: true}], + description: 'with a spec', + fullName: 'A Suite with a spec', + status: 'passed', + passedExpectations: [{ passed: true }], failedExpectations: [] }); reporter.specDone({ id: 124, - description: "with another spec", - fullName: "A Suite inner suite with another spec", - status: "passed", - passedExpectations: [{passed: true}], + description: 'with another spec', + fullName: 'A Suite inner suite with another spec', + status: 'passed', + passedExpectations: [{ passed: true }], failedExpectations: [] }); reporter.jasmineDone({}); }); - it("reports the specs counts", function() { - var alertBars = container.querySelectorAll(".jasmine-alert .jasmine-bar"); + it('reports the specs counts', function() { + var alertBars = container.querySelectorAll( + '.jasmine-alert .jasmine-bar' + ); expect(alertBars.length).toEqual(1); expect(alertBars[0].innerHTML).toMatch(/2 specs, 0 failures/); }); - it("reports no failure details", function() { - var specFailure = container.querySelector(".jasmine-failures"); + it('reports no failure details', function() { + var specFailure = container.querySelector('.jasmine-failures'); expect(specFailure.childNodes.length).toEqual(0); }); - it("reports no pending specs", function() { - var alertBar = container.querySelector(".jasmine-alert .jasmine-bar"); + it('reports no pending specs', function() { + var alertBar = container.querySelector('.jasmine-alert .jasmine-bar'); expect(alertBar.innerHTML).not.toMatch(/pending spec[s]/); }); }); - describe("and there are excluded specs", function() { + describe('and there are excluded specs', function() { var env, container, reporter, reporterConfig, specStatus; beforeEach(function() { env = new jasmineUnderTest.Env(); - container = document.createElement("div"); + container = document.createElement('div'); reporterConfig = { env: env, - getContainer: function() { return container; }, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + getContainer: function() { + return container; + }, + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }; specStatus = { id: 123, - description: "with a excluded spec", - fullName: "A Suite with a excluded spec", - status: "excluded", + description: 'with a excluded spec', + fullName: 'A Suite with a excluded spec', + status: 'excluded', passedExpectations: [], failedExpectations: [] }; }); - describe("when the specs are not filtered", function() { + describe('when the specs are not filtered', function() { beforeEach(function() { reporterConfig.filterSpecs = false; reporter = new jasmineUnderTest.HtmlReporter(reporterConfig); @@ -1041,14 +1213,14 @@ describe("HtmlReporter", function() { reporter.jasmineDone({}); }); - it("shows the excluded spec in the spec list", function() { - var specList = container.querySelector(".jasmine-summary"); + it('shows the excluded spec in the spec list', function() { + var specList = container.querySelector('.jasmine-summary'); expect(specList.innerHTML).toContain('with a excluded spec'); }); }); - describe("when the specs are filtered", function() { + describe('when the specs are filtered', function() { beforeEach(function() { reporterConfig.filterSpecs = true; reporter = new jasmineUnderTest.HtmlReporter(reporterConfig); @@ -1060,108 +1232,131 @@ describe("HtmlReporter", function() { }); it("doesn't show the excluded spec in the spec list", function() { - var specList = container.querySelector(".jasmine-summary"); + var specList = container.querySelector('.jasmine-summary'); expect(specList.innerHTML).toEqual(''); }); }); }); - describe("and there are pending specs", function() { + describe('and there are pending specs', function() { var env, container, reporter; beforeEach(function() { env = new jasmineUnderTest.Env(); - container = document.createElement("div"); - var getContainer = function() { return container; }; + container = document.createElement('div'); + var getContainer = function() { + return container; + }; reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); reporter.jasmineStarted({ totalSpecsDefined: 1 }); var specStatus = { id: 123, - description: "with a spec", - fullName: "A Suite with a spec", - status: "pending", + description: 'with a spec', + fullName: 'A Suite with a spec', + status: 'pending', passedExpectations: [], failedExpectations: [], - pendingReason: "my custom pending reason" + pendingReason: 'my custom pending reason' }; reporter.specStarted(specStatus); reporter.specDone(specStatus); reporter.jasmineDone({}); }); - it("reports the pending specs count", function() { - var alertBar = container.querySelector(".jasmine-alert .jasmine-bar"); + it('reports the pending specs count', function() { + var alertBar = container.querySelector('.jasmine-alert .jasmine-bar'); - expect(alertBar.innerHTML).toMatch(/1 spec, 0 failures, 1 pending spec/); + expect(alertBar.innerHTML).toMatch( + /1 spec, 0 failures, 1 pending spec/ + ); }); - it("reports no failure details", function() { - var specFailure = container.querySelector(".jasmine-failures"); + it('reports no failure details', function() { + var specFailure = container.querySelector('.jasmine-failures'); expect(specFailure.childNodes.length).toEqual(0); }); - it("displays the custom pending reason", function() { - var pendingDetails = container.querySelector(".jasmine-summary .jasmine-pending"); + it('displays the custom pending reason', function() { + var pendingDetails = container.querySelector( + '.jasmine-summary .jasmine-pending' + ); - expect(pendingDetails.innerHTML).toContain("my custom pending reason"); + expect(pendingDetails.innerHTML).toContain('my custom pending reason'); }); }); - describe("and some tests fail", function() { + describe('and some tests fail', function() { var env, container, reporter; beforeEach(function() { env = new jasmineUnderTest.Env(); - container = document.createElement("div"); - var getContainer = function() { return container; }; + container = document.createElement('div'); + var getContainer = function() { + return container; + }; reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); }, - addToExistingQueryString: function(key, value) { return "?foo=bar&" + key + "=" + value; } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + }, + addToExistingQueryString: function(key, value) { + return '?foo=bar&' + key + '=' + value; + } }); reporter.initialize(); reporter.jasmineStarted({ totalSpecsDefined: 1 }); reporter.suiteStarted({ id: 1, - description: "A suite" + description: 'A suite' }); reporter.suiteStarted({ id: 2, - description: "inner suite" + description: 'inner suite' }); - var passingSpecResult = {id: 123, status: "passed", passedExpectations: [{passed: true}], failedExpectations: []}; + var passingSpecResult = { + id: 123, + status: 'passed', + passedExpectations: [{ passed: true }], + failedExpectations: [] + }; reporter.specStarted(passingSpecResult); reporter.specDone(passingSpecResult); var failingSpecResult = { id: 124, - status: "failed", - description: "a failing spec", - fullName: "a suite inner suite a failing spec", + status: 'failed', + description: 'a failing spec', + fullName: 'a suite inner suite a failing spec', passedExpectations: [], failedExpectations: [ { - message: "a failure message", - stack: "a stack trace" + message: 'a failure message', + stack: 'a stack trace' } ] }; var passingSuiteResult = { id: 1, - description: "A suite" + description: 'A suite' }; var failingSuiteResult = { id: 2, @@ -1178,52 +1373,64 @@ describe("HtmlReporter", function() { reporter.jasmineDone({}); }); - it("reports the specs counts", function() { - var alertBar = container.querySelector(".jasmine-alert .jasmine-bar"); + it('reports the specs counts', function() { + var alertBar = container.querySelector('.jasmine-alert .jasmine-bar'); expect(alertBar.innerHTML).toMatch(/2 specs, 2 failure/); }); - it("reports failure messages and stack traces", function() { - var specFailures = container.querySelector(".jasmine-failures"); + it('reports failure messages and stack traces', function() { + var specFailures = container.querySelector('.jasmine-failures'); expect(specFailures.childNodes.length).toEqual(2); var specFailure = specFailures.childNodes[0]; - expect(specFailure.getAttribute("class")).toMatch(/jasmine-failed/); - expect(specFailure.getAttribute("class")).toMatch(/jasmine-spec-detail/); + expect(specFailure.getAttribute('class')).toMatch(/jasmine-failed/); + expect(specFailure.getAttribute('class')).toMatch( + /jasmine-spec-detail/ + ); var specDiv = specFailure.childNodes[0]; - expect(specDiv.getAttribute("class")).toEqual("jasmine-description"); + expect(specDiv.getAttribute('class')).toEqual('jasmine-description'); var message = specFailure.childNodes[1].childNodes[0]; - expect(message.getAttribute("class")).toEqual("jasmine-result-message"); - expect(message.innerHTML).toEqual("a failure message"); + expect(message.getAttribute('class')).toEqual('jasmine-result-message'); + expect(message.innerHTML).toEqual('a failure message'); var stackTrace = specFailure.childNodes[1].childNodes[1]; - expect(stackTrace.getAttribute("class")).toEqual("jasmine-stack-trace"); - expect(stackTrace.innerHTML).toEqual("a stack trace"); + expect(stackTrace.getAttribute('class')).toEqual('jasmine-stack-trace'); + expect(stackTrace.innerHTML).toEqual('a stack trace'); var suiteFailure = specFailures.childNodes[0]; - expect(suiteFailure.getAttribute("class")).toMatch(/jasmine-failed/); - expect(suiteFailure.getAttribute("class")).toMatch(/jasmine-spec-detail/); + expect(suiteFailure.getAttribute('class')).toMatch(/jasmine-failed/); + expect(suiteFailure.getAttribute('class')).toMatch( + /jasmine-spec-detail/ + ); var suiteDiv = suiteFailure.childNodes[0]; - expect(suiteDiv.getAttribute("class")).toEqual("jasmine-description"); + expect(suiteDiv.getAttribute('class')).toEqual('jasmine-description'); var suiteMessage = suiteFailure.childNodes[1].childNodes[0]; - expect(suiteMessage.getAttribute("class")).toEqual("jasmine-result-message"); - expect(suiteMessage.innerHTML).toEqual("a failure message"); + expect(suiteMessage.getAttribute('class')).toEqual( + 'jasmine-result-message' + ); + expect(suiteMessage.innerHTML).toEqual('a failure message'); var suiteStackTrace = suiteFailure.childNodes[1].childNodes[1]; - expect(suiteStackTrace.getAttribute("class")).toEqual("jasmine-stack-trace"); - expect(suiteStackTrace.innerHTML).toEqual("a stack trace"); + expect(suiteStackTrace.getAttribute('class')).toEqual( + 'jasmine-stack-trace' + ); + expect(suiteStackTrace.innerHTML).toEqual('a stack trace'); }); it('provides links to focus on a failure and each containing suite', function() { - var description = container.querySelector('.jasmine-failures .jasmine-description'); + var description = container.querySelector( + '.jasmine-failures .jasmine-description' + ); var links = description.querySelectorAll('a'); - expect(description.textContent).toEqual('A suite > inner suite > a failing spec'); + expect(description.textContent).toEqual( + 'A suite > inner suite > a failing spec' + ); expect(links.length).toEqual(3); expect(links[0].textContent).toEqual('A suite'); @@ -1231,40 +1438,52 @@ describe("HtmlReporter", function() { expect(links[0].getAttribute('href')).toMatch(/\?foo=bar&spec=A suite/); expect(links[1].textContent).toEqual('inner suite'); - expect(links[1].getAttribute('href')).toMatch(/\?foo=bar&spec=A suite inner suite/); + expect(links[1].getAttribute('href')).toMatch( + /\?foo=bar&spec=A suite inner suite/ + ); expect(links[2].textContent).toEqual('a failing spec'); - expect(links[2].getAttribute('href')).toMatch(/\?foo=bar&spec=a suite inner suite a failing spec/); + expect(links[2].getAttribute('href')).toMatch( + /\?foo=bar&spec=a suite inner suite a failing spec/ + ); }); - it("allows switching between failure details and the spec summary", function() { - var menuBar = container.querySelectorAll(".jasmine-bar")[1]; + it('allows switching between failure details and the spec summary', function() { + var menuBar = container.querySelectorAll('.jasmine-bar')[1]; - expect(menuBar.getAttribute("class")).not.toMatch(/hidden/); + expect(menuBar.getAttribute('class')).not.toMatch(/hidden/); var link = menuBar.querySelector('a'); - expect(link.innerHTML).toEqual("Failures"); - expect(link.getAttribute("href")).toEqual("#"); + expect(link.innerHTML).toEqual('Failures'); + expect(link.getAttribute('href')).toEqual('#'); }); it("sets the reporter to 'Failures List' mode", function() { - var reporterNode = container.querySelector(".jasmine_html-reporter"); - expect(reporterNode.getAttribute("class")).toMatch("jasmine-failure-list"); + var reporterNode = container.querySelector('.jasmine_html-reporter'); + expect(reporterNode.getAttribute('class')).toMatch( + 'jasmine-failure-list' + ); }); }); }); - describe("The overall result bar", function() { + describe('The overall result bar', function() { describe("When the jasmineDone event's overallStatus is 'passed'", function() { - it("has class jasmine-passed", function() { + it('has class jasmine-passed', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { return container; }, + container = document.createElement('div'), + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); @@ -1275,21 +1494,27 @@ describe("HtmlReporter", function() { failedExpectations: [] }); - var alertBar = container.querySelector(".jasmine-overall-result"); - expect(alertBar).toHaveClass("jasmine-passed"); + var alertBar = container.querySelector('.jasmine-overall-result'); + expect(alertBar).toHaveClass('jasmine-passed'); }); }); describe("When the jasmineDone event's overallStatus is 'failed'", function() { - it("has class jasmine-failed", function() { + it('has class jasmine-failed', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { return container; }, + container = document.createElement('div'), + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); @@ -1300,21 +1525,27 @@ describe("HtmlReporter", function() { failedExpectations: [] }); - var alertBar = container.querySelector(".jasmine-overall-result"); - expect(alertBar).toHaveClass("jasmine-failed"); + var alertBar = container.querySelector('.jasmine-overall-result'); + expect(alertBar).toHaveClass('jasmine-failed'); }); }); describe("When the jasmineDone event's overallStatus is 'incomplete'", function() { - it("has class jasmine-incomplete", function() { + it('has class jasmine-incomplete', function() { var env = new jasmineUnderTest.Env(), - container = document.createElement("div"), - getContainer = function() { return container; }, + container = document.createElement('div'), + getContainer = function() { + return container; + }, reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: getContainer, - createElement: function() { return document.createElement.apply(document, arguments); }, - createTextNode: function() { return document.createTextNode.apply(document, arguments); } + createElement: function() { + return document.createElement.apply(document, arguments); + }, + createTextNode: function() { + return document.createTextNode.apply(document, arguments); + } }); reporter.initialize(); @@ -1326,9 +1557,9 @@ describe("HtmlReporter", function() { failedExpectations: [] }); - var alertBar = container.querySelector(".jasmine-overall-result"); - expect(alertBar).toHaveClass("jasmine-incomplete"); - expect(alertBar.textContent).toContain("Incomplete: because nope"); + var alertBar = container.querySelector('.jasmine-overall-result'); + expect(alertBar).toHaveClass('jasmine-incomplete'); + expect(alertBar.textContent).toContain('Incomplete: because nope'); }); }); }); diff --git a/spec/html/HtmlSpecFilterSpec.js b/spec/html/HtmlSpecFilterSpec.js index 8a3387c0..887ee07c 100644 --- a/spec/html/HtmlSpecFilterSpec.js +++ b/spec/html/HtmlSpecFilterSpec.js @@ -1,18 +1,19 @@ -describe("jasmineUnderTest.HtmlSpecFilter", function() { - - it("should match when no string is provided", function() { +describe('jasmineUnderTest.HtmlSpecFilter', function() { + it('should match when no string is provided', function() { var specFilter = new jasmineUnderTest.HtmlSpecFilter(); - expect(specFilter.matches("foo")).toBe(true); - expect(specFilter.matches("*bar")).toBe(true); + expect(specFilter.matches('foo')).toBe(true); + expect(specFilter.matches('*bar')).toBe(true); }); - it("should only match the provided string", function() { + it('should only match the provided string', function() { var specFilter = new jasmineUnderTest.HtmlSpecFilter({ - filterString: function() { return "foo"; } + filterString: function() { + return 'foo'; + } }); - expect(specFilter.matches("foo")).toBe(true); - expect(specFilter.matches("bar")).toBe(false); + expect(specFilter.matches('foo')).toBe(true); + expect(specFilter.matches('bar')).toBe(false); }); }); diff --git a/spec/html/MatchersHtmlSpec.js b/spec/html/MatchersHtmlSpec.js index 39660c2b..75256f9d 100644 --- a/spec/html/MatchersHtmlSpec.js +++ b/spec/html/MatchersHtmlSpec.js @@ -1,12 +1,11 @@ -describe("MatchersSpec - HTML Dependent", function () { +describe('MatchersSpec - HTML Dependent', function() { var env, spec; beforeEach(function() { env = new jasmineUnderTest.Env(); - var suite = env.describe("suite", function() { - spec = env.it("spec", function() { - }); + env.describe('suite', function() { + spec = env.it('spec', function() {}); }); spyOn(spec, 'addExpectationResult'); @@ -28,10 +27,10 @@ describe("MatchersSpec - HTML Dependent", function () { return spec.addExpectationResult.mostRecentCall.args[1]; } - xit("toEqual with DOM nodes", function() { + xit('toEqual with DOM nodes', function() { var nodeA = document.createElement('div'); var nodeB = document.createElement('div'); - expect((match(nodeA).toEqual(nodeA))).toPass(); - expect((match(nodeA).toEqual(nodeB))).toFail(); + expect(match(nodeA).toEqual(nodeA)).toPass(); + expect(match(nodeA).toEqual(nodeB)).toFail(); }); }); diff --git a/spec/html/PrettyPrintHtmlSpec.js b/spec/html/PrettyPrintHtmlSpec.js index b4eb1158..77bb2bac 100644 --- a/spec/html/PrettyPrintHtmlSpec.js +++ b/spec/html/PrettyPrintHtmlSpec.js @@ -1,17 +1,19 @@ -describe("jasmineUnderTest.pp (HTML Dependent)", function () { - it("should stringify non-element HTML nodes properly", function() { - var sampleNode = document.createTextNode(""); - expect(jasmineUnderTest.pp(sampleNode)).toEqual("HTMLNode"); - expect(jasmineUnderTest.pp({foo: sampleNode})).toEqual("Object({ foo: HTMLNode })"); +describe('jasmineUnderTest.pp (HTML Dependent)', function() { + it('should stringify non-element HTML nodes properly', function() { + var sampleNode = document.createTextNode(''); + expect(jasmineUnderTest.pp(sampleNode)).toEqual('HTMLNode'); + expect(jasmineUnderTest.pp({ foo: sampleNode })).toEqual( + 'Object({ foo: HTMLNode })' + ); }); - it("should stringify empty HTML elements as their opening tags", function () { + it('should stringify empty HTML elements as their opening tags', function() { var simple = document.createElement('div'); simple.className = 'foo'; expect(jasmineUnderTest.pp(simple)).toEqual('
'); }); - it("should stringify non-empty HTML elements as tags with placeholders", function() { + it('should stringify non-empty HTML elements as tags with placeholders', function() { var nonEmpty = document.createElement('div'); nonEmpty.className = 'foo'; nonEmpty.innerHTML = '

Irrelevant

'; @@ -19,14 +21,20 @@ describe("jasmineUnderTest.pp (HTML Dependent)", function () { }); it("should print Firefox's wrapped native objects correctly", function() { - if(jasmine.getEnv().firefoxVersion) { - try { new CustomEvent(); } catch(e) { var err = e; }; + if (jasmine.getEnv().firefoxVersion) { + try { + new CustomEvent(); + } catch (e) { + var err = e; + } // Different versions of FF produce different error messages. - expect(jasmineUnderTest.pp(err)).toMatch(/Not enough arguments|CustomEvent requires at least 1 argument, but only 0 were passed/); + expect(jasmineUnderTest.pp(err)).toMatch( + /Not enough arguments|CustomEvent requires at least 1 argument, but only 0 were passed/ + ); } }); - it("should stringify HTML element with text and attributes", function() { + it('should stringify HTML element with text and attributes', function() { var el = document.createElement('div'); el.setAttribute('things', 'foo'); el.innerHTML = 'foo'; diff --git a/spec/html/QueryStringSpec.js b/spec/html/QueryStringSpec.js index 2b9c8cd6..de2f5721 100644 --- a/spec/html/QueryStringSpec.js +++ b/spec/html/QueryStringSpec.js @@ -1,28 +1,31 @@ -describe("QueryString", function() { - - describe("#navigateWithNewParam", function() { - it("sets the query string to include the given key/value pair", function() { +describe('QueryString', function() { + describe('#navigateWithNewParam', function() { + it('sets the query string to include the given key/value pair', function() { var windowLocation = { - search: "" + search: '' }, queryString = new jasmineUnderTest.QueryString({ - getWindowLocation: function() { return windowLocation } + getWindowLocation: function() { + return windowLocation; + } }); - queryString.navigateWithNewParam("foo", "bar baz"); + queryString.navigateWithNewParam('foo', 'bar baz'); expect(windowLocation.search).toMatch(/foo=bar%20baz/); }); - it("leaves existing params alone", function() { + it('leaves existing params alone', function() { var windowLocation = { - search: "?foo=bar" - }, - queryString = new jasmineUnderTest.QueryString({ - getWindowLocation: function() { return windowLocation } - }); + search: '?foo=bar' + }, + queryString = new jasmineUnderTest.QueryString({ + getWindowLocation: function() { + return windowLocation; + } + }); - queryString.navigateWithNewParam("baz", "quux"); + queryString.navigateWithNewParam('baz', 'quux'); expect(windowLocation.search).toMatch(/foo=bar/); expect(windowLocation.search).toMatch(/baz=quux/); @@ -30,43 +33,48 @@ describe("QueryString", function() { }); describe('#fullStringWithNewParam', function() { - it("gets the query string including the given key/value pair", function() { + it('gets the query string including the given key/value pair', function() { var windowLocation = { - search: "?foo=bar" - }, - queryString = new jasmineUnderTest.QueryString({ - getWindowLocation: function() { return windowLocation } - }); + search: '?foo=bar' + }, + queryString = new jasmineUnderTest.QueryString({ + getWindowLocation: function() { + return windowLocation; + } + }); - var result = queryString.fullStringWithNewParam("baz", "quux"); + var result = queryString.fullStringWithNewParam('baz', 'quux'); expect(result).toMatch(/foo=bar/); expect(result).toMatch(/baz=quux/); }); }); - describe("#getParam", function() { - - it("returns the value of the requested key", function() { + describe('#getParam', function() { + it('returns the value of the requested key', function() { var windowLocation = { - search: "?baz=quux%20corge" + search: '?baz=quux%20corge' }, queryString = new jasmineUnderTest.QueryString({ - getWindowLocation: function() { return windowLocation } + getWindowLocation: function() { + return windowLocation; + } }); - expect(queryString.getParam("baz")).toEqual("quux corge"); + expect(queryString.getParam('baz')).toEqual('quux corge'); }); - it("returns null if the key is not present", function() { + it('returns null if the key is not present', function() { var windowLocation = { - search: "" + search: '' }, queryString = new jasmineUnderTest.QueryString({ - getWindowLocation: function() { return windowLocation } + getWindowLocation: function() { + return windowLocation; + } }); - expect(queryString.getParam("baz")).toBeFalsy(); + expect(queryString.getParam('baz')).toBeFalsy(); }); }); }); diff --git a/spec/html/ResultsNodeSpec.js b/spec/html/ResultsNodeSpec.js index 34ed589d..0a57a8fc 100644 --- a/spec/html/ResultsNodeSpec.js +++ b/spec/html/ResultsNodeSpec.js @@ -1,61 +1,61 @@ -describe("ResultsNode", function() { - it("wraps a result", function() { +describe('ResultsNode', function() { + it('wraps a result', function() { var fakeResult = { id: 123, - message: "foo" + message: 'foo' }, - node = new jasmineUnderTest.ResultsNode(fakeResult, "suite", null); + node = new jasmineUnderTest.ResultsNode(fakeResult, 'suite', null); expect(node.result).toBe(fakeResult); - expect(node.type).toEqual("suite"); + expect(node.type).toEqual('suite'); }); - it("can add children with a type", function() { + it('can add children with a type', function() { var fakeResult = { id: 123, - message: "foo" + message: 'foo' }, fakeChildResult = { id: 456, - message: "bar" + message: 'bar' }, - node = new jasmineUnderTest.ResultsNode(fakeResult, "suite", null); + node = new jasmineUnderTest.ResultsNode(fakeResult, 'suite', null); - node.addChild(fakeChildResult, "spec"); + node.addChild(fakeChildResult, 'spec'); expect(node.children.length).toEqual(1); expect(node.children[0].result).toEqual(fakeChildResult); - expect(node.children[0].type).toEqual("spec"); + expect(node.children[0].type).toEqual('spec'); }); - it("has a pointer back to its parent ResultNode", function() { + it('has a pointer back to its parent ResultNode', function() { var fakeResult = { id: 123, - message: "foo" + message: 'foo' }, fakeChildResult = { id: 456, - message: "bar" + message: 'bar' }, - node = new jasmineUnderTest.ResultsNode(fakeResult, "suite", null); + node = new jasmineUnderTest.ResultsNode(fakeResult, 'suite', null); - node.addChild(fakeChildResult, "spec"); + node.addChild(fakeChildResult, 'spec'); expect(node.children[0].parent).toBe(node); }); - it("can provide the most recent child", function() { + it('can provide the most recent child', function() { var fakeResult = { id: 123, - message: "foo" + message: 'foo' }, fakeChildResult = { id: 456, - message: "bar" + message: 'bar' }, - node = new jasmineUnderTest.ResultsNode(fakeResult, "suite", null); + node = new jasmineUnderTest.ResultsNode(fakeResult, 'suite', null); - node.addChild(fakeChildResult, "spec"); + node.addChild(fakeChildResult, 'spec'); expect(node.last()).toBe(node.children[node.children.length - 1]); }); diff --git a/spec/html/SpyRegistryHtmlSpec.js b/spec/html/SpyRegistryHtmlSpec.js index c51308b8..e43e9eeb 100644 --- a/spec/html/SpyRegistryHtmlSpec.js +++ b/spec/html/SpyRegistryHtmlSpec.js @@ -8,7 +8,9 @@ describe('Spy Registry browser-specific behavior', function() { var spies = [], spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() { return spies; }, + currentSpies: function() { + return spies; + }, createSpy: createSpy, global: window }), @@ -28,7 +30,7 @@ describe('Spy Registry browser-specific behavior', function() { try { descriptor = Object.getOwnPropertyDescriptor(window, 'onerror'); - } catch(e) { + } catch (e) { // IE 8 doesn't support `definePropery` on non-DOM nodes } diff --git a/spec/npmPackage/npmPackageSpec.js b/spec/npmPackage/npmPackageSpec.js index 3460f539..5248d88c 100644 --- a/spec/npmPackage/npmPackageSpec.js +++ b/spec/npmPackage/npmPackageSpec.js @@ -1,19 +1,24 @@ describe('npm package', function() { var path = require('path'), - temp = require('temp').track(), - fs = require('fs'); + temp = require('temp').track(), + fs = require('fs'); beforeAll(function() { var shell = require('shelljs'), - pack = shell.exec('npm pack', { silent: true}); + pack = shell.exec('npm pack', { silent: true }); this.tarball = pack.stdout.split('\n')[0]; this.tmpDir = temp.mkdirSync(); // automatically deleted on exit - var untar = shell.exec('tar -xzf ' + this.tarball + ' -C ' + this.tmpDir, { silent: true }); + var untar = shell.exec('tar -xzf ' + this.tarball + ' -C ' + this.tmpDir, { + silent: true + }); expect(untar.code).toBe(0); - this.packagedCore = require(path.join(this.tmpDir, 'package/lib/jasmine-core.js')); + this.packagedCore = require(path.join( + this.tmpDir, + 'package/lib/jasmine-core.js' + )); }); beforeEach(function() { @@ -32,25 +37,19 @@ describe('npm package', function() { }); afterAll(function() { - var cleanup = function (parent, fileOrFolder) { - var fullPath = path.join(parent, fileOrFolder); - if (fs.statSync(fullPath).isFile()) { - fs.unlinkSync(fullPath); - } else { - fs.readdirSync(fullPath).forEach(cleanup.bind(null, fullPath)); - fs.rmdirSync(fullPath); - } - }; - fs.unlinkSync(this.tarball); }); it('has a root path', function() { - expect(this.packagedCore.files.path).toEqual(fs.realpathSync(path.resolve(this.tmpDir, 'package/lib/jasmine-core'))); + expect(this.packagedCore.files.path).toEqual( + fs.realpathSync(path.resolve(this.tmpDir, 'package/lib/jasmine-core')) + ); }); it('has a bootDir', function() { - expect(this.packagedCore.files.bootDir).toEqual(fs.realpathSync(path.resolve(this.tmpDir, 'package/lib/jasmine-core'))); + expect(this.packagedCore.files.bootDir).toEqual( + fs.realpathSync(path.resolve(this.tmpDir, 'package/lib/jasmine-core')) + ); }); it('has jsFiles', function() { @@ -91,7 +90,9 @@ describe('npm package', function() { }); it('has an imagesDir', function() { - expect(this.packagedCore.files.imagesDir).toEqual(fs.realpathSync(path.resolve(this.tmpDir, 'package/images'))); + expect(this.packagedCore.files.imagesDir).toEqual( + fs.realpathSync(path.resolve(this.tmpDir, 'package/images')) + ); var images = fs.readdirSync(path.resolve(this.tmpDir, 'package/images')); expect(images).toContain('jasmine-horizontal.png'); diff --git a/spec/performance/large_object_test.js b/spec/performance/large_object_test.js index a59bb105..65b28863 100644 --- a/spec/performance/large_object_test.js +++ b/spec/performance/large_object_test.js @@ -1,4 +1,4 @@ -describe('Printing a big object', function(){ +describe('Printing a big object', function() { var bigObject; function rand(upper) { return Math.round(upper * Math.random()); @@ -11,26 +11,24 @@ describe('Printing a big object', function(){ var decide = rand(2); switch (decide) { case 0: - object["cycle" + i] = object; - break; + object['cycle' + i] = object; + break; case 1: - object["number" + i] = rand(100); - break; + object['number' + i] = rand(100); + break; case 2: if (level < 3) { - object["nesting" + i] = generateObject(level + 1); - } - break; + object['nesting' + i] = generateObject(level + 1); + } + break; } - } return object; } - it('takes a reasonable amount of time', function(){ + it('takes a reasonable amount of time', function() { bigObject = generateObject(0); expect(jasmineUnderTest.pp(bigObject)).toMatch(/cycle/); }); }); - diff --git a/spec/performance/performance_test.js b/spec/performance/performance_test.js index 0c97d20c..a9139bdd 100644 --- a/spec/performance/performance_test.js +++ b/spec/performance/performance_test.js @@ -1,9 +1,9 @@ -describe("performance", function() { +describe('performance', function() { for (var i = 0; i < 10000; i++) { - it("should pass", function() { + it('should pass', function() { expect(true).toBe(true); }); - it("should fail", function() { + it('should fail', function() { expect(true).toBe(false); }); } diff --git a/src/core/CallTracker.js b/src/core/CallTracker.js index 9a26b38b..e856d2ad 100644 --- a/src/core/CallTracker.js +++ b/src/core/CallTracker.js @@ -1,5 +1,4 @@ getJasmineRequireObj().CallTracker = function(j$) { - /** * @namespace Spy#calls */ @@ -8,7 +7,7 @@ getJasmineRequireObj().CallTracker = function(j$) { var opts = {}; this.track = function(context) { - if(opts.cloneArgs) { + if (opts.cloneArgs) { context.args = j$.util.cloneArgs(context.args); } calls.push(context); @@ -64,7 +63,7 @@ getJasmineRequireObj().CallTracker = function(j$) { */ this.allArgs = function() { var callArgs = []; - for(var i = 0; i < calls.length; i++) { + for (var i = 0; i < calls.length; i++) { callArgs.push(calls[i].args); } @@ -108,7 +107,6 @@ getJasmineRequireObj().CallTracker = function(j$) { this.saveArgumentsByValue = function() { opts.cloneArgs = true; }; - } return CallTracker; diff --git a/src/core/ClearStack.js b/src/core/ClearStack.js index df5d8753..b80de2b8 100644 --- a/src/core/ClearStack.js +++ b/src/core/ClearStack.js @@ -3,8 +3,8 @@ getJasmineRequireObj().clearStack = function(j$) { function messageChannelImpl(global, setTimeout) { var channel = new global.MessageChannel(), - head = {}, - tail = head; + head = {}, + tail = head; var taskRunning = false; channel.port1.onmessage = function() { @@ -42,7 +42,7 @@ getJasmineRequireObj().clearStack = function(j$) { var currentCallCount = 0; var realSetTimeout = global.setTimeout; var setTimeoutImpl = function clearStack(fn) { - Function.prototype.apply.apply(realSetTimeout, [global, [fn, 0]]); + Function.prototype.apply.apply(realSetTimeout, [global, [fn, 0]]); }; if (j$.isFunction_(global.setImmediate)) { diff --git a/src/core/Clock.js b/src/core/Clock.js index f80244e0..370eca18 100644 --- a/src/core/Clock.js +++ b/src/core/Clock.js @@ -1,7 +1,9 @@ getJasmineRequireObj().Clock = function() { - /* global process */ - var NODE_JS = typeof process !== 'undefined' && process.versions && typeof process.versions.node === 'string'; + var NODE_JS = + typeof process !== 'undefined' && + process.versions && + typeof process.versions.node === 'string'; /** * _Note:_ Do not construct this directly, Jasmine will make one during booting. You can get the current clock with {@link jasmine.clock}. @@ -35,8 +37,10 @@ getJasmineRequireObj().Clock = function() { * @return {Clock} */ self.install = function() { - if(!originalTimingFunctionsIntact()) { - throw new Error('Jasmine Clock was unable to install over custom global timer functions. Is the clock already installed?'); + if (!originalTimingFunctionsIntact()) { + throw new Error( + 'Jasmine Clock was unable to install over custom global timer functions. Is the clock already installed?' + ); } replace(global, fakeTimingFunctions); timer = fakeTimingFunctions; @@ -88,11 +92,17 @@ getJasmineRequireObj().Clock = function() { }; self.setTimeout = function(fn, delay, params) { - return Function.prototype.apply.apply(timer.setTimeout, [global, arguments]); + return Function.prototype.apply.apply(timer.setTimeout, [ + global, + arguments + ]); }; self.setInterval = function(fn, delay, params) { - return Function.prototype.apply.apply(timer.setInterval, [global, arguments]); + return Function.prototype.apply.apply(timer.setInterval, [ + global, + arguments + ]); }; self.clearTimeout = function(id) { @@ -111,19 +121,25 @@ getJasmineRequireObj().Clock = function() { */ self.tick = function(millis) { if (installed) { - delayedFunctionScheduler.tick(millis, function(millis) { mockDate.tick(millis); }); + delayedFunctionScheduler.tick(millis, function(millis) { + mockDate.tick(millis); + }); } else { - throw new Error('Mock clock is not installed, use jasmine.clock().install()'); + throw new Error( + 'Mock clock is not installed, use jasmine.clock().install()' + ); } }; return self; function originalTimingFunctionsIntact() { - return global.setTimeout === realTimingFunctions.setTimeout && + return ( + global.setTimeout === realTimingFunctions.setTimeout && global.clearTimeout === realTimingFunctions.clearTimeout && global.setInterval === realTimingFunctions.setInterval && - global.clearInterval === realTimingFunctions.clearInterval; + global.clearInterval === realTimingFunctions.clearInterval + ); } function replace(dest, source) { @@ -134,12 +150,22 @@ getJasmineRequireObj().Clock = function() { function setTimeout(fn, delay) { if (!NODE_JS) { - return delayedFunctionScheduler.scheduleFunction(fn, delay, argSlice(arguments, 2)); + return delayedFunctionScheduler.scheduleFunction( + fn, + delay, + argSlice(arguments, 2) + ); } var timeout = new FakeTimeout(); - delayedFunctionScheduler.scheduleFunction(fn, delay, argSlice(arguments, 2), false, timeout); + delayedFunctionScheduler.scheduleFunction( + fn, + delay, + argSlice(arguments, 2), + false, + timeout + ); return timeout; } @@ -150,12 +176,23 @@ getJasmineRequireObj().Clock = function() { function setInterval(fn, interval) { if (!NODE_JS) { - return delayedFunctionScheduler.scheduleFunction(fn, interval, argSlice(arguments, 2), true); + return delayedFunctionScheduler.scheduleFunction( + fn, + interval, + argSlice(arguments, 2), + true + ); } var timeout = new FakeTimeout(); - delayedFunctionScheduler.scheduleFunction(fn, interval, argSlice(arguments, 2), true, timeout); + delayedFunctionScheduler.scheduleFunction( + fn, + interval, + argSlice(arguments, 2), + true, + timeout + ); return timeout; } @@ -174,11 +211,11 @@ getJasmineRequireObj().Clock = function() { */ function FakeTimeout() {} - FakeTimeout.prototype.ref = function () { + FakeTimeout.prototype.ref = function() { return this; }; - FakeTimeout.prototype.unref = function () { + FakeTimeout.prototype.unref = function() { return this; }; diff --git a/src/core/DelayedFunctionScheduler.js b/src/core/DelayedFunctionScheduler.js index f41e7ada..eb84c48a 100644 --- a/src/core/DelayedFunctionScheduler.js +++ b/src/core/DelayedFunctionScheduler.js @@ -15,11 +15,20 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { currentTime = endTime; }; - self.scheduleFunction = function(funcToCall, millis, params, recurring, timeoutKey, runAtMillis) { + self.scheduleFunction = function( + funcToCall, + millis, + params, + recurring, + timeoutKey, + runAtMillis + ) { var f; - if (typeof(funcToCall) === 'string') { + if (typeof funcToCall === 'string') { /* jshint evil: true */ - f = function() { return eval(funcToCall); }; + f = function() { + return eval(funcToCall); + }; /* jshint evil: false */ } else { f = funcToCall; @@ -27,7 +36,7 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { millis = millis || 0; timeoutKey = timeoutKey || ++delayedFnCount; - runAtMillis = runAtMillis || (currentTime + millis); + runAtMillis = runAtMillis || currentTime + millis; var funcToSchedule = { runAtMillis: runAtMillis, @@ -43,7 +52,7 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { } else { scheduledFunctions[runAtMillis] = [funcToSchedule]; scheduledLookup.push(runAtMillis); - scheduledLookup.sort(function (a, b) { + scheduledLookup.sort(function(a, b) { return a - b; }); } @@ -56,7 +65,7 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { for (var runAtMillis in scheduledFunctions) { var funcs = scheduledFunctions[runAtMillis]; - var i = indexOfFirstToPass(funcs, function (func) { + var i = indexOfFirstToPass(funcs, function(func) { return func.timeoutKey === timeoutKey; }); @@ -92,7 +101,7 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { function deleteFromLookup(key) { var value = Number(key); - var i = indexOfFirstToPass(scheduledLookup, function (millis) { + var i = indexOfFirstToPass(scheduledLookup, function(millis) { return millis === value; }); @@ -102,12 +111,14 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { } function reschedule(scheduledFn) { - self.scheduleFunction(scheduledFn.funcToCall, + self.scheduleFunction( + scheduledFn.funcToCall, scheduledFn.millis, scheduledFn.params, true, scheduledFn.timeoutKey, - scheduledFn.runAtMillis + scheduledFn.millis); + scheduledFn.runAtMillis + scheduledFn.millis + ); } function forEachFunction(funcsToRun, callback) { @@ -148,11 +159,13 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { funcToRun.funcToCall.apply(null, funcToRun.params || []); }); deletedKeys = []; - } while (scheduledLookup.length > 0 && - // checking first if we're out of time prevents setTimeout(0) - // scheduled in a funcToRun from forcing an extra iteration - currentTime !== endTime && - scheduledLookup[0] <= endTime); + } while ( + scheduledLookup.length > 0 && + // checking first if we're out of time prevents setTimeout(0) + // scheduled in a funcToRun from forcing an extra iteration + currentTime !== endTime && + scheduledLookup[0] <= endTime + ); // ran out of functions to call, but still time left on the clock if (currentTime !== endTime) { diff --git a/src/core/Env.js b/src/core/Env.js index b0c09040..18924dcd 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -17,7 +17,13 @@ getJasmineRequireObj().Env = function(j$) { var realSetTimeout = global.setTimeout; var realClearTimeout = global.clearTimeout; var clearStack = j$.getClearStack(global); - this.clock = new j$.Clock(global, function () { return new j$.DelayedFunctionScheduler(); }, new j$.MockDate(global)); + this.clock = new j$.Clock( + global, + function() { + return new j$.DelayedFunctionScheduler(); + }, + new j$.MockDate(global) + ); var runnableResources = {}; @@ -110,7 +116,13 @@ getJasmineRequireObj().Env = function(j$) { if (!options.suppressLoadErrors) { installGlobalErrors(); - globalErrors.pushListener(function(message, filename, lineno, colNo, err) { + globalErrors.pushListener(function( + message, + filename, + lineno, + colNo, + err + ) { topSuite.result.failedExpectations.push({ passed: false, globalErrorType: 'load', @@ -154,11 +166,15 @@ getJasmineRequireObj().Env = function(j$) { } if (configuration.hasOwnProperty('Promise')) { - if (typeof configuration.Promise.resolve === 'function' && - typeof configuration.Promise.reject === 'function') { + if ( + typeof configuration.Promise.resolve === 'function' && + typeof configuration.Promise.reject === 'function' + ) { customPromise = configuration.Promise; } else { - throw new Error('Custom promise library missing `resolve`/`reject` functions'); + throw new Error( + 'Custom promise library missing `resolve`/`reject` functions' + ); } } }; @@ -179,34 +195,47 @@ getJasmineRequireObj().Env = function(j$) { Object.defineProperty(this, 'specFilter', { get: function() { - self.deprecated('Getting specFilter directly from Env is deprecated and will be removed in a future version of Jasmine, please check the specFilter option from `configuration`'); + self.deprecated( + 'Getting specFilter directly from Env is deprecated and will be removed in a future version of Jasmine, please check the specFilter option from `configuration`' + ); return config.specFilter; }, set: function(val) { - self.deprecated('Setting specFilter directly on Env is deprecated and will be removed in a future version of Jasmine, please use the specFilter option in `configure`'); + self.deprecated( + 'Setting specFilter directly on Env is deprecated and will be removed in a future version of Jasmine, please use the specFilter option in `configure`' + ); config.specFilter = val; } }); this.addSpyStrategy = function(name, fn) { - if(!currentRunnable()) { - throw new Error('Custom spy strategies must be added in a before function or a spec'); + if (!currentRunnable()) { + throw new Error( + 'Custom spy strategies must be added in a before function or a spec' + ); } runnableResources[currentRunnable().id].customSpyStrategies[name] = fn; }; this.addCustomEqualityTester = function(tester) { - if(!currentRunnable()) { - throw new Error('Custom Equalities must be added in a before function or a spec'); + if (!currentRunnable()) { + throw new Error( + 'Custom Equalities must be added in a before function or a spec' + ); } - runnableResources[currentRunnable().id].customEqualityTesters.push(tester); + runnableResources[currentRunnable().id].customEqualityTesters.push( + tester + ); }; this.addMatchers = function(matchersToAdd) { - if(!currentRunnable()) { - throw new Error('Matchers must be added in a before function or a spec'); + if (!currentRunnable()) { + throw new Error( + 'Matchers must be added in a before function or a spec' + ); } - var customMatchers = runnableResources[currentRunnable().id].customMatchers; + var customMatchers = + runnableResources[currentRunnable().id].customMatchers; for (var matcherName in matchersToAdd) { customMatchers[matcherName] = matchersToAdd[matcherName]; } @@ -253,19 +282,28 @@ getJasmineRequireObj().Env = function(j$) { }; var defaultResourcesForRunnable = function(id, parentRunnableId) { - var resources = {spies: [], customEqualityTesters: [], customMatchers: {}, customSpyStrategies: {}}; + var resources = { + spies: [], + customEqualityTesters: [], + customMatchers: {}, + customSpyStrategies: {} + }; - if(runnableResources[parentRunnableId]) { - resources.customEqualityTesters = j$.util.clone(runnableResources[parentRunnableId].customEqualityTesters); - resources.customMatchers = j$.util.clone(runnableResources[parentRunnableId].customMatchers); + if (runnableResources[parentRunnableId]) { + resources.customEqualityTesters = j$.util.clone( + runnableResources[parentRunnableId].customEqualityTesters + ); + resources.customMatchers = j$.util.clone( + runnableResources[parentRunnableId].customMatchers + ); } runnableResources[id] = resources; }; var clearResourcesForRunnable = function(id) { - spyRegistry.clearSpies(); - delete runnableResources[id]; + spyRegistry.clearSpies(); + delete runnableResources[id]; }; var beforeAndAfterFns = function(suite) { @@ -273,7 +311,7 @@ getJasmineRequireObj().Env = function(j$) { var befores = [], afters = []; - while(suite) { + while (suite) { befores = befores.concat(suite.beforeFns); afters = afters.concat(suite.afterFns); @@ -289,7 +327,7 @@ getJasmineRequireObj().Env = function(j$) { var getSpecName = function(spec, suite) { var fullName = [spec.description], - suiteFullName = suite.getFullName(); + suiteFullName = suite.getFullName(); if (suiteFullName !== '') { fullName.unshift(suiteFullName); @@ -299,13 +337,13 @@ getJasmineRequireObj().Env = function(j$) { // TODO: we may just be able to pass in the fn instead of wrapping here var buildExpectationResult = j$.buildExpectationResult, - exceptionFormatter = new j$.ExceptionFormatter(), - expectationResultFactory = function(attrs) { - attrs.messageFormatter = exceptionFormatter.message; - attrs.stackFormatter = exceptionFormatter.stack; + exceptionFormatter = new j$.ExceptionFormatter(), + expectationResultFactory = function(attrs) { + attrs.messageFormatter = exceptionFormatter.message; + attrs.stackFormatter = exceptionFormatter.stack; - return buildExpectationResult(attrs); - }; + return buildExpectationResult(attrs); + }; /** * Sets whether Jasmine should throw an Error when an expectation fails. @@ -316,12 +354,16 @@ getJasmineRequireObj().Env = function(j$) { * @deprecated Use the `oneFailurePerSpec` option with {@link Env#configure} */ this.throwOnExpectationFailure = function(value) { - this.deprecated('Setting throwOnExpectationFailure directly on Env is deprecated and will be removed in a future version of Jasmine, please use the oneFailurePerSpec option in `configure`'); - this.configure({oneFailurePerSpec: !!value}); + this.deprecated( + 'Setting throwOnExpectationFailure directly on Env is deprecated and will be removed in a future version of Jasmine, please use the oneFailurePerSpec option in `configure`' + ); + this.configure({ oneFailurePerSpec: !!value }); }; this.throwingExpectationFailures = function() { - this.deprecated('Getting throwingExpectationFailures directly from Env is deprecated and will be removed in a future version of Jasmine, please check the oneFailurePerSpec option from `configuration`'); + this.deprecated( + 'Getting throwingExpectationFailures directly from Env is deprecated and will be removed in a future version of Jasmine, please check the oneFailurePerSpec option from `configuration`' + ); return config.oneFailurePerSpec; }; @@ -333,12 +375,16 @@ getJasmineRequireObj().Env = function(j$) { * @deprecated Use the `failFast` option with {@link Env#configure} */ this.stopOnSpecFailure = function(value) { - this.deprecated('Setting stopOnSpecFailure directly is deprecated and will be removed in a future version of Jasmine, please use the failFast option in `configure`'); - this.configure({failFast: !!value}); + this.deprecated( + 'Setting stopOnSpecFailure directly is deprecated and will be removed in a future version of Jasmine, please use the failFast option in `configure`' + ); + this.configure({ failFast: !!value }); }; this.stoppingOnSpecFailure = function() { - this.deprecated('Getting stoppingOnSpecFailure directly from Env is deprecated and will be removed in a future version of Jasmine, please check the failFast option from `configuration`'); + this.deprecated( + 'Getting stoppingOnSpecFailure directly from Env is deprecated and will be removed in a future version of Jasmine, please check the failFast option from `configuration`' + ); return config.failFast; }; @@ -350,12 +396,16 @@ getJasmineRequireObj().Env = function(j$) { * @deprecated Use the `random` option with {@link Env#configure} */ this.randomizeTests = function(value) { - this.deprecated('Setting randomizeTests directly is deprecated and will be removed in a future version of Jasmine, please use the random option in `configure`'); + this.deprecated( + 'Setting randomizeTests directly is deprecated and will be removed in a future version of Jasmine, please use the random option in `configure`' + ); config.random = !!value; }; this.randomTests = function() { - this.deprecated('Getting randomTests directly from Env is deprecated and will be removed in a future version of Jasmine, please check the random option from `configuration`'); + this.deprecated( + 'Getting randomTests directly from Env is deprecated and will be removed in a future version of Jasmine, please check the random option from `configuration`' + ); return config.random; }; @@ -367,7 +417,9 @@ getJasmineRequireObj().Env = function(j$) { * @deprecated Use the `seed` option with {@link Env#configure} */ this.seed = function(value) { - this.deprecated('Setting seed directly is deprecated and will be removed in a future version of Jasmine, please use the seed option in `configure`'); + this.deprecated( + 'Setting seed directly is deprecated and will be removed in a future version of Jasmine, please use the seed option in `configure`' + ); if (value) { config.seed = value; } @@ -375,7 +427,9 @@ getJasmineRequireObj().Env = function(j$) { }; this.hidingDisabled = function(value) { - this.deprecated('Getting hidingDisabled directly from Env is deprecated and will be removed in a future version of Jasmine, please check the hideDisabled option from `configuration`'); + this.deprecated( + 'Getting hidingDisabled directly from Env is deprecated and will be removed in a future version of Jasmine, please check the hideDisabled option from `configuration`' + ); return config.hideDisabled; }; @@ -384,14 +438,19 @@ getJasmineRequireObj().Env = function(j$) { * @function */ this.hideDisabled = function(value) { - this.deprecated('Setting hideDisabled directly is deprecated and will be removed in a future version of Jasmine, please use the hideDisabled option in `configure`'); + this.deprecated( + 'Setting hideDisabled directly is deprecated and will be removed in a future version of Jasmine, please use the hideDisabled option in `configure`' + ); config.hideDisabled = !!value; }; this.deprecated = function(deprecation) { var runnable = currentRunnable() || topSuite; runnable.addDeprecationWarning(deprecation); - if(typeof console !== 'undefined' && typeof console.error === 'function') { + if ( + typeof console !== 'undefined' && + typeof console.error === 'function' + ) { console.error('DEPRECATION:', deprecation); } }; @@ -404,13 +463,18 @@ getJasmineRequireObj().Env = function(j$) { failFast = config.failFast; } options.clearStack = options.clearStack || clearStack; - options.timeout = {setTimeout: realSetTimeout, clearTimeout: realClearTimeout}; + options.timeout = { + setTimeout: realSetTimeout, + clearTimeout: realClearTimeout + }; options.fail = self.fail; options.globalErrors = globalErrors; options.completeOnFirstError = failFast; - options.onException = options.onException || function(e) { - (currentRunnable() || topSuite).onException(e); - }; + options.onException = + options.onException || + function(e) { + (currentRunnable() || topSuite).onException(e); + }; options.deprecated = self.deprecated; new j$.QueueRunner(options).execute(args); @@ -436,78 +500,80 @@ getJasmineRequireObj().Env = function(j$) { * @interface Reporter * @see custom_reporter */ - var reporter = new j$.ReportDispatcher([ - /** - * `jasmineStarted` is called after all of the specs have been loaded, but just before execution starts. - * @function - * @name Reporter#jasmineStarted - * @param {JasmineStartedInfo} suiteInfo Information about the full Jasmine suite that is being run - * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. - * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. - * @see async - */ - 'jasmineStarted', - /** - * When the entire suite has finished execution `jasmineDone` is called - * @function - * @name Reporter#jasmineDone - * @param {JasmineDoneInfo} suiteInfo Information about the full Jasmine suite that just finished running. - * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. - * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. - * @see async - */ - 'jasmineDone', - /** - * `suiteStarted` is invoked when a `describe` starts to run - * @function - * @name Reporter#suiteStarted - * @param {SuiteResult} result Information about the individual {@link describe} being run - * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. - * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. - * @see async - */ - 'suiteStarted', - /** - * `suiteDone` is invoked when all of the child specs and suites for a given suite have been run - * - * While jasmine doesn't require any specific functions, not defining a `suiteDone` will make it impossible for a reporter to know when a suite has failures in an `afterAll`. - * @function - * @name Reporter#suiteDone - * @param {SuiteResult} result - * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. - * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. - * @see async - */ - 'suiteDone', - /** - * `specStarted` is invoked when an `it` starts to run (including associated `beforeEach` functions) - * @function - * @name Reporter#specStarted - * @param {SpecResult} result Information about the individual {@link it} being run - * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. - * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. - * @see async - */ - 'specStarted', - /** - * `specDone` is invoked when an `it` and its associated `beforeEach` and `afterEach` functions have been run. - * - * While jasmine doesn't require any specific functions, not defining a `specDone` will make it impossible for a reporter to know when a spec has failed. - * @function - * @name Reporter#specDone - * @param {SpecResult} result - * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. - * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. - * @see async - */ - 'specDone' - ], queueRunnerFactory); + var reporter = new j$.ReportDispatcher( + [ + /** + * `jasmineStarted` is called after all of the specs have been loaded, but just before execution starts. + * @function + * @name Reporter#jasmineStarted + * @param {JasmineStartedInfo} suiteInfo Information about the full Jasmine suite that is being run + * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. + * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. + * @see async + */ + 'jasmineStarted', + /** + * When the entire suite has finished execution `jasmineDone` is called + * @function + * @name Reporter#jasmineDone + * @param {JasmineDoneInfo} suiteInfo Information about the full Jasmine suite that just finished running. + * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. + * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. + * @see async + */ + 'jasmineDone', + /** + * `suiteStarted` is invoked when a `describe` starts to run + * @function + * @name Reporter#suiteStarted + * @param {SuiteResult} result Information about the individual {@link describe} being run + * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. + * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. + * @see async + */ + 'suiteStarted', + /** + * `suiteDone` is invoked when all of the child specs and suites for a given suite have been run + * + * While jasmine doesn't require any specific functions, not defining a `suiteDone` will make it impossible for a reporter to know when a suite has failures in an `afterAll`. + * @function + * @name Reporter#suiteDone + * @param {SuiteResult} result + * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. + * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. + * @see async + */ + 'suiteDone', + /** + * `specStarted` is invoked when an `it` starts to run (including associated `beforeEach` functions) + * @function + * @name Reporter#specStarted + * @param {SpecResult} result Information about the individual {@link it} being run + * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. + * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. + * @see async + */ + 'specStarted', + /** + * `specDone` is invoked when an `it` and its associated `beforeEach` and `afterEach` functions have been run. + * + * While jasmine doesn't require any specific functions, not defining a `specDone` will make it impossible for a reporter to know when a spec has failed. + * @function + * @name Reporter#specDone + * @param {SpecResult} result + * @param {Function} [done] Used to specify to Jasmine that this callback is asynchronous and Jasmine should wait until it has been called before moving on. + * @returns {} Optionally return a Promise instead of using `done` to cause Jasmine to wait for completion. + * @see async + */ + 'specDone' + ], + queueRunnerFactory + ); this.execute = function(runnablesToRun) { - var self = this; installGlobalErrors(); - if(!runnablesToRun) { + if (!runnablesToRun) { if (focusedRunnables.length) { runnablesToRun = focusedRunnables; } else { @@ -552,8 +618,10 @@ getJasmineRequireObj().Env = function(j$) { } }); - if(!processor.processTree().valid) { - throw new Error('Invalid order: would cause a beforeAll or afterAll to be run multiple times'); + if (!processor.processTree().valid) { + throw new Error( + 'Invalid order: would cause a beforeAll or afterAll to be run multiple times' + ); } /** @@ -562,47 +630,53 @@ getJasmineRequireObj().Env = function(j$) { * @property {Int} totalSpecsDefined - The total number of specs defined in this suite. * @property {Order} order - Information about the ordering (random or not) of this execution of the suite. */ - reporter.jasmineStarted({ - totalSpecsDefined: totalSpecsDefined, - order: order - }, function() { - currentlyExecutingSuites.push(topSuite); + reporter.jasmineStarted( + { + totalSpecsDefined: totalSpecsDefined, + order: order + }, + function() { + currentlyExecutingSuites.push(topSuite); - processor.execute(function () { - clearResourcesForRunnable(topSuite.id); - currentlyExecutingSuites.pop(); - var overallStatus, incompleteReason; + processor.execute(function() { + clearResourcesForRunnable(topSuite.id); + currentlyExecutingSuites.pop(); + var overallStatus, incompleteReason; - if (hasFailures || topSuite.result.failedExpectations.length > 0) { - overallStatus = 'failed'; - } else if (focusedRunnables.length > 0) { - overallStatus = 'incomplete'; - incompleteReason = 'fit() or fdescribe() was found'; - } else if (totalSpecsDefined === 0) { - overallStatus = 'incomplete'; - incompleteReason = 'No specs found'; - } else { - overallStatus = 'passed'; - } + if (hasFailures || topSuite.result.failedExpectations.length > 0) { + overallStatus = 'failed'; + } else if (focusedRunnables.length > 0) { + overallStatus = 'incomplete'; + incompleteReason = 'fit() or fdescribe() was found'; + } else if (totalSpecsDefined === 0) { + overallStatus = 'incomplete'; + incompleteReason = 'No specs found'; + } else { + overallStatus = 'passed'; + } - /** - * Information passed to the {@link Reporter#jasmineDone} event. - * @typedef JasmineDoneInfo - * @property {OverallStatus} overallStatus - The overall result of the suite: 'passed', 'failed', or 'incomplete'. - * @property {IncompleteReason} incompleteReason - Explanation of why the suite was incomplete. - * @property {Order} order - Information about the ordering (random or not) of this execution of the suite. - * @property {Expectation[]} failedExpectations - List of expectations that failed in an {@link afterAll} at the global level. - * @property {Expectation[]} deprecationWarnings - List of deprecation warnings that occurred at the global level. - */ - reporter.jasmineDone({ - overallStatus: overallStatus, - incompleteReason: incompleteReason, - order: order, - failedExpectations: topSuite.result.failedExpectations, - deprecationWarnings: topSuite.result.deprecationWarnings - }, function() {}); - }); - }); + /** + * Information passed to the {@link Reporter#jasmineDone} event. + * @typedef JasmineDoneInfo + * @property {OverallStatus} overallStatus - The overall result of the suite: 'passed', 'failed', or 'incomplete'. + * @property {IncompleteReason} incompleteReason - Explanation of why the suite was incomplete. + * @property {Order} order - Information about the ordering (random or not) of this execution of the suite. + * @property {Expectation[]} failedExpectations - List of expectations that failed in an {@link afterAll} at the global level. + * @property {Expectation[]} deprecationWarnings - List of deprecation warnings that occurred at the global level. + */ + reporter.jasmineDone( + { + overallStatus: overallStatus, + incompleteReason: incompleteReason, + order: order, + failedExpectations: topSuite.result.failedExpectations, + deprecationWarnings: topSuite.result.deprecationWarnings + }, + function() {} + ); + }); + } + ); }; /** @@ -653,8 +727,10 @@ getJasmineRequireObj().Env = function(j$) { var spyRegistry = new j$.SpyRegistry({ currentSpies: function() { - if(!currentRunnable()) { - throw new Error('Spies must be created in a before function or a spec'); + if (!currentRunnable()) { + throw new Error( + 'Spies must be created in a before function or a spec' + ); } return runnableResources[currentRunnable().id].spies; }, @@ -694,20 +770,26 @@ getJasmineRequireObj().Env = function(j$) { var ensureIsFunction = function(fn, caller) { if (!j$.isFunction_(fn)) { - throw new Error(caller + ' expects a function argument; received ' + j$.getType_(fn)); + throw new Error( + caller + ' expects a function argument; received ' + j$.getType_(fn) + ); } }; var ensureIsFunctionOrAsync = function(fn, caller) { if (!j$.isFunction_(fn) && !j$.isAsyncFunction_(fn)) { - throw new Error(caller + ' expects a function argument; received ' + j$.getType_(fn)); + throw new Error( + caller + ' expects a function argument; received ' + j$.getType_(fn) + ); } }; function ensureIsNotNested(method) { var runnable = currentRunnable(); if (runnable !== null && runnable !== undefined) { - throw new Error('\'' + method + '\' should only be used in \'describe\' function'); + throw new Error( + "'" + method + "' should only be used in 'describe' function" + ); } } @@ -821,7 +903,9 @@ getJasmineRequireObj().Env = function(j$) { description: description, expectationResultFactory: expectationResultFactory, queueRunnerFactory: queueRunnerFactory, - userContext: function() { return suite.clonedSharedUserContext(); }, + userContext: function() { + return suite.clonedSharedUserContext(); + }, queueableFn: { fn: fn, timeout: timeout || 0 @@ -888,7 +972,9 @@ getJasmineRequireObj().Env = function(j$) { this.expect = function(actual) { if (!currentRunnable()) { - throw new Error('\'expect\' was used when there was no current spec, this could be because an asynchronous test timed out'); + throw new Error( + "'expect' was used when there was no current spec, this could be because an asynchronous test timed out" + ); } return currentRunnable().expect(actual); @@ -896,7 +982,9 @@ getJasmineRequireObj().Env = function(j$) { this.expectAsync = function(actual) { if (!currentRunnable()) { - throw new Error('\'expectAsync\' was used when there was no current spec, this could be because an asynchronous test timed out'); + throw new Error( + "'expectAsync' was used when there was no current spec, this could be because an asynchronous test timed out" + ); } return currentRunnable().expectAsync(actual); @@ -941,7 +1029,7 @@ getJasmineRequireObj().Env = function(j$) { this.pending = function(message) { var fullMessage = j$.Spec.pendingSpecExceptionMessage; - if(message) { + if (message) { fullMessage += message; } throw fullMessage; @@ -949,7 +1037,9 @@ getJasmineRequireObj().Env = function(j$) { this.fail = function(error) { if (!currentRunnable()) { - throw new Error('\'fail\' was used when there was no current spec, this could be because an asynchronous test timed out'); + throw new Error( + "'fail' was used when there was no current spec, this could be because an asynchronous test timed out" + ); } var message = 'Failed'; diff --git a/src/core/ExceptionFormatter.js b/src/core/ExceptionFormatter.js index adbf984c..14534bb2 100644 --- a/src/core/ExceptionFormatter.js +++ b/src/core/ExceptionFormatter.js @@ -1,6 +1,16 @@ getJasmineRequireObj().ExceptionFormatter = function(j$) { - - var ignoredProperties = ['name', 'message', 'stack', 'fileName', 'sourceURL', 'line', 'lineNumber', 'column', 'description', 'jasmineMessage']; + var ignoredProperties = [ + 'name', + 'message', + 'stack', + 'fileName', + 'sourceURL', + 'line', + 'lineNumber', + 'column', + 'description', + 'jasmineMessage' + ]; function ExceptionFormatter(options) { var jasmineFile = (options && options.jasmineFile) || j$.util.jasmineFile(); @@ -49,7 +59,8 @@ getJasmineRequireObj().ExceptionFormatter = function(j$) { function filterJasmine(stackTrace) { var result = [], - jasmineMarker = stackTrace.style === 'webkit' ? '' : ' at '; + jasmineMarker = + stackTrace.style === 'webkit' ? '' : ' at '; stackTrace.frames.forEach(function(frame) { if (frame.file && frame.file !== jasmineFile) { diff --git a/src/core/Expectation.js b/src/core/Expectation.js index 2de1c15f..e1833433 100644 --- a/src/core/Expectation.js +++ b/src/core/Expectation.js @@ -1,6 +1,8 @@ getJasmineRequireObj().Expectation = function(j$) { var promiseForMessage = { - jasmineToString: function() { return 'a promise'; } + jasmineToString: function() { + return 'a promise'; + } }; /** @@ -12,7 +14,10 @@ getJasmineRequireObj().Expectation = function(j$) { var customMatchers = options.customMatchers || {}; for (var matcherName in customMatchers) { - this[matcherName] = wrapSyncCompare(matcherName, customMatchers[matcherName]); + this[matcherName] = wrapSyncCompare( + matcherName, + customMatchers[matcherName] + ); } } @@ -50,7 +55,9 @@ getJasmineRequireObj().Expectation = function(j$) { this.expector = new j$.Expector(options); if (!global.Promise) { - throw new Error('expectAsync is unavailable because the environment does not support promises.'); + throw new Error( + 'expectAsync is unavailable because the environment does not support promises.' + ); } if (!j$.isPromiseLike(this.expector.actual)) { @@ -100,9 +107,11 @@ getJasmineRequireObj().Expectation = function(j$) { // frames that are relevant to the user instead of just parts of Jasmine. var errorForStack = j$.util.errorWithStack(); - return this.expector.compare(name, matcherFactory, arguments).then(function(result) { - self.expector.processResult(result, errorForStack, promiseForMessage); - }); + return this.expector + .compare(name, matcherFactory, arguments) + .then(function(result) { + self.expector.processResult(result, errorForStack, promiseForMessage); + }); }; } diff --git a/src/core/ExpectationFilterChain.js b/src/core/ExpectationFilterChain.js index 83018bd6..6ecbd17c 100644 --- a/src/core/ExpectationFilterChain.js +++ b/src/core/ExpectationFilterChain.js @@ -12,7 +12,12 @@ getJasmineRequireObj().ExpectationFilterChain = function() { return this.callFirst_('selectComparisonFunc', arguments).result; }; - ExpectationFilterChain.prototype.buildFailureMessage = function(result, matcherName, args, util) { + ExpectationFilterChain.prototype.buildFailureMessage = function( + result, + matcherName, + args, + util + ) { return this.callFirst_('buildFailureMessage', arguments).result; }; @@ -39,7 +44,7 @@ getJasmineRequireObj().ExpectationFilterChain = function() { }; } - return {found: false}; + return { found: false }; }; return ExpectationFilterChain; diff --git a/src/core/ExpectationResult.js b/src/core/ExpectationResult.js index 869d5d24..43545c43 100644 --- a/src/core/ExpectationResult.js +++ b/src/core/ExpectationResult.js @@ -20,7 +20,7 @@ getJasmineRequireObj().buildExpectationResult = function() { passed: options.passed }; - if(!result.passed) { + if (!result.passed) { result.expected = options.expected; result.actual = options.actual; } diff --git a/src/core/Expector.js b/src/core/Expector.js index 55667f51..bfc443f8 100644 --- a/src/core/Expector.js +++ b/src/core/Expector.js @@ -7,7 +7,11 @@ getJasmineRequireObj().Expector = function(j$) { this.filters = new j$.ExpectationFilterChain(); } - Expector.prototype.instantiateMatcher = function(matcherName, matcherFactory, args) { + Expector.prototype.instantiateMatcher = function( + matcherName, + matcherFactory, + args + ) { this.matcherName = matcherName; this.args = Array.prototype.slice.call(args, 0); this.expected = this.args.slice(0); @@ -26,7 +30,13 @@ getJasmineRequireObj().Expector = function(j$) { return ''; } - var msg = this.filters.buildFailureMessage(result, this.matcherName, this.args, this.util, defaultMessage); + var msg = this.filters.buildFailureMessage( + result, + this.matcherName, + this.args, + this.util, + defaultMessage + ); return this.filters.modifyFailureMessage(msg || defaultMessage()); function defaultMessage() { @@ -44,7 +54,11 @@ getJasmineRequireObj().Expector = function(j$) { }; Expector.prototype.compare = function(matcherName, matcherFactory, args) { - var matcherCompare = this.instantiateMatcher(matcherName, matcherFactory, args); + var matcherCompare = this.instantiateMatcher( + matcherName, + matcherFactory, + args + ); return matcherCompare.apply(null, this.args); }; @@ -54,7 +68,11 @@ getJasmineRequireObj().Expector = function(j$) { return result; }; - Expector.prototype.processResult = function(result, errorForStack, actualOverride) { + Expector.prototype.processResult = function( + result, + errorForStack, + actualOverride + ) { this.args[0] = actualOverride || this.args[0]; var message = this.buildMessage(result); @@ -62,18 +80,15 @@ getJasmineRequireObj().Expector = function(j$) { this.expected = this.expected[0]; } - this.addExpectationResult( - result.pass, - { - matcherName: this.matcherName, - passed: result.pass, - message: message, - error: errorForStack ? undefined : result.error, - errorForStack: errorForStack || undefined, - actual: this.actual, - expected: this.expected // TODO: this may need to be arrayified/sliced - } - ); + this.addExpectationResult(result.pass, { + matcherName: this.matcherName, + passed: result.pass, + message: message, + error: errorForStack ? undefined : result.error, + errorForStack: errorForStack || undefined, + actual: this.actual, + expected: this.expected // TODO: this may need to be arrayified/sliced + }); }; return Expector; diff --git a/src/core/GlobalErrors.js b/src/core/GlobalErrors.js index 56c10c82..2c58e684 100644 --- a/src/core/GlobalErrors.js +++ b/src/core/GlobalErrors.js @@ -38,7 +38,10 @@ getJasmineRequireObj().GlobalErrors = function(j$) { var errorTypes = Object.keys(this.originalHandlers); for (var iType = 0; iType < errorTypes.length; iType++) { var errorType = errorTypes[iType]; - global.process.removeListener(errorType, this.jasmineHandlers[errorType]); + global.process.removeListener( + errorType, + this.jasmineHandlers[errorType] + ); for (var i = 0; i < this.originalHandlers[errorType].length; i++) { global.process.on(errorType, this.originalHandlers[errorType][i]); } @@ -49,7 +52,11 @@ getJasmineRequireObj().GlobalErrors = function(j$) { }; this.install = function install() { - if (global.process && global.process.listeners && j$.isFunction_(global.process.on)) { + if ( + global.process && + global.process.listeners && + j$.isFunction_(global.process.on) + ) { this.installOne_('uncaughtException', 'Uncaught exception'); this.installOne_('unhandledRejection', 'Unhandled promise rejection'); } else { diff --git a/src/core/JsApiReporter.js b/src/core/JsApiReporter.js index 241deccf..514b3a6c 100644 --- a/src/core/JsApiReporter.js +++ b/src/core/JsApiReporter.js @@ -7,7 +7,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { */ function JsApiReporter(options) { var timer = options.timer || j$.noopTimer, - status = 'loaded'; + status = 'loaded'; this.started = false; this.finished = false; @@ -117,7 +117,6 @@ getJasmineRequireObj().JsApiReporter = function(j$) { this.executionTime = function() { return executionTime; }; - } return JsApiReporter; diff --git a/src/core/MockDate.js b/src/core/MockDate.js index 9dfc0628..7b642038 100644 --- a/src/core/MockDate.js +++ b/src/core/MockDate.js @@ -37,7 +37,7 @@ getJasmineRequireObj().MockDate = function() { return self; function FakeDate() { - switch(arguments.length) { + switch (arguments.length) { case 0: return new GlobalDate(currentTime); case 1: @@ -47,16 +47,39 @@ getJasmineRequireObj().MockDate = function() { case 3: return new GlobalDate(arguments[0], arguments[1], arguments[2]); case 4: - return new GlobalDate(arguments[0], arguments[1], arguments[2], arguments[3]); + return new GlobalDate( + arguments[0], + arguments[1], + arguments[2], + arguments[3] + ); case 5: - return new GlobalDate(arguments[0], arguments[1], arguments[2], arguments[3], - arguments[4]); + return new GlobalDate( + arguments[0], + arguments[1], + arguments[2], + arguments[3], + arguments[4] + ); case 6: - return new GlobalDate(arguments[0], arguments[1], arguments[2], arguments[3], - arguments[4], arguments[5]); + return new GlobalDate( + arguments[0], + arguments[1], + arguments[2], + arguments[3], + arguments[4], + arguments[5] + ); default: - return new GlobalDate(arguments[0], arguments[1], arguments[2], arguments[3], - arguments[4], arguments[5], arguments[6]); + return new GlobalDate( + arguments[0], + arguments[1], + arguments[2], + arguments[3], + arguments[4], + arguments[5], + arguments[6] + ); } } diff --git a/src/core/Order.js b/src/core/Order.js index de35ca8e..050e1001 100644 --- a/src/core/Order.js +++ b/src/core/Order.js @@ -3,7 +3,7 @@ getJasmineRequireObj().Order = function() { function Order(options) { this.random = 'random' in options ? options.random : true; - var seed = this.seed = options.seed || generateSeed(); + var seed = (this.seed = options.seed || generateSeed()); this.sort = this.random ? randomOrder : naturalOrder; function naturalOrder(items) { @@ -29,17 +29,16 @@ getJasmineRequireObj().Order = function() { function jenkinsHash(key) { var hash, i; - for(hash = i = 0; i < key.length; ++i) { + for (hash = i = 0; i < key.length; ++i) { hash += key.charCodeAt(i); - hash += (hash << 10); - hash ^= (hash >> 6); + hash += hash << 10; + hash ^= hash >> 6; } - hash += (hash << 3); - hash ^= (hash >> 11); - hash += (hash << 15); + hash += hash << 3; + hash ^= hash >> 11; + hash += hash << 15; return hash; } - } return Order; diff --git a/src/core/PrettyPrinter.js b/src/core/PrettyPrinter.js index 5b3dd55f..67cb34d6 100644 --- a/src/core/PrettyPrinter.js +++ b/src/core/PrettyPrinter.js @@ -1,5 +1,4 @@ getJasmineRequireObj().pp = function(j$) { - function PrettyPrinter() { this.ppNestLevel_ = 0; this.seen = []; @@ -10,7 +9,11 @@ getJasmineRequireObj().pp = function(j$) { function hasCustomToString(value) { // value.toString !== Object.prototype.toString if value has no custom toString but is from another context (e.g. // iframe, web worker) - return j$.isFunction_(value.toString) && value.toString !== Object.prototype.toString && (value.toString() !== Object.prototype.toString.call(value)); + return ( + j$.isFunction_(value.toString) && + value.toString !== Object.prototype.toString && + value.toString() !== Object.prototype.toString.call(value) + ); } PrettyPrinter.prototype.format = function(value) { @@ -20,7 +23,7 @@ getJasmineRequireObj().pp = function(j$) { this.emitScalar('undefined'); } else if (value === null) { this.emitScalar('null'); - } else if (value === 0 && 1/value === -Infinity) { + } else if (value === 0 && 1 / value === -Infinity) { this.emitScalar('-0'); } else if (value === j$.getGlobal()) { this.emitScalar(''); @@ -50,10 +53,19 @@ getJasmineRequireObj().pp = function(j$) { this.emitMap(value); } else if (j$.isTypedArray_(value)) { this.emitTypedArray(value); - } else if (value.toString && typeof value === 'object' && !j$.isArray_(value) && hasCustomToString(value)) { + } else if ( + value.toString && + typeof value === 'object' && + !j$.isArray_(value) && + hasCustomToString(value) + ) { this.emitScalar(value.toString()); } else if (j$.util.arrayContains(this.seen, value)) { - this.emitScalar(''); + this.emitScalar( + '' + ); } else if (j$.isArray_(value) || j$.isA_('Object', value)) { this.seen.push(value); if (j$.isArray_(value)) { @@ -83,7 +95,6 @@ getJasmineRequireObj().pp = function(j$) { var getter = obj.__lookupGetter__(prop); return !j$.util.isUndefined(getter) && getter !== null; }; - } var length = Math.min(objKeys.length, j$.MAX_PRETTY_PRINT_ARRAY_LENGTH); for (var i = 0; i < length; i++) { @@ -99,7 +110,7 @@ getJasmineRequireObj().pp = function(j$) { }; PrettyPrinter.prototype.emitString = function(value) { - this.append('\'' + value + '\''); + this.append("'" + value + "'"); }; PrettyPrinter.prototype.emitArray = function(array) { @@ -115,7 +126,7 @@ getJasmineRequireObj().pp = function(j$) { } this.format(array[i]); } - if(array.length > length) { + if (array.length > length) { this.append(', ...'); } @@ -131,7 +142,9 @@ getJasmineRequireObj().pp = function(j$) { self.formatProperty(array, property, isGetter); }); - if (truncated) { this.append(', ...'); } + if (truncated) { + this.append(', ...'); + } this.append(' ]'); }; @@ -144,7 +157,7 @@ getJasmineRequireObj().pp = function(j$) { this.append('Set( '); var size = Math.min(set.size, j$.MAX_PRETTY_PRINT_ARRAY_LENGTH); var i = 0; - set.forEach( function( value, key ) { + set.forEach(function(value, key) { if (i >= size) { return; } @@ -154,7 +167,7 @@ getJasmineRequireObj().pp = function(j$) { this.format(value); i++; - }, this ); + }, this); if (set.size > size) { this.append(', ...'); } @@ -169,17 +182,17 @@ getJasmineRequireObj().pp = function(j$) { this.append('Map( '); var size = Math.min(map.size, j$.MAX_PRETTY_PRINT_ARRAY_LENGTH); var i = 0; - map.forEach( function( value, key ) { + map.forEach(function(value, key) { if (i >= size) { return; } if (i > 0) { this.append(', '); } - this.format([key,value]); + this.format([key, value]); i++; - }, this ); + }, this); if (map.size > size) { this.append(', ...'); } @@ -188,11 +201,12 @@ getJasmineRequireObj().pp = function(j$) { PrettyPrinter.prototype.emitObject = function(obj) { var ctor = obj.constructor, - constructorName; + constructorName; - constructorName = typeof ctor === 'function' && obj instanceof ctor ? - j$.fnNameFor(obj.constructor) : - 'null'; + constructorName = + typeof ctor === 'function' && obj instanceof ctor + ? j$.fnNameFor(obj.constructor) + : 'null'; this.append(constructorName); @@ -214,14 +228,20 @@ getJasmineRequireObj().pp = function(j$) { self.formatProperty(obj, property, isGetter); }); - if (truncated) { this.append(', ...'); } + if (truncated) { + this.append(', ...'); + } this.append(' })'); }; PrettyPrinter.prototype.emitTypedArray = function(arr) { var constructorName = j$.fnNameFor(arr.constructor), - limitedArray = Array.prototype.slice.call(arr, 0, j$.MAX_PRETTY_PRINT_ARRAY_LENGTH), + limitedArray = Array.prototype.slice.call( + arr, + 0, + j$.MAX_PRETTY_PRINT_ARRAY_LENGTH + ), itemsString = Array.prototype.join.call(limitedArray, ', '); if (limitedArray.length !== arr.length) { @@ -258,13 +278,13 @@ getJasmineRequireObj().pp = function(j$) { }; PrettyPrinter.prototype.formatProperty = function(obj, property, isGetter) { - this.append(property); - this.append(': '); - if (isGetter) { - this.append(''); - } else { - this.format(obj[property]); - } + this.append(property); + this.append(': '); + if (isGetter) { + this.append(''); + } else { + this.format(obj[property]); + } }; PrettyPrinter.prototype.append = function(value) { @@ -283,7 +303,6 @@ getJasmineRequireObj().pp = function(j$) { } }; - function truncate(s, maxlen) { if (s.length <= maxlen) { return { value: s, truncated: false }; @@ -294,30 +313,33 @@ getJasmineRequireObj().pp = function(j$) { } function MaxCharsReachedError() { - this.message = 'Exceeded ' + j$.MAX_PRETTY_PRINT_CHARS + + this.message = + 'Exceeded ' + + j$.MAX_PRETTY_PRINT_CHARS + ' characters while pretty-printing a value'; } MaxCharsReachedError.prototype = new Error(); function keys(obj, isArray) { - var allKeys = Object.keys ? Object.keys(obj) : - (function(o) { + var allKeys = Object.keys + ? Object.keys(obj) + : (function(o) { var keys = []; for (var key in o) { - if (j$.util.has(o, key)) { - keys.push(key); - } + if (j$.util.has(o, key)) { + keys.push(key); + } } return keys; - })(obj); + })(obj); if (!isArray) { return allKeys; } if (allKeys.length === 0) { - return allKeys; + return allKeys; } var extraKeys = []; diff --git a/src/core/QueueRunner.js b/src/core/QueueRunner.js index c183c1d4..27b57695 100644 --- a/src/core/QueueRunner.js +++ b/src/core/QueueRunner.js @@ -22,16 +22,26 @@ getJasmineRequireObj().QueueRunner = function(j$) { this.queueableFns = queueableFns.concat(attrs.cleanupFns || []); this.firstCleanupIx = queueableFns.length; this.onComplete = attrs.onComplete || emptyFn; - this.clearStack = attrs.clearStack || function(fn) { fn(); }; + this.clearStack = + attrs.clearStack || + function(fn) { + fn(); + }; this.onException = attrs.onException || emptyFn; this.userContext = attrs.userContext || new j$.UserContext(); - this.timeout = attrs.timeout || {setTimeout: setTimeout, clearTimeout: clearTimeout}; + this.timeout = attrs.timeout || { + setTimeout: setTimeout, + clearTimeout: clearTimeout + }; this.fail = attrs.fail || emptyFn; - this.globalErrors = attrs.globalErrors || { pushListener: emptyFn, popListener: emptyFn }; + this.globalErrors = attrs.globalErrors || { + pushListener: emptyFn, + popListener: emptyFn + }; this.completeOnFirstError = !!attrs.completeOnFirstError; this.errored = false; - if (typeof(this.onComplete) !== 'function') { + if (typeof this.onComplete !== 'function') { throw new Error('invalid onComplete ' + JSON.stringify(this.onComplete)); } this.deprecated = attrs.deprecated; @@ -55,15 +65,22 @@ getJasmineRequireObj().QueueRunner = function(j$) { }; QueueRunner.prototype.clearTimeout = function(timeoutId) { - Function.prototype.apply.apply(this.timeout.clearTimeout, [j$.getGlobal(), [timeoutId]]); + Function.prototype.apply.apply(this.timeout.clearTimeout, [ + j$.getGlobal(), + [timeoutId] + ]); }; QueueRunner.prototype.setTimeout = function(fn, timeout) { - return Function.prototype.apply.apply(this.timeout.setTimeout, [j$.getGlobal(), [fn, timeout]]); + return Function.prototype.apply.apply(this.timeout.setTimeout, [ + j$.getGlobal(), + [fn, timeout] + ]); }; QueueRunner.prototype.attempt = function attempt(iterativeIndex) { - var self = this, completedSynchronously = true, + var self = this, + completedSynchronously = true, handleError = function handleError(error) { onException(error); next(error); @@ -114,8 +131,12 @@ getJasmineRequireObj().QueueRunner = function(j$) { var timeoutInterval = queueableFn.timeout || j$.DEFAULT_TIMEOUT_INTERVAL; timeoutId = self.setTimeout(function() { var error = new Error( - 'Timeout - Async callback was not invoked within ' + timeoutInterval + 'ms ' + - (queueableFn.timeout ? '(custom timeout)' : '(set by jasmine.DEFAULT_TIMEOUT_INTERVAL)') + 'Timeout - Async callback was not invoked within ' + + timeoutInterval + + 'ms ' + + (queueableFn.timeout + ? '(custom timeout)' + : '(set by jasmine.DEFAULT_TIMEOUT_INTERVAL)') ); onException(error); next(); @@ -160,8 +181,11 @@ getJasmineRequireObj().QueueRunner = function(j$) { self = this, iterativeIndex; - - for(iterativeIndex = recursiveIndex; iterativeIndex < length; iterativeIndex++) { + for ( + iterativeIndex = recursiveIndex; + iterativeIndex < length; + iterativeIndex++ + ) { var result = this.attempt(iterativeIndex); if (!result.completedSynchronously) { @@ -180,7 +204,6 @@ getJasmineRequireObj().QueueRunner = function(j$) { self.globalErrors.popListener(self.handleFinalError); self.onComplete(self.errored && new StopExecutionError()); }); - }; return QueueRunner; diff --git a/src/core/ReportDispatcher.js b/src/core/ReportDispatcher.js index 5b2fad25..d254fb59 100644 --- a/src/core/ReportDispatcher.js +++ b/src/core/ReportDispatcher.js @@ -1,6 +1,5 @@ getJasmineRequireObj().ReportDispatcher = function(j$) { function ReportDispatcher(methods, queueRunnerFactory) { - var dispatchedMethods = methods || []; for (var i = 0; i < dispatchedMethods.length; i++) { @@ -9,7 +8,7 @@ getJasmineRequireObj().ReportDispatcher = function(j$) { return function() { dispatch(m, arguments); }; - }(method)); + })(method); } var reporters = []; @@ -31,7 +30,7 @@ getJasmineRequireObj().ReportDispatcher = function(j$) { function dispatch(method, args) { if (reporters.length === 0 && fallbackReporter !== null) { - reporters.push(fallbackReporter); + reporters.push(fallbackReporter); } var onComplete = args[args.length - 1]; args = j$.util.argsToArray(args).splice(0, args.length - 1); @@ -57,13 +56,13 @@ getJasmineRequireObj().ReportDispatcher = function(j$) { var thisArgs = j$.util.cloneArgs(args); if (fn.length <= 1) { fns.push({ - fn: function () { + fn: function() { return fn.apply(reporter, thisArgs); } }); } else { fns.push({ - fn: function (done) { + fn: function(done) { return fn.apply(reporter, thisArgs.concat([done])); } }); @@ -73,4 +72,3 @@ getJasmineRequireObj().ReportDispatcher = function(j$) { return ReportDispatcher; }; - diff --git a/src/core/Spec.js b/src/core/Spec.js index 4b31925d..53a4f0ef 100644 --- a/src/core/Spec.js +++ b/src/core/Spec.js @@ -6,13 +6,30 @@ getJasmineRequireObj().Spec = function(j$) { this.id = attrs.id; this.description = attrs.description || ''; this.queueableFn = attrs.queueableFn; - this.beforeAndAfterFns = attrs.beforeAndAfterFns || function() { return {befores: [], afters: []}; }; - this.userContext = attrs.userContext || function() { return {}; }; + this.beforeAndAfterFns = + attrs.beforeAndAfterFns || + function() { + return { befores: [], afters: [] }; + }; + this.userContext = + attrs.userContext || + function() { + return {}; + }; this.onStart = attrs.onStart || function() {}; - this.getSpecName = attrs.getSpecName || function() { return ''; }; - this.expectationResultFactory = attrs.expectationResultFactory || function() { }; + this.getSpecName = + attrs.getSpecName || + function() { + return ''; + }; + this.expectationResultFactory = + attrs.expectationResultFactory || function() {}; this.queueRunnerFactory = attrs.queueRunnerFactory || function() {}; - this.catchingExceptions = attrs.catchingExceptions || function() { return true; }; + this.catchingExceptions = + attrs.catchingExceptions || + function() { + return true; + }; this.throwOnExpectationFailure = !!attrs.throwOnExpectationFailure; this.timer = attrs.timer || j$.noopTimer; @@ -90,12 +107,15 @@ getJasmineRequireObj().Spec = function(j$) { isLeaf: true, queueableFns: regularFns, cleanupFns: fns.afters, - onException: function () { + onException: function() { self.onException.apply(self, arguments); }, onComplete: function() { self.result.duration = self.timer.elapsed(); - onComplete(self.result.status === 'failed' && new j$.StopExecutionError('spec failed')); + onComplete( + self.result.status === 'failed' && + new j$.StopExecutionError('spec failed') + ); }, userContext: this.userContext() }; @@ -121,13 +141,17 @@ getJasmineRequireObj().Spec = function(j$) { return; } - this.addExpectationResult(false, { - matcherName: '', - passed: false, - expected: '', - actual: '', - error: e - }, true); + this.addExpectationResult( + false, + { + matcherName: '', + passed: false, + expected: '', + actual: '', + error: e + }, + true + ); }; Spec.prototype.pend = function(message) { @@ -166,13 +190,16 @@ getJasmineRequireObj().Spec = function(j$) { if (typeof deprecation === 'string') { deprecation = { message: deprecation }; } - this.result.deprecationWarnings.push(this.expectationResultFactory(deprecation)); + this.result.deprecationWarnings.push( + this.expectationResultFactory(deprecation) + ); }; var extractCustomPendingMessage = function(e) { var fullMessage = e.toString(), - boilerplateStart = fullMessage.indexOf(Spec.pendingSpecExceptionMessage), - boilerplateEnd = boilerplateStart + Spec.pendingSpecExceptionMessage.length; + boilerplateStart = fullMessage.indexOf(Spec.pendingSpecExceptionMessage), + boilerplateEnd = + boilerplateStart + Spec.pendingSpecExceptionMessage.length; return fullMessage.substr(boilerplateEnd); }; @@ -180,7 +207,11 @@ getJasmineRequireObj().Spec = function(j$) { Spec.pendingSpecExceptionMessage = '=> marked Pending'; Spec.isPendingSpecException = function(e) { - return !!(e && e.toString && e.toString().indexOf(Spec.pendingSpecExceptionMessage) !== -1); + return !!( + e && + e.toString && + e.toString().indexOf(Spec.pendingSpecExceptionMessage) !== -1 + ); }; return Spec; diff --git a/src/core/Spy.js b/src/core/Spy.js index e4072f1b..753499bb 100644 --- a/src/core/Spy.js +++ b/src/core/Spy.js @@ -1,5 +1,4 @@ -getJasmineRequireObj().Spy = function (j$) { - +getJasmineRequireObj().Spy = function(j$) { var nextOrder = (function() { var order = 0; @@ -14,21 +13,21 @@ getJasmineRequireObj().Spy = function (j$) { * @name Spy */ function Spy(name, originalFn, customStrategies, getPromise) { - var numArgs = (typeof originalFn === 'function' ? originalFn.length : 0), - wrapper = makeFunc(numArgs, function () { + var numArgs = typeof originalFn === 'function' ? originalFn.length : 0, + wrapper = makeFunc(numArgs, function() { return spy.apply(this, Array.prototype.slice.call(arguments)); }), strategyDispatcher = new SpyStrategyDispatcher({ name: name, fn: originalFn, - getSpy: function () { + getSpy: function() { return wrapper; }, customStrategies: customStrategies, getPromise: getPromise }), callTracker = new j$.CallTracker(), - spy = function () { + spy = function() { /** * @name Spy.callData * @property {object} object - `this` context for the invocation. @@ -50,22 +49,54 @@ getJasmineRequireObj().Spy = function (j$) { function makeFunc(length, fn) { switch (length) { - case 1 : return function (a) { return fn.apply(this, arguments); }; - case 2 : return function (a,b) { return fn.apply(this, arguments); }; - case 3 : return function (a,b,c) { return fn.apply(this, arguments); }; - case 4 : return function (a,b,c,d) { return fn.apply(this, arguments); }; - case 5 : return function (a,b,c,d,e) { return fn.apply(this, arguments); }; - case 6 : return function (a,b,c,d,e,f) { return fn.apply(this, arguments); }; - case 7 : return function (a,b,c,d,e,f,g) { return fn.apply(this, arguments); }; - case 8 : return function (a,b,c,d,e,f,g,h) { return fn.apply(this, arguments); }; - case 9 : return function (a,b,c,d,e,f,g,h,i) { return fn.apply(this, arguments); }; - default : return function () { return fn.apply(this, arguments); }; + case 1: + return function(a) { + return fn.apply(this, arguments); + }; + case 2: + return function(a, b) { + return fn.apply(this, arguments); + }; + case 3: + return function(a, b, c) { + return fn.apply(this, arguments); + }; + case 4: + return function(a, b, c, d) { + return fn.apply(this, arguments); + }; + case 5: + return function(a, b, c, d, e) { + return fn.apply(this, arguments); + }; + case 6: + return function(a, b, c, d, e, f) { + return fn.apply(this, arguments); + }; + case 7: + return function(a, b, c, d, e, f, g) { + return fn.apply(this, arguments); + }; + case 8: + return function(a, b, c, d, e, f, g, h) { + return fn.apply(this, arguments); + }; + case 9: + return function(a, b, c, d, e, f, g, h, i) { + return fn.apply(this, arguments); + }; + default: + return function() { + return fn.apply(this, arguments); + }; } } for (var prop in originalFn) { if (prop === 'and' || prop === 'calls') { - throw new Error('Jasmine spies would overwrite the \'and\' and \'calls\' properties on the object being spied upon'); + throw new Error( + "Jasmine spies would overwrite the 'and' and 'calls' properties on the object being spied upon" + ); } wrapper[prop] = originalFn[prop]; @@ -112,7 +143,13 @@ getJasmineRequireObj().Spy = function (j$) { if (!strategy) { if (argsStrategies.any() && !baseStrategy.isConfigured()) { - throw new Error('Spy \'' + strategyArgs.name + '\' received a call with arguments ' + j$.pp(Array.prototype.slice.call(args)) + ' but all configured strategies specify other arguments.'); + throw new Error( + "Spy '" + + strategyArgs.name + + "' received a call with arguments " + + j$.pp(Array.prototype.slice.call(args)) + + ' but all configured strategies specify other arguments.' + ); } else { strategy = baseStrategy; } diff --git a/src/core/SpyFactory.js b/src/core/SpyFactory.js index 4df28e55..a622a8a3 100644 --- a/src/core/SpyFactory.js +++ b/src/core/SpyFactory.js @@ -1,5 +1,4 @@ getJasmineRequireObj().SpyFactory = function(j$) { - function SpyFactory(getCustomStrategies, getPromise) { var self = this; @@ -8,7 +7,8 @@ getJasmineRequireObj().SpyFactory = function(j$) { }; this.createSpyObj = function(baseName, methodNames) { - var baseNameIsCollection = j$.isObject_(baseName) || j$.isArray_(baseName); + var baseNameIsCollection = + j$.isObject_(baseName) || j$.isArray_(baseName); if (baseNameIsCollection && j$.util.isUndefined(methodNames)) { methodNames = baseName; diff --git a/src/core/SpyRegistry.js b/src/core/SpyRegistry.js index 3f4e3bc9..6e0bb33e 100644 --- a/src/core/SpyRegistry.js +++ b/src/core/SpyRegistry.js @@ -1,13 +1,19 @@ getJasmineRequireObj().SpyRegistry = function(j$) { - var spyOnMsg = j$.formatErrorMsg('', 'spyOn(, )'); - var spyOnPropertyMsg = j$.formatErrorMsg('', 'spyOnProperty(, , [accessType])'); + var spyOnPropertyMsg = j$.formatErrorMsg( + '', + 'spyOnProperty(, , [accessType])' + ); function SpyRegistry(options) { options = options || {}; var global = options.global || j$.getGlobal(); var createSpy = options.createSpy; - var currentSpies = options.currentSpies || function() { return []; }; + var currentSpies = + options.currentSpies || + function() { + return []; + }; this.allowRespy = function(allow) { this.respy = allow; @@ -17,7 +23,11 @@ getJasmineRequireObj().SpyRegistry = function(j$) { var getErrorMsg = spyOnMsg; if (j$.util.isUndefined(obj) || obj === null) { - throw new Error(getErrorMsg('could not find an object to spy upon for ' + methodName + '()')); + throw new Error( + getErrorMsg( + 'could not find an object to spy upon for ' + methodName + '()' + ) + ); } if (j$.util.isUndefined(methodName) || methodName === null) { @@ -28,25 +38,32 @@ getJasmineRequireObj().SpyRegistry = function(j$) { throw new Error(getErrorMsg(methodName + '() method does not exist')); } - if (obj[methodName] && j$.isSpy(obj[methodName]) ) { + if (obj[methodName] && j$.isSpy(obj[methodName])) { if (this.respy) { return obj[methodName]; - }else { - throw new Error(getErrorMsg(methodName + ' has already been spied upon')); + } else { + throw new Error( + getErrorMsg(methodName + ' has already been spied upon') + ); } } var descriptor = Object.getOwnPropertyDescriptor(obj, methodName); if (descriptor && !(descriptor.writable || descriptor.set)) { - throw new Error(getErrorMsg(methodName + ' is not declared writable or has no setter')); + throw new Error( + getErrorMsg(methodName + ' is not declared writable or has no setter') + ); } var originalMethod = obj[methodName], spiedMethod = createSpy(methodName, originalMethod), restoreStrategy; - if (Object.prototype.hasOwnProperty.call(obj, methodName) || (obj === global && methodName === 'onerror')) { + if ( + Object.prototype.hasOwnProperty.call(obj, methodName) || + (obj === global && methodName === 'onerror') + ) { restoreStrategy = function() { obj[methodName] = originalMethod; }; @@ -67,13 +84,19 @@ getJasmineRequireObj().SpyRegistry = function(j$) { return spiedMethod; }; - this.spyOnProperty = function (obj, propertyName, accessType) { + this.spyOnProperty = function(obj, propertyName, accessType) { var getErrorMsg = spyOnPropertyMsg; accessType = accessType || 'get'; if (j$.util.isUndefined(obj)) { - throw new Error(getErrorMsg('spyOn could not find an object to spy upon for ' + propertyName + '')); + throw new Error( + getErrorMsg( + 'spyOn could not find an object to spy upon for ' + + propertyName + + '' + ) + ); } if (j$.util.isUndefined(propertyName)) { @@ -87,18 +110,31 @@ getJasmineRequireObj().SpyRegistry = function(j$) { } if (!descriptor.configurable) { - throw new Error(getErrorMsg(propertyName + ' is not declared configurable')); + throw new Error( + getErrorMsg(propertyName + ' is not declared configurable') + ); } - if(!descriptor[accessType]) { - throw new Error(getErrorMsg('Property ' + propertyName + ' does not have access type ' + accessType)); + if (!descriptor[accessType]) { + throw new Error( + getErrorMsg( + 'Property ' + + propertyName + + ' does not have access type ' + + accessType + ) + ); } if (j$.isSpy(descriptor[accessType])) { if (this.respy) { return descriptor[accessType]; } else { - throw new Error(getErrorMsg(propertyName + '#' + accessType + ' has already been spied upon')); + throw new Error( + getErrorMsg( + propertyName + '#' + accessType + ' has already been spied upon' + ) + ); } } @@ -129,19 +165,27 @@ getJasmineRequireObj().SpyRegistry = function(j$) { this.spyOnAllFunctions = function(obj) { if (j$.util.isUndefined(obj)) { - throw new Error('spyOnAllFunctions could not find an object to spy upon'); + throw new Error( + 'spyOnAllFunctions could not find an object to spy upon' + ); } var pointer = obj, - props = [], - prop, - descriptor; + props = [], + prop, + descriptor; while (pointer) { for (prop in pointer) { - if (Object.prototype.hasOwnProperty.call(pointer, prop) && pointer[prop] instanceof Function) { + if ( + Object.prototype.hasOwnProperty.call(pointer, prop) && + pointer[prop] instanceof Function + ) { descriptor = Object.getOwnPropertyDescriptor(pointer, prop); - if ((descriptor.writable || descriptor.set) && descriptor.configurable) { + if ( + (descriptor.writable || descriptor.set) && + descriptor.configurable + ) { props.push(prop); } } diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index 5a785d4f..81ccf2ce 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -1,5 +1,4 @@ getJasmineRequireObj().SpyStrategy = function(j$) { - /** * @interface SpyStrategy */ @@ -19,20 +18,27 @@ getJasmineRequireObj().SpyStrategy = function(j$) { this.getSpy = options.getSpy || function() {}; this.plan = this._defaultPlan = function() {}; - var k, cs = options.customStrategies || {}; + var k, + cs = options.customStrategies || {}; for (k in cs) { if (j$.util.has(cs, k) && !this[k]) { this[k] = createCustomPlan(cs[k]); } } - var getPromise = (typeof options.getPromise === 'function') ? options.getPromise : function() {}; + var getPromise = + typeof options.getPromise === 'function' + ? options.getPromise + : function() {}; var requirePromise = function(name) { var Promise = getPromise(); if (!Promise) { - throw new Error(name + ' requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`'); + throw new Error( + name + + ' requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`' + ); } return Promise; @@ -60,7 +66,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { */ this.rejectWith = function(value) { var Promise = requirePromise('rejectWith'); - var error = (value instanceof Error) ? value : new Error(value); + var error = value instanceof Error ? value : new Error(value); self.plan = function() { return Promise.reject(error); @@ -122,7 +128,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { */ SpyStrategy.prototype.returnValues = function() { var values = Array.prototype.slice.call(arguments); - this.plan = function () { + this.plan = function() { return values.shift(); }; return this.getSpy(); @@ -135,7 +141,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { * @param {Error|String} something Thing to throw */ SpyStrategy.prototype.throwError = function(something) { - var error = (something instanceof Error) ? something : new Error(something); + var error = something instanceof Error ? something : new Error(something); this.plan = function() { throw error; }; @@ -149,8 +155,10 @@ getJasmineRequireObj().SpyStrategy = function(j$) { * @param {Function} fn The function to invoke with the passed parameters. */ SpyStrategy.prototype.callFake = function(fn) { - if(!(j$.isFunction_(fn) || j$.isAsyncFunction_(fn))) { - throw new Error('Argument passed to callFake should be a function, got ' + fn); + if (!(j$.isFunction_(fn) || j$.isAsyncFunction_(fn))) { + throw new Error( + 'Argument passed to callFake should be a function, got ' + fn + ); } this.plan = fn; return this.getSpy(); diff --git a/src/core/StackTrace.js b/src/core/StackTrace.js index 6c6ec458..3382751d 100644 --- a/src/core/StackTrace.js +++ b/src/core/StackTrace.js @@ -1,8 +1,8 @@ getJasmineRequireObj().StackTrace = function(j$) { function StackTrace(error) { - var lines = error.stack - .split('\n') - .filter(function(line) { return line !== ''; }); + var lines = error.stack.split('\n').filter(function(line) { + return line !== ''; + }); var extractResult = extractMessage(error.message, lines); @@ -21,7 +21,12 @@ getJasmineRequireObj().StackTrace = function(j$) { // e.g. " at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)" // Note that the "function name" can include a surprisingly large set of // characters, including angle brackets and square brackets. - { re: /^\s*at ([^\)]+) \(([^\)]+)\)$/, fnIx: 1, fileLineColIx: 2, style: 'v8' }, + { + re: /^\s*at ([^\)]+) \(([^\)]+)\)$/, + fnIx: 1, + fileLineColIx: 2, + style: 'v8' + }, // NodeJS alternate form, often mixed in with the Chrome style // e.g. " at /some/path:4320:20 @@ -30,7 +35,12 @@ getJasmineRequireObj().StackTrace = function(j$) { // PhantomJS on OS X, Safari, Firefox // e.g. "run@http://localhost:8888/__jasmine__/jasmine.js:4320:27" // or "http://localhost:8888/__jasmine__/jasmine.js:4320:27" - { re: /^(([^@\s]+)@)?([^\s]+)$/, fnIx: 2, fileLineColIx: 3, style: 'webkit' } + { + re: /^(([^@\s]+)@)?([^\s]+)$/, + fnIx: 2, + fileLineColIx: 3, + style: 'webkit' + } ]; // regexes should capture the function name (if any) as group 1 @@ -41,11 +51,16 @@ getJasmineRequireObj().StackTrace = function(j$) { var convertedLine = first(framePatterns, function(pattern) { var overallMatch = line.match(pattern.re), fileLineColMatch; - if (!overallMatch) { return null; } + if (!overallMatch) { + return null; + } fileLineColMatch = overallMatch[pattern.fileLineColIx].match( - /^(.*):(\d+):\d+$/); - if (!fileLineColMatch) { return null; } + /^(.*):(\d+):\d+$/ + ); + if (!fileLineColMatch) { + return null; + } style = style || pattern.style; return { diff --git a/src/core/Suite.js b/src/core/Suite.js index bbb582a8..75104068 100644 --- a/src/core/Suite.js +++ b/src/core/Suite.js @@ -48,7 +48,11 @@ getJasmineRequireObj().Suite = function(j$) { Suite.prototype.getFullName = function() { var fullName = []; - for (var parentSuite = this; parentSuite; parentSuite = parentSuite.parentSuite) { + for ( + var parentSuite = this; + parentSuite; + parentSuite = parentSuite.parentSuite + ) { if (parentSuite.parentSuite) { fullName.unshift(parentSuite.description); } @@ -85,7 +89,7 @@ getJasmineRequireObj().Suite = function(j$) { }; function removeFns(queueableFns) { - for(var i = 0; i < queueableFns.length; i++) { + for (var i = 0; i < queueableFns.length; i++) { queueableFns[i].fn = null; } } @@ -124,7 +128,9 @@ getJasmineRequireObj().Suite = function(j$) { Suite.prototype.sharedUserContext = function() { if (!this.sharedContext) { - this.sharedContext = this.parentSuite ? this.parentSuite.clonedSharedUserContext() : new j$.UserContext(); + this.sharedContext = this.parentSuite + ? this.parentSuite.clonedSharedUserContext() + : new j$.UserContext(); } return this.sharedContext; @@ -155,11 +161,11 @@ getJasmineRequireObj().Suite = function(j$) { this.result.failedExpectations.push(failedExpectation); }; - Suite.prototype.addExpectationResult = function () { - if(isFailure(arguments)) { + Suite.prototype.addExpectationResult = function() { + if (isFailure(arguments)) { var data = arguments[1]; this.result.failedExpectations.push(this.expectationResultFactory(data)); - if(this.throwOnExpectationFailure) { + if (this.throwOnExpectationFailure) { throw new j$.errors.ExpectationFailed(); } } @@ -169,7 +175,9 @@ getJasmineRequireObj().Suite = function(j$) { if (typeof deprecation === 'string') { deprecation = { message: deprecation }; } - this.result.deprecationWarnings.push(this.expectationResultFactory(deprecation)); + this.result.deprecationWarnings.push( + this.expectationResultFactory(deprecation) + ); }; function isFailure(args) { diff --git a/src/core/Timer.js b/src/core/Timer.js index f613dd1a..35ef9f32 100644 --- a/src/core/Timer.js +++ b/src/core/Timer.js @@ -1,6 +1,8 @@ getJasmineRequireObj().Timer = function() { var defaultNow = (function(Date) { - return function() { return new Date().getTime(); }; + return function() { + return new Date().getTime(); + }; })(Date); function Timer(options) { @@ -24,6 +26,8 @@ getJasmineRequireObj().Timer = function() { getJasmineRequireObj().noopTimer = function() { return { start: function() {}, - elapsed: function() { return 0; } + elapsed: function() { + return 0; + } }; -}; \ No newline at end of file +}; diff --git a/src/core/TreeProcessor.js b/src/core/TreeProcessor.js index d17b5d55..469c1009 100644 --- a/src/core/TreeProcessor.js +++ b/src/core/TreeProcessor.js @@ -1,16 +1,24 @@ getJasmineRequireObj().TreeProcessor = function() { function TreeProcessor(attrs) { var tree = attrs.tree, - runnableIds = attrs.runnableIds, - queueRunnerFactory = attrs.queueRunnerFactory, - nodeStart = attrs.nodeStart || function() {}, - nodeComplete = attrs.nodeComplete || function() {}, - orderChildren = attrs.orderChildren || function(node) { return node.children; }, - excludeNode = attrs.excludeNode || function(node) { return false; }, - stats = { valid: true }, - processed = false, - defaultMin = Infinity, - defaultMax = 1 - Infinity; + runnableIds = attrs.runnableIds, + queueRunnerFactory = attrs.queueRunnerFactory, + nodeStart = attrs.nodeStart || function() {}, + nodeComplete = attrs.nodeComplete || function() {}, + orderChildren = + attrs.orderChildren || + function(node) { + return node.children; + }, + excludeNode = + attrs.excludeNode || + function(node) { + return false; + }, + stats = { valid: true }, + processed = false, + defaultMin = Infinity, + defaultMax = 1 - Infinity; this.processTree = function() { processNode(tree, true); @@ -59,13 +67,15 @@ getJasmineRequireObj().TreeProcessor = function() { stats[node.id] = { excluded: excluded, willExecute: !excluded && !node.markedPending, - segments: [{ - index: 0, - owner: node, - nodes: [node], - min: startingMin(executableIndex), - max: startingMax(executableIndex) - }] + segments: [ + { + index: 0, + owner: node, + nodes: [node], + min: startingMin(executableIndex), + max: startingMax(executableIndex) + } + ] }; } else { var hasExecutableChild = false; @@ -107,14 +117,29 @@ getJasmineRequireObj().TreeProcessor = function() { return executableIndex === undefined ? defaultMax : executableIndex; } - function segmentChildren(node, orderedChildren, nodeStats, executableIndex) { - var currentSegment = { index: 0, owner: node, nodes: [], min: startingMin(executableIndex), max: startingMax(executableIndex) }, - result = [currentSegment], - lastMax = defaultMax, - orderedChildSegments = orderChildSegments(orderedChildren); + function segmentChildren( + node, + orderedChildren, + nodeStats, + executableIndex + ) { + var currentSegment = { + index: 0, + owner: node, + nodes: [], + min: startingMin(executableIndex), + max: startingMax(executableIndex) + }, + result = [currentSegment], + lastMax = defaultMax, + orderedChildSegments = orderChildSegments(orderedChildren); function isSegmentBoundary(minIndex) { - return lastMax !== defaultMax && minIndex !== defaultMin && lastMax < minIndex - 1; + return ( + lastMax !== defaultMax && + minIndex !== defaultMin && + lastMax < minIndex - 1 + ); } for (var i = 0; i < orderedChildSegments.length; i++) { @@ -123,7 +148,13 @@ getJasmineRequireObj().TreeProcessor = function() { minIndex = childSegment.min; if (isSegmentBoundary(minIndex)) { - currentSegment = {index: result.length, owner: node, nodes: [], min: defaultMin, max: defaultMax}; + currentSegment = { + index: result.length, + owner: node, + nodes: [], + min: defaultMin, + max: defaultMax + }; result.push(currentSegment); } @@ -138,11 +169,11 @@ getJasmineRequireObj().TreeProcessor = function() { function orderChildSegments(children) { var specifiedOrder = [], - unspecifiedOrder = []; + unspecifiedOrder = []; for (var i = 0; i < children.length; i++) { var child = children[i], - segments = stats[child.id].segments; + segments = stats[child.id].segments; for (var j = 0; j < segments.length; j++) { var seg = segments[j]; @@ -173,7 +204,7 @@ getJasmineRequireObj().TreeProcessor = function() { }; queueRunnerFactory({ - onComplete: function () { + onComplete: function() { var args = Array.prototype.slice.call(arguments, [0]); node.cleanupBeforeAfter(); nodeComplete(node, node.getResult(), function() { @@ -182,7 +213,7 @@ getJasmineRequireObj().TreeProcessor = function() { }, queueableFns: [onStart].concat(wrapChildren(node, segmentNumber)), userContext: node.sharedUserContext(), - onException: function () { + onException: function() { node.onException.apply(node, arguments); } }); @@ -190,17 +221,21 @@ getJasmineRequireObj().TreeProcessor = function() { }; } else { return { - fn: function(done) { node.execute(done, stats[node.id].excluded); } + fn: function(done) { + node.execute(done, stats[node.id].excluded); + } }; } } function wrapChildren(node, segmentNumber) { var result = [], - segmentChildren = stats[node.id].segments[segmentNumber].nodes; + segmentChildren = stats[node.id].segments[segmentNumber].nodes; for (var i = 0; i < segmentChildren.length; i++) { - result.push(executeNode(segmentChildren[i].owner, segmentChildren[i].index)); + result.push( + executeNode(segmentChildren[i].owner, segmentChildren[i].index) + ); } if (!stats[node.id].willExecute) { diff --git a/src/core/UserContext.js b/src/core/UserContext.js index 3b82ce8e..83e253fa 100644 --- a/src/core/UserContext.js +++ b/src/core/UserContext.js @@ -1,6 +1,5 @@ getJasmineRequireObj().UserContext = function(j$) { - function UserContext() { - } + function UserContext() {} UserContext.fromExisting = function(oldContext) { var context = new UserContext(); @@ -14,5 +13,5 @@ getJasmineRequireObj().UserContext = function(j$) { return context; }; - return UserContext; + return UserContext; }; diff --git a/src/core/base.js b/src/core/base.js index 9c8be408..40faa4ce 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -40,7 +40,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @return {Env} */ j$.getEnv = function(options) { - var env = j$.currentEnv_ = j$.currentEnv_ || new j$.Env(options); + var env = (j$.currentEnv_ = j$.currentEnv_ || new j$.Env(options)); //jasmine. singletons in here (setTimeout blah blah). return env; }; @@ -50,7 +50,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { }; j$.isObject_ = function(value) { - return !j$.util.isUndefined(value) && value !== null && j$.isA_('Object', value); + return ( + !j$.util.isUndefined(value) && value !== null && j$.isA_('Object', value) + ); }; j$.isString_ = function(value) { @@ -70,7 +72,8 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { }; j$.isTypedArray_ = function(value) { - return j$.isA_('Float32Array', value) || + return ( + j$.isA_('Float32Array', value) || j$.isA_('Float64Array', value) || j$.isA_('Int16Array', value) || j$.isA_('Int32Array', value) || @@ -78,7 +81,8 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { j$.isA_('Uint16Array', value) || j$.isA_('Uint32Array', value) || j$.isA_('Uint8Array', value) || - j$.isA_('Uint8ClampedArray', value); + j$.isA_('Uint8ClampedArray', value) + ); }; j$.isA_ = function(typeName, value) { @@ -108,9 +112,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { j$.isDomNode = function(obj) { // Node is a function, because constructors - return typeof jasmineGlobal.Node !== 'undefined' ? - obj instanceof jasmineGlobal.Node : - obj !== null && + return typeof jasmineGlobal.Node !== 'undefined' + ? obj instanceof jasmineGlobal.Node + : obj !== null && typeof obj === 'object' && typeof obj.nodeType === 'number' && typeof obj.nodeName === 'string'; @@ -118,15 +122,25 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { }; j$.isMap = function(obj) { - return typeof jasmineGlobal.Map !== 'undefined' && obj.constructor === jasmineGlobal.Map; + return ( + typeof jasmineGlobal.Map !== 'undefined' && + obj.constructor === jasmineGlobal.Map + ); }; j$.isSet = function(obj) { - return typeof jasmineGlobal.Set !== 'undefined' && obj.constructor === jasmineGlobal.Set; + return ( + typeof jasmineGlobal.Set !== 'undefined' && + obj.constructor === jasmineGlobal.Set + ); }; j$.isPromise = function(obj) { - return typeof jasmineGlobal.Promise !== 'undefined' && !!obj && obj.constructor === jasmineGlobal.Promise; + return ( + typeof jasmineGlobal.Promise !== 'undefined' && + !!obj && + obj.constructor === jasmineGlobal.Promise + ); }; j$.isPromiseLike = function(obj) { @@ -138,7 +152,8 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return func.name; } - var matches = func.toString().match(/^\s*function\s*(\w+)\s*\(/) || + var matches = + func.toString().match(/^\s*function\s*(\w+)\s*\(/) || func.toString().match(/^\s*\[object\s*(\w+)Constructor\]/); return matches ? matches[1] : ''; @@ -171,7 +186,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @name jasmine.truthy * @function */ - j$.truthy = function() { return new j$.Truthy(); }; + j$.truthy = function() { + return new j$.Truthy(); + }; /** * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), @@ -179,7 +196,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @name jasmine.falsy * @function */ - j$.falsy = function() { return new j$.Falsy(); }; + j$.falsy = function() { + return new j$.Falsy(); + }; /** * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), @@ -187,7 +206,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @name jasmine.empty * @function */ - j$.empty = function() { return new j$.Empty(); }; + j$.empty = function() { + return new j$.Empty(); + }; /** * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), @@ -195,7 +216,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * @name jasmine.notEmpty * @function */ - j$.notEmpty = function() { return new j$.NotEmpty(); }; + j$.notEmpty = function() { + return new j$.NotEmpty(); + }; /** * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), @@ -245,7 +268,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { if (!putativeSpy) { return false; } - return putativeSpy.and instanceof j$.SpyStrategy && - putativeSpy.calls instanceof j$.CallTracker; + return ( + putativeSpy.and instanceof j$.SpyStrategy && + putativeSpy.calls instanceof j$.CallTracker + ); }; }; diff --git a/src/core/errors.js b/src/core/errors.js index e3683c5a..ba7a502d 100644 --- a/src/core/errors.js +++ b/src/core/errors.js @@ -7,4 +7,4 @@ getJasmineRequireObj().errors = function() { return { ExpectationFailed: ExpectationFailed }; -}; \ No newline at end of file +}; diff --git a/src/core/requireCore.js b/src/core/requireCore.js index 622bc8c0..d6b98eb5 100644 --- a/src/core/requireCore.js +++ b/src/core/requireCore.js @@ -1,8 +1,12 @@ -var getJasmineRequireObj = (function (jasmineGlobal) { - /* globals exports, global, module, window */ +// eslint-disable-next-line no-unused-vars +var getJasmineRequireObj = (function(jasmineGlobal) { var jasmineRequire; - if (typeof module !== 'undefined' && module.exports && typeof exports !== 'undefined') { + if ( + typeof module !== 'undefined' && + module.exports && + typeof exports !== 'undefined' + ) { if (typeof global !== 'undefined') { jasmineGlobal = global; } else { @@ -10,7 +14,11 @@ var getJasmineRequireObj = (function (jasmineGlobal) { } jasmineRequire = exports; } else { - if (typeof window !== 'undefined' && typeof window.toString === 'function' && window.toString() === '[object GjsGlobal]') { + if ( + typeof window !== 'undefined' && + typeof window.toString === 'function' && + window.toString() === '[object GjsGlobal]' + ) { jasmineGlobal = window; } jasmineRequire = jasmineGlobal.jasmineRequire = {}; diff --git a/src/core/requireInterface.js b/src/core/requireInterface.js index c2d6de8e..cff7403b 100644 --- a/src/core/requireInterface.js +++ b/src/core/requireInterface.js @@ -203,7 +203,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * @function * @global * @param {String|Error} [error] - Reason for the failure. - */ + */ fail: function() { return env.fail.apply(env, arguments); }, diff --git a/src/core/util.js b/src/core/util.js index f885d2cb..0c25382a 100644 --- a/src/core/util.js +++ b/src/core/util.js @@ -1,10 +1,8 @@ getJasmineRequireObj().util = function(j$) { - var util = {}; util.inherit = function(childClass, parentClass) { - var Subclass = function() { - }; + var Subclass = function() {}; Subclass.prototype = parentClass.prototype; childClass.prototype = new Subclass(); }; @@ -13,7 +11,8 @@ getJasmineRequireObj().util = function(j$) { if (!str) { return str; } - return str.replace(/&/g, '&') + return str + .replace(/&/g, '&') .replace(//g, '>'); }; @@ -58,7 +57,7 @@ getJasmineRequireObj().util = function(j$) { util.cloneArgs = function(args) { var clonedArgs = []; var argsAsArray = j$.util.argsToArray(args); - for(var i = 0; i < argsAsArray.length; i++) { + for (var i = 0; i < argsAsArray.length; i++) { var str = Object.prototype.toString.apply(argsAsArray[i]), primitives = /^\[object (Boolean|String|RegExp|Number)/; @@ -100,7 +99,7 @@ getJasmineRequireObj().util = function(j$) { return Object.prototype.hasOwnProperty.call(obj, key); }; - util.errorWithStack = function errorWithStack () { + util.errorWithStack = function errorWithStack() { // Don't throw and catch if we don't have to, because it makes it harder // for users to debug their code with exception breakpoints. var error = new Error(); @@ -132,7 +131,7 @@ getJasmineRequireObj().util = function(j$) { return result; }; - }()); + })(); return util; }; diff --git a/src/html/HtmlReporter.js b/src/html/HtmlReporter.js index 880f9558..2a89aaca 100644 --- a/src/html/HtmlReporter.js +++ b/src/html/HtmlReporter.js @@ -23,8 +23,7 @@ jasmineRequire.HtmlReporter = function(j$) { } }; - ResultsStateBuilder.prototype.specStarted = function(result) { - }; + ResultsStateBuilder.prototype.specStarted = function(result) {}; ResultsStateBuilder.prototype.specDone = function(result) { this.currentParent.addChild(result, 'spec'); @@ -42,15 +41,16 @@ jasmineRequire.HtmlReporter = function(j$) { } }; - - function HtmlReporter(options) { - var config = function() { return (options.env && options.env.configuration()) || {}; }, + var config = function() { + return (options.env && options.env.configuration()) || {}; + }, getContainer = options.getContainer, createElement = options.createElement, createTextNode = options.createTextNode, navigateWithNewParam = options.navigateWithNewParam || function() {}, - addToExistingQueryString = options.addToExistingQueryString || defaultQueryString, + addToExistingQueryString = + options.addToExistingQueryString || defaultQueryString, filterSpecs = options.filterSpecs, timer = options.timer || j$.noopTimer, htmlReporterMain, @@ -59,15 +59,25 @@ jasmineRequire.HtmlReporter = function(j$) { this.initialize = function() { clearPrior(); - htmlReporterMain = createDom('div', {className: 'jasmine_html-reporter'}, - createDom('div', {className: 'jasmine-banner'}, - createDom('a', {className: 'jasmine-title', href: 'http://jasmine.github.io/', target: '_blank'}), - createDom('span', {className: 'jasmine-version'}, j$.version) + htmlReporterMain = createDom( + 'div', + { className: 'jasmine_html-reporter' }, + createDom( + 'div', + { className: 'jasmine-banner' }, + createDom('a', { + className: 'jasmine-title', + href: 'http://jasmine.github.io/', + target: '_blank' + }), + createDom('span', { className: 'jasmine-version' }, j$.version) ), - createDom('ul', {className: 'jasmine-symbol-summary'}), - createDom('div', {className: 'jasmine-alert'}), - createDom('div', {className: 'jasmine-results'}, - createDom('div', {className: 'jasmine-failures'}) + createDom('ul', { className: 'jasmine-symbol-summary' }), + createDom('div', { className: 'jasmine-alert' }), + createDom( + 'div', + { className: 'jasmine-results' }, + createDom('div', { className: 'jasmine-failures' }) ) ); getContainer().appendChild(htmlReporterMain); @@ -79,7 +89,7 @@ jasmineRequire.HtmlReporter = function(j$) { timer.start(); }; - var summary = createDom('div', {className: 'jasmine-summary'}); + var summary = createDom('div', { className: 'jasmine-summary' }); var stateBuilder = new ResultsStateBuilder(); @@ -104,20 +114,25 @@ jasmineRequire.HtmlReporter = function(j$) { this.specDone = function(result) { stateBuilder.specDone(result); - if(noExpectations(result) && typeof console !== 'undefined' && typeof console.error !== 'undefined') { - console.error('Spec \'' + result.fullName + '\' has no expectations.'); + if ( + noExpectations(result) && + typeof console !== 'undefined' && + typeof console.error !== 'undefined' + ) { + console.error("Spec '" + result.fullName + "' has no expectations."); } if (!symbols) { symbols = find('.jasmine-symbol-summary'); } - symbols.appendChild(createDom('li', { + symbols.appendChild( + createDom('li', { className: this.displaySpecInCorrectFormat(result), id: 'spec_' + result.id, title: result.fullName - } - )); + }) + ); if (result.status === 'failed') { failures.push(failureDom(result)); @@ -127,12 +142,16 @@ jasmineRequire.HtmlReporter = function(j$) { }; this.displaySpecInCorrectFormat = function(result) { - return noExpectations(result) ? 'jasmine-empty' : this.resultStatus(result.status); + return noExpectations(result) + ? 'jasmine-empty' + : this.resultStatus(result.status); }; this.resultStatus = function(status) { - if(status === 'excluded') { - return config().hideDisabled ? 'jasmine-excluded-no-display' : 'jasmine-excluded'; + if (status === 'excluded') { + return config().hideDisabled + ? 'jasmine-excluded-no-display' + : 'jasmine-excluded'; } return 'jasmine-' + status; }; @@ -142,16 +161,33 @@ jasmineRequire.HtmlReporter = function(j$) { var alert = find('.jasmine-alert'); var order = doneResult && doneResult.order; var i; - alert.appendChild(createDom('span', {className: 'jasmine-duration'}, 'finished in ' + timer.elapsed() / 1000 + 's')); + alert.appendChild( + createDom( + 'span', + { className: 'jasmine-duration' }, + 'finished in ' + timer.elapsed() / 1000 + 's' + ) + ); banner.appendChild(optionsMenu(config())); if (stateBuilder.specsExecuted < totalSpecsDefined) { - var skippedMessage = 'Ran ' + stateBuilder.specsExecuted + ' of ' + totalSpecsDefined + ' specs - run all'; + var skippedMessage = + 'Ran ' + + stateBuilder.specsExecuted + + ' of ' + + totalSpecsDefined + + ' specs - run all'; var skippedLink = addToExistingQueryString('spec', ''); alert.appendChild( - createDom('span', {className: 'jasmine-bar jasmine-skipped'}, - createDom('a', {href: skippedLink, title: 'Run all specs'}, skippedMessage) + createDom( + 'span', + { className: 'jasmine-bar jasmine-skipped' }, + createDom( + 'a', + { href: skippedLink, title: 'Run all specs' }, + skippedMessage + ) ) ); } @@ -161,34 +197,66 @@ jasmineRequire.HtmlReporter = function(j$) { var failed = stateBuilder.failureCount + globalFailures.length > 0; if (totalSpecsDefined > 0 || failed) { - statusBarMessage += pluralize('spec', stateBuilder.specsExecuted) + ', ' + pluralize('failure', stateBuilder.failureCount); - if (stateBuilder.pendingSpecCount) { statusBarMessage += ', ' + pluralize('pending spec', stateBuilder.pendingSpecCount); } + statusBarMessage += + pluralize('spec', stateBuilder.specsExecuted) + + ', ' + + pluralize('failure', stateBuilder.failureCount); + if (stateBuilder.pendingSpecCount) { + statusBarMessage += + ', ' + pluralize('pending spec', stateBuilder.pendingSpecCount); + } } if (doneResult.overallStatus === 'passed') { statusBarClassName += ' jasmine-passed '; } else if (doneResult.overallStatus === 'incomplete') { statusBarClassName += ' jasmine-incomplete '; - statusBarMessage = 'Incomplete: ' + doneResult.incompleteReason + ', ' + statusBarMessage; + statusBarMessage = + 'Incomplete: ' + + doneResult.incompleteReason + + ', ' + + statusBarMessage; } else { statusBarClassName += ' jasmine-failed '; } var seedBar; if (order && order.random) { - seedBar = createDom('span', {className: 'jasmine-seed-bar'}, + seedBar = createDom( + 'span', + { className: 'jasmine-seed-bar' }, ', randomized with seed ', - createDom('a', {title: 'randomized with seed ' + order.seed, href: seedHref(order.seed)}, order.seed) + createDom( + 'a', + { + title: 'randomized with seed ' + order.seed, + href: seedHref(order.seed) + }, + order.seed + ) ); } - alert.appendChild(createDom('span', {className: statusBarClassName}, statusBarMessage, seedBar)); + alert.appendChild( + createDom( + 'span', + { className: statusBarClassName }, + statusBarMessage, + seedBar + ) + ); var errorBarClassName = 'jasmine-bar jasmine-errored'; var afterAllMessagePrefix = 'AfterAll '; - for(i = 0; i < globalFailures.length; i++) { - alert.appendChild(createDom('span', {className: errorBarClassName}, globalFailureMessage(globalFailures[i]))); + for (i = 0; i < globalFailures.length; i++) { + alert.appendChild( + createDom( + 'span', + { className: errorBarClassName }, + globalFailureMessage(globalFailures[i]) + ) + ); } function globalFailureMessage(failure) { @@ -196,7 +264,9 @@ jasmineRequire.HtmlReporter = function(j$) { var prefix = 'Error during loading: ' + failure.message; if (failure.filename) { - return prefix + ' in ' + failure.filename + ' line ' + failure.lineno; + return ( + prefix + ' in ' + failure.filename + ' line ' + failure.lineno + ); } else { return prefix; } @@ -208,9 +278,15 @@ jasmineRequire.HtmlReporter = function(j$) { addDeprecationWarnings(doneResult); var warningBarClassName = 'jasmine-bar jasmine-warning'; - for(i = 0; i < deprecationWarnings.length; i++) { + for (i = 0; i < deprecationWarnings.length; i++) { var warning = deprecationWarnings[i]; - alert.appendChild(createDom('span', {className: warningBarClassName}, 'DEPRECATION: ' + warning)); + alert.appendChild( + createDom( + 'span', + { className: warningBarClassName }, + 'DEPRECATION: ' + warning + ) + ); } var results = find('.jasmine-results'); @@ -220,13 +296,29 @@ jasmineRequire.HtmlReporter = function(j$) { if (failures.length) { alert.appendChild( - createDom('span', {className: 'jasmine-menu jasmine-bar jasmine-spec-list'}, + createDom( + 'span', + { className: 'jasmine-menu jasmine-bar jasmine-spec-list' }, createDom('span', {}, 'Spec List | '), - createDom('a', {className: 'jasmine-failures-menu', href: '#'}, 'Failures'))); + createDom( + 'a', + { className: 'jasmine-failures-menu', href: '#' }, + 'Failures' + ) + ) + ); alert.appendChild( - createDom('span', {className: 'jasmine-menu jasmine-bar jasmine-failure-list'}, - createDom('a', {className: 'jasmine-spec-list-menu', href: '#'}, 'Spec List'), - createDom('span', {}, ' | Failures '))); + createDom( + 'span', + { className: 'jasmine-menu jasmine-bar jasmine-failure-list' }, + createDom( + 'a', + { className: 'jasmine-spec-list-menu', href: '#' }, + 'Spec List' + ), + createDom('span', {}, ' | Failures ') + ) + ); find('.jasmine-failures-menu').onclick = function() { setMenuModeTo('jasmine-failure-list'); @@ -247,17 +339,30 @@ jasmineRequire.HtmlReporter = function(j$) { return this; function failureDom(result) { - var failure = - createDom('div', {className: 'jasmine-spec-detail jasmine-failed'}, - failureDescription(result, stateBuilder.currentParent), - createDom('div', {className: 'jasmine-messages'}) - ); + var failure = createDom( + 'div', + { className: 'jasmine-spec-detail jasmine-failed' }, + failureDescription(result, stateBuilder.currentParent), + createDom('div', { className: 'jasmine-messages' }) + ); var messages = failure.childNodes[1]; for (var i = 0; i < result.failedExpectations.length; i++) { var expectation = result.failedExpectations[i]; - messages.appendChild(createDom('div', {className: 'jasmine-result-message'}, expectation.message)); - messages.appendChild(createDom('div', {className: 'jasmine-stack-trace'}, expectation.stack)); + messages.appendChild( + createDom( + 'div', + { className: 'jasmine-result-message' }, + expectation.message + ) + ); + messages.appendChild( + createDom( + 'div', + { className: 'jasmine-stack-trace' }, + expectation.stack + ) + ); } return failure; @@ -271,9 +376,20 @@ jasmineRequire.HtmlReporter = function(j$) { continue; } if (resultNode.type === 'suite') { - var suiteListNode = createDom('ul', {className: 'jasmine-suite', id: 'suite-' + resultNode.result.id}, - createDom('li', {className: 'jasmine-suite-detail jasmine-' + resultNode.result.status}, - createDom('a', {href: specHref(resultNode.result)}, resultNode.result.description) + var suiteListNode = createDom( + 'ul', + { className: 'jasmine-suite', id: 'suite-' + resultNode.result.id }, + createDom( + 'li', + { + className: + 'jasmine-suite-detail jasmine-' + resultNode.result.status + }, + createDom( + 'a', + { href: specHref(resultNode.result) }, + resultNode.result.description + ) ) ); @@ -282,22 +398,34 @@ jasmineRequire.HtmlReporter = function(j$) { } if (resultNode.type === 'spec') { if (domParent.getAttribute('class') !== 'jasmine-specs') { - specListNode = createDom('ul', {className: 'jasmine-specs'}); + specListNode = createDom('ul', { className: 'jasmine-specs' }); domParent.appendChild(specListNode); } var specDescription = resultNode.result.description; - if(noExpectations(resultNode.result)) { + if (noExpectations(resultNode.result)) { specDescription = 'SPEC HAS NO EXPECTATIONS ' + specDescription; } - if(resultNode.result.status === 'pending' && resultNode.result.pendingReason !== '') { - specDescription = specDescription + ' PENDING WITH MESSAGE: ' + resultNode.result.pendingReason; + if ( + resultNode.result.status === 'pending' && + resultNode.result.pendingReason !== '' + ) { + specDescription = + specDescription + + ' PENDING WITH MESSAGE: ' + + resultNode.result.pendingReason; } specListNode.appendChild( - createDom('li', { + createDom( + 'li', + { className: 'jasmine-' + resultNode.result.status, id: 'spec-' + resultNode.result.id }, - createDom('a', {href: specHref(resultNode.result)}, specDescription) + createDom( + 'a', + { href: specHref(resultNode.result) }, + specDescription + ) ) ); } @@ -305,37 +433,69 @@ jasmineRequire.HtmlReporter = function(j$) { } function optionsMenu(config) { - var optionsMenuDom = createDom('div', { className: 'jasmine-run-options' }, + var optionsMenuDom = createDom( + 'div', + { className: 'jasmine-run-options' }, createDom('span', { className: 'jasmine-trigger' }, 'Options'), - createDom('div', { className: 'jasmine-payload' }, - createDom('div', { className: 'jasmine-stop-on-failure' }, + createDom( + 'div', + { className: 'jasmine-payload' }, + createDom( + 'div', + { className: 'jasmine-stop-on-failure' }, createDom('input', { className: 'jasmine-fail-fast', id: 'jasmine-fail-fast', type: 'checkbox' }), - createDom('label', { className: 'jasmine-label', 'for': 'jasmine-fail-fast' }, 'stop execution on spec failure')), - createDom('div', { className: 'jasmine-throw-failures' }, + createDom( + 'label', + { className: 'jasmine-label', for: 'jasmine-fail-fast' }, + 'stop execution on spec failure' + ) + ), + createDom( + 'div', + { className: 'jasmine-throw-failures' }, createDom('input', { className: 'jasmine-throw', id: 'jasmine-throw-failures', type: 'checkbox' }), - createDom('label', { className: 'jasmine-label', 'for': 'jasmine-throw-failures' }, 'stop spec on expectation failure')), - createDom('div', { className: 'jasmine-random-order' }, + createDom( + 'label', + { className: 'jasmine-label', for: 'jasmine-throw-failures' }, + 'stop spec on expectation failure' + ) + ), + createDom( + 'div', + { className: 'jasmine-random-order' }, createDom('input', { className: 'jasmine-random', id: 'jasmine-random-order', type: 'checkbox' }), - createDom('label', { className: 'jasmine-label', 'for': 'jasmine-random-order' }, 'run tests in random order')), - createDom('div', { className: 'jasmine-hide-disabled' }, + createDom( + 'label', + { className: 'jasmine-label', for: 'jasmine-random-order' }, + 'run tests in random order' + ) + ), + createDom( + 'div', + { className: 'jasmine-hide-disabled' }, createDom('input', { className: 'jasmine-disabled', id: 'jasmine-hide-disabled', type: 'checkbox' }), - createDom('label', { className: 'jasmine-label', 'for': 'jasmine-hide-disabled' }, 'hide disabled tests')) + createDom( + 'label', + { className: 'jasmine-label', for: 'jasmine-hide-disabled' }, + 'hide disabled tests' + ) + ) ) ); @@ -345,13 +505,17 @@ jasmineRequire.HtmlReporter = function(j$) { navigateWithNewParam('failFast', !config.failFast); }; - var throwCheckbox = optionsMenuDom.querySelector('#jasmine-throw-failures'); + var throwCheckbox = optionsMenuDom.querySelector( + '#jasmine-throw-failures' + ); throwCheckbox.checked = config.oneFailurePerSpec; throwCheckbox.onclick = function() { navigateWithNewParam('throwFailures', !config.oneFailurePerSpec); }; - var randomCheckbox = optionsMenuDom.querySelector('#jasmine-random-order'); + var randomCheckbox = optionsMenuDom.querySelector( + '#jasmine-random-order' + ); randomCheckbox.checked = config.random; randomCheckbox.onclick = function() { navigateWithNewParam('random', !config.random); @@ -369,7 +533,10 @@ jasmineRequire.HtmlReporter = function(j$) { optionsTrigger.onclick = function() { if (isOpen.test(optionsPayload.className)) { - optionsPayload.className = optionsPayload.className.replace(isOpen, ''); + optionsPayload.className = optionsPayload.className.replace( + isOpen, + '' + ); } else { optionsPayload.className += ' jasmine-open'; } @@ -379,14 +546,24 @@ jasmineRequire.HtmlReporter = function(j$) { } function failureDescription(result, suite) { - var wrapper = createDom('div', {className: 'jasmine-description'}, - createDom('a', {title: result.description, href: specHref(result)}, result.description) + var wrapper = createDom( + 'div', + { className: 'jasmine-description' }, + createDom( + 'a', + { title: result.description, href: specHref(result) }, + result.description + ) ); var suiteLink; while (suite && suite.parent) { wrapper.insertBefore(createTextNode(' > '), wrapper.firstChild); - suiteLink = createDom('a', {href: suiteHref(suite)}, suite.result.description); + suiteLink = createDom( + 'a', + { href: suiteHref(suite) }, + suite.result.description + ); wrapper.insertBefore(suiteLink, wrapper.firstChild); suite = suite.parent; @@ -408,7 +585,7 @@ jasmineRequire.HtmlReporter = function(j$) { function addDeprecationWarnings(result) { if (result && result.deprecationWarnings) { - for(var i = 0; i < result.deprecationWarnings.length; i++) { + for (var i = 0; i < result.deprecationWarnings.length; i++) { var warning = result.deprecationWarnings[i].message; if (!j$.util.arrayContains(warning)) { deprecationWarnings.push(warning); @@ -425,7 +602,7 @@ jasmineRequire.HtmlReporter = function(j$) { // return the reporter var oldReporter = find(''); - if(oldReporter) { + if (oldReporter) { getContainer().removeChild(oldReporter); } } @@ -457,7 +634,7 @@ jasmineRequire.HtmlReporter = function(j$) { } function pluralize(singular, count) { - var word = (count == 1 ? singular : singular + 's'); + var word = count == 1 ? singular : singular + 's'; return '' + count + ' ' + word; } @@ -479,8 +656,10 @@ jasmineRequire.HtmlReporter = function(j$) { } function noExpectations(result) { - return (result.failedExpectations.length + result.passedExpectations.length) === 0 && - result.status === 'passed'; + return ( + result.failedExpectations.length + result.passedExpectations.length === + 0 && result.status === 'passed' + ); } function hasActiveSpec(resultNode) { diff --git a/src/html/HtmlSpecFilter.js b/src/html/HtmlSpecFilter.js index 3d0a6c23..7a18f1ec 100644 --- a/src/html/HtmlSpecFilter.js +++ b/src/html/HtmlSpecFilter.js @@ -1,6 +1,9 @@ jasmineRequire.HtmlSpecFilter = function() { function HtmlSpecFilter(options) { - var filterString = options && options.filterString() && options.filterString().replace(/[-[\]{}()*+?.,\\^$|#\s]/g, '\\$&'); + var filterString = + options && + options.filterString() && + options.filterString().replace(/[-[\]{}()*+?.,\\^$|#\s]/g, '\\$&'); var filterPattern = new RegExp(filterString); this.matches = function(specName) { diff --git a/src/html/QueryString.js b/src/html/QueryString.js index a72d92d8..c4ce950e 100644 --- a/src/html/QueryString.js +++ b/src/html/QueryString.js @@ -1,8 +1,10 @@ jasmineRequire.QueryString = function() { function QueryString(options) { - this.navigateWithNewParam = function(key, value) { - options.getWindowLocation().search = this.fullStringWithNewParam(key, value); + options.getWindowLocation().search = this.fullStringWithNewParam( + key, + value + ); }; this.fullStringWithNewParam = function(key, value) { @@ -20,7 +22,9 @@ jasmineRequire.QueryString = function() { function toQueryString(paramMap) { var qStrPairs = []; for (var prop in paramMap) { - qStrPairs.push(encodeURIComponent(prop) + '=' + encodeURIComponent(paramMap[prop])); + qStrPairs.push( + encodeURIComponent(prop) + '=' + encodeURIComponent(paramMap[prop]) + ); } return '?' + qStrPairs.join('&'); } @@ -44,7 +48,6 @@ jasmineRequire.QueryString = function() { return paramMap; } - } return QueryString; From 8af669677adcaeb8f74761991c99d4d702a3a410 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Thu, 23 May 2019 17:29:12 -0700 Subject: [PATCH 031/201] Cleanup spy promise strategies to be more consistent with Jasmine at large - Rename `resolveWith` to `resolveTo` to match `toBeResolvedTo` - No longer wrap non-Errors in `rejectWith` - Fixes #1715 --- lib/jasmine-core/jasmine.js | 9 ++++----- spec/core/SpySpec.js | 4 ++-- spec/core/SpyStrategySpec.js | 12 ++++++------ src/core/SpyStrategy.js | 9 ++++----- 4 files changed, 16 insertions(+), 18 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 3bd8dd93..50346ee0 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -6989,12 +6989,12 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to return a promise resolving to the specified value when invoked. - * @name SpyStrategy#resolveWith + * @name SpyStrategy#resolveTo * @function * @param {*} value The value to return. */ - this.resolveWith = function(value) { - var Promise = requirePromise('resolveWith'); + this.resolveTo = function(value) { + var Promise = requirePromise('resolveTo'); self.plan = function() { return Promise.resolve(value); }; @@ -7009,10 +7009,9 @@ getJasmineRequireObj().SpyStrategy = function(j$) { */ this.rejectWith = function(value) { var Promise = requirePromise('rejectWith'); - var error = value instanceof Error ? value : new Error(value); self.plan = function() { - return Promise.reject(error); + return Promise.reject(value); }; return self.getSpy(); }; diff --git a/spec/core/SpySpec.js b/spec/core/SpySpec.js index fd7dc4e6..f2eea200 100644 --- a/spec/core/SpySpec.js +++ b/spec/core/SpySpec.js @@ -208,7 +208,7 @@ describe('Spies', function() { it('works with global Promise library when available', function(done) { jasmine.getEnv().requirePromises(); - var spy = env.createSpy('foo').and.resolveWith(42); + var spy = env.createSpy('foo').and.resolveTo(42); spy() .then(function(result) { expect(result).toEqual(42); @@ -225,7 +225,7 @@ describe('Spies', function() { customPromise.resolve.and.returnValue('resolved'); env.configure({ Promise: customPromise }); - var spy = env.createSpy('foo').and.resolveWith(42); + var spy = env.createSpy('foo').and.resolveTo(42); expect(spy()).toEqual('resolved'); expect(customPromise.resolve).toHaveBeenCalledWith(42); }); diff --git a/spec/core/SpyStrategySpec.js b/spec/core/SpyStrategySpec.js index ae2679ac..e861dc8b 100644 --- a/spec/core/SpyStrategySpec.js +++ b/spec/core/SpyStrategySpec.js @@ -117,7 +117,7 @@ describe('SpyStrategy', function() { }); }); - describe('#resolveWith', function() { + describe('#resolveTo', function() { it('allows a resolved promise to be returned', function(done) { jasmine.getEnv().requirePromises(); @@ -130,7 +130,7 @@ describe('SpyStrategy', function() { getPromise: getPromise }); - spyStrategy.resolveWith(37); + spyStrategy.resolveTo(37); spyStrategy .exec() .then(function(returnValue) { @@ -145,9 +145,9 @@ describe('SpyStrategy', function() { spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }); expect(function() { - spyStrategy.resolveWith(37); + spyStrategy.resolveTo(37); }).toThrowError( - 'resolveWith requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`' + 'resolveTo requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`' ); }); }); @@ -176,7 +176,7 @@ describe('SpyStrategy', function() { .catch(done.fail); }); - it('allows a non-Error to be rejected, wrapping it in an exception when executed', function(done) { + it('allows a non-Error to be rejected', function(done) { jasmine.getEnv().requirePromises(); var originalFn = jasmine.createSpy('original'), @@ -193,7 +193,7 @@ describe('SpyStrategy', function() { .exec() .then(done.fail) .catch(function(error) { - expect(error).toEqual(new Error('oops')); + expect(error).toEqual('oops'); done(); }) .catch(done.fail); diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index 81ccf2ce..e1559a7d 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -46,12 +46,12 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to return a promise resolving to the specified value when invoked. - * @name SpyStrategy#resolveWith + * @name SpyStrategy#resolveTo * @function * @param {*} value The value to return. */ - this.resolveWith = function(value) { - var Promise = requirePromise('resolveWith'); + this.resolveTo = function(value) { + var Promise = requirePromise('resolveTo'); self.plan = function() { return Promise.resolve(value); }; @@ -66,10 +66,9 @@ getJasmineRequireObj().SpyStrategy = function(j$) { */ this.rejectWith = function(value) { var Promise = requirePromise('rejectWith'); - var error = value instanceof Error ? value : new Error(value); self.plan = function() { - return Promise.reject(error); + return Promise.reject(value); }; return self.getSpy(); }; From 0644731680de46ed90ead2908eff262ea1696156 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Mon, 11 Mar 2019 17:27:46 -0700 Subject: [PATCH 032/201] Switch to using new `jasmine-browser-runner` to server files for local testing --- .github/CONTRIBUTING.md | 28 +++++------------------ .travis.yml | 2 +- Gemfile | 7 ------ MIT.LICENSE | 2 +- Rakefile | 18 --------------- jasmine-core.gemspec | 4 ---- package.json | 6 +++-- spec/support/jasmine-browser.json | 33 +++++++++++++++++++++++++++ spec/support/jasmine.yml | 35 ----------------------------- spec/support/jasmine_helper.rb | 3 --- spec/support/localJasmineBrowser.js | 8 +++++++ 11 files changed, 53 insertions(+), 93 deletions(-) delete mode 100644 Rakefile create mode 100644 spec/support/jasmine-browser.json delete mode 100644 spec/support/jasmine.yml delete mode 100644 spec/support/jasmine_helper.rb create mode 100644 spec/support/localJasmineBrowser.js diff --git a/.github/CONTRIBUTING.md b/.github/CONTRIBUTING.md index 25a848fd..2ee4cbd3 100644 --- a/.github/CONTRIBUTING.md +++ b/.github/CONTRIBUTING.md @@ -64,7 +64,7 @@ Jasmine supports the following environments: * Node.js * 8 * 10 - * 11 + * 12 ## Development @@ -80,9 +80,9 @@ To install the Node dependencies, you will need Node.js, Npm, and [Grunt](http:/ ...will install all of the node modules locally. Now run - $ grunt + $ npm test -...if you see that JSHint runs, your system is ready. +...you should see tests run and eslint checking formatting. ### How to write new Jasmine code @@ -93,7 +93,7 @@ Or, How to make a successful pull request * _Be browser agnostic_ - if you must rely on browser-specific functionality, please write it in a way that degrades gracefully * _Write specs_ - Jasmine's a testing framework; don't add functionality without test-driving it * _Write code in the style of the rest of the repo_ - Jasmine should look like a cohesive whole -* _Ensure the *entire* test suite is green_ in all the big browsers, Node, and JSHint - your contribution shouldn't break Jasmine for other users +* _Ensure the *entire* test suite is green_ in all the big browsers, Node, and ESLint - your contribution shouldn't break Jasmine for other users Follow these tips and your pull request, patch, or suggestion is much more likely to be integrated. @@ -105,35 +105,19 @@ Jasmine uses some internal tooling to test itself in browser on Travis. This too You can also set the `JASMINE_BROWSER` environment variable to specify which browser should be used. -Jasmine uses the [Jasmine NPM package](http://github.com/jasmine/jasmine-npm) to test itself in a Node.js/npm environment. - - $ npm test - -...and then the results will print to the console. All specs run except those that expect a browser (the specs in `spec/html` are ignored). - The easiest way to run the tests in **Internet Explorer** is to run a VM that has IE installed. It's easy to do this with VirtualBox. -__Note__: these steps currently still rely on the Jasmine ruby gem and not the new Node.js based tooling. To install the Ruby dependencies, you will need Ruby, Rubygems, and Bundler available. Then: - - $ bundle - -...will install all of the Ruby dependencies. If the ffi gem fails to build its native extensions, you may need to manually install some system dependencies. On Ubuntu: - - $ apt-get install gcc ruby ruby-dev libxml2 libxml2-dev libxslt1-dev - -...should get you to the point that `bundle` can install everything. - 1. Download and install [VirtualBox](https://www.virtualbox.org/wiki/Downloads). 1. Download a VM image [from Microsoft](https://developer.microsoft.com/en-us/microsoft-edge/tools/vms/). Select "VirtualBox" as the platform. 1. Unzip the downloaded archive. There should be an OVA file inside. 1. In VirtualBox, choose `File > Import Appliance` and select the OVA file. Accept the default settings in the dialog that appears. Now you have a Windows VM! 1. Run the VM and start IE. -1. With `bundle exec rake jasmine` running on your host machine, navigate to `http://10.0.2.2:8888` in IE. +1. With `npm run serve` running on your host machine, navigate to `http://10.0.2.2:8888` in IE. ## Before Committing or Submitting a Pull Request 1. Ensure all specs are green in browser *and* node -1. Ensure JSHint is green with `grunt jshint` +1. Ensure eslint and prettier are clean as part of your `npm test` command. You can run `npm run cleanup` to have prettier re-write the files. 1. Build `jasmine.js` with `grunt buildDistribution` and run all specs again - this ensures that your changes self-test well 1. Revert your changes to `jasmine.js` and `jasmine-html.js` * We do this because `jasmine.js` and `jasmine-html.js` are auto-generated (as you've seen in the previous steps) and accepting multiple pull requests when this auto-generated file changes causes lots of headaches diff --git a/.travis.yml b/.travis.yml index 0ce6dc7d..09af26cb 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,6 +1,6 @@ language: node_js node_js: - - "11" + - "12" - "10" - "8" diff --git a/Gemfile b/Gemfile index 907e2780..851fabc2 100644 --- a/Gemfile +++ b/Gemfile @@ -1,9 +1,2 @@ source 'https://rubygems.org' -gem "jasmine", :git => 'https://github.com/jasmine/jasmine-gem.git' -# gem "jasmine", path: "../jasmine-gem" - gemspec - -gem "jasmine_selenium_runner", :github => 'jasmine/jasmine_selenium_runner' - -gem "anchorman" diff --git a/MIT.LICENSE b/MIT.LICENSE index db12c929..25c23f9d 100644 --- a/MIT.LICENSE +++ b/MIT.LICENSE @@ -1,4 +1,4 @@ -Copyright (c) 2008-2017 Pivotal Labs +Copyright (c) 2008-2019 Pivotal Labs Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the diff --git a/Rakefile b/Rakefile deleted file mode 100644 index da161143..00000000 --- a/Rakefile +++ /dev/null @@ -1,18 +0,0 @@ -require "bundler" -Bundler::GemHelper.install_tasks -require "json" -require "jasmine" -unless ENV["JASMINE_BROWSER"] == 'phantomjs' - require "jasmine_selenium_runner" -end -load "jasmine/tasks/jasmine.rake" - -namespace :jasmine do - task :set_env do - ENV['JASMINE_CONFIG_PATH'] ||= 'spec/support/jasmine.yml' - end -end - -task "jasmine:configure" => "jasmine:set_env" - -task :default => "jasmine:ci" diff --git a/jasmine-core.gemspec b/jasmine-core.gemspec index 3e0a6f96..df310a85 100644 --- a/jasmine-core.gemspec +++ b/jasmine-core.gemspec @@ -16,8 +16,4 @@ Gem::Specification.new do |s| s.files = Dir.glob("./lib/**/*") s.require_paths = ["lib"] - s.add_development_dependency "rake" - s.add_development_dependency "sauce-connect" - s.add_development_dependency "compass" - s.add_development_dependency "jasmine_selenium_runner", ">= 0.2.0" end diff --git a/package.json b/package.json index 9cefdc97..d0599ac2 100644 --- a/package.json +++ b/package.json @@ -13,9 +13,10 @@ "bdd" ], "scripts": { - "pretest": "eslint src/**/*.js spec/**/*.js && prettier --check src/**/*.js spec/**/*.js", + "posttest": "eslint src/**/*.js spec/**/*.js && prettier --check src/**/*.js spec/**/*.js", "test": "grunt execSpecsInNode", - "cleanup": "prettier --write src/**/*.js spec/**/*.js" + "cleanup": "prettier --write src/**/*.js spec/**/*.js", + "serve": "node spec/support/localJasmineBrowser.js" }, "description": "Official packaging of Jasmine's core files for use by Node.js projects.", "homepage": "https://jasmine.github.io", @@ -32,6 +33,7 @@ "grunt-css-url-embed": "^1.11.1", "grunt-sass": "^3.0.2", "jasmine": "^3.4.0", + "jasmine-browser-runner": "0.0.2", "jsdom": "^15.0.0", "load-grunt-tasks": "^4.0.0", "node-sass": "^4.11.0", diff --git a/spec/support/jasmine-browser.json b/spec/support/jasmine-browser.json new file mode 100644 index 00000000..de122f43 --- /dev/null +++ b/spec/support/jasmine-browser.json @@ -0,0 +1,33 @@ +{ + "srcDir": "src", + "srcFiles": [ + "core/requireCore.js", + "core/base.js", + "core/util.js", + "core/Spec.js", + "core/Env.js", + "core/JsApiReporter.js", + "core/PrettyPrinter.js", + "core/Suite.js", + "core/**/*.js", + "html/**/*.js", + "**/*.js" + ], + "specDir": "spec", + "specFiles": [ + "**/*[Ss]pec.js", + "!npmPackage/**/*" + ], + "helpers": [ + "helpers/asyncAwait.js", + "helpers/BrowserFlags.js", + "helpers/checkForMap.js", + "helpers/checkForSet.js", + "helpers/checkForSymbol.js", + "helpers/checkForTypedArrays.js", + "helpers/integrationMatchers.js", + "helpers/promises.js", + "helpers/defineJasmineUnderTest.js" + ], + "random": true +} diff --git a/spec/support/jasmine.yml b/spec/support/jasmine.yml deleted file mode 100644 index 6460624e..00000000 --- a/spec/support/jasmine.yml +++ /dev/null @@ -1,35 +0,0 @@ -#This 'magic' inclusion order allows the travis build to pass. -#TODO: search for the correct files to include to prevent -src_dir: - - 'src' -src_files: - - 'core/requireCore.js' - - 'core/base.js' - - 'core/util.js' - #end of known dependencies - - 'core/Spec.js' - - 'core/Env.js' - - 'core/JsApiReporter.js' - - 'core/PrettyPrinter.js' - - 'core/Suite.js' - - 'core/**/*.js' - - 'html/**/*.js' - - '**/*.js' -stylesheets: -helpers: - - 'helpers/asyncAwait.js' - - 'helpers/BrowserFlags.js' - - 'helpers/checkForMap.js' - - 'helpers/checkForSet.js' - - 'helpers/checkForSymbol.js' - - 'helpers/checkForTypedArrays.js' - - 'helpers/integrationMatchers.js' - - 'helpers/promises.js' - - 'helpers/defineJasmineUnderTest.js' -spec_files: - - '**/*[Ss]pec.js' - - '!npmPackage/**/*' -spec_dir: spec -random: true -spec_helper: spec/support/jasmine_helper.rb - diff --git a/spec/support/jasmine_helper.rb b/spec/support/jasmine_helper.rb deleted file mode 100644 index 037f205e..00000000 --- a/spec/support/jasmine_helper.rb +++ /dev/null @@ -1,3 +0,0 @@ -Jasmine.configure do |config| - config.prevent_phantom_js_auto_install = true -end diff --git a/spec/support/localJasmineBrowser.js b/spec/support/localJasmineBrowser.js new file mode 100644 index 00000000..b7b4875b --- /dev/null +++ b/spec/support/localJasmineBrowser.js @@ -0,0 +1,8 @@ +var path = require('path'), + jasmineBrowser = require('jasmine-browser-runner'), + jasmineCore = require('../../lib/jasmine-core.js'); + +var config = require(path.resolve('spec/support/jasmine-browser.json')); +config.jasmineCore = jasmineCore; + +jasmineBrowser.startServer(config); From d610d0bdad1e510c4181ba2e05bdfc770bdf9a4e Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Thu, 6 Jun 2019 14:46:19 -0700 Subject: [PATCH 033/201] Use browser-runner to start server in CI --- ci.js | 55 ++++++++++--------------------------------------------- 1 file changed, 10 insertions(+), 45 deletions(-) diff --git a/ci.js b/ci.js index ffa1457e..c90b6dc2 100644 --- a/ci.js +++ b/ci.js @@ -1,6 +1,7 @@ const path = require("path"), fs = require('fs'), - port = 5555, + jasmineBrowser = require('jasmine-browser-runner'), + jasmineCore = require('./lib/jasmine-core.js'), colors = { "passed" : "\x1B[32m", "failed": "\x1B[31m", @@ -15,41 +16,14 @@ const path = require("path"), "excluded": "", "none": "" }, - host = `http://localhost:${port}`, useSauce = process.env.USE_SAUCE === 'true'; + +var config = require(path.resolve('spec/support/jasmine-browser.json')); +config.jasmineCore = jasmineCore; +config.port = 0; + let driver, server; -function pageGenerator() { - const ejs = require("ejs"), - fg = require("fast-glob"), - templatePath = path.resolve(__dirname, 'spec/support/index.html.ejs'), - template = ejs.compile(fs.readFileSync(templatePath).toString()), - patterns = [ - "lib/jasmine-core/jasmine.js", - "lib/jasmine-core/json2.js", - "lib/jasmine-core/jasmine-html.js", - "lib/jasmine-core/boot.js", - "src/core/requireCore.js", - "src/core/base.js", - "src/core/util.js", - "src/core/Spec.js", - "src/core/Env.js", - "src/**/*.js", - "spec/helpers/*.js", - "spec/**/*[Ss]pec.js" - ], - ignore = [ - "spec/helpers/nodeDefineJasmineUnderTest.js", - "spec/npmPackage/**/*", - "lib/jasmine-core/node_boot.js" - ]; - - return function toHtml() { - const files = fg.sync(patterns, {ignore}); - return template({files}); - } -} - function buildWebdriver() { const webdriver = require("selenium-webdriver"), Capability = webdriver.Capability; @@ -130,19 +104,10 @@ function cleanup() { } (async function () { - await new Promise(resolve => { - console.log("Creating an express app for browers to run the tests...") - const express = require("express"), - app = express(), - html = pageGenerator(); + server = await jasmineBrowser.startServer(config); + const host = `http://localhost:${server.address().port}`; - app.use(express.static(__dirname)); - app.get("/", (req, res) => res.send(html())); - server = app.listen(port, resolve); - }); - - - console.log("Running the tests in browser...") + console.log("Running the tests in browser..."); driver = buildWebdriver(); await driver.get(`${host}/?throwFailures=false&failFast=false&random=true`) await new Promise(resolve => { From 96786c793fcba2a3fe3a182a65c97cd6ee57a7db Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Sun, 2 Jun 2019 09:05:45 -0400 Subject: [PATCH 034/201] Allow users to set a default spy strategy --- .../integration/DefaultSpyStrategySpec.js | 68 +++++++++++++++++++ src/core/Env.js | 20 +++++- src/core/Spy.js | 6 +- src/core/SpyFactory.js | 4 +- src/core/requireInterface.js | 16 +++++ 5 files changed, 110 insertions(+), 4 deletions(-) create mode 100644 spec/core/integration/DefaultSpyStrategySpec.js diff --git a/spec/core/integration/DefaultSpyStrategySpec.js b/spec/core/integration/DefaultSpyStrategySpec.js new file mode 100644 index 00000000..0b02c572 --- /dev/null +++ b/spec/core/integration/DefaultSpyStrategySpec.js @@ -0,0 +1,68 @@ +describe('Default Spy Strategy (Integration)', function() { + var env; + + beforeEach(function() { + env = new jasmineUnderTest.Env(); + env.configure({random: false}); + }); + + it('allows defining a default spy strategy', function(done) { + env.describe('suite with default strategy', function() { + env.beforeEach(function() { + env.setDefaultSpyStrategy(function (and) { + and.returnValue(42); + }); + }); + + env.it('spec in suite', function() { + var spy = env.createSpy('something'); + expect(spy()).toBe(42); + }); + }); + + env.it('spec not in suite', function() { + var spy = env.createSpy('something'); + expect(spy()).toBeUndefined(); + }); + + function jasmineDone(result) { + expect(result.overallStatus).toEqual('passed'); + done(); + } + + env.addReporter({ jasmineDone: jasmineDone }); + env.execute(); + }); + + it('uses the default spy strategy defined when the spy is created', function (done) { + env.it('spec', function() { + var a = env.createSpy('a'); + env.setDefaultSpyStrategy(function (and) { and.returnValue(42); }); + var b = env.createSpy('b'); + env.setDefaultSpyStrategy(function (and) { and.stub(); }); + var c = env.createSpy('c'); + env.setDefaultSpyStrategy(); + var d = env.createSpy('d'); + + expect(a()).toBeUndefined(); + expect(b()).toBe(42); + expect(c()).toBeUndefined(); + expect(d()).toBeUndefined(); + + // Check our assumptions about which spies are "configured" (this matters because + // spies that use withArgs() behave differently if they are not configured). + expect(a.and.isConfigured()).toBe(false); + expect(b.and.isConfigured()).toBe(true); + expect(c.and.isConfigured()).toBe(true); + expect(d.and.isConfigured()).toBe(false); + }); + + function jasmineDone(result) { + expect(result.overallStatus).toEqual('passed'); + done(); + } + + env.addReporter({ jasmineDone: jasmineDone }); + env.execute(); + }); +}); diff --git a/src/core/Env.js b/src/core/Env.js index 18924dcd..63d86365 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -208,6 +208,13 @@ getJasmineRequireObj().Env = function(j$) { } }); + this.setDefaultSpyStrategy = function(defaultStrategyFn) { + if (!currentRunnable()) { + throw new Error('Default spy strategy must be set in a before function or a spec'); + } + runnableResources[currentRunnable().id].defaultStrategyFn = defaultStrategyFn; + }; + this.addSpyStrategy = function(name, fn) { if (!currentRunnable()) { throw new Error( @@ -286,7 +293,8 @@ getJasmineRequireObj().Env = function(j$) { spies: [], customEqualityTesters: [], customMatchers: {}, - customSpyStrategies: {} + customSpyStrategies: {}, + defaultStrategyFn: undefined }; if (runnableResources[parentRunnableId]) { @@ -296,6 +304,7 @@ getJasmineRequireObj().Env = function(j$) { resources.customMatchers = j$.util.clone( runnableResources[parentRunnableId].customMatchers ); + resources.defaultStrategyFn = runnableResources[parentRunnableId].defaultStrategyFn; } runnableResources[id] = resources; @@ -720,6 +729,15 @@ getJasmineRequireObj().Env = function(j$) { return {}; }, + function getDefaultStrategyFn() { + var runnable = currentRunnable(); + + if (runnable) { + return runnableResources[runnable.id].defaultStrategyFn; + } + + return undefined; + }, function getPromise() { return customPromise || global.Promise; } diff --git a/src/core/Spy.js b/src/core/Spy.js index 753499bb..42de6035 100644 --- a/src/core/Spy.js +++ b/src/core/Spy.js @@ -12,7 +12,7 @@ getJasmineRequireObj().Spy = function(j$) { * @constructor * @name Spy */ - function Spy(name, originalFn, customStrategies, getPromise) { + function Spy(name, originalFn, customStrategies, defaultStrategyFn, getPromise) { var numArgs = typeof originalFn === 'function' ? originalFn.length : 0, wrapper = makeFunc(numArgs, function() { return spy.apply(this, Array.prototype.slice.call(arguments)); @@ -127,6 +127,10 @@ getJasmineRequireObj().Spy = function(j$) { }; wrapper.calls = callTracker; + if (defaultStrategyFn) { + defaultStrategyFn(wrapper.and); + } + return wrapper; } diff --git a/src/core/SpyFactory.js b/src/core/SpyFactory.js index a622a8a3..984573c0 100644 --- a/src/core/SpyFactory.js +++ b/src/core/SpyFactory.js @@ -1,9 +1,9 @@ getJasmineRequireObj().SpyFactory = function(j$) { - function SpyFactory(getCustomStrategies, getPromise) { + function SpyFactory(getCustomStrategies, getDefaultStrategyFn, getPromise) { var self = this; this.createSpy = function(name, originalFn) { - return j$.Spy(name, originalFn, getCustomStrategies(), getPromise); + return j$.Spy(name, originalFn, getCustomStrategies(), getDefaultStrategyFn(), getPromise); }; this.createSpyObj = function(baseName, methodNames) { diff --git a/src/core/requireInterface.js b/src/core/requireInterface.js index cff7403b..2e509348 100644 --- a/src/core/requireInterface.js +++ b/src/core/requireInterface.js @@ -330,5 +330,21 @@ getJasmineRequireObj().interface = function(jasmine, env) { return env.addSpyStrategy(name, factory); }; + /** + * Set the default spy strategy for the current scope of specs. + * + * _Note:_ This is only callable from within a {@link beforeEach}, {@link it}, or {@link beforeAll}. + * @name jasmine.setDefaultSpyStrategy + * @function + * @param {Function} defaultStrategyFn - a function that assigns a strategy + * @example + * beforeEach(function() { + * jasmine.setDefaultSpyStrategy(and => and.returnValue(true)); + * }); + */ + jasmine.setDefaultSpyStrategy = function(defaultStrategyFn) { + return env.setDefaultSpyStrategy(defaultStrategyFn); + }; + return jasmineInterface; }; From e07da963545da8e2711a7057ed42a80e08782ca8 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Fri, 7 Jun 2019 23:33:06 -0400 Subject: [PATCH 035/201] Apply prettier --- src/core/Env.js | 11 ++++++++--- src/core/Spy.js | 8 +++++++- src/core/SpyFactory.js | 8 +++++++- 3 files changed, 22 insertions(+), 5 deletions(-) diff --git a/src/core/Env.js b/src/core/Env.js index 63d86365..52bdd4d8 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -210,9 +210,13 @@ getJasmineRequireObj().Env = function(j$) { this.setDefaultSpyStrategy = function(defaultStrategyFn) { if (!currentRunnable()) { - throw new Error('Default spy strategy must be set in a before function or a spec'); + throw new Error( + 'Default spy strategy must be set in a before function or a spec' + ); } - runnableResources[currentRunnable().id].defaultStrategyFn = defaultStrategyFn; + runnableResources[ + currentRunnable().id + ].defaultStrategyFn = defaultStrategyFn; }; this.addSpyStrategy = function(name, fn) { @@ -304,7 +308,8 @@ getJasmineRequireObj().Env = function(j$) { resources.customMatchers = j$.util.clone( runnableResources[parentRunnableId].customMatchers ); - resources.defaultStrategyFn = runnableResources[parentRunnableId].defaultStrategyFn; + resources.defaultStrategyFn = + runnableResources[parentRunnableId].defaultStrategyFn; } runnableResources[id] = resources; diff --git a/src/core/Spy.js b/src/core/Spy.js index 42de6035..86d44b07 100644 --- a/src/core/Spy.js +++ b/src/core/Spy.js @@ -12,7 +12,13 @@ getJasmineRequireObj().Spy = function(j$) { * @constructor * @name Spy */ - function Spy(name, originalFn, customStrategies, defaultStrategyFn, getPromise) { + function Spy( + name, + originalFn, + customStrategies, + defaultStrategyFn, + getPromise + ) { var numArgs = typeof originalFn === 'function' ? originalFn.length : 0, wrapper = makeFunc(numArgs, function() { return spy.apply(this, Array.prototype.slice.call(arguments)); diff --git a/src/core/SpyFactory.js b/src/core/SpyFactory.js index 984573c0..21a5d465 100644 --- a/src/core/SpyFactory.js +++ b/src/core/SpyFactory.js @@ -3,7 +3,13 @@ getJasmineRequireObj().SpyFactory = function(j$) { var self = this; this.createSpy = function(name, originalFn) { - return j$.Spy(name, originalFn, getCustomStrategies(), getDefaultStrategyFn(), getPromise); + return j$.Spy( + name, + originalFn, + getCustomStrategies(), + getDefaultStrategyFn(), + getPromise + ); }; this.createSpyObj = function(baseName, methodNames) { From 243adfd4ce2332e9a3acddd92f400460c4e48fa9 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Wed, 12 Jun 2019 11:33:14 -0700 Subject: [PATCH 036/201] Use jasmine-browser-runner to execute browser tests --- .travis.yml | 4 +- ci.js | 188 ------------------ package.json | 6 +- spec/support/ci.js | 48 +++++ spec/support/jasmine-browser-performance.json | 11 + spec/support/localJasmineBrowser.js | 5 +- travis-core-script.sh | 2 +- 7 files changed, 70 insertions(+), 194 deletions(-) delete mode 100644 ci.js create mode 100644 spec/support/ci.js create mode 100644 spec/support/jasmine-browser-performance.json diff --git a/.travis.yml b/.travis.yml index 09af26cb..d8d308d8 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,8 +1,8 @@ language: node_js node_js: - - "12" - - "10" - "8" + - "10" + - "12" script: $TEST_COMMAND diff --git a/ci.js b/ci.js deleted file mode 100644 index c90b6dc2..00000000 --- a/ci.js +++ /dev/null @@ -1,188 +0,0 @@ -const path = require("path"), - fs = require('fs'), - jasmineBrowser = require('jasmine-browser-runner'), - jasmineCore = require('./lib/jasmine-core.js'), - colors = { - "passed" : "\x1B[32m", - "failed": "\x1B[31m", - "pending": "\x1B[33m", - "excluded": "\x1B[0m", - "none": "\x1B[0m" - }, - symbols = { - "passed" : ".", - "failed": "F", - "pending": "*", - "excluded": "", - "none": "" - }, - useSauce = process.env.USE_SAUCE === 'true'; - -var config = require(path.resolve('spec/support/jasmine-browser.json')); -config.jasmineCore = jasmineCore; -config.port = 0; - -let driver, server; - -function buildWebdriver() { - const webdriver = require("selenium-webdriver"), - Capability = webdriver.Capability; - if (useSauce) { - const username = process.env['SAUCE_USERNAME'], - accessKey = process.env['SAUCE_ACCESS_KEY']; - return new webdriver.Builder() - .withCapabilities({ - name: `jasmine-core ${new Date().toISOString()}`, - [Capability.PLATFORM]: process.env['SAUCE_OS'], - [Capability.BROWSER_NAME]: process.env['JASMINE_BROWSER'], - [Capability.VERSION]: process.env['SAUCE_BROWSER_VERSION'], - build: `Core ${process.env['TRAVIS_BUILD_NUMBER'] || 'Ran locally'}`, - tags: ['Jasmine-Core'], - "tunnel-identifier": process.env['TRAVIS_JOB_NUMBER'] ? process.env['TRAVIS_JOB_NUMBER'].toString() : null - }) - .usingServer(`http://${username}:${accessKey}@localhost:4445/wd/hub`) - .build(); - } else { - return new webdriver.Builder() - .forBrowser(process.env["JASMINE_BROWSER"] || "firefox") - .build(); - } -} - -async function resultsWithoutCircularReferences(driver, resultType, index, batchSize) { - return await driver.executeScript( - `var results = jsApiReporter.${resultType}Results(${index}, ${batchSize});\n` + - 'for (var i = 0; i < results.length; i++) {\n' + - 'var expectations = results[i].failedExpectations;\n' + - 'if (results[i].passedExpectations) {\n' + - 'expectations = expectations.concat(results[i].passedExpectations);\n' + - '}\n' + - 'for (var j = 0; j < expectations.length; j++) {\n' + - 'var expectation = expectations[j];\n' + - "try { JSON.stringify(expectation.expected); } catch (e) { expectation.expected = ''; }\n" + - "try { JSON.stringify(expectation.actual); } catch (e) { expectation.actual = ''; }\n" + - '}\n' + - '}\n' + - 'return results;' - ); -} - -function flatten(arr) { - return Array.prototype.concat.apply([], arr); -} - -async function getResults(driver) { - const batchSize = 50, - specResults = [], - failedSuiteResults = []; - let index = 0, - slice = []; - - do { - slice = await resultsWithoutCircularReferences(driver, 'spec', index, batchSize); - specResults.push(slice); - index += batchSize; - } while (slice.length === batchSize); - - index = 0; - do { - slice = await resultsWithoutCircularReferences(driver, 'suite', index, batchSize); - failedSuiteResults.push(slice.filter(function(suite) { return suite.status === 'failed' })); - index += batchSize; - } while (slice.length === batchSize); - - return {specResults: flatten(specResults), failedSuiteResults: flatten(failedSuiteResults)}; -} - -function cleanup() { - return Promise.all([ - driver ? driver.close() : true, - new Promise(resolve => server ? server.close(resolve) : resolve()) - ]).catch(error => { - console.error(error); - }); -} - -(async function () { - server = await jasmineBrowser.startServer(config); - const host = `http://localhost:${server.address().port}`; - - console.log("Running the tests in browser..."); - driver = buildWebdriver(); - await driver.get(`${host}/?throwFailures=false&failFast=false&random=true`) - await new Promise(resolve => { - const intervalId = setInterval(async () => { - const isFinished = await driver.executeScript("return jsApiReporter && jsApiReporter.finished") - if (isFinished) { - clearInterval(intervalId) - resolve(); - } - }, 500) - }); - - const {specResults, failedSuiteResults} = await getResults(driver); - console.log(specResults.map(spec => `${colors[spec.status]}${symbols[spec.status]}`).join("") + colors["none"]); - - const result = specResults.reduce((result, spec) => { - result[spec.status] = [...result[spec.status], spec]; - return result; - }, {pending: [], failed: [], passed: [], excluded: []}); - - if (result.pending.length) { - console.log(`${colors["pending"]}Pending:`); - result.pending.forEach((spec, index) => { - console.log(`${colors["none"]}${index}) ${spec.fullName}`) - console.group(); - console.log(`${colors["pending"]}${spec.pendingReason || "no reason given"}`); - console.groupEnd(); - console.log(); - }); - } - - if (result.failed.length) { - console.log(`${colors["failed"]}Failed:`); - result["failed"].forEach((spec, index) => { - console.log(`${colors["none"]}${index}) ${spec.fullName}`) - console.group(); - spec.failedExpectations.forEach((expect) => { - console.log(`${colors["none"]}Message:`); - console.group(); - console.log(`${colors["failed"]}${expect.message}`); - console.groupEnd(); - console.log(`${colors["none"]}Stack:`); - console.group(); - console.log(`${colors["failed"]}${expect.stack}`); - console.groupEnd(); - console.groupEnd(); - }) - console.groupEnd(); - console.log(); - }); - } - - const details = await driver.executeScript(` - return { - overallStatus: jsApiReporter.runDetails.overallStatus, - overallFailures: jsApiReporter.runDetails.failedExpectations, - executionTime: jsApiReporter.executionTime(), - random: jsApiReporter.runDetails.order.random, - seed: jsApiReporter.runDetails.order.seed - }`); - - console.log(`${colors["none"]}${specResults.length} spec(s), ${result.failed.length} failure(s), ${result.pending.length} pending spec(s)`); - console.log(`Finished in ${details.executionTime / 1000} second(s)`); - console.log(`Randomized with seed ${details.seed} ( ${host}/?random=${details.random}&seed=${details.seed} )`); - process.exitCode = details.overallStatus === 'passed' ? 0 : 1; - - // Print details of global errors encountered during the test run. (Most likely, - // some type of file loading or syntax error.) - if (details.overallFailures && details.overallFailures.length > 0) { - console.error('Failures encountered during test run:', JSON.stringify(details.overallFailures, undefined, 2)); - } - - if (useSauce) { - driver.executeScript(`sauce:job-result=${process.exitCode === 0}`); - } -})().catch(error => { - console.error(error); -}).then(cleanup); diff --git a/package.json b/package.json index d0599ac2..f768c99b 100644 --- a/package.json +++ b/package.json @@ -16,7 +16,9 @@ "posttest": "eslint src/**/*.js spec/**/*.js && prettier --check src/**/*.js spec/**/*.js", "test": "grunt execSpecsInNode", "cleanup": "prettier --write src/**/*.js spec/**/*.js", - "serve": "node spec/support/localJasmineBrowser.js" + "serve": "node spec/support/localJasmineBrowser.js", + "serve:performance": "node spec/support/localJasmineBrowser.js jasmine-browser-performance.json", + "ci": "node spec/support/ci.js" }, "description": "Official packaging of Jasmine's core files for use by Node.js projects.", "homepage": "https://jasmine.github.io", @@ -33,7 +35,7 @@ "grunt-css-url-embed": "^1.11.1", "grunt-sass": "^3.0.2", "jasmine": "^3.4.0", - "jasmine-browser-runner": "0.0.2", + "jasmine-browser-runner": "^0.1.0", "jsdom": "^15.0.0", "load-grunt-tasks": "^4.0.0", "node-sass": "^4.11.0", diff --git a/spec/support/ci.js b/spec/support/ci.js new file mode 100644 index 00000000..d5956d3a --- /dev/null +++ b/spec/support/ci.js @@ -0,0 +1,48 @@ +const path = require("path"), + fs = require('fs'), + util = require('util'), + jasmineBrowser = require('jasmine-browser-runner'), + ConsoleReporter = require('jasmine').ConsoleReporter, + jasmineCore = require('../../lib/jasmine-core'), + useSauce = process.env.USE_SAUCE === 'true'; + +var config = require(path.resolve('spec/support/jasmine-browser.json')); +config.jasmineCore = jasmineCore; + +function buildWebdriver() { + const webdriver = require("selenium-webdriver"), + Capability = webdriver.Capability; + if (useSauce) { + const username = process.env['SAUCE_USERNAME'], + accessKey = process.env['SAUCE_ACCESS_KEY']; + return new webdriver.Builder() + .withCapabilities({ + name: `jasmine-core ${new Date().toISOString()}`, + [Capability.PLATFORM]: process.env['SAUCE_OS'], + [Capability.BROWSER_NAME]: process.env['JASMINE_BROWSER'], + [Capability.VERSION]: process.env['SAUCE_BROWSER_VERSION'], + build: `Core ${process.env['TRAVIS_BUILD_NUMBER'] || 'Ran locally'}`, + tags: ['Jasmine-Core'], + "tunnel-identifier": process.env['TRAVIS_JOB_NUMBER'] ? process.env['TRAVIS_JOB_NUMBER'].toString() : null + }) + .usingServer(`http://${username}:${accessKey}@localhost:4445/wd/hub`) + .build(); + } else { + return new webdriver.Builder() + .forBrowser(process.env["JASMINE_BROWSER"] || "firefox") + .build(); + } +} + +const driver = buildWebdriver(); +jasmineBrowser.runSpecs(config, driver).then(function(runDetails) { + process.exitCode = runDetails.overallStatus === 'passed' ? 0 : 1; + + if (useSauce) { + driver.executeScript(`sauce:job-result=${process.exitCode === 0}`); + } +}).catch(error => { + console.error(error); +}).then(function () { + return driver ? driver.close() : true; +}); diff --git a/spec/support/jasmine-browser-performance.json b/spec/support/jasmine-browser-performance.json new file mode 100644 index 00000000..863b7252 --- /dev/null +++ b/spec/support/jasmine-browser-performance.json @@ -0,0 +1,11 @@ +{ + "srcDir": "src", + "specDir": "spec", + "specFiles": [ + "performance/performance_test.js" + ], + "helpers": [ + "helpers/defineJasmineUnderTest.js" + ], + "random": true +} diff --git a/spec/support/localJasmineBrowser.js b/spec/support/localJasmineBrowser.js index b7b4875b..ec9affe2 100644 --- a/spec/support/localJasmineBrowser.js +++ b/spec/support/localJasmineBrowser.js @@ -2,7 +2,10 @@ var path = require('path'), jasmineBrowser = require('jasmine-browser-runner'), jasmineCore = require('../../lib/jasmine-core.js'); -var config = require(path.resolve('spec/support/jasmine-browser.json')); +var configFile = process.argv[2] || 'jasmine-browser.json'; + +var config = require(path.resolve('spec/support', configFile)); config.jasmineCore = jasmineCore; +config.batchReporter = true; jasmineBrowser.startServer(config); diff --git a/travis-core-script.sh b/travis-core-script.sh index c721ab82..1e5733b1 100644 --- a/travis-core-script.sh +++ b/travis-core-script.sh @@ -9,4 +9,4 @@ then fi fi -node ci.js +npm run ci From c73c5a9dbddce7fc27824f61c274162813714d9c Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Wed, 12 Jun 2019 11:42:47 -0700 Subject: [PATCH 037/201] WIP --- package.json | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/package.json b/package.json index f768c99b..dc9c3512 100644 --- a/package.json +++ b/package.json @@ -18,7 +18,8 @@ "cleanup": "prettier --write src/**/*.js spec/**/*.js", "serve": "node spec/support/localJasmineBrowser.js", "serve:performance": "node spec/support/localJasmineBrowser.js jasmine-browser-performance.json", - "ci": "node spec/support/ci.js" + "ci": "node spec/support/ci.js", + "ci:performance": "node spec/support/ci.js jasmine-browser-performance.json" }, "description": "Official packaging of Jasmine's core files for use by Node.js projects.", "homepage": "https://jasmine.github.io", From 0f4e53d0e61364f5ca2106c1b21919ea85476ffa Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Wed, 12 Jun 2019 12:15:34 -0700 Subject: [PATCH 038/201] Update ci script to pass linting --- spec/support/ci.js | 44 ++++++++++++++++++++++++-------------------- 1 file changed, 24 insertions(+), 20 deletions(-) diff --git a/spec/support/ci.js b/spec/support/ci.js index d5956d3a..573a9c6d 100644 --- a/spec/support/ci.js +++ b/spec/support/ci.js @@ -1,16 +1,14 @@ -const path = require("path"), - fs = require('fs'), - util = require('util'), - jasmineBrowser = require('jasmine-browser-runner'), - ConsoleReporter = require('jasmine').ConsoleReporter, - jasmineCore = require('../../lib/jasmine-core'), - useSauce = process.env.USE_SAUCE === 'true'; +/* eslint-env node, es6 */ +const path = require('path'), + jasmineBrowser = require('jasmine-browser-runner'), + jasmineCore = require('../../lib/jasmine-core'), + useSauce = process.env.USE_SAUCE === 'true'; var config = require(path.resolve('spec/support/jasmine-browser.json')); config.jasmineCore = jasmineCore; function buildWebdriver() { - const webdriver = require("selenium-webdriver"), + const webdriver = require('selenium-webdriver'), Capability = webdriver.Capability; if (useSauce) { const username = process.env['SAUCE_USERNAME'], @@ -23,26 +21,32 @@ function buildWebdriver() { [Capability.VERSION]: process.env['SAUCE_BROWSER_VERSION'], build: `Core ${process.env['TRAVIS_BUILD_NUMBER'] || 'Ran locally'}`, tags: ['Jasmine-Core'], - "tunnel-identifier": process.env['TRAVIS_JOB_NUMBER'] ? process.env['TRAVIS_JOB_NUMBER'].toString() : null + 'tunnel-identifier': process.env['TRAVIS_JOB_NUMBER'] + ? process.env['TRAVIS_JOB_NUMBER'].toString() + : null }) .usingServer(`http://${username}:${accessKey}@localhost:4445/wd/hub`) .build(); } else { return new webdriver.Builder() - .forBrowser(process.env["JASMINE_BROWSER"] || "firefox") + .forBrowser(process.env['JASMINE_BROWSER'] || 'firefox') .build(); } } const driver = buildWebdriver(); -jasmineBrowser.runSpecs(config, driver).then(function(runDetails) { - process.exitCode = runDetails.overallStatus === 'passed' ? 0 : 1; +jasmineBrowser + .runSpecs(config, driver) + .then(function(runDetails) { + process.exitCode = runDetails.overallStatus === 'passed' ? 0 : 1; - if (useSauce) { - driver.executeScript(`sauce:job-result=${process.exitCode === 0}`); - } -}).catch(error => { - console.error(error); -}).then(function () { - return driver ? driver.close() : true; -}); + if (useSauce) { + driver.executeScript(`sauce:job-result=${process.exitCode === 0}`); + } + }) + .catch(error => { + console.error(error); + }) + .then(function() { + return driver ? driver.close() : true; + }); From 984018bfdf70a55c4bf2aa0f591d8823db272847 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Wed, 12 Jun 2019 13:31:25 -0700 Subject: [PATCH 039/201] Make no expectations in HTML Reporter message a warning - Fixes #1704 --- lib/jasmine-core/jasmine-html.js | 2 +- spec/html/HtmlReporterSpec.js | 6 +++--- src/html/HtmlReporter.js | 2 +- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/lib/jasmine-core/jasmine-html.js b/lib/jasmine-core/jasmine-html.js index be86ad18..f2a05183 100644 --- a/lib/jasmine-core/jasmine-html.js +++ b/lib/jasmine-core/jasmine-html.js @@ -148,7 +148,7 @@ jasmineRequire.HtmlReporter = function(j$) { typeof console !== 'undefined' && typeof console.error !== 'undefined' ) { - console.error("Spec '" + result.fullName + "' has no expectations."); + console.warn("Spec '" + result.fullName + "' has no expectations."); } if (!symbols) { diff --git a/spec/html/HtmlReporterSpec.js b/spec/html/HtmlReporterSpec.js index a8790f87..2bff3c1f 100644 --- a/spec/html/HtmlReporterSpec.js +++ b/spec/html/HtmlReporterSpec.js @@ -80,7 +80,7 @@ describe('HtmlReporter', function() { describe('when a spec is done', function() { it('logs errors to the console and prints a special symbol if it is an empty spec', function() { if (typeof console === 'undefined') { - console = { error: function() {} }; + console = { warn: function() {} }; } var env = new jasmineUnderTest.Env(), @@ -99,7 +99,7 @@ describe('HtmlReporter', function() { } }); - spyOn(console, 'error'); + spyOn(console, 'warn'); reporter.initialize(); @@ -109,7 +109,7 @@ describe('HtmlReporter', function() { passedExpectations: [], failedExpectations: [] }); - expect(console.error).toHaveBeenCalledWith( + expect(console.warn).toHaveBeenCalledWith( "Spec 'Some Name' has no expectations." ); var specEl = container.querySelector('.jasmine-symbol-summary li'); diff --git a/src/html/HtmlReporter.js b/src/html/HtmlReporter.js index 2a89aaca..5d838ab3 100644 --- a/src/html/HtmlReporter.js +++ b/src/html/HtmlReporter.js @@ -119,7 +119,7 @@ jasmineRequire.HtmlReporter = function(j$) { typeof console !== 'undefined' && typeof console.error !== 'undefined' ) { - console.error("Spec '" + result.fullName + "' has no expectations."); + console.warn("Spec '" + result.fullName + "' has no expectations."); } if (!symbols) { From 15f969bee7066526ba44e562407c728d4a1740df Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Wed, 12 Jun 2019 16:23:12 -0700 Subject: [PATCH 040/201] Add `@since` to most JSDoc comments - See jasmine/jasmine.github.io#117 --- lib/jasmine-core/jasmine.js | 127 ++++++++++++++++++ src/core/CallTracker.js | 10 ++ src/core/Clock.js | 5 + src/core/Env.js | 19 +++ src/core/Expectation.js | 3 + src/core/JsApiReporter.js | 6 + src/core/Spy.js | 2 + src/core/SpyStrategy.js | 10 ++ src/core/base.js | 15 +++ src/core/matchers/async/toBeRejected.js | 1 + src/core/matchers/async/toBeRejectedWith.js | 1 + .../matchers/async/toBeRejectedWithError.js | 1 + src/core/matchers/async/toBeResolved.js | 1 + src/core/matchers/async/toBeResolvedTo.js | 1 + src/core/matchers/nothing.js | 1 + src/core/matchers/toBe.js | 1 + src/core/matchers/toBeCloseTo.js | 1 + src/core/matchers/toBeDefined.js | 1 + src/core/matchers/toBeFalse.js | 1 + src/core/matchers/toBeFalsy.js | 1 + src/core/matchers/toBeGreaterThan.js | 1 + src/core/matchers/toBeGreaterThanOrEqual.js | 1 + src/core/matchers/toBeInstanceOf.js | 1 + src/core/matchers/toBeLessThan.js | 1 + src/core/matchers/toBeLessThanOrEqual.js | 1 + src/core/matchers/toBeNaN.js | 1 + src/core/matchers/toBeNegativeInfinity.js | 1 + src/core/matchers/toBeNull.js | 1 + src/core/matchers/toBePositiveInfinity.js | 1 + src/core/matchers/toBeTrue.js | 1 + src/core/matchers/toBeTruthy.js | 1 + src/core/matchers/toBeUndefined.js | 1 + src/core/matchers/toContain.js | 1 + src/core/matchers/toEqual.js | 1 + src/core/matchers/toHaveBeenCalled.js | 1 + src/core/matchers/toHaveBeenCalledBefore.js | 1 + src/core/matchers/toHaveBeenCalledTimes.js | 1 + src/core/matchers/toHaveBeenCalledWith.js | 1 + src/core/matchers/toHaveClass.js | 1 + src/core/matchers/toMatch.js | 1 + src/core/matchers/toThrow.js | 1 + src/core/matchers/toThrowError.js | 1 + src/core/matchers/toThrowMatching.js | 1 + src/core/requireInterface.js | 23 ++++ 44 files changed, 254 insertions(+) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 50346ee0..abbd7262 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -162,6 +162,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Maximum object depth the pretty printer will print to. * Set this to a lower value to speed up pretty printing if you have large objects. * @name jasmine.MAX_PRETTY_PRINT_DEPTH + * @since 1.3.0 */ j$.MAX_PRETTY_PRINT_DEPTH = 8; /** @@ -169,17 +170,20 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * This will also limit the number of keys and values displayed for an object. * Elements past this number will be ellipised. * @name jasmine.MAX_PRETTY_PRINT_ARRAY_LENGTH + * @since 2.7.0 */ j$.MAX_PRETTY_PRINT_ARRAY_LENGTH = 50; /** * Maximum number of characters to display when pretty printing objects. * Characters past this number will be ellipised. * @name jasmine.MAX_PRETTY_PRINT_CHARS + * @since 2.9.0 */ j$.MAX_PRETTY_PRINT_CHARS = 1000; /** * Default number of milliseconds Jasmine will wait for an asynchronous spec to complete. * @name jasmine.DEFAULT_TIMEOUT_INTERVAL + * @since 1.3.0 */ j$.DEFAULT_TIMEOUT_INTERVAL = 5000; @@ -191,6 +195,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get the currently booted Jasmine Environment. * * @name jasmine.getEnv + * @since 1.3.0 * @function * @return {Env} */ @@ -318,6 +323,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared is an instance of the specified class/constructor. * @name jasmine.any + * @since 1.3.0 * @function * @param {Constructor} clazz - The constructor to check against. */ @@ -329,6 +335,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared is not `null` and not `undefined`. * @name jasmine.anything + * @since 2.2.0 * @function */ j$.anything = function() { @@ -339,6 +346,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared is `true` or anything truthy. * @name jasmine.truthy + * @since 3.1.0 * @function */ j$.truthy = function() { @@ -349,6 +357,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared is `null`, `undefined`, `0`, `false` or anything falsey. * @name jasmine.falsy + * @since 3.1.0 * @function */ j$.falsy = function() { @@ -359,6 +368,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared is empty. * @name jasmine.empty + * @since 3.1.0 * @function */ j$.empty = function() { @@ -369,6 +379,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared is not empty. * @name jasmine.notEmpty + * @since 3.1.0 * @function */ j$.notEmpty = function() { @@ -379,6 +390,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared contains at least the keys and values. * @name jasmine.objectContaining + * @since 1.3.0 * @function * @param {Object} sample - The subset of properties that _must_ be in the actual. */ @@ -390,6 +402,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value is a `String` that matches the `RegExp` or `String`. * @name jasmine.stringMatching + * @since 2.2.0 * @function * @param {RegExp|String} expected */ @@ -401,6 +414,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value is an `Array` that contains at least the elements in the sample. * @name jasmine.arrayContaining + * @since 2.2.0 * @function * @param {Array} sample */ @@ -412,6 +426,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value is an `Array` that contains all of the elements in the sample in any order. * @name jasmine.arrayWithExactContents + * @since 2.8.0 * @function * @param {Array} sample */ @@ -842,6 +857,7 @@ getJasmineRequireObj().Env = function(j$) { /** * _Note:_ Do not construct this directly, Jasmine will make one during booting. * @name Env + * @since 2.0.0 * @classdesc The Jasmine environment * @constructor */ @@ -876,11 +892,13 @@ getJasmineRequireObj().Env = function(j$) { * This represents the available options to configure Jasmine. * Options that are not provided will use their default values * @interface Configuration + * @since 3.3.0 */ var config = { /** * Whether to randomize spec execution order * @name Configuration#random + * @since 3.3.0 * @type Boolean * @default true */ @@ -889,6 +907,7 @@ getJasmineRequireObj().Env = function(j$) { * Seed to use as the basis of randomization. * Null causes the seed to be determined randomly at the start of execution. * @name Configuration#seed + * @since 3.3.0 * @type function * @default null */ @@ -896,6 +915,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Whether to stop execution of the suite after the first spec failure * @name Configuration#failFast + * @since 3.3.0 * @type Boolean * @default false */ @@ -903,6 +923,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Whether to cause specs to only have one expectation failure. * @name Configuration#oneFailurePerSpec + * @since 3.3.0 * @type Boolean * @default false */ @@ -910,6 +931,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Function to use to filter specs * @name Configuration#specFilter + * @since 3.3.0 * @type function * @default true */ @@ -920,6 +942,7 @@ getJasmineRequireObj().Env = function(j$) { * Whether or not reporters should hide disabled specs from their output. * Currently only supported by Jasmine's HTMLReporter * @name Configuration#hideDisabled + * @since 3.3.0 * @type Boolean * @default false */ @@ -929,6 +952,7 @@ getJasmineRequireObj().Env = function(j$) { * to create a promise. If not set, it will default to whatever global Promise * library is available (if any). * @name Configuration#Promise + * @since 3.5.0 * @type function * @default undefined */ @@ -977,6 +1001,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Configure your jasmine environment * @name Env#configure + * @since 3.3.0 * @argument {Configuration} configuration * @function */ @@ -1022,6 +1047,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Get the current configuration for your jasmine environment * @name Env#configuration + * @since 3.3.0 * @function * @returns {Configuration} */ @@ -1189,6 +1215,7 @@ getJasmineRequireObj().Env = function(j$) { * Sets whether Jasmine should throw an Error when an expectation fails. * This causes a spec to only have one expectation failure. * @name Env#throwOnExpectationFailure + * @since 2.3.0 * @function * @param {Boolean} value Whether to throw when a expectation fails * @deprecated Use the `oneFailurePerSpec` option with {@link Env#configure} @@ -1210,6 +1237,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Set whether to stop suite execution when a spec fails * @name Env#stopOnSpecFailure + * @since 2.7.0 * @function * @param {Boolean} value Whether to stop suite execution when a spec fails * @deprecated Use the `failFast` option with {@link Env#configure} @@ -1231,6 +1259,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Set whether to randomize test execution order * @name Env#randomizeTests + * @since 2.4.0 * @function * @param {Boolean} value Whether to randomize execution order * @deprecated Use the `random` option with {@link Env#configure} @@ -1252,6 +1281,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Set the random number seed for spec randomization * @name Env#seed + * @since 2.4.0 * @function * @param {Number} value The seed value * @deprecated Use the `seed` option with {@link Env#configure} @@ -1275,6 +1305,7 @@ getJasmineRequireObj().Env = function(j$) { /** * @name Env#hideDisabled + * @since 3.2.0 * @function */ this.hideDisabled = function(value) { @@ -1522,6 +1553,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Add a custom reporter to the Jasmine environment. * @name Env#addReporter + * @since 2.0.0 * @function * @param {Reporter} reporterToAdd The reporter to be added. * @see custom_reporter @@ -1533,6 +1565,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Provide a fallback reporter if no other reporters have been specified. * @name Env#provideFallbackReporter + * @since 2.5.0 * @function * @param {Reporter} reporterToAdd The reporter * @see custom_reporter @@ -1544,6 +1577,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Clear all registered reporters * @name Env#clearReporters + * @since 2.5.2 * @function */ this.clearReporters = function() { @@ -1946,6 +1980,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { /** * Get the current status for the Jasmine environment. * @name jsApiReporter#status + * @since 2.0.0 * @function * @return {String} - One of `loaded`, `started`, or `done` */ @@ -1969,6 +2004,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { * * Retrievable in slices for easier serialization. * @name jsApiReporter#suiteResults + * @since 2.1.0 * @function * @param {Number} index - The position in the suites list to start from. * @param {Number} length - Maximum number of suite results to return. @@ -1986,6 +2022,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { /** * Get all of the suites in a single object, with their `id` as the key. * @name jsApiReporter#suites + * @since 2.0.0 * @function * @return {Object} - Map of suite id to {@link SuiteResult} */ @@ -2004,6 +2041,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { * * Retrievable in slices for easier serialization. * @name jsApiReporter#specResults + * @since 2.0.0 * @function * @param {Number} index - The position in the specs list to start from. * @param {Number} length - Maximum number of specs results to return. @@ -2016,6 +2054,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { /** * Get all spec results. * @name jsApiReporter#specs + * @since 2.0.0 * @function * @return {SpecResult[]} */ @@ -2026,6 +2065,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { /** * Get the number of milliseconds it took for the full Jasmine suite to run. * @name jsApiReporter#executionTime + * @since 2.0.0 * @function * @return {Number} */ @@ -2318,6 +2358,7 @@ getJasmineRequireObj().Truthy = function(j$) { getJasmineRequireObj().CallTracker = function(j$) { /** * @namespace Spy#calls + * @since 2.0.0 */ function CallTracker() { var calls = []; @@ -2333,6 +2374,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Check whether this spy has been invoked. * @name Spy#calls#any + * @since 2.0.0 * @function * @return {Boolean} */ @@ -2343,6 +2385,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Get the number of invocations of this spy. * @name Spy#calls#count + * @since 2.0.0 * @function * @return {Integer} */ @@ -2353,6 +2396,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Get the arguments that were passed to a specific invocation of this spy. * @name Spy#calls#argsFor + * @since 2.0.0 * @function * @param {Integer} index The 0-based invocation index. * @return {Array} @@ -2365,6 +2409,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Get the raw calls array for this spy. * @name Spy#calls#all + * @since 2.0.0 * @function * @return {Spy.callData[]} */ @@ -2375,6 +2420,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Get all of the arguments for each invocation of this spy in the order they were received. * @name Spy#calls#allArgs + * @since 2.0.0 * @function * @return {Array} */ @@ -2390,6 +2436,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Get the first invocation of this spy. * @name Spy#calls#first + * @since 2.0.0 * @function * @return {ObjecSpy.callData} */ @@ -2400,6 +2447,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Get the most recent invocation of this spy. * @name Spy#calls#mostRecent + * @since 2.0.0 * @function * @return {ObjecSpy.callData} */ @@ -2410,6 +2458,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Reset this spy as if it has never been called. * @name Spy#calls#reset + * @since 2.0.0 * @function */ this.reset = function() { @@ -2419,6 +2468,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Set this spy to do a shallow clone of arguments passed to each invocation. * @name Spy#calls#saveArgumentsByValue + * @since 2.5.0 * @function */ this.saveArgumentsByValue = function() { @@ -2534,6 +2584,7 @@ getJasmineRequireObj().Clock = function() { /** * Install the mock clock over the built-in methods. * @name Clock#install + * @since 2.0.0 * @function * @return {Clock} */ @@ -2554,6 +2605,7 @@ getJasmineRequireObj().Clock = function() { /** * Uninstall the mock clock, returning the built-in methods to their places. * @name Clock#uninstall + * @since 2.0.0 * @function */ self.uninstall = function() { @@ -2570,6 +2622,7 @@ getJasmineRequireObj().Clock = function() { * * The clock will be {@link Clock#install|install}ed before the function is called and {@link Clock#uninstall|uninstall}ed in a `finally` after the function completes. * @name Clock#withMock + * @since 2.3.0 * @function * @param {Function} closure The function to be called. */ @@ -2585,6 +2638,7 @@ getJasmineRequireObj().Clock = function() { /** * Instruct the installed Clock to also mock the date returned by `new Date()` * @name Clock#mockDate + * @since 2.1.0 * @function * @param {Date} [initialDate=now] The `Date` to provide. */ @@ -2617,6 +2671,7 @@ getJasmineRequireObj().Clock = function() { /** * Tick the Clock forward, running any enqueued timeouts along the way * @name Clock#tick + * @since 1.3.0 * @function * @param {int} millis The number of milliseconds to tick. */ @@ -3042,6 +3097,7 @@ getJasmineRequireObj().Expectation = function(j$) { * Add some context for an {@link expect} * @function * @name matchers#withContext + * @since 3.3.0 * @param {String} message - Additional context to show when the matcher fails * @return {matchers} */ @@ -3053,6 +3109,7 @@ getJasmineRequireObj().Expectation = function(j$) { * Invert the matcher following this {@link expect} * @member * @name matchers#not + * @since 1.3.0 * @type {matchers} * @example * expect(something).not.toBe(true); @@ -3086,6 +3143,7 @@ getJasmineRequireObj().Expectation = function(j$) { * Add some context for an {@link expectAsync} * @function * @name async-matchers#withContext + * @since 3.3.0 * @param {String} message - Additional context to show when the async matcher fails * @return {async-matchers} */ @@ -3526,6 +3584,7 @@ getJasmineRequireObj().toBeRejected = function(j$) { * @function * @async * @name async-matchers#toBeRejected + * @since 3.1.0 * @example * await expectAsync(aPromise).toBeRejected(); * @example @@ -3549,6 +3608,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { * @function * @async * @name async-matchers#toBeRejectedWith + * @since 3.3.0 * @param {Object} expected - Value that the promise is expected to be rejected with * @example * await expectAsync(aPromise).toBeRejectedWith({prop: 'value'}); @@ -3596,6 +3656,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { * @function * @async * @name async-matchers#toBeRejectedWithError + * @since 3.5.0 * @param {Error} [expected] - `Error` constructor the object that was thrown needs to be an instance of. If not provided, `Error` will be used. * @param {RegExp|String} [message] - The message that should be set on the thrown `Error` * @example @@ -3685,6 +3746,7 @@ getJasmineRequireObj().toBeResolved = function(j$) { * @function * @async * @name async-matchers#toBeResolved + * @since 3.1.0 * @example * await expectAsync(aPromise).toBeResolved(); * @example @@ -3708,6 +3770,7 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { * @function * @async * @name async-matchers#toBeResolvedTo + * @since 3.1.0 * @param {Object} expected - Value that the promise is expected to resolve to * @example * await expectAsync(aPromise).toBeResolvedTo({prop: 'value'}); @@ -4259,6 +4322,7 @@ getJasmineRequireObj().nothing = function() { * {@link expect} nothing explicitly. * @function * @name matchers#nothing + * @since 2.8.0 * @example * expect().nothing(); */ @@ -4357,6 +4421,7 @@ getJasmineRequireObj().toBe = function(j$) { * {@link expect} the actual value to be `===` to the expected value. * @function * @name matchers#toBe + * @since 1.3.0 * @param {Object} expected - The expected value to compare against. * @example * expect(thing).toBe(realThing); @@ -4387,6 +4452,7 @@ getJasmineRequireObj().toBeCloseTo = function() { * {@link expect} the actual value to be within a specified precision of the expected value. * @function * @name matchers#toBeCloseTo + * @since 1.3.0 * @param {Object} expected - The expected value to compare against. * @param {Number} [precision=2] - The number of decimal points to check. * @example @@ -4424,6 +4490,7 @@ getJasmineRequireObj().toBeDefined = function() { * {@link expect} the actual value to be defined. (Not `undefined`) * @function * @name matchers#toBeDefined + * @since 1.3.0 * @example * expect(result).toBeDefined(); */ @@ -4445,6 +4512,7 @@ getJasmineRequireObj().toBeFalse = function() { * {@link expect} the actual value to be `false`. * @function * @name matchers#toBeFalse + * @since 3.5.0 * @example * expect(result).toBeFalse(); */ @@ -4466,6 +4534,7 @@ getJasmineRequireObj().toBeFalsy = function() { * {@link expect} the actual value to be falsy * @function * @name matchers#toBeFalsy + * @since 2.0.0 * @example * expect(result).toBeFalsy(); */ @@ -4487,6 +4556,7 @@ getJasmineRequireObj().toBeGreaterThan = function() { * {@link expect} the actual value to be greater than the expected value. * @function * @name matchers#toBeGreaterThan + * @since 2.0.0 * @param {Number} expected - The value to compare against. * @example * expect(result).toBeGreaterThan(3); @@ -4510,6 +4580,7 @@ getJasmineRequireObj().toBeGreaterThanOrEqual = function() { * {@link expect} the actual value to be greater than or equal to the expected value. * @function * @name matchers#toBeGreaterThanOrEqual + * @since 2.0.0 * @param {Number} expected - The expected value to compare against. * @example * expect(result).toBeGreaterThanOrEqual(25); @@ -4534,6 +4605,7 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { * {@link expect} the actual to be an instance of the expected class * @function * @name matchers#toBeInstanceOf + * @since 3.5.0 * @param {Object} expected - The class or constructor function to check for * @example * expect('foo').toBeInstanceOf(String); @@ -4578,6 +4650,7 @@ getJasmineRequireObj().toBeLessThan = function() { * {@link expect} the actual value to be less than the expected value. * @function * @name matchers#toBeLessThan + * @since 2.0.0 * @param {Number} expected - The expected value to compare against. * @example * expect(result).toBeLessThan(0); @@ -4601,6 +4674,7 @@ getJasmineRequireObj().toBeLessThanOrEqual = function() { * {@link expect} the actual value to be less than or equal to the expected value. * @function * @name matchers#toBeLessThanOrEqual + * @since 2.0.0 * @param {Number} expected - The expected value to compare against. * @example * expect(result).toBeLessThanOrEqual(123); @@ -4624,6 +4698,7 @@ getJasmineRequireObj().toBeNaN = function(j$) { * {@link expect} the actual value to be `NaN` (Not a Number). * @function * @name matchers#toBeNaN + * @since 1.3.0 * @example * expect(thing).toBeNaN(); */ @@ -4653,6 +4728,7 @@ getJasmineRequireObj().toBeNegativeInfinity = function(j$) { * {@link expect} the actual value to be `-Infinity` (-infinity). * @function * @name matchers#toBeNegativeInfinity + * @since 2.6.0 * @example * expect(thing).toBeNegativeInfinity(); */ @@ -4682,6 +4758,7 @@ getJasmineRequireObj().toBeNull = function() { * {@link expect} the actual value to be `null`. * @function * @name matchers#toBeNull + * @since 1.3.0 * @example * expect(result).toBeNull(); */ @@ -4703,6 +4780,7 @@ getJasmineRequireObj().toBePositiveInfinity = function(j$) { * {@link expect} the actual value to be `Infinity` (infinity). * @function * @name matchers#toBePositiveInfinity + * @since 2.6.0 * @example * expect(thing).toBePositiveInfinity(); */ @@ -4732,6 +4810,7 @@ getJasmineRequireObj().toBeTrue = function() { * {@link expect} the actual value to be `true`. * @function * @name matchers#toBeTrue + * @since 3.5.0 * @example * expect(result).toBeTrue(); */ @@ -4753,6 +4832,7 @@ getJasmineRequireObj().toBeTruthy = function() { * {@link expect} the actual value to be truthy. * @function * @name matchers#toBeTruthy + * @since 2.0.0 * @example * expect(thing).toBeTruthy(); */ @@ -4774,6 +4854,7 @@ getJasmineRequireObj().toBeUndefined = function() { * {@link expect} the actual value to be `undefined`. * @function * @name matchers#toBeUndefined + * @since 1.3.0 * @example * expect(result).toBeUndefined(): */ @@ -4795,6 +4876,7 @@ getJasmineRequireObj().toContain = function() { * {@link expect} the actual value to contain a specific value. * @function * @name matchers#toContain + * @since 2.0.0 * @param {Object} expected - The value to look for. * @example * expect(array).toContain(anElement); @@ -4821,6 +4903,7 @@ getJasmineRequireObj().toEqual = function(j$) { * {@link expect} the actual value to be equal to the expected, using deep equality comparison. * @function * @name matchers#toEqual + * @since 1.3.0 * @param {Object} expected - Expected value * @example * expect(bigObject).toEqual({"foo": ['bar', 'baz']}); @@ -4856,6 +4939,7 @@ getJasmineRequireObj().toHaveBeenCalled = function(j$) { * {@link expect} the actual (a {@link Spy}) to have been called. * @function * @name matchers#toHaveBeenCalled + * @since 1.3.0 * @example * expect(mySpy).toHaveBeenCalled(); * expect(mySpy).not.toHaveBeenCalled(); @@ -4895,6 +4979,7 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { * {@link expect} the actual value (a {@link Spy}) to have been called before another {@link Spy}. * @function * @name matchers#toHaveBeenCalledBefore + * @since 2.6.0 * @param {Spy} expected - {@link Spy} that should have been called after the `actual` {@link Spy}. * @example * expect(mySpy).toHaveBeenCalledBefore(otherSpy); @@ -4956,6 +5041,7 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { * {@link expect} the actual (a {@link Spy}) to have been called the specified number of times. * @function * @name matchers#toHaveBeenCalledTimes + * @since 2.4.0 * @param {Number} expected - The number of invocations to look for. * @example * expect(mySpy).toHaveBeenCalledTimes(3); @@ -4997,6 +5083,7 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { * {@link expect} the actual (a {@link Spy}) to have been called with particular arguments at least once. * @function * @name matchers#toHaveBeenCalledWith + * @since 1.3.0 * @param {...Object} - The arguments to look for * @example * expect(mySpy).toHaveBeenCalledWith('foo', 'bar', 2); @@ -5038,6 +5125,7 @@ getJasmineRequireObj().toHaveClass = function(j$) { * {@link expect} the actual value to be a DOM element that has the expected class * @function * @name matchers#toHaveClass + * @since 3.0.0 * @param {Object} expected - The class name to test for * @example * var el = document.createElement('div'); @@ -5075,6 +5163,7 @@ getJasmineRequireObj().toMatch = function(j$) { * {@link expect} the actual value to match a regular expression * @function * @name matchers#toMatch + * @since 1.3.0 * @param {RegExp|String} expected - Value to look for in the string. * @example * expect("my string").toMatch(/string$/); @@ -5107,6 +5196,7 @@ getJasmineRequireObj().toThrow = function(j$) { * {@link expect} a function to `throw` something. * @function * @name matchers#toThrow + * @since 2.0.0 * @param {Object} [expected] - Value that should be thrown. If not provided, simply the fact that something was thrown will be checked. * @example * expect(function() { return 'things'; }).toThrow('foo'); @@ -5165,6 +5255,7 @@ getJasmineRequireObj().toThrowError = function(j$) { * {@link expect} a function to `throw` an `Error`. * @function * @name matchers#toThrowError + * @since 2.0.0 * @param {Error} [expected] - `Error` constructor the object that was thrown needs to be an instance of. If not provided, `Error` will be used. * @param {RegExp|String} [message] - The message that should be set on the thrown `Error` * @example @@ -5331,6 +5422,7 @@ getJasmineRequireObj().toThrowMatching = function(j$) { * {@link expect} a function to `throw` something matching a predicate. * @function * @name matchers#toThrowMatching + * @since 3.0.0 * @param {Function} predicate - A function that takes the thrown exception as its parameter and returns true if it matches. * @example * expect(function() { throw new Error('nope'); }).toThrowMatching(function(thrown) { return thrown.message === 'nope'; }); @@ -6162,6 +6254,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * Calls to `describe` can be nested within other calls to compose your suite as a tree. * @name describe + * @since 1.3.0 * @function * @global * @param {String} description Textual description of the group @@ -6176,6 +6269,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * Specs within an `xdescribe` will be marked pending and not executed * @name xdescribe + * @since 1.3.0 * @function * @global * @param {String} description Textual description of the group @@ -6191,6 +6285,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * If suites or specs are focused, only those that are focused will be executed * @see fit * @name fdescribe + * @since 2.1.0 * @function * @global * @param {String} description Textual description of the group @@ -6205,6 +6300,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * A spec whose expectations all succeed will be passing and a spec with any failures will fail. * @name it + * @since 1.3.0 * @function * @global * @param {String} description Textual description of what this spec is checking @@ -6221,6 +6317,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * The spec will report as `pending` and will not be executed. * @name xit + * @since 1.3.0 * @function * @global * @param {String} description Textual description of what this spec is checking. @@ -6235,6 +6332,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * If suites or specs are focused, only those that are focused will be executed. * @name fit + * @since 2.1.0 * @function * @global * @param {String} description Textual description of what this spec is checking. @@ -6249,6 +6347,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Run some shared setup before each of the specs in the {@link describe} in which it is called. * @name beforeEach + * @since 1.3.0 * @function * @global * @param {implementationCallback} [function] Function that contains the code to setup your specs. @@ -6262,6 +6361,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Run some shared teardown after each of the specs in the {@link describe} in which it is called. * @name afterEach + * @since 1.3.0 * @function * @global * @param {implementationCallback} [function] Function that contains the code to teardown your specs. @@ -6277,6 +6377,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * _Note:_ Be careful, sharing the setup from a beforeAll makes it easy to accidentally leak state between your specs so that they erroneously pass or fail. * @name beforeAll + * @since 2.1.0 * @function * @global * @param {implementationCallback} [function] Function that contains the code to setup your specs. @@ -6292,6 +6393,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * _Note:_ Be careful, sharing the teardown from a afterAll makes it easy to accidentally leak state between your specs so that they erroneously pass or fail. * @name afterAll + * @since 2.1.0 * @function * @global * @param {implementationCallback} [function] Function that contains the code to teardown your specs. @@ -6305,6 +6407,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Create an expectation for a spec. * @name expect + * @since 1.3.0 * @function * @global * @param {Object} actual - Actual computed value to test expectations against. @@ -6320,6 +6423,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * which must be either returned from the spec or waited for using `await` * in order for Jasmine to associate them with the correct spec. * @name expectAsync + * @since 3.3.0 * @function * @global * @param {Object} actual - Actual computed value to test expectations against. @@ -6336,6 +6440,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Mark a spec as pending, expectation results will be ignored. * @name pending + * @since 2.0.0 * @function * @global * @param {String} [message] - Reason the spec is pending. @@ -6347,6 +6452,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Explicitly mark a spec as failed. * @name fail + * @since 2.1.0 * @function * @global * @param {String|Error} [error] - Reason for the failure. @@ -6358,6 +6464,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Install a spy onto an existing object. * @name spyOn + * @since 1.3.0 * @function * @global * @param {Object} obj - The object upon which to install the {@link Spy}. @@ -6371,6 +6478,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Install a spy on a property installed with `Object.defineProperty` onto an existing object. * @name spyOnProperty + * @since 2.6.0 * @function * @global * @param {Object} obj - The object upon which to install the {@link Spy} @@ -6385,6 +6493,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Installs spies on all writable and configurable properties of an object. * @name spyOnAllFunctions + * @since 3.2.1 * @function * @global * @param {Object} obj - The object upon which to install the {@link Spy}s @@ -6409,6 +6518,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * _Note:_ This is only callable from within a {@link beforeEach}, {@link it}, or {@link beforeAll}. * @name jasmine.addCustomEqualityTester + * @since 2.0.0 * @function * @param {Function} tester - A function which takes two arguments to compare and returns a `true` or `false` comparison result if it knows how to compare them, and `undefined` otherwise. * @see custom_equality @@ -6422,6 +6532,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * _Note:_ This is only callable from within a {@link beforeEach}, {@link it}, or {@link beforeAll}. * @name jasmine.addMatchers + * @since 2.0.0 * @function * @param {Object} matchers - Keys from this object will be the new matcher names. * @see custom_matcher @@ -6433,6 +6544,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Get the currently booted mock {Clock} for this Jasmine environment. * @name jasmine.clock + * @since 2.0.0 * @function * @returns {Clock} */ @@ -6443,6 +6555,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Create a bare {@link Spy} object. This won't be installed anywhere and will not have any implementation behind it. * @name jasmine.createSpy + * @since 1.3.0 * @function * @param {String} [name] - Name to give the spy. This will be displayed in failure messages. * @param {Function} [originalFn] - Function to act as the real implementation. @@ -6455,6 +6568,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Create an object with multiple {@link Spy}s as its members. * @name jasmine.createSpyObj + * @since 1.3.0 * @function * @param {String} [baseName] - Base name for the spies in the object. * @param {String[]|Object} methodNames - Array of method names to create spies for, or Object whose keys will be method names and values the {@link Spy#and#returnValue|returnValue}. @@ -6469,6 +6583,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * _Note:_ This is only callable from within a {@link beforeEach}, {@link it}, or {@link beforeAll}. * @name jasmine.addSpyStrategy + * @since 3.5.0 * @function * @param {String} name - The name of the strategy (i.e. what you call from `and`) * @param {Function} factory - Factory function that returns the plan to be executed. @@ -6589,6 +6704,7 @@ getJasmineRequireObj().Spy = function(j$) { * whenever the spy is called with arguments that don't match any strategy * created with {@link Spy#withArgs}. * @name Spy#and + * @since 2.0.0 * @example * spyOn(someObj, 'func').and.returnValue(42); */ @@ -6597,6 +6713,7 @@ getJasmineRequireObj().Spy = function(j$) { * Specifies a strategy to be used for calls to the spy that have the * specified arguments. * @name Spy#withArgs + * @since 3.0.0 * @function * @param {...*} args - The arguments to match * @type {SpyStrategy} @@ -6953,6 +7070,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Get the identifying information for the spy. * @name SpyStrategy#identity + * @since 3.0.0 * @member * @type {String} */ @@ -6990,6 +7108,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to return a promise resolving to the specified value when invoked. * @name SpyStrategy#resolveTo + * @since 3.5.0 * @function * @param {*} value The value to return. */ @@ -7004,6 +7123,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to return a promise rejecting with the specified value when invoked. * @name SpyStrategy#rejectWith + * @since 3.5.0 * @function * @param {*} value The value to return. */ @@ -7033,6 +7153,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Execute the current spy strategy. * @name SpyStrategy#exec + * @since 2.0.0 * @function */ SpyStrategy.prototype.exec = function(context, args) { @@ -7042,6 +7163,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to call through to the real implementation when invoked. * @name SpyStrategy#callThrough + * @since 2.0.0 * @function */ SpyStrategy.prototype.callThrough = function() { @@ -7052,6 +7174,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to return the value when invoked. * @name SpyStrategy#returnValue + * @since 2.0.0 * @function * @param {*} value The value to return. */ @@ -7065,6 +7188,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to return one of the specified values (sequentially) each time the spy is invoked. * @name SpyStrategy#returnValues + * @since 2.1.0 * @function * @param {...*} values - Values to be returned on subsequent calls to the spy. */ @@ -7079,6 +7203,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to throw an error when invoked. * @name SpyStrategy#throwError + * @since 2.0.0 * @function * @param {Error|String} something Thing to throw */ @@ -7093,6 +7218,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to call a fake implementation when invoked. * @name SpyStrategy#callFake + * @since 2.0.0 * @function * @param {Function} fn The function to invoke with the passed parameters. */ @@ -7109,6 +7235,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to do nothing when invoked. This is the default. * @name SpyStrategy#stub + * @since 2.0.0 * @function */ SpyStrategy.prototype.stub = function(fn) { diff --git a/src/core/CallTracker.js b/src/core/CallTracker.js index e856d2ad..8613a250 100644 --- a/src/core/CallTracker.js +++ b/src/core/CallTracker.js @@ -1,6 +1,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * @namespace Spy#calls + * @since 2.0.0 */ function CallTracker() { var calls = []; @@ -16,6 +17,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Check whether this spy has been invoked. * @name Spy#calls#any + * @since 2.0.0 * @function * @return {Boolean} */ @@ -26,6 +28,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Get the number of invocations of this spy. * @name Spy#calls#count + * @since 2.0.0 * @function * @return {Integer} */ @@ -36,6 +39,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Get the arguments that were passed to a specific invocation of this spy. * @name Spy#calls#argsFor + * @since 2.0.0 * @function * @param {Integer} index The 0-based invocation index. * @return {Array} @@ -48,6 +52,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Get the raw calls array for this spy. * @name Spy#calls#all + * @since 2.0.0 * @function * @return {Spy.callData[]} */ @@ -58,6 +63,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Get all of the arguments for each invocation of this spy in the order they were received. * @name Spy#calls#allArgs + * @since 2.0.0 * @function * @return {Array} */ @@ -73,6 +79,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Get the first invocation of this spy. * @name Spy#calls#first + * @since 2.0.0 * @function * @return {ObjecSpy.callData} */ @@ -83,6 +90,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Get the most recent invocation of this spy. * @name Spy#calls#mostRecent + * @since 2.0.0 * @function * @return {ObjecSpy.callData} */ @@ -93,6 +101,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Reset this spy as if it has never been called. * @name Spy#calls#reset + * @since 2.0.0 * @function */ this.reset = function() { @@ -102,6 +111,7 @@ getJasmineRequireObj().CallTracker = function(j$) { /** * Set this spy to do a shallow clone of arguments passed to each invocation. * @name Spy#calls#saveArgumentsByValue + * @since 2.5.0 * @function */ this.saveArgumentsByValue = function() { diff --git a/src/core/Clock.js b/src/core/Clock.js index 370eca18..0ec89e23 100644 --- a/src/core/Clock.js +++ b/src/core/Clock.js @@ -33,6 +33,7 @@ getJasmineRequireObj().Clock = function() { /** * Install the mock clock over the built-in methods. * @name Clock#install + * @since 2.0.0 * @function * @return {Clock} */ @@ -53,6 +54,7 @@ getJasmineRequireObj().Clock = function() { /** * Uninstall the mock clock, returning the built-in methods to their places. * @name Clock#uninstall + * @since 2.0.0 * @function */ self.uninstall = function() { @@ -69,6 +71,7 @@ getJasmineRequireObj().Clock = function() { * * The clock will be {@link Clock#install|install}ed before the function is called and {@link Clock#uninstall|uninstall}ed in a `finally` after the function completes. * @name Clock#withMock + * @since 2.3.0 * @function * @param {Function} closure The function to be called. */ @@ -84,6 +87,7 @@ getJasmineRequireObj().Clock = function() { /** * Instruct the installed Clock to also mock the date returned by `new Date()` * @name Clock#mockDate + * @since 2.1.0 * @function * @param {Date} [initialDate=now] The `Date` to provide. */ @@ -116,6 +120,7 @@ getJasmineRequireObj().Clock = function() { /** * Tick the Clock forward, running any enqueued timeouts along the way * @name Clock#tick + * @since 1.3.0 * @function * @param {int} millis The number of milliseconds to tick. */ diff --git a/src/core/Env.js b/src/core/Env.js index 18924dcd..a031f3ff 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -2,6 +2,7 @@ getJasmineRequireObj().Env = function(j$) { /** * _Note:_ Do not construct this directly, Jasmine will make one during booting. * @name Env + * @since 2.0.0 * @classdesc The Jasmine environment * @constructor */ @@ -36,11 +37,13 @@ getJasmineRequireObj().Env = function(j$) { * This represents the available options to configure Jasmine. * Options that are not provided will use their default values * @interface Configuration + * @since 3.3.0 */ var config = { /** * Whether to randomize spec execution order * @name Configuration#random + * @since 3.3.0 * @type Boolean * @default true */ @@ -49,6 +52,7 @@ getJasmineRequireObj().Env = function(j$) { * Seed to use as the basis of randomization. * Null causes the seed to be determined randomly at the start of execution. * @name Configuration#seed + * @since 3.3.0 * @type function * @default null */ @@ -56,6 +60,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Whether to stop execution of the suite after the first spec failure * @name Configuration#failFast + * @since 3.3.0 * @type Boolean * @default false */ @@ -63,6 +68,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Whether to cause specs to only have one expectation failure. * @name Configuration#oneFailurePerSpec + * @since 3.3.0 * @type Boolean * @default false */ @@ -70,6 +76,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Function to use to filter specs * @name Configuration#specFilter + * @since 3.3.0 * @type function * @default true */ @@ -80,6 +87,7 @@ getJasmineRequireObj().Env = function(j$) { * Whether or not reporters should hide disabled specs from their output. * Currently only supported by Jasmine's HTMLReporter * @name Configuration#hideDisabled + * @since 3.3.0 * @type Boolean * @default false */ @@ -89,6 +97,7 @@ getJasmineRequireObj().Env = function(j$) { * to create a promise. If not set, it will default to whatever global Promise * library is available (if any). * @name Configuration#Promise + * @since 3.5.0 * @type function * @default undefined */ @@ -137,6 +146,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Configure your jasmine environment * @name Env#configure + * @since 3.3.0 * @argument {Configuration} configuration * @function */ @@ -182,6 +192,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Get the current configuration for your jasmine environment * @name Env#configuration + * @since 3.3.0 * @function * @returns {Configuration} */ @@ -349,6 +360,7 @@ getJasmineRequireObj().Env = function(j$) { * Sets whether Jasmine should throw an Error when an expectation fails. * This causes a spec to only have one expectation failure. * @name Env#throwOnExpectationFailure + * @since 2.3.0 * @function * @param {Boolean} value Whether to throw when a expectation fails * @deprecated Use the `oneFailurePerSpec` option with {@link Env#configure} @@ -370,6 +382,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Set whether to stop suite execution when a spec fails * @name Env#stopOnSpecFailure + * @since 2.7.0 * @function * @param {Boolean} value Whether to stop suite execution when a spec fails * @deprecated Use the `failFast` option with {@link Env#configure} @@ -391,6 +404,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Set whether to randomize test execution order * @name Env#randomizeTests + * @since 2.4.0 * @function * @param {Boolean} value Whether to randomize execution order * @deprecated Use the `random` option with {@link Env#configure} @@ -412,6 +426,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Set the random number seed for spec randomization * @name Env#seed + * @since 2.4.0 * @function * @param {Number} value The seed value * @deprecated Use the `seed` option with {@link Env#configure} @@ -435,6 +450,7 @@ getJasmineRequireObj().Env = function(j$) { /** * @name Env#hideDisabled + * @since 3.2.0 * @function */ this.hideDisabled = function(value) { @@ -682,6 +698,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Add a custom reporter to the Jasmine environment. * @name Env#addReporter + * @since 2.0.0 * @function * @param {Reporter} reporterToAdd The reporter to be added. * @see custom_reporter @@ -693,6 +710,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Provide a fallback reporter if no other reporters have been specified. * @name Env#provideFallbackReporter + * @since 2.5.0 * @function * @param {Reporter} reporterToAdd The reporter * @see custom_reporter @@ -704,6 +722,7 @@ getJasmineRequireObj().Env = function(j$) { /** * Clear all registered reporters * @name Env#clearReporters + * @since 2.5.2 * @function */ this.clearReporters = function() { diff --git a/src/core/Expectation.js b/src/core/Expectation.js index e1833433..4bfbb327 100644 --- a/src/core/Expectation.js +++ b/src/core/Expectation.js @@ -25,6 +25,7 @@ getJasmineRequireObj().Expectation = function(j$) { * Add some context for an {@link expect} * @function * @name matchers#withContext + * @since 3.3.0 * @param {String} message - Additional context to show when the matcher fails * @return {matchers} */ @@ -36,6 +37,7 @@ getJasmineRequireObj().Expectation = function(j$) { * Invert the matcher following this {@link expect} * @member * @name matchers#not + * @since 1.3.0 * @type {matchers} * @example * expect(something).not.toBe(true); @@ -69,6 +71,7 @@ getJasmineRequireObj().Expectation = function(j$) { * Add some context for an {@link expectAsync} * @function * @name async-matchers#withContext + * @since 3.3.0 * @param {String} message - Additional context to show when the async matcher fails * @return {async-matchers} */ diff --git a/src/core/JsApiReporter.js b/src/core/JsApiReporter.js index 514b3a6c..8875a45e 100644 --- a/src/core/JsApiReporter.js +++ b/src/core/JsApiReporter.js @@ -31,6 +31,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { /** * Get the current status for the Jasmine environment. * @name jsApiReporter#status + * @since 2.0.0 * @function * @return {String} - One of `loaded`, `started`, or `done` */ @@ -54,6 +55,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { * * Retrievable in slices for easier serialization. * @name jsApiReporter#suiteResults + * @since 2.1.0 * @function * @param {Number} index - The position in the suites list to start from. * @param {Number} length - Maximum number of suite results to return. @@ -71,6 +73,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { /** * Get all of the suites in a single object, with their `id` as the key. * @name jsApiReporter#suites + * @since 2.0.0 * @function * @return {Object} - Map of suite id to {@link SuiteResult} */ @@ -89,6 +92,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { * * Retrievable in slices for easier serialization. * @name jsApiReporter#specResults + * @since 2.0.0 * @function * @param {Number} index - The position in the specs list to start from. * @param {Number} length - Maximum number of specs results to return. @@ -101,6 +105,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { /** * Get all spec results. * @name jsApiReporter#specs + * @since 2.0.0 * @function * @return {SpecResult[]} */ @@ -111,6 +116,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { /** * Get the number of milliseconds it took for the full Jasmine suite to run. * @name jsApiReporter#executionTime + * @since 2.0.0 * @function * @return {Number} */ diff --git a/src/core/Spy.js b/src/core/Spy.js index 753499bb..c3a0f3fb 100644 --- a/src/core/Spy.js +++ b/src/core/Spy.js @@ -107,6 +107,7 @@ getJasmineRequireObj().Spy = function(j$) { * whenever the spy is called with arguments that don't match any strategy * created with {@link Spy#withArgs}. * @name Spy#and + * @since 2.0.0 * @example * spyOn(someObj, 'func').and.returnValue(42); */ @@ -115,6 +116,7 @@ getJasmineRequireObj().Spy = function(j$) { * Specifies a strategy to be used for calls to the spy that have the * specified arguments. * @name Spy#withArgs + * @since 3.0.0 * @function * @param {...*} args - The arguments to match * @type {SpyStrategy} diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index e1559a7d..83985967 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -10,6 +10,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Get the identifying information for the spy. * @name SpyStrategy#identity + * @since 3.0.0 * @member * @type {String} */ @@ -47,6 +48,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to return a promise resolving to the specified value when invoked. * @name SpyStrategy#resolveTo + * @since 3.5.0 * @function * @param {*} value The value to return. */ @@ -61,6 +63,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to return a promise rejecting with the specified value when invoked. * @name SpyStrategy#rejectWith + * @since 3.5.0 * @function * @param {*} value The value to return. */ @@ -90,6 +93,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Execute the current spy strategy. * @name SpyStrategy#exec + * @since 2.0.0 * @function */ SpyStrategy.prototype.exec = function(context, args) { @@ -99,6 +103,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to call through to the real implementation when invoked. * @name SpyStrategy#callThrough + * @since 2.0.0 * @function */ SpyStrategy.prototype.callThrough = function() { @@ -109,6 +114,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to return the value when invoked. * @name SpyStrategy#returnValue + * @since 2.0.0 * @function * @param {*} value The value to return. */ @@ -122,6 +128,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to return one of the specified values (sequentially) each time the spy is invoked. * @name SpyStrategy#returnValues + * @since 2.1.0 * @function * @param {...*} values - Values to be returned on subsequent calls to the spy. */ @@ -136,6 +143,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to throw an error when invoked. * @name SpyStrategy#throwError + * @since 2.0.0 * @function * @param {Error|String} something Thing to throw */ @@ -150,6 +158,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to call a fake implementation when invoked. * @name SpyStrategy#callFake + * @since 2.0.0 * @function * @param {Function} fn The function to invoke with the passed parameters. */ @@ -166,6 +175,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { /** * Tell the spy to do nothing when invoked. This is the default. * @name SpyStrategy#stub + * @since 2.0.0 * @function */ SpyStrategy.prototype.stub = function(fn) { diff --git a/src/core/base.js b/src/core/base.js index 40faa4ce..deed4ef2 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -7,6 +7,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Maximum object depth the pretty printer will print to. * Set this to a lower value to speed up pretty printing if you have large objects. * @name jasmine.MAX_PRETTY_PRINT_DEPTH + * @since 1.3.0 */ j$.MAX_PRETTY_PRINT_DEPTH = 8; /** @@ -14,17 +15,20 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * This will also limit the number of keys and values displayed for an object. * Elements past this number will be ellipised. * @name jasmine.MAX_PRETTY_PRINT_ARRAY_LENGTH + * @since 2.7.0 */ j$.MAX_PRETTY_PRINT_ARRAY_LENGTH = 50; /** * Maximum number of characters to display when pretty printing objects. * Characters past this number will be ellipised. * @name jasmine.MAX_PRETTY_PRINT_CHARS + * @since 2.9.0 */ j$.MAX_PRETTY_PRINT_CHARS = 1000; /** * Default number of milliseconds Jasmine will wait for an asynchronous spec to complete. * @name jasmine.DEFAULT_TIMEOUT_INTERVAL + * @since 1.3.0 */ j$.DEFAULT_TIMEOUT_INTERVAL = 5000; @@ -36,6 +40,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get the currently booted Jasmine Environment. * * @name jasmine.getEnv + * @since 1.3.0 * @function * @return {Env} */ @@ -163,6 +168,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared is an instance of the specified class/constructor. * @name jasmine.any + * @since 1.3.0 * @function * @param {Constructor} clazz - The constructor to check against. */ @@ -174,6 +180,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared is not `null` and not `undefined`. * @name jasmine.anything + * @since 2.2.0 * @function */ j$.anything = function() { @@ -184,6 +191,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared is `true` or anything truthy. * @name jasmine.truthy + * @since 3.1.0 * @function */ j$.truthy = function() { @@ -194,6 +202,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared is `null`, `undefined`, `0`, `false` or anything falsey. * @name jasmine.falsy + * @since 3.1.0 * @function */ j$.falsy = function() { @@ -204,6 +213,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared is empty. * @name jasmine.empty + * @since 3.1.0 * @function */ j$.empty = function() { @@ -214,6 +224,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared is not empty. * @name jasmine.notEmpty + * @since 3.1.0 * @function */ j$.notEmpty = function() { @@ -224,6 +235,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value being compared contains at least the keys and values. * @name jasmine.objectContaining + * @since 1.3.0 * @function * @param {Object} sample - The subset of properties that _must_ be in the actual. */ @@ -235,6 +247,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value is a `String` that matches the `RegExp` or `String`. * @name jasmine.stringMatching + * @since 2.2.0 * @function * @param {RegExp|String} expected */ @@ -246,6 +259,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value is an `Array` that contains at least the elements in the sample. * @name jasmine.arrayContaining + * @since 2.2.0 * @function * @param {Array} sample */ @@ -257,6 +271,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if the actual value is an `Array` that contains all of the elements in the sample in any order. * @name jasmine.arrayWithExactContents + * @since 2.8.0 * @function * @param {Array} sample */ diff --git a/src/core/matchers/async/toBeRejected.js b/src/core/matchers/async/toBeRejected.js index 8451e8df..c3b53aa4 100644 --- a/src/core/matchers/async/toBeRejected.js +++ b/src/core/matchers/async/toBeRejected.js @@ -4,6 +4,7 @@ getJasmineRequireObj().toBeRejected = function(j$) { * @function * @async * @name async-matchers#toBeRejected + * @since 3.1.0 * @example * await expectAsync(aPromise).toBeRejected(); * @example diff --git a/src/core/matchers/async/toBeRejectedWith.js b/src/core/matchers/async/toBeRejectedWith.js index 3e302de2..62748412 100644 --- a/src/core/matchers/async/toBeRejectedWith.js +++ b/src/core/matchers/async/toBeRejectedWith.js @@ -4,6 +4,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { * @function * @async * @name async-matchers#toBeRejectedWith + * @since 3.3.0 * @param {Object} expected - Value that the promise is expected to be rejected with * @example * await expectAsync(aPromise).toBeRejectedWith({prop: 'value'}); diff --git a/src/core/matchers/async/toBeRejectedWithError.js b/src/core/matchers/async/toBeRejectedWithError.js index 88f1c11f..84144c31 100644 --- a/src/core/matchers/async/toBeRejectedWithError.js +++ b/src/core/matchers/async/toBeRejectedWithError.js @@ -4,6 +4,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { * @function * @async * @name async-matchers#toBeRejectedWithError + * @since 3.5.0 * @param {Error} [expected] - `Error` constructor the object that was thrown needs to be an instance of. If not provided, `Error` will be used. * @param {RegExp|String} [message] - The message that should be set on the thrown `Error` * @example diff --git a/src/core/matchers/async/toBeResolved.js b/src/core/matchers/async/toBeResolved.js index a26f265d..e998a116 100644 --- a/src/core/matchers/async/toBeResolved.js +++ b/src/core/matchers/async/toBeResolved.js @@ -4,6 +4,7 @@ getJasmineRequireObj().toBeResolved = function(j$) { * @function * @async * @name async-matchers#toBeResolved + * @since 3.1.0 * @example * await expectAsync(aPromise).toBeResolved(); * @example diff --git a/src/core/matchers/async/toBeResolvedTo.js b/src/core/matchers/async/toBeResolvedTo.js index f178b673..ff2b943c 100644 --- a/src/core/matchers/async/toBeResolvedTo.js +++ b/src/core/matchers/async/toBeResolvedTo.js @@ -4,6 +4,7 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { * @function * @async * @name async-matchers#toBeResolvedTo + * @since 3.1.0 * @param {Object} expected - Value that the promise is expected to resolve to * @example * await expectAsync(aPromise).toBeResolvedTo({prop: 'value'}); diff --git a/src/core/matchers/nothing.js b/src/core/matchers/nothing.js index 625236b3..687cec28 100644 --- a/src/core/matchers/nothing.js +++ b/src/core/matchers/nothing.js @@ -3,6 +3,7 @@ getJasmineRequireObj().nothing = function() { * {@link expect} nothing explicitly. * @function * @name matchers#nothing + * @since 2.8.0 * @example * expect().nothing(); */ diff --git a/src/core/matchers/toBe.js b/src/core/matchers/toBe.js index f92ed1ba..3aab9416 100644 --- a/src/core/matchers/toBe.js +++ b/src/core/matchers/toBe.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBe = function(j$) { * {@link expect} the actual value to be `===` to the expected value. * @function * @name matchers#toBe + * @since 1.3.0 * @param {Object} expected - The expected value to compare against. * @example * expect(thing).toBe(realThing); diff --git a/src/core/matchers/toBeCloseTo.js b/src/core/matchers/toBeCloseTo.js index b57ca1ad..6cd0a018 100644 --- a/src/core/matchers/toBeCloseTo.js +++ b/src/core/matchers/toBeCloseTo.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeCloseTo = function() { * {@link expect} the actual value to be within a specified precision of the expected value. * @function * @name matchers#toBeCloseTo + * @since 1.3.0 * @param {Object} expected - The expected value to compare against. * @param {Number} [precision=2] - The number of decimal points to check. * @example diff --git a/src/core/matchers/toBeDefined.js b/src/core/matchers/toBeDefined.js index c9b7203b..ae95091a 100644 --- a/src/core/matchers/toBeDefined.js +++ b/src/core/matchers/toBeDefined.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeDefined = function() { * {@link expect} the actual value to be defined. (Not `undefined`) * @function * @name matchers#toBeDefined + * @since 1.3.0 * @example * expect(result).toBeDefined(); */ diff --git a/src/core/matchers/toBeFalse.js b/src/core/matchers/toBeFalse.js index 619e5c36..e26fb834 100644 --- a/src/core/matchers/toBeFalse.js +++ b/src/core/matchers/toBeFalse.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeFalse = function() { * {@link expect} the actual value to be `false`. * @function * @name matchers#toBeFalse + * @since 3.5.0 * @example * expect(result).toBeFalse(); */ diff --git a/src/core/matchers/toBeFalsy.js b/src/core/matchers/toBeFalsy.js index 9ef75792..db61d465 100644 --- a/src/core/matchers/toBeFalsy.js +++ b/src/core/matchers/toBeFalsy.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeFalsy = function() { * {@link expect} the actual value to be falsy * @function * @name matchers#toBeFalsy + * @since 2.0.0 * @example * expect(result).toBeFalsy(); */ diff --git a/src/core/matchers/toBeGreaterThan.js b/src/core/matchers/toBeGreaterThan.js index 8bda38a4..ffe7ad61 100644 --- a/src/core/matchers/toBeGreaterThan.js +++ b/src/core/matchers/toBeGreaterThan.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeGreaterThan = function() { * {@link expect} the actual value to be greater than the expected value. * @function * @name matchers#toBeGreaterThan + * @since 2.0.0 * @param {Number} expected - The value to compare against. * @example * expect(result).toBeGreaterThan(3); diff --git a/src/core/matchers/toBeGreaterThanOrEqual.js b/src/core/matchers/toBeGreaterThanOrEqual.js index f3327ce1..1f33b5e6 100644 --- a/src/core/matchers/toBeGreaterThanOrEqual.js +++ b/src/core/matchers/toBeGreaterThanOrEqual.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeGreaterThanOrEqual = function() { * {@link expect} the actual value to be greater than or equal to the expected value. * @function * @name matchers#toBeGreaterThanOrEqual + * @since 2.0.0 * @param {Number} expected - The expected value to compare against. * @example * expect(result).toBeGreaterThanOrEqual(25); diff --git a/src/core/matchers/toBeInstanceOf.js b/src/core/matchers/toBeInstanceOf.js index 55d419b3..66b658c1 100644 --- a/src/core/matchers/toBeInstanceOf.js +++ b/src/core/matchers/toBeInstanceOf.js @@ -5,6 +5,7 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { * {@link expect} the actual to be an instance of the expected class * @function * @name matchers#toBeInstanceOf + * @since 3.5.0 * @param {Object} expected - The class or constructor function to check for * @example * expect('foo').toBeInstanceOf(String); diff --git a/src/core/matchers/toBeLessThan.js b/src/core/matchers/toBeLessThan.js index 58681cae..319113a0 100644 --- a/src/core/matchers/toBeLessThan.js +++ b/src/core/matchers/toBeLessThan.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeLessThan = function() { * {@link expect} the actual value to be less than the expected value. * @function * @name matchers#toBeLessThan + * @since 2.0.0 * @param {Number} expected - The expected value to compare against. * @example * expect(result).toBeLessThan(0); diff --git a/src/core/matchers/toBeLessThanOrEqual.js b/src/core/matchers/toBeLessThanOrEqual.js index a0c91790..4820fc97 100644 --- a/src/core/matchers/toBeLessThanOrEqual.js +++ b/src/core/matchers/toBeLessThanOrEqual.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeLessThanOrEqual = function() { * {@link expect} the actual value to be less than or equal to the expected value. * @function * @name matchers#toBeLessThanOrEqual + * @since 2.0.0 * @param {Number} expected - The expected value to compare against. * @example * expect(result).toBeLessThanOrEqual(123); diff --git a/src/core/matchers/toBeNaN.js b/src/core/matchers/toBeNaN.js index 15cff52a..dcff00a1 100644 --- a/src/core/matchers/toBeNaN.js +++ b/src/core/matchers/toBeNaN.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeNaN = function(j$) { * {@link expect} the actual value to be `NaN` (Not a Number). * @function * @name matchers#toBeNaN + * @since 1.3.0 * @example * expect(thing).toBeNaN(); */ diff --git a/src/core/matchers/toBeNegativeInfinity.js b/src/core/matchers/toBeNegativeInfinity.js index d7d24d59..ce60a62d 100644 --- a/src/core/matchers/toBeNegativeInfinity.js +++ b/src/core/matchers/toBeNegativeInfinity.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeNegativeInfinity = function(j$) { * {@link expect} the actual value to be `-Infinity` (-infinity). * @function * @name matchers#toBeNegativeInfinity + * @since 2.6.0 * @example * expect(thing).toBeNegativeInfinity(); */ diff --git a/src/core/matchers/toBeNull.js b/src/core/matchers/toBeNull.js index d347d445..36b06133 100644 --- a/src/core/matchers/toBeNull.js +++ b/src/core/matchers/toBeNull.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeNull = function() { * {@link expect} the actual value to be `null`. * @function * @name matchers#toBeNull + * @since 1.3.0 * @example * expect(result).toBeNull(); */ diff --git a/src/core/matchers/toBePositiveInfinity.js b/src/core/matchers/toBePositiveInfinity.js index 60acded4..c1c41f8e 100644 --- a/src/core/matchers/toBePositiveInfinity.js +++ b/src/core/matchers/toBePositiveInfinity.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBePositiveInfinity = function(j$) { * {@link expect} the actual value to be `Infinity` (infinity). * @function * @name matchers#toBePositiveInfinity + * @since 2.6.0 * @example * expect(thing).toBePositiveInfinity(); */ diff --git a/src/core/matchers/toBeTrue.js b/src/core/matchers/toBeTrue.js index 4834bf4e..63331093 100644 --- a/src/core/matchers/toBeTrue.js +++ b/src/core/matchers/toBeTrue.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeTrue = function() { * {@link expect} the actual value to be `true`. * @function * @name matchers#toBeTrue + * @since 3.5.0 * @example * expect(result).toBeTrue(); */ diff --git a/src/core/matchers/toBeTruthy.js b/src/core/matchers/toBeTruthy.js index 7806bcda..3bece851 100644 --- a/src/core/matchers/toBeTruthy.js +++ b/src/core/matchers/toBeTruthy.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeTruthy = function() { * {@link expect} the actual value to be truthy. * @function * @name matchers#toBeTruthy + * @since 2.0.0 * @example * expect(thing).toBeTruthy(); */ diff --git a/src/core/matchers/toBeUndefined.js b/src/core/matchers/toBeUndefined.js index 455b8f76..04469364 100644 --- a/src/core/matchers/toBeUndefined.js +++ b/src/core/matchers/toBeUndefined.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toBeUndefined = function() { * {@link expect} the actual value to be `undefined`. * @function * @name matchers#toBeUndefined + * @since 1.3.0 * @example * expect(result).toBeUndefined(): */ diff --git a/src/core/matchers/toContain.js b/src/core/matchers/toContain.js index 141c3ded..440bb4c4 100644 --- a/src/core/matchers/toContain.js +++ b/src/core/matchers/toContain.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toContain = function() { * {@link expect} the actual value to contain a specific value. * @function * @name matchers#toContain + * @since 2.0.0 * @param {Object} expected - The value to look for. * @example * expect(array).toContain(anElement); diff --git a/src/core/matchers/toEqual.js b/src/core/matchers/toEqual.js index 33be478e..8697ed67 100644 --- a/src/core/matchers/toEqual.js +++ b/src/core/matchers/toEqual.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toEqual = function(j$) { * {@link expect} the actual value to be equal to the expected, using deep equality comparison. * @function * @name matchers#toEqual + * @since 1.3.0 * @param {Object} expected - Expected value * @example * expect(bigObject).toEqual({"foo": ['bar', 'baz']}); diff --git a/src/core/matchers/toHaveBeenCalled.js b/src/core/matchers/toHaveBeenCalled.js index b6836f45..bf1df2ed 100644 --- a/src/core/matchers/toHaveBeenCalled.js +++ b/src/core/matchers/toHaveBeenCalled.js @@ -6,6 +6,7 @@ getJasmineRequireObj().toHaveBeenCalled = function(j$) { * {@link expect} the actual (a {@link Spy}) to have been called. * @function * @name matchers#toHaveBeenCalled + * @since 1.3.0 * @example * expect(mySpy).toHaveBeenCalled(); * expect(mySpy).not.toHaveBeenCalled(); diff --git a/src/core/matchers/toHaveBeenCalledBefore.js b/src/core/matchers/toHaveBeenCalledBefore.js index eb98c07d..5c9b7063 100644 --- a/src/core/matchers/toHaveBeenCalledBefore.js +++ b/src/core/matchers/toHaveBeenCalledBefore.js @@ -6,6 +6,7 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { * {@link expect} the actual value (a {@link Spy}) to have been called before another {@link Spy}. * @function * @name matchers#toHaveBeenCalledBefore + * @since 2.6.0 * @param {Spy} expected - {@link Spy} that should have been called after the `actual` {@link Spy}. * @example * expect(mySpy).toHaveBeenCalledBefore(otherSpy); diff --git a/src/core/matchers/toHaveBeenCalledTimes.js b/src/core/matchers/toHaveBeenCalledTimes.js index b05ee8fe..282f8776 100644 --- a/src/core/matchers/toHaveBeenCalledTimes.js +++ b/src/core/matchers/toHaveBeenCalledTimes.js @@ -6,6 +6,7 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { * {@link expect} the actual (a {@link Spy}) to have been called the specified number of times. * @function * @name matchers#toHaveBeenCalledTimes + * @since 2.4.0 * @param {Number} expected - The number of invocations to look for. * @example * expect(mySpy).toHaveBeenCalledTimes(3); diff --git a/src/core/matchers/toHaveBeenCalledWith.js b/src/core/matchers/toHaveBeenCalledWith.js index 0cafcc69..05ddd4e2 100644 --- a/src/core/matchers/toHaveBeenCalledWith.js +++ b/src/core/matchers/toHaveBeenCalledWith.js @@ -6,6 +6,7 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { * {@link expect} the actual (a {@link Spy}) to have been called with particular arguments at least once. * @function * @name matchers#toHaveBeenCalledWith + * @since 1.3.0 * @param {...Object} - The arguments to look for * @example * expect(mySpy).toHaveBeenCalledWith('foo', 'bar', 2); diff --git a/src/core/matchers/toHaveClass.js b/src/core/matchers/toHaveClass.js index 99f784f3..a2fd7507 100644 --- a/src/core/matchers/toHaveClass.js +++ b/src/core/matchers/toHaveClass.js @@ -3,6 +3,7 @@ getJasmineRequireObj().toHaveClass = function(j$) { * {@link expect} the actual value to be a DOM element that has the expected class * @function * @name matchers#toHaveClass + * @since 3.0.0 * @param {Object} expected - The class name to test for * @example * var el = document.createElement('div'); diff --git a/src/core/matchers/toMatch.js b/src/core/matchers/toMatch.js index 380dfc26..7d8f658c 100644 --- a/src/core/matchers/toMatch.js +++ b/src/core/matchers/toMatch.js @@ -6,6 +6,7 @@ getJasmineRequireObj().toMatch = function(j$) { * {@link expect} the actual value to match a regular expression * @function * @name matchers#toMatch + * @since 1.3.0 * @param {RegExp|String} expected - Value to look for in the string. * @example * expect("my string").toMatch(/string$/); diff --git a/src/core/matchers/toThrow.js b/src/core/matchers/toThrow.js index 5337c7f7..a7e089d6 100644 --- a/src/core/matchers/toThrow.js +++ b/src/core/matchers/toThrow.js @@ -6,6 +6,7 @@ getJasmineRequireObj().toThrow = function(j$) { * {@link expect} a function to `throw` something. * @function * @name matchers#toThrow + * @since 2.0.0 * @param {Object} [expected] - Value that should be thrown. If not provided, simply the fact that something was thrown will be checked. * @example * expect(function() { return 'things'; }).toThrow('foo'); diff --git a/src/core/matchers/toThrowError.js b/src/core/matchers/toThrowError.js index ca3bfc5e..11c6d746 100644 --- a/src/core/matchers/toThrowError.js +++ b/src/core/matchers/toThrowError.js @@ -6,6 +6,7 @@ getJasmineRequireObj().toThrowError = function(j$) { * {@link expect} a function to `throw` an `Error`. * @function * @name matchers#toThrowError + * @since 2.0.0 * @param {Error} [expected] - `Error` constructor the object that was thrown needs to be an instance of. If not provided, `Error` will be used. * @param {RegExp|String} [message] - The message that should be set on the thrown `Error` * @example diff --git a/src/core/matchers/toThrowMatching.js b/src/core/matchers/toThrowMatching.js index bcc37166..bf9be39e 100644 --- a/src/core/matchers/toThrowMatching.js +++ b/src/core/matchers/toThrowMatching.js @@ -5,6 +5,7 @@ getJasmineRequireObj().toThrowMatching = function(j$) { * {@link expect} a function to `throw` something matching a predicate. * @function * @name matchers#toThrowMatching + * @since 3.0.0 * @param {Function} predicate - A function that takes the thrown exception as its parameter and returns true if it matches. * @example * expect(function() { throw new Error('nope'); }).toThrowMatching(function(thrown) { return thrown.message === 'nope'; }); diff --git a/src/core/requireInterface.js b/src/core/requireInterface.js index cff7403b..2abe12d2 100644 --- a/src/core/requireInterface.js +++ b/src/core/requireInterface.js @@ -15,6 +15,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * Calls to `describe` can be nested within other calls to compose your suite as a tree. * @name describe + * @since 1.3.0 * @function * @global * @param {String} description Textual description of the group @@ -29,6 +30,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * Specs within an `xdescribe` will be marked pending and not executed * @name xdescribe + * @since 1.3.0 * @function * @global * @param {String} description Textual description of the group @@ -44,6 +46,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * If suites or specs are focused, only those that are focused will be executed * @see fit * @name fdescribe + * @since 2.1.0 * @function * @global * @param {String} description Textual description of the group @@ -58,6 +61,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * A spec whose expectations all succeed will be passing and a spec with any failures will fail. * @name it + * @since 1.3.0 * @function * @global * @param {String} description Textual description of what this spec is checking @@ -74,6 +78,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * The spec will report as `pending` and will not be executed. * @name xit + * @since 1.3.0 * @function * @global * @param {String} description Textual description of what this spec is checking. @@ -88,6 +93,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * If suites or specs are focused, only those that are focused will be executed. * @name fit + * @since 2.1.0 * @function * @global * @param {String} description Textual description of what this spec is checking. @@ -102,6 +108,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Run some shared setup before each of the specs in the {@link describe} in which it is called. * @name beforeEach + * @since 1.3.0 * @function * @global * @param {implementationCallback} [function] Function that contains the code to setup your specs. @@ -115,6 +122,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Run some shared teardown after each of the specs in the {@link describe} in which it is called. * @name afterEach + * @since 1.3.0 * @function * @global * @param {implementationCallback} [function] Function that contains the code to teardown your specs. @@ -130,6 +138,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * _Note:_ Be careful, sharing the setup from a beforeAll makes it easy to accidentally leak state between your specs so that they erroneously pass or fail. * @name beforeAll + * @since 2.1.0 * @function * @global * @param {implementationCallback} [function] Function that contains the code to setup your specs. @@ -145,6 +154,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * _Note:_ Be careful, sharing the teardown from a afterAll makes it easy to accidentally leak state between your specs so that they erroneously pass or fail. * @name afterAll + * @since 2.1.0 * @function * @global * @param {implementationCallback} [function] Function that contains the code to teardown your specs. @@ -158,6 +168,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Create an expectation for a spec. * @name expect + * @since 1.3.0 * @function * @global * @param {Object} actual - Actual computed value to test expectations against. @@ -173,6 +184,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * which must be either returned from the spec or waited for using `await` * in order for Jasmine to associate them with the correct spec. * @name expectAsync + * @since 3.3.0 * @function * @global * @param {Object} actual - Actual computed value to test expectations against. @@ -189,6 +201,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Mark a spec as pending, expectation results will be ignored. * @name pending + * @since 2.0.0 * @function * @global * @param {String} [message] - Reason the spec is pending. @@ -200,6 +213,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Explicitly mark a spec as failed. * @name fail + * @since 2.1.0 * @function * @global * @param {String|Error} [error] - Reason for the failure. @@ -211,6 +225,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Install a spy onto an existing object. * @name spyOn + * @since 1.3.0 * @function * @global * @param {Object} obj - The object upon which to install the {@link Spy}. @@ -224,6 +239,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Install a spy on a property installed with `Object.defineProperty` onto an existing object. * @name spyOnProperty + * @since 2.6.0 * @function * @global * @param {Object} obj - The object upon which to install the {@link Spy} @@ -238,6 +254,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Installs spies on all writable and configurable properties of an object. * @name spyOnAllFunctions + * @since 3.2.1 * @function * @global * @param {Object} obj - The object upon which to install the {@link Spy}s @@ -262,6 +279,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * _Note:_ This is only callable from within a {@link beforeEach}, {@link it}, or {@link beforeAll}. * @name jasmine.addCustomEqualityTester + * @since 2.0.0 * @function * @param {Function} tester - A function which takes two arguments to compare and returns a `true` or `false` comparison result if it knows how to compare them, and `undefined` otherwise. * @see custom_equality @@ -275,6 +293,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * _Note:_ This is only callable from within a {@link beforeEach}, {@link it}, or {@link beforeAll}. * @name jasmine.addMatchers + * @since 2.0.0 * @function * @param {Object} matchers - Keys from this object will be the new matcher names. * @see custom_matcher @@ -286,6 +305,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Get the currently booted mock {Clock} for this Jasmine environment. * @name jasmine.clock + * @since 2.0.0 * @function * @returns {Clock} */ @@ -296,6 +316,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Create a bare {@link Spy} object. This won't be installed anywhere and will not have any implementation behind it. * @name jasmine.createSpy + * @since 1.3.0 * @function * @param {String} [name] - Name to give the spy. This will be displayed in failure messages. * @param {Function} [originalFn] - Function to act as the real implementation. @@ -308,6 +329,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { /** * Create an object with multiple {@link Spy}s as its members. * @name jasmine.createSpyObj + * @since 1.3.0 * @function * @param {String} [baseName] - Base name for the spies in the object. * @param {String[]|Object} methodNames - Array of method names to create spies for, or Object whose keys will be method names and values the {@link Spy#and#returnValue|returnValue}. @@ -322,6 +344,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * * _Note:_ This is only callable from within a {@link beforeEach}, {@link it}, or {@link beforeAll}. * @name jasmine.addSpyStrategy + * @since 3.5.0 * @function * @param {String} name - The name of the strategy (i.e. what you call from `and`) * @param {Function} factory - Factory function that returns the plan to be executed. From 3e888105f0d7819dfff855dde3c1c64e663c5d6e Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Fri, 14 Jun 2019 14:59:33 -0700 Subject: [PATCH 041/201] Calculate total suite run time inside the env and report in `jasmineDone` --- .gitignore | 1 + lib/jasmine-core/jasmine.js | 5 +++ spec/html/HtmlReporterSpec.js | 23 ++----------- spec/support/ci.js | 50 +++-------------------------- spec/support/jasmine-browser.js | 47 +++++++++++++++++++++++++++ spec/support/jasmine-browser.json | 33 ------------------- spec/support/localJasmineBrowser.js | 2 +- src/core/Env.js | 5 +++ src/html/HtmlReporter.js | 4 +-- 9 files changed, 66 insertions(+), 104 deletions(-) create mode 100644 spec/support/jasmine-browser.js delete mode 100644 spec/support/jasmine-browser.json diff --git a/.gitignore b/.gitignore index d8958bd2..4536a071 100644 --- a/.gitignore +++ b/.gitignore @@ -12,6 +12,7 @@ site/ tags Gemfile.lock package-lock.json +yarn.lock pkg/* .sass-cache/* src/html/.sass-cache/* diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index abbd7262..03666af2 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1495,6 +1495,9 @@ getJasmineRequireObj().Env = function(j$) { ); } + var jasmineTimer = new j$.Timer(); + jasmineTimer.start(); + /** * Information passed to the {@link Reporter#jasmineStarted} event. * @typedef JasmineStartedInfo @@ -1530,6 +1533,7 @@ getJasmineRequireObj().Env = function(j$) { * Information passed to the {@link Reporter#jasmineDone} event. * @typedef JasmineDoneInfo * @property {OverallStatus} overallStatus - The overall result of the suite: 'passed', 'failed', or 'incomplete'. + * @property {Int} totalTime - The total time (in ms) that it took to execute the suite * @property {IncompleteReason} incompleteReason - Explanation of why the suite was incomplete. * @property {Order} order - Information about the ordering (random or not) of this execution of the suite. * @property {Expectation[]} failedExpectations - List of expectations that failed in an {@link afterAll} at the global level. @@ -1538,6 +1542,7 @@ getJasmineRequireObj().Env = function(j$) { reporter.jasmineDone( { overallStatus: overallStatus, + totalTime: jasmineTimer.elapsed(), incompleteReason: incompleteReason, order: order, failedExpectations: topSuite.result.failedExpectations, diff --git a/spec/html/HtmlReporterSpec.js b/spec/html/HtmlReporterSpec.js index 2bff3c1f..da18deb3 100644 --- a/spec/html/HtmlReporterSpec.js +++ b/spec/html/HtmlReporterSpec.js @@ -61,22 +61,6 @@ describe('HtmlReporter', function() { ).toEqual(1); }); - it('starts the timer when jasmine begins', function() { - var env = new jasmine.Env(), - startTimerSpy = jasmine.createSpy('start-timer-spy'), - reporter = new jasmineUnderTest.HtmlReporter({ - env: env, - createElement: function() { - return document.createElement.apply(document, arguments); - }, - timer: { start: startTimerSpy } - }); - - reporter.jasmineStarted({}); - - expect(startTimerSpy).toHaveBeenCalled(); - }); - describe('when a spec is done', function() { it('logs errors to the console and prints a special symbol if it is an empty spec', function() { if (typeof console === 'undefined') { @@ -343,7 +327,6 @@ describe('HtmlReporter', function() { it('reports the run time', function() { var env = new jasmineUnderTest.Env(), container = document.createElement('div'), - timer = jasmine.createSpyObj('timer', ['start', 'elapsed']), getContainer = function() { return container; }, @@ -355,16 +338,14 @@ describe('HtmlReporter', function() { }, createTextNode: function() { return document.createTextNode.apply(document, arguments); - }, - timer: timer + } }); reporter.initialize(); reporter.jasmineStarted({}); - timer.elapsed.and.returnValue(100); - reporter.jasmineDone({}); + reporter.jasmineDone({ totalTime: 100 }); var duration = container.querySelector( '.jasmine-alert .jasmine-duration' diff --git a/spec/support/ci.js b/spec/support/ci.js index 573a9c6d..79a980df 100644 --- a/spec/support/ci.js +++ b/spec/support/ci.js @@ -1,52 +1,10 @@ /* eslint-env node, es6 */ const path = require('path'), jasmineBrowser = require('jasmine-browser-runner'), - jasmineCore = require('../../lib/jasmine-core'), - useSauce = process.env.USE_SAUCE === 'true'; + jasmineCore = require('../../lib/jasmine-core'); -var config = require(path.resolve('spec/support/jasmine-browser.json')); +var config = require(path.resolve('spec/support/jasmine-browser.js')); +config.clearReporters = true; config.jasmineCore = jasmineCore; -function buildWebdriver() { - const webdriver = require('selenium-webdriver'), - Capability = webdriver.Capability; - if (useSauce) { - const username = process.env['SAUCE_USERNAME'], - accessKey = process.env['SAUCE_ACCESS_KEY']; - return new webdriver.Builder() - .withCapabilities({ - name: `jasmine-core ${new Date().toISOString()}`, - [Capability.PLATFORM]: process.env['SAUCE_OS'], - [Capability.BROWSER_NAME]: process.env['JASMINE_BROWSER'], - [Capability.VERSION]: process.env['SAUCE_BROWSER_VERSION'], - build: `Core ${process.env['TRAVIS_BUILD_NUMBER'] || 'Ran locally'}`, - tags: ['Jasmine-Core'], - 'tunnel-identifier': process.env['TRAVIS_JOB_NUMBER'] - ? process.env['TRAVIS_JOB_NUMBER'].toString() - : null - }) - .usingServer(`http://${username}:${accessKey}@localhost:4445/wd/hub`) - .build(); - } else { - return new webdriver.Builder() - .forBrowser(process.env['JASMINE_BROWSER'] || 'firefox') - .build(); - } -} - -const driver = buildWebdriver(); -jasmineBrowser - .runSpecs(config, driver) - .then(function(runDetails) { - process.exitCode = runDetails.overallStatus === 'passed' ? 0 : 1; - - if (useSauce) { - driver.executeScript(`sauce:job-result=${process.exitCode === 0}`); - } - }) - .catch(error => { - console.error(error); - }) - .then(function() { - return driver ? driver.close() : true; - }); +jasmineBrowser.runSpecs(config); diff --git a/spec/support/jasmine-browser.js b/spec/support/jasmine-browser.js new file mode 100644 index 00000000..9986ba08 --- /dev/null +++ b/spec/support/jasmine-browser.js @@ -0,0 +1,47 @@ +/* eslint-env node, es6 */ +module.exports = { + srcDir: 'src', + srcFiles: [ + 'core/requireCore.js', + 'core/base.js', + 'core/util.js', + 'core/Spec.js', + 'core/Env.js', + 'core/JsApiReporter.js', + 'core/PrettyPrinter.js', + 'core/Suite.js', + 'core/**/*.js', + 'html/**/*.js', + '**/*.js' + ], + specDir: 'spec', + specFiles: ['**/*[Ss]pec.js', '!npmPackage/**/*'], + helpers: [ + 'helpers/asyncAwait.js', + 'helpers/BrowserFlags.js', + 'helpers/checkForMap.js', + 'helpers/checkForSet.js', + 'helpers/checkForSymbol.js', + 'helpers/checkForTypedArrays.js', + 'helpers/integrationMatchers.js', + 'helpers/promises.js', + 'helpers/defineJasmineUnderTest.js' + ], + random: true, + browser: { + name: process.env.JASMINE_BROWSER || 'firefox', + useSauce: process.env.USE_SAUCE === 'true', + sauce: { + name: `jasmine-core ${new Date().toISOString()}`, + os: process.env.SAUCE_OS, + browserVersion: process.env.SAUCE_BROWSER_VERSION, + build: `Core ${process.env.TRAVIS_BUILD_NUMBER || 'Ran locally'}`, + tags: ['Jasmine-Core'], + tunnelIdentifier: process.env.TRAVIS_JOB_NUMBER + ? process.env.TRAVIS_JOB_NUMBER.toString() + : null, + username: process.env.SAUCE_USERNAME, + accessKey: process.env.SAUCE_ACCESS_KEY + } + } +}; diff --git a/spec/support/jasmine-browser.json b/spec/support/jasmine-browser.json deleted file mode 100644 index de122f43..00000000 --- a/spec/support/jasmine-browser.json +++ /dev/null @@ -1,33 +0,0 @@ -{ - "srcDir": "src", - "srcFiles": [ - "core/requireCore.js", - "core/base.js", - "core/util.js", - "core/Spec.js", - "core/Env.js", - "core/JsApiReporter.js", - "core/PrettyPrinter.js", - "core/Suite.js", - "core/**/*.js", - "html/**/*.js", - "**/*.js" - ], - "specDir": "spec", - "specFiles": [ - "**/*[Ss]pec.js", - "!npmPackage/**/*" - ], - "helpers": [ - "helpers/asyncAwait.js", - "helpers/BrowserFlags.js", - "helpers/checkForMap.js", - "helpers/checkForSet.js", - "helpers/checkForSymbol.js", - "helpers/checkForTypedArrays.js", - "helpers/integrationMatchers.js", - "helpers/promises.js", - "helpers/defineJasmineUnderTest.js" - ], - "random": true -} diff --git a/spec/support/localJasmineBrowser.js b/spec/support/localJasmineBrowser.js index ec9affe2..d08261ee 100644 --- a/spec/support/localJasmineBrowser.js +++ b/spec/support/localJasmineBrowser.js @@ -2,7 +2,7 @@ var path = require('path'), jasmineBrowser = require('jasmine-browser-runner'), jasmineCore = require('../../lib/jasmine-core.js'); -var configFile = process.argv[2] || 'jasmine-browser.json'; +var configFile = process.argv[2] || 'jasmine-browser.js'; var config = require(path.resolve('spec/support', configFile)); config.jasmineCore = jasmineCore; diff --git a/src/core/Env.js b/src/core/Env.js index a031f3ff..d3e9e257 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -640,6 +640,9 @@ getJasmineRequireObj().Env = function(j$) { ); } + var jasmineTimer = new j$.Timer(); + jasmineTimer.start(); + /** * Information passed to the {@link Reporter#jasmineStarted} event. * @typedef JasmineStartedInfo @@ -675,6 +678,7 @@ getJasmineRequireObj().Env = function(j$) { * Information passed to the {@link Reporter#jasmineDone} event. * @typedef JasmineDoneInfo * @property {OverallStatus} overallStatus - The overall result of the suite: 'passed', 'failed', or 'incomplete'. + * @property {Int} totalTime - The total time (in ms) that it took to execute the suite * @property {IncompleteReason} incompleteReason - Explanation of why the suite was incomplete. * @property {Order} order - Information about the ordering (random or not) of this execution of the suite. * @property {Expectation[]} failedExpectations - List of expectations that failed in an {@link afterAll} at the global level. @@ -683,6 +687,7 @@ getJasmineRequireObj().Env = function(j$) { reporter.jasmineDone( { overallStatus: overallStatus, + totalTime: jasmineTimer.elapsed(), incompleteReason: incompleteReason, order: order, failedExpectations: topSuite.result.failedExpectations, diff --git a/src/html/HtmlReporter.js b/src/html/HtmlReporter.js index 5d838ab3..6bc8d1eb 100644 --- a/src/html/HtmlReporter.js +++ b/src/html/HtmlReporter.js @@ -52,7 +52,6 @@ jasmineRequire.HtmlReporter = function(j$) { addToExistingQueryString = options.addToExistingQueryString || defaultQueryString, filterSpecs = options.filterSpecs, - timer = options.timer || j$.noopTimer, htmlReporterMain, symbols, deprecationWarnings = []; @@ -86,7 +85,6 @@ jasmineRequire.HtmlReporter = function(j$) { var totalSpecsDefined; this.jasmineStarted = function(options) { totalSpecsDefined = options.totalSpecsDefined || 0; - timer.start(); }; var summary = createDom('div', { className: 'jasmine-summary' }); @@ -165,7 +163,7 @@ jasmineRequire.HtmlReporter = function(j$) { createDom( 'span', { className: 'jasmine-duration' }, - 'finished in ' + timer.elapsed() / 1000 + 's' + 'finished in ' + doneResult.totalTime / 1000 + 's' ) ); From 18dbbca43680fc34453ecd9ec0550c8d25d28774 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Fri, 14 Jun 2019 15:10:16 -0700 Subject: [PATCH 042/201] Refactor travis matrix to compress a bit more --- .travis.yml | 72 ++++++++++++++--------------------------------------- 1 file changed, 19 insertions(+), 53 deletions(-) diff --git a/.travis.yml b/.travis.yml index d8d308d8..66de972d 100644 --- a/.travis.yml +++ b/.travis.yml @@ -8,67 +8,33 @@ script: $TEST_COMMAND env: global: - - USE_SAUCE=false - - NOKOGIRI_USE_SYSTEM_LIBRARIES=true - - TEST_COMMAND="npm test" + - USE_SAUCE=true + - TEST_COMMAND="bash travis-core-script.sh" - secure: WSPWhlnC4mWSnSPquX+m1/BCu5ch5NygkaHuM2Nea7lD8oS3XLX8QncZZAsQ4lnNfqoDDuBOizG0AESiqNvE4y6x5qvLLTS6q+ce255ZEMZ71TBdZgDEEvGMEjOPPsVXiXyTQOP1lwOPlrbZvaPgWV7e11KIBab6DfFcQpnvDgo= - secure: SW7CJhZnwaNT749Gdnhvqb5rbXlAOsygUAzh9qhtyvbqXKkmJdBIEsO01YF6pbju1X2twE9JvWCOxeZju43NgQChJlPsGbjY2j3k/TdQeTAJesQe2K7ytwghunI30gjEovtRH0T3w1EmcKPH8yj5eBIcB2OYoJHx8KEC7e68q1g= + matrix: + - JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='' SAUCE_OS="Linux" + - JASMINE_BROWSER="chrome" SAUCE_BROWSER_VERSION='' SAUCE_OS="Linux" + - JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="10" SAUCE_OS="OS X 10.12" + - JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="9" SAUCE_OS="OS X 10.11" + - JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="8" SAUCE_OS="OS X 10.10" + - JASMINE_BROWSER="MicrosoftEdge" SAUCE_BROWSER_VERSION="15" SAUCE_OS="Windows 10" + - JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=11 SAUCE_OS="Windows 8.1" + - JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=10 SAUCE_OS="Windows 8" addons: sauce_connect: true matrix: include: - - env: - - USE_SAUCE=true - - TEST_COMMAND="bash travis-core-script.sh" - - JASMINE_BROWSER="firefox" - - SAUCE_OS="Linux" - - SAUCE_BROWSER_VERSION='' - - env: - - USE_SAUCE=true - - TEST_COMMAND="bash travis-core-script.sh" - - JASMINE_BROWSER="safari" - - SAUCE_OS="OS X 10.12" - - SAUCE_BROWSER_VERSION=10 - - env: - - USE_SAUCE=true - - TEST_COMMAND="bash travis-core-script.sh" - - JASMINE_BROWSER="safari" - - SAUCE_OS="OS X 10.11" - - SAUCE_BROWSER_VERSION=9 - - env: - - USE_SAUCE=true - - TEST_COMMAND="bash travis-core-script.sh" - - JASMINE_BROWSER="safari" - - SAUCE_OS="OS X 10.10" - - SAUCE_BROWSER_VERSION=8 - - env: - - USE_SAUCE=true - - TEST_COMMAND="bash travis-core-script.sh" - - JASMINE_BROWSER="MicrosoftEdge" - - SAUCE_OS="Windows 10" - - SAUCE_BROWSER_VERSION="15" - - env: - - USE_SAUCE=true - - TEST_COMMAND="bash travis-core-script.sh" - - JASMINE_BROWSER="internet explorer" - - SAUCE_OS="Windows 8.1" - - SAUCE_BROWSER_VERSION=11 - - env: - - USE_SAUCE=true - - TEST_COMMAND="bash travis-core-script.sh" - - JASMINE_BROWSER="internet explorer" - - SAUCE_OS="Windows 8" - - SAUCE_BROWSER_VERSION=10 - - env: - - USE_SAUCE=true - - TEST_COMMAND="bash travis-core-script.sh" - - JASMINE_BROWSER="chrome" - - SAUCE_OS="Linux" - - SAUCE_BROWSER_VERSION='' - - env: + - node_js: "10" + env: + - TEST_COMMAND="npm test - USE_SAUCE=false - - TEST_COMMAND="bash travis-core-script.sh" + - node_js: "12" + env: + - TEST_COMMAND="npm test" + - USE_SAUCE=false + - env: - JASMINE_BROWSER="phantomjs" - USE_SAUCE=false From 5c058b5bc46e7fe354caec3b453a44cceba2bc54 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Fri, 14 Jun 2019 15:11:41 -0700 Subject: [PATCH 043/201] Don't include node 10 & 12 in matrix, we're explicit later --- .travis.yml | 2 -- 1 file changed, 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index 66de972d..f11afde8 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,8 +1,6 @@ language: node_js node_js: - "8" - - "10" - - "12" script: $TEST_COMMAND From 49fd22ffe66628eb5378a5342ed672fda89e3ba2 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Fri, 14 Jun 2019 15:15:29 -0700 Subject: [PATCH 044/201] move everything we can into the `env` matrix for travis --- .travis.yml | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/.travis.yml b/.travis.yml index f11afde8..de702787 100644 --- a/.travis.yml +++ b/.travis.yml @@ -19,6 +19,8 @@ env: - JASMINE_BROWSER="MicrosoftEdge" SAUCE_BROWSER_VERSION="15" SAUCE_OS="Windows 10" - JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=11 SAUCE_OS="Windows 8.1" - JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=10 SAUCE_OS="Windows 8" + - TEST_COMMAND="npm test" + - JASMINE_BROWSER="phantomjs" USE_SAUCE=false addons: sauce_connect: true @@ -28,11 +30,6 @@ matrix: - node_js: "10" env: - TEST_COMMAND="npm test - - USE_SAUCE=false - node_js: "12" env: - TEST_COMMAND="npm test" - - USE_SAUCE=false - - env: - - JASMINE_BROWSER="phantomjs" - - USE_SAUCE=false From 031515db234844eb534805bd349c4140f7311e4e Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Fri, 14 Jun 2019 15:27:24 -0700 Subject: [PATCH 045/201] rejigger travis again to not run sauce jobs for PRs --- .travis.yml | 34 +++++++++++++++++++--------------- 1 file changed, 19 insertions(+), 15 deletions(-) diff --git a/.travis.yml b/.travis.yml index de702787..be271de4 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,6 +1,8 @@ language: node_js node_js: - "8" + - "10" + - "12" script: $TEST_COMMAND @@ -11,25 +13,27 @@ env: - secure: WSPWhlnC4mWSnSPquX+m1/BCu5ch5NygkaHuM2Nea7lD8oS3XLX8QncZZAsQ4lnNfqoDDuBOizG0AESiqNvE4y6x5qvLLTS6q+ce255ZEMZ71TBdZgDEEvGMEjOPPsVXiXyTQOP1lwOPlrbZvaPgWV7e11KIBab6DfFcQpnvDgo= - secure: SW7CJhZnwaNT749Gdnhvqb5rbXlAOsygUAzh9qhtyvbqXKkmJdBIEsO01YF6pbju1X2twE9JvWCOxeZju43NgQChJlPsGbjY2j3k/TdQeTAJesQe2K7ytwghunI30gjEovtRH0T3w1EmcKPH8yj5eBIcB2OYoJHx8KEC7e68q1g= matrix: - - JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='' SAUCE_OS="Linux" - - JASMINE_BROWSER="chrome" SAUCE_BROWSER_VERSION='' SAUCE_OS="Linux" - - JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="10" SAUCE_OS="OS X 10.12" - - JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="9" SAUCE_OS="OS X 10.11" - - JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="8" SAUCE_OS="OS X 10.10" - - JASMINE_BROWSER="MicrosoftEdge" SAUCE_BROWSER_VERSION="15" SAUCE_OS="Windows 10" - - JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=11 SAUCE_OS="Windows 8.1" - - JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=10 SAUCE_OS="Windows 8" - TEST_COMMAND="npm test" - - JASMINE_BROWSER="phantomjs" USE_SAUCE=false addons: sauce_connect: true matrix: include: - - node_js: "10" - env: - - TEST_COMMAND="npm test - - node_js: "12" - env: - - TEST_COMMAND="npm test" + - env: JASMINE_BROWSER="phantomjs" USE_SAUCE=false + - env: JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='' SAUCE_OS="Linux" + if: type != pull_request + - env: JASMINE_BROWSER="chrome" SAUCE_BROWSER_VERSION='' SAUCE_OS="Linux" + if: type != pull_request + - env: JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="10" SAUCE_OS="OS X 10.12" + if: type != pull_request + - env: JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="9" SAUCE_OS="OS X 10.11" + if: type != pull_request + - env: JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="8" SAUCE_OS="OS X 10.10" + if: type != pull_request + - env: JASMINE_BROWSER="MicrosoftEdge" SAUCE_BROWSER_VERSION="15" SAUCE_OS="Windows 10" + if: type != pull_request + - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=11 SAUCE_OS="Windows 8.1" + if: type != pull_request + - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=10 SAUCE_OS="Windows 8" + if: type != pull_request From e7d0d742a8ecb1b2fcd234bb0a0cf371bda18511 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Fri, 14 Jun 2019 15:43:14 -0700 Subject: [PATCH 046/201] only turn on sauce_connect for jobs that need it (I think) --- .travis.yml | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index be271de4..3b00841b 100644 --- a/.travis.yml +++ b/.travis.yml @@ -15,25 +15,39 @@ env: matrix: - TEST_COMMAND="npm test" -addons: - sauce_connect: true matrix: include: - env: JASMINE_BROWSER="phantomjs" USE_SAUCE=false - env: JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='' SAUCE_OS="Linux" if: type != pull_request + addons: + sauce_connect: true - env: JASMINE_BROWSER="chrome" SAUCE_BROWSER_VERSION='' SAUCE_OS="Linux" if: type != pull_request + addons: + sauce_connect: true - env: JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="10" SAUCE_OS="OS X 10.12" if: type != pull_request + addons: + sauce_connect: true - env: JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="9" SAUCE_OS="OS X 10.11" if: type != pull_request + addons: + sauce_connect: true - env: JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="8" SAUCE_OS="OS X 10.10" if: type != pull_request + addons: + sauce_connect: true - env: JASMINE_BROWSER="MicrosoftEdge" SAUCE_BROWSER_VERSION="15" SAUCE_OS="Windows 10" if: type != pull_request + addons: + sauce_connect: true - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=11 SAUCE_OS="Windows 8.1" if: type != pull_request + addons: + sauce_connect: true - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=10 SAUCE_OS="Windows 8" if: type != pull_request + addons: + sauce_connect: true From 9a6262e3cd3b6aad95780b7d30a71f91a3182443 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Fri, 14 Jun 2019 16:42:10 -0700 Subject: [PATCH 047/201] bump browser runner to new version --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index dc9c3512..741d963c 100644 --- a/package.json +++ b/package.json @@ -36,7 +36,7 @@ "grunt-css-url-embed": "^1.11.1", "grunt-sass": "^3.0.2", "jasmine": "^3.4.0", - "jasmine-browser-runner": "^0.1.0", + "jasmine-browser-runner": "0.2.0", "jsdom": "^15.0.0", "load-grunt-tasks": "^4.0.0", "node-sass": "^4.11.0", From a536ca19f282c7fd232ae0925c0a3f963c71c5c0 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Thu, 20 Jun 2019 06:46:51 -0400 Subject: [PATCH 048/201] Don't attempt to normalize PNGs --- .gitattributes | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitattributes b/.gitattributes index 6313b56c..05881d4e 100644 --- a/.gitattributes +++ b/.gitattributes @@ -1 +1,2 @@ * text=auto eol=lf +*.png -text From 45475f6d1ecc489025e9f1f756847a33bc5bc98d Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Thu, 20 Jun 2019 07:33:10 -0400 Subject: [PATCH 049/201] Allow users to pass property names to createSpyObj --- spec/core/SpySpec.js | 39 +++++++++++++++++++++++++ src/core/Env.js | 4 +-- src/core/SpyFactory.js | 55 +++++++++++++++++++++++++----------- src/core/requireInterface.js | 5 ++-- 4 files changed, 83 insertions(+), 20 deletions(-) diff --git a/spec/core/SpySpec.js b/spec/core/SpySpec.js index f2eea200..2295d8a6 100644 --- a/spec/core/SpySpec.js +++ b/spec/core/SpySpec.js @@ -174,6 +174,45 @@ describe('Spies', function() { 'createSpyObj requires a non-empty array or object of method names to create spies for' ); }); + + it('creates an object with spy properties if a second list is passed', function() { + var spyObj = env.createSpyObj('base', ['method1'], ['prop1']); + + expect(spyObj).toEqual({ + method1: jasmine.any(Function) + }); + + var descriptor = Object.getOwnPropertyDescriptor(spyObj, 'prop1'); + expect(descriptor.get.and.identity).toEqual('base.prop1.get'); + expect(descriptor.set.and.identity).toEqual('base.prop1.set'); + + expect(spyObj.prop1).toBeUndefined(); + }); + + it('creates an object with property names and return values if second object is passed', function() { + var spyObj = env.createSpyObj('base', ['method1'], { + prop1: 'foo', + prop2: 37 + }); + + expect(spyObj).toEqual({ + method1: jasmine.any(Function) + }); + + expect(spyObj.prop1).toEqual('foo'); + expect(spyObj.prop2).toEqual(37); + spyObj.prop2 = 4; + expect(spyObj.prop2).toEqual(37); + expect(Object.getOwnPropertyDescriptor(spyObj, 'prop2').set.calls.count()).toBe(1); + }); + + it('allows base name to be ommitted when assigning methods and properties', function() { + var spyObj = env.createSpyObj({ m: 3 }, { p: 4 }); + + expect(spyObj.m()).toEqual(3); + expect(spyObj.p).toEqual(4); + expect(Object.getOwnPropertyDescriptor(spyObj, 'p').get.and.identity).toEqual('unknown.p.get'); + }); }); it('can use different strategies for different arguments', function() { diff --git a/src/core/Env.js b/src/core/Env.js index 18924dcd..0bed0229 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -764,8 +764,8 @@ getJasmineRequireObj().Env = function(j$) { return spyFactory.createSpy(name, originalFn); }; - this.createSpyObj = function(baseName, methodNames) { - return spyFactory.createSpyObj(baseName, methodNames); + this.createSpyObj = function(baseName, methodNames, propertyNames) { + return spyFactory.createSpyObj(baseName, methodNames, propertyNames); }; var ensureIsFunction = function(fn, caller) { diff --git a/src/core/SpyFactory.js b/src/core/SpyFactory.js index a622a8a3..d7446cb7 100644 --- a/src/core/SpyFactory.js +++ b/src/core/SpyFactory.js @@ -6,34 +6,41 @@ getJasmineRequireObj().SpyFactory = function(j$) { return j$.Spy(name, originalFn, getCustomStrategies(), getPromise); }; - this.createSpyObj = function(baseName, methodNames) { + this.createSpyObj = function(baseName, methodNames, propertyNames) { var baseNameIsCollection = j$.isObject_(baseName) || j$.isArray_(baseName); - if (baseNameIsCollection && j$.util.isUndefined(methodNames)) { + if (baseNameIsCollection) { + propertyNames = methodNames; methodNames = baseName; baseName = 'unknown'; } var obj = {}; - var spiesWereSet = false; + var spy, descriptor; - if (j$.isArray_(methodNames)) { - for (var i = 0; i < methodNames.length; i++) { - obj[methodNames[i]] = self.createSpy(baseName + '.' + methodNames[i]); - spiesWereSet = true; - } - } else if (j$.isObject_(methodNames)) { - for (var key in methodNames) { - if (methodNames.hasOwnProperty(key)) { - obj[key] = self.createSpy(baseName + '.' + key); - obj[key].and.returnValue(methodNames[key]); - spiesWereSet = true; - } + var methods = normalizeKeyValues(methodNames); + for (var i = 0; i < methods.length; i++) { + spy = obj[methods[i][0]] = self.createSpy(baseName + '.' + methods[i][0]); + if (methods[i].length > 1) { + spy.and.returnValue(methods[i][1]); } } - if (!spiesWereSet) { + var properties = normalizeKeyValues(propertyNames); + for (var i = 0; i < properties.length; i++) { + descriptor = { + get: self.createSpy(baseName + '.' + properties[i][0] + '.get'), + set: self.createSpy(baseName + '.' + properties[i][0] + '.set') + }; + if (properties[i].length > 1) { + descriptor.get.and.returnValue(properties[i][1]); + descriptor.set.and.returnValue(properties[i][1]); + } + Object.defineProperty(obj, properties[i][0], descriptor); + } + + if (methods.length === 0 && properties.length === 0) { throw 'createSpyObj requires a non-empty array or object of method names to create spies for'; } @@ -41,5 +48,21 @@ getJasmineRequireObj().SpyFactory = function(j$) { }; } + function normalizeKeyValues(object) { + var result = []; + if (j$.isArray_(object)) { + for (var i = 0; i < object.length; i++) { + result.push([object[i]]); + } + } else if (j$.isObject_(object)) { + for (var key in object) { + if (object.hasOwnProperty(key)) { + result.push([key, object[key]]); + } + } + } + return result; + } + return SpyFactory; }; diff --git a/src/core/requireInterface.js b/src/core/requireInterface.js index cff7403b..494c2823 100644 --- a/src/core/requireInterface.js +++ b/src/core/requireInterface.js @@ -311,10 +311,11 @@ getJasmineRequireObj().interface = function(jasmine, env) { * @function * @param {String} [baseName] - Base name for the spies in the object. * @param {String[]|Object} methodNames - Array of method names to create spies for, or Object whose keys will be method names and values the {@link Spy#and#returnValue|returnValue}. + * @param {String[]|Object} [propertyNames] - Array of property names to create spies for, or Object whose keys will be propertynames and values the {@link Spy#and#returnValue|returnValue}. * @return {Object} */ - jasmine.createSpyObj = function(baseName, methodNames) { - return env.createSpyObj(baseName, methodNames); + jasmine.createSpyObj = function(baseName, methodNames, propertyNames) { + return env.createSpyObj(baseName, methodNames, propertyNames); }; /** From 65e6df55ee094487913025e04b9474569a3b43ad Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Thu, 20 Jun 2019 07:34:31 -0400 Subject: [PATCH 050/201] Linting fixes --- spec/core/SpySpec.js | 8 ++++++-- src/core/SpyFactory.js | 4 +++- 2 files changed, 9 insertions(+), 3 deletions(-) diff --git a/spec/core/SpySpec.js b/spec/core/SpySpec.js index 2295d8a6..b1165dd3 100644 --- a/spec/core/SpySpec.js +++ b/spec/core/SpySpec.js @@ -203,7 +203,9 @@ describe('Spies', function() { expect(spyObj.prop2).toEqual(37); spyObj.prop2 = 4; expect(spyObj.prop2).toEqual(37); - expect(Object.getOwnPropertyDescriptor(spyObj, 'prop2').set.calls.count()).toBe(1); + expect( + Object.getOwnPropertyDescriptor(spyObj, 'prop2').set.calls.count() + ).toBe(1); }); it('allows base name to be ommitted when assigning methods and properties', function() { @@ -211,7 +213,9 @@ describe('Spies', function() { expect(spyObj.m()).toEqual(3); expect(spyObj.p).toEqual(4); - expect(Object.getOwnPropertyDescriptor(spyObj, 'p').get.and.identity).toEqual('unknown.p.get'); + expect( + Object.getOwnPropertyDescriptor(spyObj, 'p').get.and.identity + ).toEqual('unknown.p.get'); }); }); diff --git a/src/core/SpyFactory.js b/src/core/SpyFactory.js index d7446cb7..d9cdc228 100644 --- a/src/core/SpyFactory.js +++ b/src/core/SpyFactory.js @@ -21,7 +21,9 @@ getJasmineRequireObj().SpyFactory = function(j$) { var methods = normalizeKeyValues(methodNames); for (var i = 0; i < methods.length; i++) { - spy = obj[methods[i][0]] = self.createSpy(baseName + '.' + methods[i][0]); + spy = obj[methods[i][0]] = self.createSpy( + baseName + '.' + methods[i][0] + ); if (methods[i].length > 1) { spy.and.returnValue(methods[i][1]); } From 6324fda0650e9989f456424eaedb0d625d2b4abf Mon Sep 17 00:00:00 2001 From: johnjbarton Date: Thu, 27 Jun 2019 10:35:59 -0700 Subject: [PATCH 051/201] PrettyPrinter survives if objects throw in toString --- spec/core/PrettyPrintSpec.js | 10 ++++++++-- src/core/PrettyPrinter.js | 21 +++++++++++++++------ 2 files changed, 23 insertions(+), 8 deletions(-) diff --git a/spec/core/PrettyPrintSpec.js b/spec/core/PrettyPrintSpec.js index 0e3c48ad..1249d8c6 100644 --- a/spec/core/PrettyPrintSpec.js +++ b/spec/core/PrettyPrintSpec.js @@ -457,11 +457,17 @@ describe('jasmineUnderTest.pp', function() { // Valid: an actual number baz: 3, // Valid: an actual Error object - qux: new Error('bar') + qux: new Error('bar'), + // + baddy: { + toString: function() { + throw new Error('I am a bad toString'); + } + } }; expect(jasmineUnderTest.pp(obj)).toEqual( - 'Object({ foo: [object Number], bar: [object Object], baz: 3, qux: Error: bar })' + 'Object({ foo: [object Number], bar: [object Object], baz: 3, qux: Error: bar, baddy: has-invalid-toString-method })' ); }); }); diff --git a/src/core/PrettyPrinter.js b/src/core/PrettyPrinter.js index 67cb34d6..e01afc80 100644 --- a/src/core/PrettyPrinter.js +++ b/src/core/PrettyPrinter.js @@ -9,11 +9,16 @@ getJasmineRequireObj().pp = function(j$) { function hasCustomToString(value) { // value.toString !== Object.prototype.toString if value has no custom toString but is from another context (e.g. // iframe, web worker) - return ( - j$.isFunction_(value.toString) && - value.toString !== Object.prototype.toString && - value.toString() !== Object.prototype.toString.call(value) - ); + try { + return ( + j$.isFunction_(value.toString) && + value.toString !== Object.prototype.toString && + value.toString() !== Object.prototype.toString.call(value) + ); + } catch (e) { + // The custom toString() threw. + return true; + } } PrettyPrinter.prototype.format = function(value) { @@ -59,7 +64,11 @@ getJasmineRequireObj().pp = function(j$) { !j$.isArray_(value) && hasCustomToString(value) ) { - this.emitScalar(value.toString()); + try { + this.emitScalar(value.toString()); + } catch (e) { + this.emitScalar('has-invalid-toString-method'); + } } else if (j$.util.arrayContains(this.seen, value)) { this.emitScalar( ' Date: Sun, 7 Jul 2019 19:01:36 -0700 Subject: [PATCH 052/201] Use node 10 for browser based builds --- .travis.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index 3b00841b..8c9ebe78 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,7 +1,7 @@ language: node_js node_js: - - "8" - "10" + - "8" - "12" script: $TEST_COMMAND From 5e87e1410d6a8e38b049081b8ed6d88d00935505 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Sun, 7 Jul 2019 19:20:45 -0700 Subject: [PATCH 053/201] update to newer jasmine-browser-runner --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 741d963c..4ccabce9 100644 --- a/package.json +++ b/package.json @@ -36,7 +36,7 @@ "grunt-css-url-embed": "^1.11.1", "grunt-sass": "^3.0.2", "jasmine": "^3.4.0", - "jasmine-browser-runner": "0.2.0", + "jasmine-browser-runner": "0.3.0", "jsdom": "^15.0.0", "load-grunt-tasks": "^4.0.0", "node-sass": "^4.11.0", From c37e9b9db005b2432ac0ad93373f2c6139739163 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Sun, 7 Jul 2019 19:37:09 -0700 Subject: [PATCH 054/201] Add saucelabs badge to readme --- README.md | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index cdfdd539..30c09023 100644 --- a/README.md +++ b/README.md @@ -54,6 +54,7 @@ Add the following to your HTML file: Jasmine tests itself across many browsers (Safari, Chrome, Firefox, PhantomJS, Microsoft Edge, and new Internet Explorer) as well as nodejs. To see the exact version tests are run against look at our [.travis.yml](https://github.com/jasmine/jasmine/blob/master/.travis.yml) +[![Sauce Test Status](https://saucelabs.com/browser-matrix/jasmine-js.svg)](https://saucelabs.com/u/jasmine-js) ## Support @@ -79,4 +80,4 @@ Copyright (c) 2008-2018 Pivotal Labs. This software is licensed under the MIT Li ## License -[![FOSSA Status](https://app.fossa.io/api/projects/git%2Bgithub.com%2Fjasmine%2Fjasmine.svg?type=large)](https://app.fossa.io/projects/git%2Bgithub.com%2Fjasmine%2Fjasmine?ref=badge_large) \ No newline at end of file +[![FOSSA Status](https://app.fossa.io/api/projects/git%2Bgithub.com%2Fjasmine%2Fjasmine.svg?type=large)](https://app.fossa.io/projects/git%2Bgithub.com%2Fjasmine%2Fjasmine?ref=badge_large) From c100bb6242adde9fab8b323bf2807c1015307dac Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 13 Jul 2019 10:05:20 -0700 Subject: [PATCH 055/201] Made output of toHaveBeenCalledWith more readable This breaks each call out onto its own line, so that it's much easier to see where each call starts and how they differ. E.g. previously the output would be: Expected spy foo to have been called with [ 'bar', 'baz', 'qux' ] but actual calls were [ [ 42, 'wibble' ], [ 'bar' 'qux' ], [ 'grault '] ] Now it's: Expected spy foo to have been called with: [ 'bar', 'baz', 'qux' ] but actual calls were: [ 42, 'wibble' ], [ 'bar' 'qux' ], [ 'grault ']. --- lib/jasmine-core/jasmine.js | 23 ++++++++++++++++--- .../core/matchers/toHaveBeenCalledWithSpec.js | 6 ++--- src/core/matchers/toHaveBeenCalledWith.js | 23 ++++++++++++++++--- 3 files changed, 43 insertions(+), 9 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 2f48e945..eea53a21 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -5106,15 +5106,32 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { } if (!actual.calls.any()) { - result.message = function() { return 'Expected spy ' + actual.and.identity + ' to have been called with ' + j$.pp(expectedArgs) + ' but it was never called.'; }; + result.message = function() { + return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + + ' ' + j$.pp(expectedArgs) + + '\nbut it was never called.'; + }; return result; } if (util.contains(actual.calls.allArgs(), expectedArgs, customEqualityTesters)) { result.pass = true; - result.message = function() { return 'Expected spy ' + actual.and.identity + ' not to have been called with ' + j$.pp(expectedArgs) + ' but it was.'; }; + result.message = function() { + return 'Expected spy ' + actual.and.identity + ' not to have been called with:\n' + + ' ' + j$.pp(expectedArgs) + + '\nbut it was.'; + }; } else { - result.message = function() { return 'Expected spy ' + actual.and.identity + ' to have been called with ' + j$.pp(expectedArgs) + ' but actual calls were ' + j$.pp(actual.calls.allArgs()).replace(/^\[ | \]$/g, '') + '.'; }; + result.message = function() { + var prettyPrintedCalls = actual.calls.allArgs().map(function(argsForCall) { + return ' ' + j$.pp(argsForCall); + }); + + return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + + ' ' + j$.pp(expectedArgs) + '\n' + '' + + 'but actual calls were:\n' + + prettyPrintedCalls.join(',\n') + '.'; + }; } return result; diff --git a/spec/core/matchers/toHaveBeenCalledWithSpec.js b/spec/core/matchers/toHaveBeenCalledWithSpec.js index 110e3dc2..534eca46 100644 --- a/spec/core/matchers/toHaveBeenCalledWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledWithSpec.js @@ -12,7 +12,7 @@ describe("toHaveBeenCalledWith", function() { result = matcher.compare(calledSpy, 'a', 'b'); expect(result.pass).toBe(true); - expect(result.message()).toEqual("Expected spy called-spy not to have been called with [ 'a', 'b' ] but it was."); + expect(result.message()).toEqual("Expected spy called-spy not to have been called with:\n [ 'a', 'b' ]\nbut it was."); }); it("passes through the custom equality testers", function() { @@ -39,7 +39,7 @@ describe("toHaveBeenCalledWith", function() { result = matcher.compare(uncalledSpy); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected spy uncalled spy to have been called with [ ] but it was never called."); + expect(result.message()).toEqual("Expected spy uncalled spy to have been called with:\n [ ]\nbut it was never called."); }); it("fails when the actual was called with different parameters", function() { @@ -55,7 +55,7 @@ describe("toHaveBeenCalledWith", function() { result = matcher.compare(calledSpy, 'a', 'b'); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected spy called spy to have been called with [ 'a', 'b' ] but actual calls were [ 'a' ], [ 'c', 'd' ]."); + expect(result.message()).toEqual("Expected spy called spy to have been called with:\n [ 'a', 'b' ]\nbut actual calls were:\n [ 'a' ],\n [ 'c', 'd' ]."); }); it("throws an exception when the actual is not a spy", function() { diff --git a/src/core/matchers/toHaveBeenCalledWith.js b/src/core/matchers/toHaveBeenCalledWith.js index 05ddd4e2..79197813 100644 --- a/src/core/matchers/toHaveBeenCalledWith.js +++ b/src/core/matchers/toHaveBeenCalledWith.js @@ -24,15 +24,32 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { } if (!actual.calls.any()) { - result.message = function() { return 'Expected spy ' + actual.and.identity + ' to have been called with ' + j$.pp(expectedArgs) + ' but it was never called.'; }; + result.message = function() { + return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + + ' ' + j$.pp(expectedArgs) + + '\nbut it was never called.'; + }; return result; } if (util.contains(actual.calls.allArgs(), expectedArgs, customEqualityTesters)) { result.pass = true; - result.message = function() { return 'Expected spy ' + actual.and.identity + ' not to have been called with ' + j$.pp(expectedArgs) + ' but it was.'; }; + result.message = function() { + return 'Expected spy ' + actual.and.identity + ' not to have been called with:\n' + + ' ' + j$.pp(expectedArgs) + + '\nbut it was.'; + }; } else { - result.message = function() { return 'Expected spy ' + actual.and.identity + ' to have been called with ' + j$.pp(expectedArgs) + ' but actual calls were ' + j$.pp(actual.calls.allArgs()).replace(/^\[ | \]$/g, '') + '.'; }; + result.message = function() { + var prettyPrintedCalls = actual.calls.allArgs().map(function(argsForCall) { + return ' ' + j$.pp(argsForCall); + }); + + return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + + ' ' + j$.pp(expectedArgs) + '\n' + '' + + 'but actual calls were:\n' + + prettyPrintedCalls.join(',\n') + '.'; + }; } return result; From d68b47b76dfeea72dd0da836a264bfc1e11bb821 Mon Sep 17 00:00:00 2001 From: Olle Jonsson Date: Sun, 14 Jul 2019 10:38:36 +0200 Subject: [PATCH 056/201] Gemspec: Drop EOL'd property rubyforge_project --- jasmine-core.gemspec | 1 - 1 file changed, 1 deletion(-) diff --git a/jasmine-core.gemspec b/jasmine-core.gemspec index df310a85..427d48c7 100644 --- a/jasmine-core.gemspec +++ b/jasmine-core.gemspec @@ -11,7 +11,6 @@ Gem::Specification.new do |s| s.description = %q{Test your JavaScript without any framework dependencies, in any environment, and with a nice descriptive syntax.} s.email = %q{jasmine-js@googlegroups.com} s.homepage = "http://jasmine.github.io" - s.rubyforge_project = "jasmine-core" s.license = "MIT" s.files = Dir.glob("./lib/**/*") From df4b6e58e2063b6bccb762927dcc1bb6c45376d4 Mon Sep 17 00:00:00 2001 From: Ferdinand Prantl Date: Mon, 15 Jul 2019 14:43:22 +0200 Subject: [PATCH 057/201] Pass the error including stacktrace to error handlers and reporters The global window error handler is used to handle errors thrown from within asynchronous functions and tests. The first parameter is the error; the fifth parameter is the full error object including the stacktrace. Searching for the first occurrence of an error instance to work with browsers, which may not comply with the HTML5 standard. --- src/core/GlobalErrors.js | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/core/GlobalErrors.js b/src/core/GlobalErrors.js index 2c58e684..e8430c1e 100644 --- a/src/core/GlobalErrors.js +++ b/src/core/GlobalErrors.js @@ -7,7 +7,12 @@ getJasmineRequireObj().GlobalErrors = function(j$) { var handler = handlers[handlers.length - 1]; if (handler) { - handler.apply(null, Array.prototype.slice.call(arguments, 0)); + // Get error from (message, source, lineno, colno, error) + var args = Array.prototype.slice.call(arguments, 0); + var error = args.find(function(arg) { + return arg instanceof Error; + }); + handler.apply(null, error ? [error] : args); } else { throw arguments[0]; } From 4858a62fdc55516888c906cb91dc3c37925c44c6 Mon Sep 17 00:00:00 2001 From: Ferdinand Prantl Date: Tue, 16 Jul 2019 12:00:09 +0200 Subject: [PATCH 058/201] Add a unit test for the global error handling including stacktrace --- spec/core/GlobalErrorsSpec.js | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/spec/core/GlobalErrorsSpec.js b/spec/core/GlobalErrorsSpec.js index 9ff19891..b4a54282 100644 --- a/spec/core/GlobalErrorsSpec.js +++ b/spec/core/GlobalErrorsSpec.js @@ -12,6 +12,20 @@ describe('GlobalErrors', function() { expect(handler).toHaveBeenCalledWith('foo'); }); + it('prefers passing the error including stack to the handler', function() { + var fakeGlobal = { onerror: null }, + handler = jasmine.createSpy('errorHandler'), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal), + fooError = new Error('foo'); + + errors.install(); + errors.pushListener(handler); + + fakeGlobal.onerror(fooError.message, 'foo.js', 1, 1, fooError); + + expect(handler).toHaveBeenCalledWith(fooError); + }); + it('only calls the most recent handler', function() { var fakeGlobal = { onerror: null }, handler1 = jasmine.createSpy('errorHandler1'), From 7c3434723e05fad11ad5d6e6a532944e88c2fb42 Mon Sep 17 00:00:00 2001 From: Ferdinand Prantl Date: Sun, 21 Jul 2019 23:46:14 +0200 Subject: [PATCH 059/201] Use the documented interface to pick the error instance from the global error handler --- src/core/GlobalErrors.js | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/src/core/GlobalErrors.js b/src/core/GlobalErrors.js index e8430c1e..f62208b4 100644 --- a/src/core/GlobalErrors.js +++ b/src/core/GlobalErrors.js @@ -3,16 +3,14 @@ getJasmineRequireObj().GlobalErrors = function(j$) { var handlers = []; global = global || j$.getGlobal(); - var onerror = function onerror() { + var onerror = function onerror(message, source, lineno, colno, error) { var handler = handlers[handlers.length - 1]; if (handler) { - // Get error from (message, source, lineno, colno, error) var args = Array.prototype.slice.call(arguments, 0); - var error = args.find(function(arg) { - return arg instanceof Error; - }); - handler.apply(null, error ? [error] : args); + // Prefer passing the error to the error handler + // to be able to print the stack trace. + handler.apply(null, error instanceof Error ? [error] : args); } else { throw arguments[0]; } From 18195a868cab335705d8bb1a5030e7939d6994ef Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 3 Aug 2019 08:25:57 -0700 Subject: [PATCH 060/201] Updated async timeout message There are now multiple ways to do async functions, and callbacks are probably the least common in new code, so the message should be more general rather than referring to callbacks. --- lib/jasmine-core/jasmine.js | 2 +- spec/core/integration/EnvSpec.js | 12 ++++++------ src/core/QueueRunner.js | 2 +- 3 files changed, 8 insertions(+), 8 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index eea53a21..ca636eca 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -6106,7 +6106,7 @@ getJasmineRequireObj().QueueRunner = function(j$) { var timeoutInterval = queueableFn.timeout || j$.DEFAULT_TIMEOUT_INTERVAL; timeoutId = self.setTimeout(function() { var error = new Error( - 'Timeout - Async callback was not invoked within ' + + 'Timeout - Async function did not complete within ' + timeoutInterval + 'ms ' + (queueableFn.timeout diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index 3a10e30b..9c827b24 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -1106,17 +1106,17 @@ describe("Env integration", function() { env.execute(); }); - it('should wait a custom interval before reporting async functions that fail to call done', function(done) { + it('should wait a custom interval before reporting async functions that fail to complete', function(done) { var env = createMockedEnv(), reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(r) { expect(r.failedExpectations).toEqual([]); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('suite beforeAll', [ /^Error: Timeout - Async callback was not invoked within 5000ms \(custom timeout\)/ ]); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('suite afterAll', [ /^Error: Timeout - Async callback was not invoked within 2000ms \(custom timeout\)/ ]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite beforeEach times out', [/^Error: Timeout - Async callback was not invoked within 1000ms \(custom timeout\)/]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite afterEach times out', [ /^Error: Timeout - Async callback was not invoked within 4000ms \(custom timeout\)/ ]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite it times out', [ /^Error: Timeout - Async callback was not invoked within 6000ms \(custom timeout\)/ ]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('suite beforeAll', [ /^Error: Timeout - Async function did not complete within 5000ms \(custom timeout\)/ ]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('suite afterAll', [ /^Error: Timeout - Async function did not complete within 2000ms \(custom timeout\)/ ]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite beforeEach times out', [/^Error: Timeout - Async function did not complete within 1000ms \(custom timeout\)/]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite afterEach times out', [ /^Error: Timeout - Async function did not complete within 4000ms \(custom timeout\)/ ]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite it times out', [ /^Error: Timeout - Async function did not complete within 6000ms \(custom timeout\)/ ]); jasmine.clock().tick(1); realSetTimeout(done); diff --git a/src/core/QueueRunner.js b/src/core/QueueRunner.js index 27b57695..63bc60ba 100644 --- a/src/core/QueueRunner.js +++ b/src/core/QueueRunner.js @@ -131,7 +131,7 @@ getJasmineRequireObj().QueueRunner = function(j$) { var timeoutInterval = queueableFn.timeout || j$.DEFAULT_TIMEOUT_INTERVAL; timeoutId = self.setTimeout(function() { var error = new Error( - 'Timeout - Async callback was not invoked within ' + + 'Timeout - Async function did not complete within ' + timeoutInterval + 'ms ' + (queueableFn.timeout From b01d86840aba922d45207778b16a186e1da30830 Mon Sep 17 00:00:00 2001 From: Olga Kozlova Date: Sat, 3 Aug 2019 22:14:17 +0300 Subject: [PATCH 061/201] `mapContaining` and `setContaining` asymmetric matchers --- .../asymmetric_equality/MapContainingSpec.js | 183 ++++++++++++++++++ .../asymmetric_equality/SetContainingSpec.js | 118 +++++++++++ spec/core/matchers/matchersUtilSpec.js | 46 +++++ src/core/asymmetric_equality/MapContaining.js | 41 ++++ src/core/asymmetric_equality/SetContaining.js | 39 ++++ src/core/base.js | 30 +++ src/core/matchers/matchersUtil.js | 2 +- src/core/requireCore.js | 2 + src/core/util.js | 19 ++ 9 files changed, 479 insertions(+), 1 deletion(-) create mode 100644 spec/core/asymmetric_equality/MapContainingSpec.js create mode 100644 spec/core/asymmetric_equality/SetContainingSpec.js create mode 100644 src/core/asymmetric_equality/MapContaining.js create mode 100644 src/core/asymmetric_equality/SetContaining.js diff --git a/spec/core/asymmetric_equality/MapContainingSpec.js b/spec/core/asymmetric_equality/MapContainingSpec.js new file mode 100644 index 00000000..a214dce8 --- /dev/null +++ b/spec/core/asymmetric_equality/MapContainingSpec.js @@ -0,0 +1,183 @@ +describe('MapContaining', function() { + function MapI(iterable) { // for IE11 + var map = new Map(); + iterable.forEach(function(kv) { + map.set(kv[0], kv[1]); + }); + return map; + } + + beforeEach(function() { + jasmine.getEnv().requireFunctioningMaps(); + }); + + + it('matches any actual map to an empty map', function() { + var actualMap = new MapI([['foo', 'bar']]); + var containing = new jasmineUnderTest.MapContaining(new Map()); + + expect(containing.asymmetricMatch(actualMap)).toBe(true); + }); + + it('matches when all the key/value pairs in sample have matches in actual', function() { + var actualMap = new MapI([ + ['foo', [1, 2, 3]], + [{'foo': 'bar'}, 'baz'], + ['other', 'any'], + ]); + + var containingMap = new MapI([ + [{'foo': 'bar'}, 'baz'], + ['foo', [1, 2, 3]], + ]); + var containing = new jasmineUnderTest.MapContaining(containingMap); + + expect(containing.asymmetricMatch(actualMap)).toBe(true); + }); + + it('does not match when a key is not in actual', function() { + var actualMap = new MapI([ + ['foo', [1, 2, 3]], + [{'foo': 'not a bar'}, 'baz'], + ]); + + var containingMap = new MapI([ + [{'foo': 'bar'}, 'baz'], + ['foo', [1, 2, 3]], + ]); + var containing = new jasmineUnderTest.MapContaining(containingMap); + + expect(containing.asymmetricMatch(actualMap)).toBe(false); + }); + + it('does not match when a value is not in actual', function() { + var actualMap = new MapI([ + ['foo', [1, 2, 3]], + [{'foo': 'bar'}, 'baz'], + ]); + + var containingMap = new MapI([ + [{'foo': 'bar'}, 'baz'], + ['foo', [1, 2]], + ]); + var containing = new jasmineUnderTest.MapContaining(containingMap); + + expect(containing.asymmetricMatch(actualMap)).toBe(false); + }); + + it('matches when all the key/value pairs in sample have asymmetric matches in actual', function() { + var actualMap = new MapI([ + ['foo1', 'not a bar'], + ['foo2', 'bar'], + ['baz', [1, 2, 3, 4]], + ]); + + var containingMap = new MapI([ + [ + jasmine.stringMatching(/^foo\d/), + 'bar' + ], + [ + 'baz', + jasmine.arrayContaining([2, 3]) + ], + ]); + var containing = new jasmineUnderTest.MapContaining(containingMap); + + expect(containing.asymmetricMatch(actualMap)).toBe(true); + }); + + it('does not match when a key in sample has no asymmetric matches in actual', function() { + var actualMap = new MapI([ + ['a-foo1', 'bar'], + ['baz', [1, 2, 3, 4]], + ]); + + var containingMap = new MapI([ + [ + jasmine.stringMatching(/^foo\d/), + 'bar' + ], + [ + 'baz', + jasmine.arrayContaining([2, 3]) + ], + ]); + var containing = new jasmineUnderTest.MapContaining(containingMap); + + expect(containing.asymmetricMatch(actualMap)).toBe(false); + }); + + it('does not match when a value in sample has no asymmetric matches in actual', function() { + var actualMap = new MapI([ + ['foo1', 'bar'], + ['baz', [1, 2, 3, 4]], + ]); + + var containingMap = new MapI([ + [ + jasmine.stringMatching(/^foo\d/), + 'bar' + ], + [ + 'baz', + jasmine.arrayContaining([4, 5]) + ], + ]); + var containing = new jasmineUnderTest.MapContaining(containingMap); + + expect(containing.asymmetricMatch(actualMap)).toBe(false); + }); + + it('matches recursively', function() { + var actualMap = new MapI([ + ['foo', new MapI([['foo1', 1], ['foo2', 2]])], + [new MapI([[1, 'bar1'], [2, 'bar2']]), 'bar'], + ['other', 'any'], + ]); + + var containingMap = new MapI([ + [ + 'foo', + new jasmineUnderTest.MapContaining(new MapI([['foo1', 1]])) + ], + [ + new jasmineUnderTest.MapContaining(new MapI([[2, 'bar2']])), + 'bar' + ], + ]); + var containing = new jasmineUnderTest.MapContaining(containingMap); + + expect(containing.asymmetricMatch(actualMap)).toBe(true); + }); + + it('uses custom equality testers', function() { + function tester(a, b) { + // treat all negative numbers as equal + return (typeof a == 'number' && typeof b == 'number') ? (a < 0 && b < 0) : a === b; + } + var actualMap = new MapI([['foo', -1]]); + var containing = new jasmineUnderTest.MapContaining(new MapI([['foo', -2]])); + + expect(containing.asymmetricMatch(actualMap, [tester])).toBe(true); + }); + + it('does not match when actual is not a map', function() { + var containingMap = new MapI([['foo', 'bar']]); + expect(new jasmineUnderTest.MapContaining(containingMap).asymmetricMatch('foo')).toBe(false); + expect(new jasmineUnderTest.MapContaining(containingMap).asymmetricMatch(-1)).toBe(false); + expect(new jasmineUnderTest.MapContaining(containingMap).asymmetricMatch({'foo': 'bar'})).toBe(false); + }); + + it('throws an error when sample is not a map', function() { + expect(function() { + new jasmineUnderTest.MapContaining({'foo': 'bar'}).asymmetricMatch(new Map()); + }).toThrowError(/You must provide a map/); + }); + + it('defines a `jasmineToString` method', function() { + var containing = new jasmineUnderTest.MapContaining(new Map()); + + expect(containing.jasmineToString()).toMatch(/^'; + }; + + return MapContaining; +}; diff --git a/src/core/asymmetric_equality/SetContaining.js b/src/core/asymmetric_equality/SetContaining.js new file mode 100644 index 00000000..d9dd8fd2 --- /dev/null +++ b/src/core/asymmetric_equality/SetContaining.js @@ -0,0 +1,39 @@ +getJasmineRequireObj().SetContaining = function(j$) { + function SetContaining(sample) { + if (!j$.isSet(sample)) { + throw new Error('You must provide a set to `setContaining`, not ' + j$.pp(sample)); + } + + this.sample = sample; + } + + SetContaining.prototype.asymmetricMatch = function(other, customTesters) { + if (!j$.isSet(other)) return false; + + var hasAllMatches = true; + j$.util.forEachBreakable(this.sample, function(breakLoop, item) { + // for each item in `sample` there should be at least one matching item in `other` + // (not using `j$.matchersUtil.contains` because it compares set members by reference, + // not by deep value equality) + var hasMatch = false; + j$.util.forEachBreakable(other, function(oBreakLoop, oItem) { + if (j$.matchersUtil.equals(oItem, item, customTesters)) { + hasMatch = true; + oBreakLoop(); + } + }); + if (!hasMatch) { + hasAllMatches = false; + breakLoop(); + } + }); + + return hasAllMatches; + }; + + SetContaining.prototype.jasmineToString = function() { + return ''; + }; + + return SetContaining; +}; diff --git a/src/core/base.js b/src/core/base.js index deed4ef2..b962e129 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -128,6 +128,8 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { j$.isMap = function(obj) { return ( + obj !== null && + typeof obj !== 'undefined' && typeof jasmineGlobal.Map !== 'undefined' && obj.constructor === jasmineGlobal.Map ); @@ -135,6 +137,8 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { j$.isSet = function(obj) { return ( + obj !== null && + typeof obj !== 'undefined' && typeof jasmineGlobal.Set !== 'undefined' && obj.constructor === jasmineGlobal.Set ); @@ -279,6 +283,32 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return new j$.ArrayWithExactContents(sample); }; + /** + * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), + * that will succeed if every key/value pair in the sample passes the deep equality comparison + * with at least one key/value pair in the actual value being compared + * @name jasmine.mapContaining + * @since + * @function + * @param {Map} sample - The subset of items that _must_ be in the actual. + */ + j$.mapContaining = function(sample) { + return new j$.MapContaining(sample); + }; + + /** + * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), + * that will succeed if every item in the sample passes the deep equality comparison + * with at least one item in the actual value being compared + * @name jasmine.mapContaining + * @since + * @function + * @param {Set} sample - The subset of items that _must_ be in the actual. + */ + j$.setContaining = function(sample) { + return new j$.SetContaining(sample); + }; + j$.isSpy = function(putativeSpy) { if (!putativeSpy) { return false; diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index 14647dd6..cfc0c749 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -7,7 +7,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { contains: function(haystack, needle, customTesters) { customTesters = customTesters || []; - if ((Object.prototype.toString.apply(haystack) === '[object Set]')) { + if (j$.isSet(haystack)) { return haystack.has(needle); } diff --git a/src/core/requireCore.js b/src/core/requireCore.js index d6b98eb5..a2c5f177 100644 --- a/src/core/requireCore.js +++ b/src/core/requireCore.js @@ -55,6 +55,8 @@ var getJasmineRequireObj = (function(jasmineGlobal) { j$.ObjectContaining = jRequire.ObjectContaining(j$); j$.ArrayContaining = jRequire.ArrayContaining(j$); j$.ArrayWithExactContents = jRequire.ArrayWithExactContents(j$); + j$.MapContaining = jRequire.MapContaining(j$); + j$.SetContaining = jRequire.SetContaining(j$); j$.pp = jRequire.pp(j$); j$.QueueRunner = jRequire.QueueRunner(j$); j$.ReportDispatcher = jRequire.ReportDispatcher(j$); diff --git a/src/core/util.js b/src/core/util.js index 0c25382a..4118deec 100644 --- a/src/core/util.js +++ b/src/core/util.js @@ -133,5 +133,24 @@ getJasmineRequireObj().util = function(j$) { }; })(); + function StopIteration() {} + StopIteration.prototype = Object.create(Error.prototype); + StopIteration.prototype.constructor = StopIteration; + + // useful for maps and sets since `forEach` is the only IE11-compatible way to iterate them + util.forEachBreakable = function(iterable, iteratee) { + function breakLoop() { + throw new StopIteration(); + } + + try { + iterable.forEach(function(value, key) { + iteratee(breakLoop, value, key, iterable); + }); + } catch (error) { + if (!(error instanceof StopIteration)) throw error; + } + }; + return util; }; From b2d9aab2b86f29da538a63c5c7438ce04336ae19 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 3 Aug 2019 12:15:55 -0700 Subject: [PATCH 062/201] Use the same spec file pattern for both node and browser --- spec/support/jasmine.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/spec/support/jasmine.json b/spec/support/jasmine.json index 1d94e2f5..ffcd6b7d 100644 --- a/spec/support/jasmine.json +++ b/spec/support/jasmine.json @@ -1,8 +1,8 @@ { "spec_dir": "spec", "spec_files": [ - "core/**/*.js", - "npmPackage/**/*.js" + "core/**/*[Ss]pec.js", + "npmPackage/**/*[Ss]pec.js" ], "helpers": [ "helpers/asyncAwait.js", From 527619b0aa5cdfc7bc5f8f863680a2df8bc4f58e Mon Sep 17 00:00:00 2001 From: Ferdinand Prantl Date: Sun, 11 Aug 2019 09:31:43 +0200 Subject: [PATCH 063/201] Restore the original global error hanler to pass all parameters along --- spec/core/GlobalErrorsSpec.js | 10 ++++++++-- src/core/GlobalErrors.js | 7 ++----- 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/spec/core/GlobalErrorsSpec.js b/spec/core/GlobalErrorsSpec.js index b4a54282..3880b041 100644 --- a/spec/core/GlobalErrorsSpec.js +++ b/spec/core/GlobalErrorsSpec.js @@ -12,7 +12,7 @@ describe('GlobalErrors', function() { expect(handler).toHaveBeenCalledWith('foo'); }); - it('prefers passing the error including stack to the handler', function() { + it('calls the global error handler with all parameters', function() { var fakeGlobal = { onerror: null }, handler = jasmine.createSpy('errorHandler'), errors = new jasmineUnderTest.GlobalErrors(fakeGlobal), @@ -23,7 +23,13 @@ describe('GlobalErrors', function() { fakeGlobal.onerror(fooError.message, 'foo.js', 1, 1, fooError); - expect(handler).toHaveBeenCalledWith(fooError); + expect(handler).toHaveBeenCalledWith( + fooError.message, + 'foo.js', + 1, + 1, + fooError + ); }); it('only calls the most recent handler', function() { diff --git a/src/core/GlobalErrors.js b/src/core/GlobalErrors.js index f62208b4..2c58e684 100644 --- a/src/core/GlobalErrors.js +++ b/src/core/GlobalErrors.js @@ -3,14 +3,11 @@ getJasmineRequireObj().GlobalErrors = function(j$) { var handlers = []; global = global || j$.getGlobal(); - var onerror = function onerror(message, source, lineno, colno, error) { + var onerror = function onerror() { var handler = handlers[handlers.length - 1]; if (handler) { - var args = Array.prototype.slice.call(arguments, 0); - // Prefer passing the error to the error handler - // to be able to print the stack trace. - handler.apply(null, error instanceof Error ? [error] : args); + handler.apply(null, Array.prototype.slice.call(arguments, 0)); } else { throw arguments[0]; } From 3a7fc638790014d6ac79b0bdac88976655ba5dc4 Mon Sep 17 00:00:00 2001 From: Ferdinand Prantl Date: Sun, 11 Aug 2019 09:32:31 +0200 Subject: [PATCH 064/201] Pick the error instance to pass to error handlers in QueueRunner The first number is the error message in HTML5 browser, which does not include the call stack. The error instance allows logging the complete call stack in reporters. --- spec/core/QueueRunnerSpec.js | 26 ++++++++++++++++++++++++++ src/core/QueueRunner.js | 7 +++++-- 2 files changed, 31 insertions(+), 2 deletions(-) diff --git a/spec/core/QueueRunnerSpec.js b/spec/core/QueueRunnerSpec.js index e0b4c23c..ac18b81d 100644 --- a/spec/core/QueueRunnerSpec.js +++ b/spec/core/QueueRunnerSpec.js @@ -514,6 +514,32 @@ describe('QueueRunner', function() { }); }); + it('passes the error instance to exception handlers in HTML browsers', function() { + var error = new Error('fake error'), + onExceptionCallback = jasmine.createSpy('on exception callback'), + queueRunner = new jasmineUnderTest.QueueRunner({ + onException: onExceptionCallback + }); + + queueRunner.execute(); + queueRunner.handleFinalError(error.message, 'fake.js', 1, 1, error); + + expect(onExceptionCallback).toHaveBeenCalledWith(error); + }); + + it('passes the first argument to exception handlers for compatibility', function() { + var error = new Error('fake error'), + onExceptionCallback = jasmine.createSpy('on exception callback'), + queueRunner = new jasmineUnderTest.QueueRunner({ + onException: onExceptionCallback + }); + + queueRunner.execute(); + queueRunner.handleFinalError(error.message); + + expect(onExceptionCallback).toHaveBeenCalledWith(error.message); + }); + it('calls exception handlers when an exception is thrown in a fn', function() { var queueableFn = { type: 'queueable', diff --git a/src/core/QueueRunner.js b/src/core/QueueRunner.js index 27b57695..639296d7 100644 --- a/src/core/QueueRunner.js +++ b/src/core/QueueRunner.js @@ -49,8 +49,11 @@ getJasmineRequireObj().QueueRunner = function(j$) { QueueRunner.prototype.execute = function() { var self = this; - this.handleFinalError = function(error) { - self.onException(error); + this.handleFinalError = function(message, source, lineno, colno, error) { + // Older browsers would send the error as the first parameter. HTML5 + // specifies the the five parameters above. The error instance should + // be preffered, otherwise the call stack would get lost. + self.onException(error || message); }; this.globalErrors.pushListener(this.handleFinalError); this.run(0); From 1a63ab4677eff29f2b6b86f7067f804a1da9c964 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Mon, 26 Aug 2019 15:45:13 -0700 Subject: [PATCH 065/201] Accept configurations with `Promise: undefined`. Fixes Karma and anything else that uses Env#configuration as a starting point for a Jasmine config. --- lib/jasmine-core/jasmine.js | 5 ++++- spec/core/EnvSpec.js | 9 +++++++++ src/core/Env.js | 5 ++++- 3 files changed, 17 insertions(+), 2 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index d05ae562..eb9b54dc 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1081,7 +1081,10 @@ getJasmineRequireObj().Env = function(j$) { config.hideDisabled = configuration.hideDisabled; } - if (configuration.hasOwnProperty('Promise')) { + // Don't use hasOwnProperty to check for Promise existence because Promise + // can be initialized to undefined, either explicitly or by using the + // object returned from Env#configuration. In particular, Karma does this. + if (configuration.Promise) { if ( typeof configuration.Promise.resolve === 'function' && typeof configuration.Promise.reject === 'function' diff --git a/spec/core/EnvSpec.js b/spec/core/EnvSpec.js index 72c8d979..aa87a997 100644 --- a/spec/core/EnvSpec.js +++ b/spec/core/EnvSpec.js @@ -28,6 +28,10 @@ describe('Env', function() { }); }); + it('accepts its own current configureation', function() { + env.configure(env.configuration()); + }); + it('can configure specs to throw errors on expectation failures', function() { env.configure({ oneFailurePerSpec: true }); @@ -53,6 +57,11 @@ describe('Env', function() { }); describe('promise library', function() { + it('can be configured without a custom library', function() { + env.configure({}); + env.configure({ Promise: undefined }); + }); + it('can be configured with a custom library', function() { var myLibrary = { resolve: jasmine.createSpy(), diff --git a/src/core/Env.js b/src/core/Env.js index 43e4a8e7..d769d1c4 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -175,7 +175,10 @@ getJasmineRequireObj().Env = function(j$) { config.hideDisabled = configuration.hideDisabled; } - if (configuration.hasOwnProperty('Promise')) { + // Don't use hasOwnProperty to check for Promise existence because Promise + // can be initialized to undefined, either explicitly or by using the + // object returned from Env#configuration. In particular, Karma does this. + if (configuration.Promise) { if ( typeof configuration.Promise.resolve === 'function' && typeof configuration.Promise.reject === 'function' From 0bd636b5d2e903856b80375b4f07f504a60a1c1e Mon Sep 17 00:00:00 2001 From: David Diederich Date: Fri, 30 Aug 2019 01:09:53 -0400 Subject: [PATCH 066/201] Updated arrayContaining to require actual values to be arrays If the actual value of a test was a string, this was matching against arrays that contained the strings. This was due to the use of the contains matcher, which against string looks for substrings, when it was intended to look for array elements. --- spec/core/asymmetric_equality/ArrayContainingSpec.js | 6 ++++++ src/core/asymmetric_equality/ArrayContaining.js | 7 +++++++ 2 files changed, 13 insertions(+) diff --git a/spec/core/asymmetric_equality/ArrayContainingSpec.js b/spec/core/asymmetric_equality/ArrayContainingSpec.js index 778eca43..30b5aaad 100644 --- a/spec/core/asymmetric_equality/ArrayContainingSpec.js +++ b/spec/core/asymmetric_equality/ArrayContainingSpec.js @@ -31,6 +31,12 @@ describe("ArrayContaining", function() { expect(containing.asymmetricMatch(["bar"])).toBe(false); }); + it("does not match when the actual is not an array", function() { + var containing = new jasmineUnderTest.ArrayContaining(["foo"]); + + expect(containing.asymmetricMatch("foo")).toBe(false); + }); + it("jasmineToStrings itself", function() { var containing = new jasmineUnderTest.ArrayContaining([]); diff --git a/src/core/asymmetric_equality/ArrayContaining.js b/src/core/asymmetric_equality/ArrayContaining.js index b39fb857..92a85ed0 100644 --- a/src/core/asymmetric_equality/ArrayContaining.js +++ b/src/core/asymmetric_equality/ArrayContaining.js @@ -8,6 +8,13 @@ getJasmineRequireObj().ArrayContaining = function(j$) { throw new Error('You must provide an array to arrayContaining, not ' + j$.pp(this.sample) + '.'); } + // If the actual parameter is not an array, we can fail immediately, since it couldn't + // possibly be an "array containing" anything. However, we also want an empty sample + // array to match anything, so we need to double-check we aren't in that case + if (!j$.isArray_(other) && this.sample.length > 0) { + return false; + } + for (var i = 0; i < this.sample.length; i++) { var item = this.sample[i]; if (!j$.matchersUtil.contains(other, item, customTesters)) { From f77ee32c5663c17919604f235fda222ad412fb11 Mon Sep 17 00:00:00 2001 From: Tony Brix Date: Mon, 8 Jul 2019 15:13:06 -0500 Subject: [PATCH 067/201] Add custom async matchers --- lib/jasmine-core/jasmine.js | 78 ++- spec/core/AsyncExpectationSpec.js | 620 +++++++++++++++++- .../integration/CustomAsyncMatchersSpec.js | 78 +++ spec/core/integration/EnvSpec.js | 6 +- spec/core/matchers/async/toBeRejectedSpec.js | 13 + .../async/toBeRejectedWithErrorSpec.js | 13 + .../matchers/async/toBeRejectedWithSpec.js | 13 + spec/core/matchers/async/toBeResolvedSpec.js | 13 + .../core/matchers/async/toBeResolvedToSpec.js | 13 + src/core/Env.js | 18 + src/core/Expectation.js | 18 +- src/core/Expector.js | 7 +- src/core/matchers/async/toBeRejected.js | 5 +- src/core/matchers/async/toBeRejectedWith.js | 4 + .../matchers/async/toBeRejectedWithError.js | 4 + src/core/matchers/async/toBeResolved.js | 4 + src/core/matchers/async/toBeResolvedTo.js | 4 + src/core/requireInterface.js | 14 + 18 files changed, 876 insertions(+), 49 deletions(-) create mode 100644 spec/core/integration/CustomAsyncMatchersSpec.js diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 4ce3c980..e4b9b656 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1172,6 +1172,19 @@ getJasmineRequireObj().Env = function(j$) { } }; + this.addAsyncMatchers = function(matchersToAdd) { + if (!currentRunnable()) { + throw new Error( + 'Async Matchers must be added in a before function or a spec' + ); + } + var customAsyncMatchers = + runnableResources[currentRunnable().id].customAsyncMatchers; + for (var matcherName in matchersToAdd) { + customAsyncMatchers[matcherName] = matchersToAdd[matcherName]; + } + }; + j$.Expectation.addCoreMatchers(j$.matchers); j$.Expectation.addAsyncCoreMatchers(j$.asyncMatchers); @@ -1203,6 +1216,7 @@ getJasmineRequireObj().Env = function(j$) { return j$.Expectation.asyncFactory({ util: j$.matchersUtil, customEqualityTesters: runnableResources[spec.id].customEqualityTesters, + customAsyncMatchers: runnableResources[spec.id].customAsyncMatchers, actual: actual, addExpectationResult: addExpectationResult }); @@ -1217,6 +1231,7 @@ getJasmineRequireObj().Env = function(j$) { spies: [], customEqualityTesters: [], customMatchers: {}, + customAsyncMatchers: {}, customSpyStrategies: {}, defaultStrategyFn: undefined }; @@ -1228,6 +1243,9 @@ getJasmineRequireObj().Env = function(j$) { resources.customMatchers = j$.util.clone( runnableResources[parentRunnableId].customMatchers ); + resources.customAsyncMatchers = j$.util.clone( + runnableResources[parentRunnableId].customAsyncMatchers + ); resources.defaultStrategyFn = runnableResources[parentRunnableId].defaultStrategyFn; } @@ -3235,12 +3253,6 @@ getJasmineRequireObj().ExceptionFormatter = function(j$) { }; getJasmineRequireObj().Expectation = function(j$) { - var promiseForMessage = { - jasmineToString: function() { - return 'a promise'; - } - }; - /** * Matchers that come with Jasmine out of the box. * @namespace matchers @@ -3298,8 +3310,12 @@ getJasmineRequireObj().Expectation = function(j$) { ); } - if (!j$.isPromiseLike(this.expector.actual)) { - throw new Error('Expected expectAsync to be called with a promise.'); + var customAsyncMatchers = options.customAsyncMatchers || {}; + for (var matcherName in customAsyncMatchers) { + this[matcherName] = wrapAsyncCompare( + matcherName, + customAsyncMatchers[matcherName] + ); } } @@ -3349,7 +3365,7 @@ getJasmineRequireObj().Expectation = function(j$) { return this.expector .compare(name, matcherFactory, arguments) .then(function(result) { - self.expector.processResult(result, errorForStack, promiseForMessage); + self.expector.processResult(result, errorForStack); }); }; } @@ -3404,7 +3420,7 @@ getJasmineRequireObj().Expectation = function(j$) { return matcher.compare.apply(this, arguments).then(negate); } - return defaultNegativeCompare; + return matcher.negativeCompare || defaultNegativeCompare; }, buildFailureMessage: negatedFailureMessage }; @@ -3621,12 +3637,7 @@ getJasmineRequireObj().Expector = function(j$) { return result; }; - Expector.prototype.processResult = function( - result, - errorForStack, - actualOverride - ) { - this.args[0] = actualOverride || this.args[0]; + Expector.prototype.processResult = function(result, errorForStack) { var message = this.buildMessage(result); if (this.expected.length === 1) { @@ -3754,9 +3765,12 @@ getJasmineRequireObj().toBeRejected = function(j$) { * @example * return expectAsync(aPromise).toBeRejected(); */ - return function toBeResolved(util) { + return function toBeRejected(util) { return { compare: function(actual) { + if (!j$.isPromiseLike(actual)) { + throw new Error('Expected toBeRejected to be called on a promise.'); + } return actual.then( function() { return {pass: false}; }, function() { return {pass: true}; } @@ -3782,6 +3796,10 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { return function toBeRejectedWith(util, customEqualityTesters) { return { compare: function(actualPromise, expectedValue) { + if (!j$.isPromiseLike(actualPromise)) { + throw new Error('Expected toBeRejectedWith to be called on a promise.'); + } + function prefix(passed) { return 'Expected a promise ' + (passed ? 'not ' : '') + @@ -3833,6 +3851,10 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return function toBeRejectedWithError() { return { compare: function(actualPromise, arg1, arg2) { + if (!j$.isPromiseLike(actualPromise)) { + throw new Error('Expected toBeRejectedWithError to be called on a promise.'); + } + var expected = getExpectedFromArgs(arg1, arg2); return actualPromise.then( @@ -3919,6 +3941,10 @@ getJasmineRequireObj().toBeResolved = function(j$) { return function toBeResolved(util) { return { compare: function(actual) { + if (!j$.isPromiseLike(actual)) { + throw new Error('Expected toBeResolved to be called on a promise.'); + } + return actual.then( function() { return {pass: true}; }, function() { return {pass: false}; } @@ -3944,6 +3970,10 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { return function toBeResolvedTo(util, customEqualityTesters) { return { compare: function(actualPromise, expectedValue) { + if (!j$.isPromiseLike(actualPromise)) { + throw new Error('Expected toBeResolvedTo to be called on a promise.'); + } + function prefix(passed) { return 'Expected a promise ' + (passed ? 'not ' : '') + @@ -6731,6 +6761,20 @@ getJasmineRequireObj().interface = function(jasmine, env) { return env.addMatchers(matchers); }; + /** + * Add custom async matchers for the current scope of specs. + * + * _Note:_ This is only callable from within a {@link beforeEach}, {@link it}, or {@link beforeAll}. + * @name jasmine.addMatchers + * @since 3.5.0 + * @function + * @param {Object} matchers - Keys from this object will be the new async matcher names. + * @see custom_matcher + */ + jasmine.addAsyncMatchers = function(matchers) { + return env.addAsyncMatchers(matchers); + }; + /** * Get the currently booted mock {Clock} for this Jasmine environment. * @name jasmine.clock diff --git a/spec/core/AsyncExpectationSpec.js b/spec/core/AsyncExpectationSpec.js index 42fcd544..3d4eb426 100644 --- a/spec/core/AsyncExpectationSpec.js +++ b/spec/core/AsyncExpectationSpec.js @@ -16,16 +16,6 @@ describe('AsyncExpectation', function() { 'expectAsync is unavailable because the environment does not support promises.' ); }); - - it('throws an Error if the argument is not a promise', function() { - jasmine.getEnv().requirePromises(); - function f() { - jasmineUnderTest.Expectation.asyncFactory({ actual: 'not a promise' }); - } - expect(f).toThrowError( - 'Expected expectAsync to be called with a promise.' - ); - }); }); describe('#not', function() { @@ -45,7 +35,7 @@ describe('AsyncExpectation', function() { false, jasmine.objectContaining({ passed: false, - message: 'Expected a promise not to be resolved.' + message: 'Expected [object Promise] not to be resolved.' }) ); }); @@ -203,7 +193,8 @@ describe('AsyncExpectation', function() { expect(addExpectationResult).toHaveBeenCalledWith( false, jasmine.objectContaining({ - message: 'Some context: Expected a promise not to be resolved.' + message: + 'Some context: Expected [object Promise] not to be resolved.' }) ); }); @@ -235,6 +226,611 @@ describe('AsyncExpectation', function() { }); }); + describe('async matchers', function() { + it('makes custom matchers available to this expectation', function() { + var asyncMatchers = { + toFoo: function() {}, + toBar: function() {} + }, + expectation; + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + customAsyncMatchers: asyncMatchers + }); + + expect(expectation.toFoo).toBeDefined(); + expect(expectation.toBar).toBeDefined(); + }); + + it("wraps matchers's compare functions, passing in matcher dependencies", function() { + jasmine.getEnv().requirePromises(); + + var fakeCompare = function() { + return Promise.resolve({ pass: true }); + }, + matcherFactory = jasmine + .createSpy('matcher') + .and.returnValue({ compare: fakeCompare }), + matchers = { + toFoo: matcherFactory + }, + util = { + buildFailureMessage: jasmine.createSpy('buildFailureMessage') + }, + customEqualityTesters = ['a'], + addExpectationResult = jasmine.createSpy('addExpectationResult'), + expectation; + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + util: util, + customAsyncMatchers: matchers, + customEqualityTesters: customEqualityTesters, + actual: 'an actual', + addExpectationResult: addExpectationResult + }); + + return expectation.toFoo('hello').then(function() { + expect(matcherFactory).toHaveBeenCalledWith( + util, + customEqualityTesters + ); + }); + }); + + it("wraps matchers's compare functions, passing the actual and expected", function() { + jasmine.getEnv().requirePromises(); + + var fakeCompare = jasmine + .createSpy('fake-compare') + .and.returnValue(Promise.resolve({ pass: true })), + matchers = { + toFoo: function() { + return { + compare: fakeCompare + }; + } + }, + util = { + buildFailureMessage: jasmine.createSpy('buildFailureMessage') + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + expectation; + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + util: util, + customAsyncMatchers: matchers, + actual: 'an actual', + addExpectationResult: addExpectationResult + }); + + return expectation.toFoo('hello').then(function() { + expect(fakeCompare).toHaveBeenCalledWith('an actual', 'hello'); + }); + }); + + it('reports a passing result to the spec when the comparison passes', function() { + jasmine.getEnv().requirePromises(); + + var matchers = { + toFoo: function() { + return { + compare: function() { + return Promise.resolve({ pass: true }); + } + }; + } + }, + util = { + buildFailureMessage: jasmine.createSpy('buildFailureMessage') + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + errorWithStack = new Error('errorWithStack'), + expectation; + + spyOn(jasmineUnderTest.util, 'errorWithStack').and.returnValue( + errorWithStack + ); + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + customAsyncMatchers: matchers, + util: util, + actual: 'an actual', + addExpectationResult: addExpectationResult + }); + + return expectation.toFoo('hello').then(function() { + expect(addExpectationResult).toHaveBeenCalledWith(true, { + matcherName: 'toFoo', + passed: true, + message: '', + error: undefined, + expected: 'hello', + actual: 'an actual', + errorForStack: errorWithStack + }); + }); + }); + + it('reports a failing result to the spec when the comparison fails', function() { + jasmine.getEnv().requirePromises(); + + var matchers = { + toFoo: function() { + return { + compare: function() { + return Promise.resolve({ pass: false }); + } + }; + } + }, + util = { + buildFailureMessage: function() { + return ''; + } + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + errorWithStack = new Error('errorWithStack'), + expectation; + + spyOn(jasmineUnderTest.util, 'errorWithStack').and.returnValue( + errorWithStack + ); + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + customAsyncMatchers: matchers, + util: util, + actual: 'an actual', + addExpectationResult: addExpectationResult + }); + + return expectation.toFoo('hello').then(function() { + expect(addExpectationResult).toHaveBeenCalledWith(false, { + matcherName: 'toFoo', + passed: false, + expected: 'hello', + actual: 'an actual', + message: '', + error: undefined, + errorForStack: errorWithStack + }); + }); + }); + + it('reports a failing result and a custom fail message to the spec when the comparison fails', function() { + jasmine.getEnv().requirePromises(); + + var matchers = { + toFoo: function() { + return { + compare: function() { + return Promise.resolve({ + pass: false, + message: 'I am a custom message' + }); + } + }; + } + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + errorWithStack = new Error('errorWithStack'), + expectation; + + spyOn(jasmineUnderTest.util, 'errorWithStack').and.returnValue( + errorWithStack + ); + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + actual: 'an actual', + customAsyncMatchers: matchers, + addExpectationResult: addExpectationResult + }); + + return expectation.toFoo('hello').then(function() { + expect(addExpectationResult).toHaveBeenCalledWith(false, { + matcherName: 'toFoo', + passed: false, + expected: 'hello', + actual: 'an actual', + message: 'I am a custom message', + error: undefined, + errorForStack: errorWithStack + }); + }); + }); + + it('reports a failing result with a custom fail message function to the spec when the comparison fails', function() { + jasmine.getEnv().requirePromises(); + + var matchers = { + toFoo: function() { + return { + compare: function() { + return Promise.resolve({ + pass: false, + message: function() { + return 'I am a custom message'; + } + }); + } + }; + } + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + errorWithStack = new Error('errorWithStack'), + expectation; + + spyOn(jasmineUnderTest.util, 'errorWithStack').and.returnValue( + errorWithStack + ); + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + customAsyncMatchers: matchers, + actual: 'an actual', + addExpectationResult: addExpectationResult + }); + + return expectation.toFoo('hello').then(function() { + expect(addExpectationResult).toHaveBeenCalledWith(false, { + matcherName: 'toFoo', + passed: false, + expected: 'hello', + actual: 'an actual', + message: 'I am a custom message', + error: undefined, + errorForStack: errorWithStack + }); + }); + }); + + it('reports a passing result to the spec when the comparison fails for a negative expectation', function() { + jasmine.getEnv().requirePromises(); + + var matchers = { + toFoo: function() { + return { + compare: function() { + return Promise.resolve({ pass: false }); + } + }; + } + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + actual = 'an actual', + errorWithStack = new Error('errorWithStack'), + expectation; + + spyOn(jasmineUnderTest.util, 'errorWithStack').and.returnValue( + errorWithStack + ); + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + customAsyncMatchers: matchers, + actual: 'an actual', + addExpectationResult: addExpectationResult + }).not; + + return expectation.toFoo('hello').then(function() { + expect(addExpectationResult).toHaveBeenCalledWith(true, { + matcherName: 'toFoo', + passed: true, + message: '', + error: undefined, + expected: 'hello', + actual: actual, + errorForStack: errorWithStack + }); + }); + }); + + it('reports a failing result to the spec when the comparison passes for a negative expectation', function() { + jasmine.getEnv().requirePromises(); + + var matchers = { + toFoo: function() { + return { + compare: function() { + return Promise.resolve({ pass: true }); + } + }; + } + }, + util = { + buildFailureMessage: function() { + return 'default message'; + } + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + actual = 'an actual', + errorWithStack = new Error('errorWithStack'), + expectation; + + spyOn(jasmineUnderTest.util, 'errorWithStack').and.returnValue( + errorWithStack + ); + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + customAsyncMatchers: matchers, + actual: 'an actual', + util: util, + addExpectationResult: addExpectationResult + }).not; + + return expectation.toFoo('hello').then(function() { + expect(addExpectationResult).toHaveBeenCalledWith(false, { + matcherName: 'toFoo', + passed: false, + expected: 'hello', + actual: actual, + message: 'default message', + error: undefined, + errorForStack: errorWithStack + }); + }); + }); + + it('reports a failing result and a custom fail message to the spec when the comparison passes for a negative expectation', function() { + jasmine.getEnv().requirePromises(); + + var matchers = { + toFoo: function() { + return { + compare: function() { + return Promise.resolve({ + pass: true, + message: 'I am a custom message' + }); + } + }; + } + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + actual = 'an actual', + errorWithStack = new Error('errorWithStack'), + expectation; + + spyOn(jasmineUnderTest.util, 'errorWithStack').and.returnValue( + errorWithStack + ); + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + customAsyncMatchers: matchers, + actual: 'an actual', + addExpectationResult: addExpectationResult + }).not; + + return expectation.toFoo('hello').then(function() { + expect(addExpectationResult).toHaveBeenCalledWith(false, { + matcherName: 'toFoo', + passed: false, + expected: 'hello', + actual: actual, + message: 'I am a custom message', + error: undefined, + errorForStack: errorWithStack + }); + }); + }); + + it("reports a passing result to the spec when the 'not' comparison passes, given a negativeCompare", function() { + jasmine.getEnv().requirePromises(); + + var matchers = { + toFoo: function() { + return { + compare: function() { + return Promise.resolve({ pass: true }); + }, + negativeCompare: function() { + return Promise.resolve({ pass: true }); + } + }; + } + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + actual = 'an actual', + errorWithStack = new Error('errorWithStack'), + expectation; + + spyOn(jasmineUnderTest.util, 'errorWithStack').and.returnValue( + errorWithStack + ); + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + customAsyncMatchers: matchers, + actual: 'an actual', + addExpectationResult: addExpectationResult + }).not; + + return expectation.toFoo('hello').then(function() { + expect(addExpectationResult).toHaveBeenCalledWith(true, { + matcherName: 'toFoo', + passed: true, + expected: 'hello', + actual: actual, + message: '', + error: undefined, + errorForStack: errorWithStack + }); + }); + }); + + it("reports a failing result and a custom fail message to the spec when the 'not' comparison fails, given a negativeCompare", function() { + jasmine.getEnv().requirePromises(); + + var matchers = { + toFoo: function() { + return { + compare: function() { + return Promise.resolve({ pass: true }); + }, + negativeCompare: function() { + return Promise.resolve({ + pass: false, + message: "I'm a custom message" + }); + } + }; + } + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + actual = 'an actual', + errorWithStack = new Error('errorWithStack'), + expectation; + + spyOn(jasmineUnderTest.util, 'errorWithStack').and.returnValue( + errorWithStack + ); + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + customAsyncMatchers: matchers, + actual: 'an actual', + addExpectationResult: addExpectationResult + }).not; + + return expectation.toFoo('hello').then(function() { + expect(addExpectationResult).toHaveBeenCalledWith(false, { + matcherName: 'toFoo', + passed: false, + expected: 'hello', + actual: actual, + message: "I'm a custom message", + error: undefined, + errorForStack: errorWithStack + }); + }); + }); + + it('reports errorWithStack when a custom error message is returned', function() { + jasmine.getEnv().requirePromises(); + + var customError = new Error('I am a custom error'); + var matchers = { + toFoo: function() { + return { + compare: function() { + return Promise.resolve({ + pass: false, + message: 'I am a custom message', + error: customError + }); + } + }; + } + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + errorWithStack = new Error('errorWithStack'), + expectation; + + spyOn(jasmineUnderTest.util, 'errorWithStack').and.returnValue( + errorWithStack + ); + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + actual: 'an actual', + customAsyncMatchers: matchers, + addExpectationResult: addExpectationResult + }); + + return expectation.toFoo('hello').then(function() { + expect(addExpectationResult).toHaveBeenCalledWith(false, { + matcherName: 'toFoo', + passed: false, + expected: 'hello', + actual: 'an actual', + message: 'I am a custom message', + error: undefined, + errorForStack: errorWithStack + }); + }); + }); + + it("reports a custom message to the spec when a 'not' comparison fails", function() { + jasmine.getEnv().requirePromises(); + + var matchers = { + toFoo: function() { + return { + compare: function() { + return Promise.resolve({ + pass: true, + message: 'I am a custom message' + }); + } + }; + } + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + errorWithStack = new Error('errorWithStack'), + expectation; + + spyOn(jasmineUnderTest.util, 'errorWithStack').and.returnValue( + errorWithStack + ); + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + actual: 'an actual', + customAsyncMatchers: matchers, + addExpectationResult: addExpectationResult + }).not; + + return expectation.toFoo('hello').then(function() { + expect(addExpectationResult).toHaveBeenCalledWith(false, { + matcherName: 'toFoo', + passed: false, + expected: 'hello', + actual: 'an actual', + message: 'I am a custom message', + error: undefined, + errorForStack: errorWithStack + }); + }); + }); + + it("reports a custom message func to the spec when a 'not' comparison fails", function() { + jasmine.getEnv().requirePromises(); + + var matchers = { + toFoo: function() { + return { + compare: function() { + return Promise.resolve({ + pass: true, + message: function() { + return 'I am a custom message'; + } + }); + } + }; + } + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + errorWithStack = new Error('errorWithStack'), + expectation; + + spyOn(jasmineUnderTest.util, 'errorWithStack').and.returnValue( + errorWithStack + ); + + expectation = jasmineUnderTest.Expectation.asyncFactory({ + actual: 'an actual', + customAsyncMatchers: matchers, + addExpectationResult: addExpectationResult + }).not; + + return expectation.toFoo('hello').then(function() { + expect(addExpectationResult).toHaveBeenCalledWith(false, { + matcherName: 'toFoo', + passed: false, + expected: 'hello', + actual: 'an actual', + message: 'I am a custom message', + error: undefined, + errorForStack: errorWithStack + }); + }); + }); + }); + function dummyPromise() { return new Promise(function(resolve, reject) {}); } diff --git a/spec/core/integration/CustomAsyncMatchersSpec.js b/spec/core/integration/CustomAsyncMatchersSpec.js new file mode 100644 index 00000000..0849e42a --- /dev/null +++ b/spec/core/integration/CustomAsyncMatchersSpec.js @@ -0,0 +1,78 @@ +describe('Custom Async Matchers (Integration)', function() { + var env; + + beforeEach(function() { + env = new jasmineUnderTest.Env(); + env.configure({random: false}); + }); + + it('passes the spec if the custom async matcher passes', function(done) { + jasmine.getEnv().requirePromises(); + + env.it('spec using custom async matcher', function() { + env.addAsyncMatchers({ + toBeReal: function() { + return { compare: function() { return Promise.resolve({ pass: true }); } }; + } + }); + + return env.expectAsync(true).toBeReal(); + }); + + var specExpectations = function(result) { + expect(result.status).toEqual('passed'); + }; + + env.addReporter({ specDone: specExpectations, jasmineDone: done }); + env.execute(); + }); + + it('uses the negative compare function for a negative comparison, if provided', function(done) { + jasmine.getEnv().requirePromises(); + + env.it('spec with custom negative comparison matcher', function() { + env.addAsyncMatchers({ + toBeReal: function() { + return { + compare: function() { return Promise.resolve({ pass: true }); }, + negativeCompare: function() { return Promise.resolve({ pass: true }); } + }; + } + }); + + return env.expectAsync(true).not.toBeReal(); + }); + + var specExpectations = function(result) { + expect(result.status).toEqual('passed'); + }; + + env.addReporter({ specDone: specExpectations, jasmineDone: done }); + env.execute(); + }); + + it('generates messages with the same rules as built in matchers absent a custom message', function(done) { + jasmine.getEnv().requirePromises(); + + env.it('spec with an expectation', function() { + env.addAsyncMatchers({ + toBeReal: function() { + return { + compare: function() { + return Promise.resolve({ pass: false }); + } + }; + } + }); + + return env.expectAsync('a').toBeReal(); + }); + + var specExpectations = function(result) { + expect(result.failedExpectations[0].message).toEqual("Expected 'a' to be real."); + }; + + env.addReporter({ specDone: specExpectations, jasmineDone: done }); + env.execute(); + }); +}); diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index 9c827b24..45b91601 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -2432,20 +2432,20 @@ describe("Env integration", function() { suiteDone: suiteDone, jasmineDone: function(result) { expect(result.failedExpectations).toEqual([jasmine.objectContaining({ - message: 'Expected a promise to be rejected.' + message: 'Expected [object Promise] to be rejected.' })]); expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ description: 'has an async failure', failedExpectations: [jasmine.objectContaining({ - message: 'Expected a promise to be rejected.' + message: 'Expected [object Promise] to be rejected.' })] })); expect(suiteDone).toHaveBeenCalledWith(jasmine.objectContaining({ description: 'a suite', failedExpectations: [jasmine.objectContaining({ - message: 'Expected a promise to be rejected.' + message: 'Expected [object Promise] to be rejected.' })] })); diff --git a/spec/core/matchers/async/toBeRejectedSpec.js b/spec/core/matchers/async/toBeRejectedSpec.js index ff718e49..442ddba2 100644 --- a/spec/core/matchers/async/toBeRejectedSpec.js +++ b/spec/core/matchers/async/toBeRejectedSpec.js @@ -20,4 +20,17 @@ describe('toBeRejected', function() { expect(result).toEqual(jasmine.objectContaining({pass: false})); }); }); + + it('fails if actual is not a promise', function() { + var matcher = jasmineUnderTest.asyncMatchers.toBeRejected(jasmineUnderTest.matchersUtil), + actual = 'not a promise'; + + function f() { + return matcher.compare(actual); + } + + expect(f).toThrowError( + 'Expected toBeRejected to be called on a promise.' + ); + }); }); diff --git a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js index 6ec2a31a..ebf2e9e6 100644 --- a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js @@ -138,4 +138,17 @@ describe('#toBeRejectedWithError', function () { })); }); }); + + it('fails if actual is not a promise', function() { + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + actual = 'not a promise'; + + function f() { + return matcher.compare(actual); + } + + expect(f).toThrowError( + 'Expected toBeRejectedWithError to be called on a promise.' + ); + }); }); diff --git a/spec/core/matchers/async/toBeRejectedWithSpec.js b/spec/core/matchers/async/toBeRejectedWithSpec.js index 899d8a79..ea927c20 100644 --- a/spec/core/matchers/async/toBeRejectedWithSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithSpec.js @@ -60,4 +60,17 @@ describe('#toBeRejectedWith', function () { expect(result).toEqual(jasmine.objectContaining({pass: true})); }); }); + + it('fails if actual is not a promise', function() { + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(jasmineUnderTest.matchersUtil), + actual = 'not a promise'; + + function f() { + return matcher.compare(actual); + } + + expect(f).toThrowError( + 'Expected toBeRejectedWith to be called on a promise.' + ); + }); }); diff --git a/spec/core/matchers/async/toBeResolvedSpec.js b/spec/core/matchers/async/toBeResolvedSpec.js index ba66ab67..28297e30 100644 --- a/spec/core/matchers/async/toBeResolvedSpec.js +++ b/spec/core/matchers/async/toBeResolvedSpec.js @@ -20,4 +20,17 @@ describe('toBeResolved', function() { expect(result).toEqual(jasmine.objectContaining({pass: false})); }); }); + + it('fails if actual is not a promise', function() { + var matcher = jasmineUnderTest.asyncMatchers.toBeResolved(jasmineUnderTest.matchersUtil), + actual = 'not a promise'; + + function f() { + return matcher.compare(actual); + } + + expect(f).toThrowError( + 'Expected toBeResolved to be called on a promise.' + ); + }); }); diff --git a/spec/core/matchers/async/toBeResolvedToSpec.js b/spec/core/matchers/async/toBeResolvedToSpec.js index e8baaf7d..dc330920 100644 --- a/spec/core/matchers/async/toBeResolvedToSpec.js +++ b/spec/core/matchers/async/toBeResolvedToSpec.js @@ -63,4 +63,17 @@ describe('#toBeResolvedTo', function() { expect(result).toEqual(jasmine.objectContaining({pass: true})); }); }); + + it('fails if actual is not a promise', function() { + var matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(jasmineUnderTest.matchersUtil), + actual = 'not a promise'; + + function f() { + return matcher.compare(actual); + } + + expect(f).toThrowError( + 'Expected toBeResolvedTo to be called on a promise.' + ); + }); }); diff --git a/src/core/Env.js b/src/core/Env.js index 6e4e79e7..20221550 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -266,6 +266,19 @@ getJasmineRequireObj().Env = function(j$) { } }; + this.addAsyncMatchers = function(matchersToAdd) { + if (!currentRunnable()) { + throw new Error( + 'Async Matchers must be added in a before function or a spec' + ); + } + var customAsyncMatchers = + runnableResources[currentRunnable().id].customAsyncMatchers; + for (var matcherName in matchersToAdd) { + customAsyncMatchers[matcherName] = matchersToAdd[matcherName]; + } + }; + j$.Expectation.addCoreMatchers(j$.matchers); j$.Expectation.addAsyncCoreMatchers(j$.asyncMatchers); @@ -297,6 +310,7 @@ getJasmineRequireObj().Env = function(j$) { return j$.Expectation.asyncFactory({ util: j$.matchersUtil, customEqualityTesters: runnableResources[spec.id].customEqualityTesters, + customAsyncMatchers: runnableResources[spec.id].customAsyncMatchers, actual: actual, addExpectationResult: addExpectationResult }); @@ -311,6 +325,7 @@ getJasmineRequireObj().Env = function(j$) { spies: [], customEqualityTesters: [], customMatchers: {}, + customAsyncMatchers: {}, customSpyStrategies: {}, defaultStrategyFn: undefined }; @@ -322,6 +337,9 @@ getJasmineRequireObj().Env = function(j$) { resources.customMatchers = j$.util.clone( runnableResources[parentRunnableId].customMatchers ); + resources.customAsyncMatchers = j$.util.clone( + runnableResources[parentRunnableId].customAsyncMatchers + ); resources.defaultStrategyFn = runnableResources[parentRunnableId].defaultStrategyFn; } diff --git a/src/core/Expectation.js b/src/core/Expectation.js index 4bfbb327..add788cb 100644 --- a/src/core/Expectation.js +++ b/src/core/Expectation.js @@ -1,10 +1,4 @@ getJasmineRequireObj().Expectation = function(j$) { - var promiseForMessage = { - jasmineToString: function() { - return 'a promise'; - } - }; - /** * Matchers that come with Jasmine out of the box. * @namespace matchers @@ -62,8 +56,12 @@ getJasmineRequireObj().Expectation = function(j$) { ); } - if (!j$.isPromiseLike(this.expector.actual)) { - throw new Error('Expected expectAsync to be called with a promise.'); + var customAsyncMatchers = options.customAsyncMatchers || {}; + for (var matcherName in customAsyncMatchers) { + this[matcherName] = wrapAsyncCompare( + matcherName, + customAsyncMatchers[matcherName] + ); } } @@ -113,7 +111,7 @@ getJasmineRequireObj().Expectation = function(j$) { return this.expector .compare(name, matcherFactory, arguments) .then(function(result) { - self.expector.processResult(result, errorForStack, promiseForMessage); + self.expector.processResult(result, errorForStack); }); }; } @@ -168,7 +166,7 @@ getJasmineRequireObj().Expectation = function(j$) { return matcher.compare.apply(this, arguments).then(negate); } - return defaultNegativeCompare; + return matcher.negativeCompare || defaultNegativeCompare; }, buildFailureMessage: negatedFailureMessage }; diff --git a/src/core/Expector.js b/src/core/Expector.js index bfc443f8..78db5c1b 100644 --- a/src/core/Expector.js +++ b/src/core/Expector.js @@ -68,12 +68,7 @@ getJasmineRequireObj().Expector = function(j$) { return result; }; - Expector.prototype.processResult = function( - result, - errorForStack, - actualOverride - ) { - this.args[0] = actualOverride || this.args[0]; + Expector.prototype.processResult = function(result, errorForStack) { var message = this.buildMessage(result); if (this.expected.length === 1) { diff --git a/src/core/matchers/async/toBeRejected.js b/src/core/matchers/async/toBeRejected.js index c3b53aa4..62f1a3e9 100644 --- a/src/core/matchers/async/toBeRejected.js +++ b/src/core/matchers/async/toBeRejected.js @@ -10,9 +10,12 @@ getJasmineRequireObj().toBeRejected = function(j$) { * @example * return expectAsync(aPromise).toBeRejected(); */ - return function toBeResolved(util) { + return function toBeRejected(util) { return { compare: function(actual) { + if (!j$.isPromiseLike(actual)) { + throw new Error('Expected toBeRejected to be called on a promise.'); + } return actual.then( function() { return {pass: false}; }, function() { return {pass: true}; } diff --git a/src/core/matchers/async/toBeRejectedWith.js b/src/core/matchers/async/toBeRejectedWith.js index 62748412..031230a1 100644 --- a/src/core/matchers/async/toBeRejectedWith.js +++ b/src/core/matchers/async/toBeRejectedWith.js @@ -14,6 +14,10 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { return function toBeRejectedWith(util, customEqualityTesters) { return { compare: function(actualPromise, expectedValue) { + if (!j$.isPromiseLike(actualPromise)) { + throw new Error('Expected toBeRejectedWith to be called on a promise.'); + } + function prefix(passed) { return 'Expected a promise ' + (passed ? 'not ' : '') + diff --git a/src/core/matchers/async/toBeRejectedWithError.js b/src/core/matchers/async/toBeRejectedWithError.js index 84144c31..43dd4bc9 100644 --- a/src/core/matchers/async/toBeRejectedWithError.js +++ b/src/core/matchers/async/toBeRejectedWithError.js @@ -17,6 +17,10 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return function toBeRejectedWithError() { return { compare: function(actualPromise, arg1, arg2) { + if (!j$.isPromiseLike(actualPromise)) { + throw new Error('Expected toBeRejectedWithError to be called on a promise.'); + } + var expected = getExpectedFromArgs(arg1, arg2); return actualPromise.then( diff --git a/src/core/matchers/async/toBeResolved.js b/src/core/matchers/async/toBeResolved.js index e998a116..efe367e9 100644 --- a/src/core/matchers/async/toBeResolved.js +++ b/src/core/matchers/async/toBeResolved.js @@ -13,6 +13,10 @@ getJasmineRequireObj().toBeResolved = function(j$) { return function toBeResolved(util) { return { compare: function(actual) { + if (!j$.isPromiseLike(actual)) { + throw new Error('Expected toBeResolved to be called on a promise.'); + } + return actual.then( function() { return {pass: true}; }, function() { return {pass: false}; } diff --git a/src/core/matchers/async/toBeResolvedTo.js b/src/core/matchers/async/toBeResolvedTo.js index ff2b943c..015262f2 100644 --- a/src/core/matchers/async/toBeResolvedTo.js +++ b/src/core/matchers/async/toBeResolvedTo.js @@ -14,6 +14,10 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { return function toBeResolvedTo(util, customEqualityTesters) { return { compare: function(actualPromise, expectedValue) { + if (!j$.isPromiseLike(actualPromise)) { + throw new Error('Expected toBeResolvedTo to be called on a promise.'); + } + function prefix(passed) { return 'Expected a promise ' + (passed ? 'not ' : '') + diff --git a/src/core/requireInterface.js b/src/core/requireInterface.js index 3738954a..091bb7a0 100644 --- a/src/core/requireInterface.js +++ b/src/core/requireInterface.js @@ -302,6 +302,20 @@ getJasmineRequireObj().interface = function(jasmine, env) { return env.addMatchers(matchers); }; + /** + * Add custom async matchers for the current scope of specs. + * + * _Note:_ This is only callable from within a {@link beforeEach}, {@link it}, or {@link beforeAll}. + * @name jasmine.addMatchers + * @since 3.5.0 + * @function + * @param {Object} matchers - Keys from this object will be the new async matcher names. + * @see custom_matcher + */ + jasmine.addAsyncMatchers = function(matchers) { + return env.addAsyncMatchers(matchers); + }; + /** * Get the currently booted mock {Clock} for this Jasmine environment. * @name jasmine.clock From c42358c68623dd0b735071bf0a45367d263180be Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Fri, 30 Aug 2019 09:13:12 -0700 Subject: [PATCH 068/201] Fixed test failure on IE --- spec/core/AsyncExpectationSpec.js | 2 ++ 1 file changed, 2 insertions(+) diff --git a/spec/core/AsyncExpectationSpec.js b/spec/core/AsyncExpectationSpec.js index 3d4eb426..9b2e3f26 100644 --- a/spec/core/AsyncExpectationSpec.js +++ b/spec/core/AsyncExpectationSpec.js @@ -228,6 +228,8 @@ describe('AsyncExpectation', function() { describe('async matchers', function() { it('makes custom matchers available to this expectation', function() { + jasmine.getEnv().requirePromises(); + var asyncMatchers = { toFoo: function() {}, toBar: function() {} From 07318fba37d72ac44ca90ee05d5e6834c642ff42 Mon Sep 17 00:00:00 2001 From: Tony Brix Date: Fri, 30 Aug 2019 12:14:19 -0500 Subject: [PATCH 069/201] docs change --- src/core/requireInterface.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/core/requireInterface.js b/src/core/requireInterface.js index 091bb7a0..f8f15ac6 100644 --- a/src/core/requireInterface.js +++ b/src/core/requireInterface.js @@ -306,7 +306,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * Add custom async matchers for the current scope of specs. * * _Note:_ This is only callable from within a {@link beforeEach}, {@link it}, or {@link beforeAll}. - * @name jasmine.addMatchers + * @name jasmine.addAsyncMatchers * @since 3.5.0 * @function * @param {Object} matchers - Keys from this object will be the new async matcher names. From 92dfbdcdc92420cdb94ba6f26310d9acc4ad6c7c Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 3 Sep 2019 15:30:42 -0700 Subject: [PATCH 070/201] Depend on acorn to work around broken deduping See . --- package.json | 1 + 1 file changed, 1 insertion(+) diff --git a/package.json b/package.json index 4ccabce9..618a10bb 100644 --- a/package.json +++ b/package.json @@ -25,6 +25,7 @@ "homepage": "https://jasmine.github.io", "main": "./lib/jasmine-core.js", "devDependencies": { + "acorn": "^6.0.0", "ejs": "^2.5.5", "eslint": "^5.16.0", "express": "^4.16.4", From f8e5ea14bc9909baeebfff59db60613e28c3ff6b Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 3 Sep 2019 15:34:56 -0700 Subject: [PATCH 071/201] Fail the CI build if the promise returned from `jasmineBrowser.runSpecs` is rejected --- spec/support/ci.js | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/spec/support/ci.js b/spec/support/ci.js index 79a980df..0a941f07 100644 --- a/spec/support/ci.js +++ b/spec/support/ci.js @@ -7,4 +7,8 @@ var config = require(path.resolve('spec/support/jasmine-browser.js')); config.clearReporters = true; config.jasmineCore = jasmineCore; -jasmineBrowser.runSpecs(config); +jasmineBrowser.runSpecs(config) + .catch(function(error) { + console.error(error); + process.exit(1); + }); From ba71989d4b87738bd486c9097909891709ebf81b Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 3 Sep 2019 15:39:00 -0700 Subject: [PATCH 072/201] Fixed code formatting --- spec/support/ci.js | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/spec/support/ci.js b/spec/support/ci.js index 0a941f07..576fc6b3 100644 --- a/spec/support/ci.js +++ b/spec/support/ci.js @@ -7,8 +7,7 @@ var config = require(path.resolve('spec/support/jasmine-browser.js')); config.clearReporters = true; config.jasmineCore = jasmineCore; -jasmineBrowser.runSpecs(config) - .catch(function(error) { - console.error(error); - process.exit(1); - }); +jasmineBrowser.runSpecs(config).catch(function(error) { + console.error(error); + process.exit(1); +}); From 19292e4ea41591b842e96abde1ce367b33d3eb55 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 3 Sep 2019 15:40:53 -0700 Subject: [PATCH 073/201] Stop testing against PhantomJS PhantomJS is at end of life, and the last version of Selenium that supported it was 3.6.0, released almost three years ago. We can't test Jasmine against PhantomJS without pinning key pieces of the project to increasingly outdated versions of key libraries. --- .travis.yml | 1 - README.md | 2 +- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index 8c9ebe78..b6b2209d 100644 --- a/.travis.yml +++ b/.travis.yml @@ -18,7 +18,6 @@ env: matrix: include: - - env: JASMINE_BROWSER="phantomjs" USE_SAUCE=false - env: JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='' SAUCE_OS="Linux" if: type != pull_request addons: diff --git a/README.md b/README.md index 30c09023..c6a5ff36 100644 --- a/README.md +++ b/README.md @@ -52,7 +52,7 @@ Add the following to your HTML file: ## Supported environments -Jasmine tests itself across many browsers (Safari, Chrome, Firefox, PhantomJS, Microsoft Edge, and new Internet Explorer) as well as nodejs. To see the exact version tests are run against look at our [.travis.yml](https://github.com/jasmine/jasmine/blob/master/.travis.yml) +Jasmine tests itself across many browsers (Safari, Chrome, Firefox, Microsoft Edge, and new Internet Explorer) as well as nodejs. To see the exact version tests are run against look at our [.travis.yml](https://github.com/jasmine/jasmine/blob/master/.travis.yml) [![Sauce Test Status](https://saucelabs.com/browser-matrix/jasmine-js.svg)](https://saucelabs.com/u/jasmine-js) From 35d15085e35397811233833327a941f3916bcd3e Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 3 Sep 2019 17:12:35 -0700 Subject: [PATCH 074/201] Show argument diffs in toHaveBeenCalledWith failure messages * Fixes #1641 --- lib/jasmine-core/jasmine.js | 10 ++++++++- .../core/matchers/toHaveBeenCalledWithSpec.js | 22 +++++++++++++++---- src/core/matchers/toHaveBeenCalledWith.js | 10 ++++++++- 3 files changed, 36 insertions(+), 6 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index fc1cc6f1..b04cf054 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -5323,10 +5323,18 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { return ' ' + j$.pp(argsForCall); }); + var diffs = actual.calls.allArgs().map(function(argsForCall, callIx) { + var diffBuilder = new j$.DiffBuilder(); + util.equals(argsForCall, expectedArgs, customEqualityTesters, diffBuilder); + return 'Call ' + callIx + ':\n' + + diffBuilder.getMessage().replace(/^/mg, ' '); + }); + return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + ' ' + j$.pp(expectedArgs) + '\n' + '' + 'but actual calls were:\n' + - prettyPrintedCalls.join(',\n') + '.'; + prettyPrintedCalls.join(',\n') + '.\n\n' + + diffs.join('\n'); }; } diff --git a/spec/core/matchers/toHaveBeenCalledWithSpec.js b/spec/core/matchers/toHaveBeenCalledWithSpec.js index 534eca46..4ac7e074 100644 --- a/spec/core/matchers/toHaveBeenCalledWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledWithSpec.js @@ -43,19 +43,33 @@ describe("toHaveBeenCalledWith", function() { }); it("fails when the actual was called with different parameters", function() { - var util = { - contains: jasmine.createSpy('delegated-contains').and.returnValue(false) - }, + var util = jasmineUnderTest.matchersUtil, matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util), calledSpy = new jasmineUnderTest.Env().createSpy('called spy'), result; calledSpy('a'); calledSpy('c', 'd'); + calledSpy('a', 'b', 'c'); result = matcher.compare(calledSpy, 'a', 'b'); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected spy called spy to have been called with:\n [ 'a', 'b' ]\nbut actual calls were:\n [ 'a' ],\n [ 'c', 'd' ]."); + expect(result.message()).toEqual( + "Expected spy called spy to have been called with:\n" + + " [ 'a', 'b' ]\n" + + "but actual calls were:\n" + + " [ 'a' ],\n" + + " [ 'c', 'd' ],\n" + + " [ 'a', 'b', 'c' ].\n\n" + + "Call 0:\n" + + " Expected $.length = 1 to equal 2.\n" + + " Expected $[1] = undefined to equal 'b'.\n" + + "Call 1:\n" + + " Expected $[0] = 'c' to equal 'a'.\n" + + " Expected $[1] = 'd' to equal 'b'.\n" + + "Call 2:\n" + + " Expected $.length = 3 to equal 2.\n" + + " Unexpected $[2] = 'c' in array."); }); it("throws an exception when the actual is not a spy", function() { diff --git a/src/core/matchers/toHaveBeenCalledWith.js b/src/core/matchers/toHaveBeenCalledWith.js index 79197813..277b33f3 100644 --- a/src/core/matchers/toHaveBeenCalledWith.js +++ b/src/core/matchers/toHaveBeenCalledWith.js @@ -45,10 +45,18 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { return ' ' + j$.pp(argsForCall); }); + var diffs = actual.calls.allArgs().map(function(argsForCall, callIx) { + var diffBuilder = new j$.DiffBuilder(); + util.equals(argsForCall, expectedArgs, customEqualityTesters, diffBuilder); + return 'Call ' + callIx + ':\n' + + diffBuilder.getMessage().replace(/^/mg, ' '); + }); + return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + ' ' + j$.pp(expectedArgs) + '\n' + '' + 'but actual calls were:\n' + - prettyPrintedCalls.join(',\n') + '.'; + prettyPrintedCalls.join(',\n') + '.\n\n' + + diffs.join('\n'); }; } From 7263a38c3fb04d7fb27c468cdec8ec3eb53e0766 Mon Sep 17 00:00:00 2001 From: Dmitriy T Date: Thu, 22 Aug 2019 16:08:43 -0400 Subject: [PATCH 075/201] Adds new configuration option to failSpecWithNoExpectations that will report specs without expectations as failures if enabled --- .github/CONTRIBUTING.md | 2 +- package.json | 1 + spec/core/TreeProcessorSpec.js | 43 +++++++++++++++++---- spec/core/integration/EnvSpec.js | 35 +++++++++++++++++ spec/html/HtmlReporterSpec.js | 66 ++++++++++++++++++++------------ src/core/Env.js | 16 ++++++++ src/core/Spec.js | 18 ++++++--- src/core/TreeProcessor.js | 7 +++- src/html/HtmlReporter.js | 32 +++++++++++----- 9 files changed, 172 insertions(+), 48 deletions(-) diff --git a/.github/CONTRIBUTING.md b/.github/CONTRIBUTING.md index 2ee4cbd3..686c71de 100644 --- a/.github/CONTRIBUTING.md +++ b/.github/CONTRIBUTING.md @@ -118,7 +118,7 @@ The easiest way to run the tests in **Internet Explorer** is to run a VM that ha 1. Ensure all specs are green in browser *and* node 1. Ensure eslint and prettier are clean as part of your `npm test` command. You can run `npm run cleanup` to have prettier re-write the files. -1. Build `jasmine.js` with `grunt buildDistribution` and run all specs again - this ensures that your changes self-test well +1. Build `jasmine.js` with `npm run build` and run all specs again - this ensures that your changes self-test well 1. Revert your changes to `jasmine.js` and `jasmine-html.js` * We do this because `jasmine.js` and `jasmine-html.js` are auto-generated (as you've seen in the previous steps) and accepting multiple pull requests when this auto-generated file changes causes lots of headaches * When we accept your pull request, we will generate these files as a separate commit and merge the entire branch into master diff --git a/package.json b/package.json index 618a10bb..f5cb97b9 100644 --- a/package.json +++ b/package.json @@ -16,6 +16,7 @@ "posttest": "eslint src/**/*.js spec/**/*.js && prettier --check src/**/*.js spec/**/*.js", "test": "grunt execSpecsInNode", "cleanup": "prettier --write src/**/*.js spec/**/*.js", + "build": "grunt buildDistribution", "serve": "node spec/support/localJasmineBrowser.js", "serve:performance": "node spec/support/localJasmineBrowser.js jasmine-browser-performance.json", "ci": "node spec/support/ci.js", diff --git a/spec/core/TreeProcessorSpec.js b/spec/core/TreeProcessorSpec.js index 18f4267f..5c31f100 100644 --- a/spec/core/TreeProcessorSpec.js +++ b/spec/core/TreeProcessorSpec.js @@ -296,7 +296,7 @@ describe('TreeProcessor', function() { queueRunner.calls.mostRecent().args[0].queueableFns[0].fn('foo'); - expect(leaf.execute).toHaveBeenCalledWith('foo', false); + expect(leaf.execute).toHaveBeenCalledWith('foo', false, false); }); it('runs a node with no children', function() { @@ -368,10 +368,10 @@ describe('TreeProcessor', function() { expect(queueableFns.length).toBe(3); queueableFns[1].fn('foo'); - expect(leaf1.execute).toHaveBeenCalledWith('foo', false); + expect(leaf1.execute).toHaveBeenCalledWith('foo', false, false); queueableFns[2].fn('bar'); - expect(leaf2.execute).toHaveBeenCalledWith('bar', false); + expect(leaf2.execute).toHaveBeenCalledWith('bar', false, false); }); it('cascades errors up the tree', function() { @@ -397,7 +397,7 @@ describe('TreeProcessor', function() { expect(queueableFns.length).toBe(2); queueableFns[1].fn('foo'); - expect(leaf.execute).toHaveBeenCalledWith('foo', false); + expect(leaf.execute).toHaveBeenCalledWith('foo', false, false); queueRunner.calls.mostRecent().args[0].onComplete('things'); expect(nodeComplete).toHaveBeenCalled(); @@ -433,7 +433,7 @@ describe('TreeProcessor', function() { expect(nodeStart).toHaveBeenCalledWith(node, 'bar'); queueableFns[1].fn('foo'); - expect(leaf1.execute).toHaveBeenCalledWith('foo', true); + expect(leaf1.execute).toHaveBeenCalledWith('foo', true, false); node.getResult.and.returnValue({ im: 'disabled' }); @@ -445,6 +445,35 @@ describe('TreeProcessor', function() { ); }); + it('should execute node with correct arguments when failSpecWithNoExpectations option is set', function() { + var leaf = new Leaf(), + node = new Node({ children: [leaf] }), + root = new Node({ children: [node] }), + queueRunner = jasmine.createSpy('queueRunner'), + nodeStart = jasmine.createSpy('nodeStart'), + nodeComplete = jasmine.createSpy('nodeComplete'), + processor = new jasmineUnderTest.TreeProcessor({ + tree: root, + runnableIds: [], + queueRunnerFactory: queueRunner, + nodeStart: nodeStart, + nodeComplete: nodeComplete, + failSpecWithNoExpectations: true + }), + treeComplete = jasmine.createSpy('treeComplete'), + nodeDone = jasmine.createSpy('nodeDone'); + + processor.execute(treeComplete); + var queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; + queueableFns[0].fn(nodeDone); + + queueableFns = queueRunner.calls.mostRecent().args[0].queueableFns; + expect(queueableFns.length).toBe(2); + + queueableFns[1].fn('foo'); + expect(leaf.execute).toHaveBeenCalledWith('foo', true, true); + }); + it('runs beforeAlls for a node with children', function() { var leaf = new Leaf(), node = new Node({ @@ -600,11 +629,11 @@ describe('TreeProcessor', function() { queueableFns[0].fn(); expect(nonSpecified.execute).not.toHaveBeenCalled(); - expect(specified.execute).toHaveBeenCalledWith(undefined, false); + expect(specified.execute).toHaveBeenCalledWith(undefined, false, false); queueableFns[1].fn(); - expect(nonSpecified.execute).toHaveBeenCalledWith(undefined, true); + expect(nonSpecified.execute).toHaveBeenCalledWith(undefined, true, false); }); it('runs nodes and leaves with a specified order', function() { diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index 45b91601..e31f7d9d 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -2138,6 +2138,41 @@ describe("Env integration", function() { }); }); + describe('when spec has no expectations', function() { + var env, reporter; + + beforeEach(function() { + env = new jasmineUnderTest.Env(); + reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + + env.addReporter(reporter); + env.it('is a spec without any expectations', function() { + // does nothing, just a mock spec without expectations + }); + + }); + + it('should report "failed" status if "failSpecWithNoExpectations" is enabled', function(done) { + reporter.jasmineDone.and.callFake(function(e) { + expect(e.overallStatus).toEqual('failed'); + done(); + }); + + env.configure({ failSpecWithNoExpectations: true }); + env.execute(); + }); + + it('should report "passed" status if "failSpecWithNoExpectations" is disabled', function(done) { + reporter.jasmineDone.and.callFake(function(e) { + expect(e.overallStatus).toEqual('passed'); + done(); + }); + + env.configure({ failSpecWithNoExpectations: false }); + env.execute(); + }); + }); + describe('When a top-level beforeAll fails', function() { it('is "failed"', function(done) { var env = new jasmineUnderTest.Env(), diff --git a/spec/html/HtmlReporterSpec.js b/spec/html/HtmlReporterSpec.js index da18deb3..526fa76c 100644 --- a/spec/html/HtmlReporterSpec.js +++ b/spec/html/HtmlReporterSpec.js @@ -62,19 +62,19 @@ describe('HtmlReporter', function() { }); describe('when a spec is done', function() { - it('logs errors to the console and prints a special symbol if it is an empty spec', function() { - if (typeof console === 'undefined') { - console = { warn: function() {} }; - } + describe('and no expectations ran', function() { + var container, reporter; + beforeEach(function() { + if (typeof console === 'undefined') { + console = { warn: function() {}, error: function() {} }; + } - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), - getContainer = function() { - return container; - }, + container = document.createElement('div'); reporter = new jasmineUnderTest.HtmlReporter({ - env: env, - getContainer: getContainer, + env: new jasmineUnderTest.Env(), + getContainer: function() { + return container; + }, createElement: function() { return document.createElement.apply(document, arguments); }, @@ -83,21 +83,39 @@ describe('HtmlReporter', function() { } }); - spyOn(console, 'warn'); + spyOn(console, 'warn'); + spyOn(console, 'error'); - reporter.initialize(); - - reporter.specDone({ - status: 'passed', - fullName: 'Some Name', - passedExpectations: [], - failedExpectations: [] + reporter.initialize(); + }); + + it('should log warning to the console and print a special symbol when empty spec status is passed', function() { + reporter.specDone({ + status: 'passed', + fullName: 'Some Name', + passedExpectations: [], + failedExpectations: [] + }); + expect(console.warn).toHaveBeenCalledWith( + "Spec 'Some Name' has no expectations." + ); + var specEl = container.querySelector('.jasmine-symbol-summary li'); + expect(specEl.getAttribute('class')).toEqual('jasmine-empty'); + }); + + it('should log error to the console and print a failure symbol when empty spec status is failed', function() { + reporter.specDone({ + status: 'failed', + fullName: 'Some Name', + passedExpectations: [], + failedExpectations: [] + }); + expect(console.error).toHaveBeenCalledWith( + "Spec 'Some Name' has no expectations." + ); + var specEl = container.querySelector('.jasmine-symbol-summary li'); + expect(specEl.getAttribute('class')).toEqual('jasmine-failed'); }); - expect(console.warn).toHaveBeenCalledWith( - "Spec 'Some Name' has no expectations." - ); - var specEl = container.querySelector('.jasmine-symbol-summary li'); - expect(specEl.getAttribute('class')).toEqual('jasmine-empty'); }); it('reports the status symbol of a excluded spec', function() { diff --git a/src/core/Env.js b/src/core/Env.js index 20221550..7d6a1210 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -65,6 +65,16 @@ getJasmineRequireObj().Env = function(j$) { * @default false */ failFast: false, + /** + * Whether to fail the spec if it ran no expectations. By default + * a spec that ran no expectations is reported as passed. Setting this + * to true will report such spec as a failure. + * @name Configuration#failSpecWithNoExpectations + * @since 3.5.0 + * @type Boolean + * @default false + */ + failSpecWithNoExpectations: false, /** * Whether to cause specs to only have one expectation failure. * @name Configuration#oneFailurePerSpec @@ -167,6 +177,11 @@ getJasmineRequireObj().Env = function(j$) { config.failFast = configuration.failFast; } + if (configuration.hasOwnProperty('failSpecWithNoExpectations')) { + config.failSpecWithNoExpectations = + configuration.failSpecWithNoExpectations; + } + if (configuration.hasOwnProperty('oneFailurePerSpec')) { config.oneFailurePerSpec = configuration.oneFailurePerSpec; } @@ -641,6 +656,7 @@ getJasmineRequireObj().Env = function(j$) { tree: topSuite, runnableIds: runnablesToRun, queueRunnerFactory: queueRunnerFactory, + failSpecWithNoExpectations: config.failSpecWithNoExpectations, nodeStart: function(suite, next) { currentlyExecutingSuites.push(suite); defaultResourcesForRunnable(suite.id, suite.parentSuite.id); diff --git a/src/core/Spec.js b/src/core/Spec.js index 53a4f0ef..b8791890 100644 --- a/src/core/Spec.js +++ b/src/core/Spec.js @@ -82,7 +82,7 @@ getJasmineRequireObj().Spec = function(j$) { return this.asyncExpectationFactory(actual, this); }; - Spec.prototype.execute = function(onComplete, excluded) { + Spec.prototype.execute = function(onComplete, excluded, failSpecWithNoExp) { var self = this; var onStart = { @@ -95,7 +95,7 @@ getJasmineRequireObj().Spec = function(j$) { var complete = { fn: function(done) { self.queueableFn.fn = null; - self.result.status = self.status(excluded); + self.result.status = self.status(excluded, failSpecWithNoExp); self.resultCallback(self.result, done); } }; @@ -166,7 +166,7 @@ getJasmineRequireObj().Spec = function(j$) { return this.result; }; - Spec.prototype.status = function(excluded) { + Spec.prototype.status = function(excluded, failSpecWithNoExpectations) { if (excluded === true) { return 'excluded'; } @@ -175,11 +175,17 @@ getJasmineRequireObj().Spec = function(j$) { return 'pending'; } - if (this.result.failedExpectations.length > 0) { + if ( + this.result.failedExpectations.length > 0 || + (failSpecWithNoExpectations && + this.result.failedExpectations.length + + this.result.passedExpectations.length === + 0) + ) { return 'failed'; - } else { - return 'passed'; } + + return 'passed'; }; Spec.prototype.getFullName = function() { diff --git a/src/core/TreeProcessor.js b/src/core/TreeProcessor.js index 469c1009..14798d77 100644 --- a/src/core/TreeProcessor.js +++ b/src/core/TreeProcessor.js @@ -5,6 +5,7 @@ getJasmineRequireObj().TreeProcessor = function() { queueRunnerFactory = attrs.queueRunnerFactory, nodeStart = attrs.nodeStart || function() {}, nodeComplete = attrs.nodeComplete || function() {}, + failSpecWithNoExpectations = !!attrs.failSpecWithNoExpectations, orderChildren = attrs.orderChildren || function(node) { @@ -222,7 +223,11 @@ getJasmineRequireObj().TreeProcessor = function() { } else { return { fn: function(done) { - node.execute(done, stats[node.id].excluded); + node.execute( + done, + stats[node.id].excluded, + failSpecWithNoExpectations + ); } }; } diff --git a/src/html/HtmlReporter.js b/src/html/HtmlReporter.js index 6bc8d1eb..1c6478cf 100644 --- a/src/html/HtmlReporter.js +++ b/src/html/HtmlReporter.js @@ -112,12 +112,13 @@ jasmineRequire.HtmlReporter = function(j$) { this.specDone = function(result) { stateBuilder.specDone(result); - if ( - noExpectations(result) && - typeof console !== 'undefined' && - typeof console.error !== 'undefined' - ) { - console.warn("Spec '" + result.fullName + "' has no expectations."); + if (noExpectations(result)) { + var noSpecMsg = "Spec '" + result.fullName + "' has no expectations."; + if (result.status === 'failed') { + console.error(noSpecMsg); + } else { + console.warn(noSpecMsg); + } } if (!symbols) { @@ -140,7 +141,7 @@ jasmineRequire.HtmlReporter = function(j$) { }; this.displaySpecInCorrectFormat = function(result) { - return noExpectations(result) + return noExpectations(result) && result.status === 'passed' ? 'jasmine-empty' : this.resultStatus(result.status); }; @@ -363,6 +364,16 @@ jasmineRequire.HtmlReporter = function(j$) { ); } + if (result.failedExpectations.length === 0) { + messages.appendChild( + createDom( + 'div', + { className: 'jasmine-result-message' }, + 'Spec has no expectations' + ) + ); + } + return failure; } @@ -654,9 +665,12 @@ jasmineRequire.HtmlReporter = function(j$) { } function noExpectations(result) { + var allExpectations = + result.failedExpectations.length + result.passedExpectations.length; + return ( - result.failedExpectations.length + result.passedExpectations.length === - 0 && result.status === 'passed' + allExpectations === 0 && + (result.status === 'passed' || result.status === 'failed') ); } From f056f3b86c59444cb02ec9d5eda8fc4920a780a6 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Fri, 6 Sep 2019 12:27:43 -0700 Subject: [PATCH 076/201] Fixed indentation --- src/core/matchers/async/toBeResolvedTo.js | 28 +++++++++++------------ 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/src/core/matchers/async/toBeResolvedTo.js b/src/core/matchers/async/toBeResolvedTo.js index 015262f2..9d5aa370 100644 --- a/src/core/matchers/async/toBeResolvedTo.js +++ b/src/core/matchers/async/toBeResolvedTo.js @@ -26,24 +26,24 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { return actualPromise.then( function(actualValue) { - if (util.equals(actualValue, expectedValue, customEqualityTesters)) { - return { - pass: true, - message: prefix(true) + '.' - }; - } else { + if (util.equals(actualValue, expectedValue, customEqualityTesters)) { + return { + pass: true, + message: prefix(true) + '.' + }; + } else { + return { + pass: false, + message: prefix(false) + ' but it was resolved to ' + j$.pp(actualValue) + '.' + }; + } + }, + function() { return { pass: false, - message: prefix(false) + ' but it was resolved to ' + j$.pp(actualValue) + '.' + message: prefix(false) + ' but it was rejected.' }; } - }, - function() { - return { - pass: false, - message: prefix(false) + ' but it was rejected.' - }; - } ); } }; From 5a219da848d2a4e0c394bf96275e3f8afc3849a4 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Fri, 6 Sep 2019 13:44:15 -0700 Subject: [PATCH 077/201] Added basic integration tests for all built-in matchers --- spec/core/integration/MatchersSpec.js | 475 ++++++++++++++++++++++++++ spec/core/matchers/toHaveClassSpec.js | 22 +- spec/helpers/domHelpers.js | 24 ++ spec/support/jasmine-browser.js | 1 + spec/support/jasmine.json | 1 + 5 files changed, 506 insertions(+), 17 deletions(-) create mode 100644 spec/core/integration/MatchersSpec.js create mode 100644 spec/helpers/domHelpers.js diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js new file mode 100644 index 00000000..64c780cd --- /dev/null +++ b/spec/core/integration/MatchersSpec.js @@ -0,0 +1,475 @@ +describe('Matchers (Integration)', function() { + function verifyPasses(expectations) { + var env = new jasmineUnderTest.Env(); + + it('passes', function(done) { + env.it('a spec', function() { + expectations(env); + }); + + var specExpectations = function(result) { + expect(result.status).toEqual('passed'); + expect(result.passedExpectations.length) + .withContext('Number of passed expectations') + .toEqual(1); + expect(result.failedExpectations.length) + .withContext('Number of failed expectations') + .toEqual(0); + expect(result.failedExpectations[0] && result.failedExpectations[0].message) + .withContext('Failure message') + .toBeUndefined(); + }; + + env.addReporter({ specDone: specExpectations, jasmineDone: done }); + env.execute(); + }); + } + + function verifyFails(expectations) { + var env = new jasmineUnderTest.Env(); + + it('fails', function(done) { + env.it('a spec', function() { + expectations(env); + }); + + var specExpectations = function(result) { + expect(result.status).toEqual('failed'); + expect(result.failedExpectations.length) + .withContext('Number of failed expectations') + .toEqual(1); + expect(result.failedExpectations[0].message) + .withContext('Failed with a thrown error rather than a matcher failure') + .not.toMatch(/^Error: /); + expect(result.failedExpectations[0].matcherName).withContext('Matcher name') + .not.toEqual(''); + }; + + env.addReporter({ specDone: specExpectations, jasmineDone: done }); + env.execute(); + }); + } + + function verifyPassesAsync(expectations) { + var env = new jasmineUnderTest.Env(); + + it('passes', function(done) { + jasmine.getEnv().requirePromises(); + + env.it('a spec', function() { + return expectations(env); + }); + + var specExpectations = function(result) { + expect(result.status).toEqual('passed'); + expect(result.passedExpectations.length) + .withContext('Number of passed expectations') + .toEqual(1); + expect(result.failedExpectations.length) + .withContext('Number of failed expectations') + .toEqual(0); + expect(result.failedExpectations[0] && result.failedExpectations[0].message) + .withContext('Failure message') + .toBeUndefined(); + }; + + env.addReporter({ specDone: specExpectations, jasmineDone: done }); + env.execute(); + }); + } + + function verifyFailsAsync(expectations) { + var env = new jasmineUnderTest.Env(); + + it('fails', function(done) { + jasmine.getEnv().requirePromises(); + + env.it('a spec', function() { + return expectations(env); + }); + + var specExpectations = function(result) { + expect(result.status).toEqual('failed'); + expect(result.failedExpectations.length) + .withContext('Number of failed expectations') + .toEqual(1); + expect(result.failedExpectations[0].message) + .withContext('Failed with a thrown error rather than a matcher failure') + .not.toMatch(/^Error: /); + expect(result.failedExpectations[0].matcherName).withContext('Matcher name') + .not.toEqual(''); + }; + + env.addReporter({ specDone: specExpectations, jasmineDone: done }); + env.execute(); + }); + } + + describe('nothing', function() { + verifyPasses(function(env) { + env.expect().nothing(); + }); + }); + + describe('toBe', function() { + verifyPasses(function(env) { + env.expect(1).toBe(1); + }); + + verifyFails(function(env) { + env.expect(2).toBe(1); + }); + }); + + describe('toBeCloseTo', function() { + verifyPasses(function(env) { + env.expect(1.001).toBeCloseTo(1, 2); + }); + + verifyFails(function(env) { + env.expect(1.1).toBeCloseTo(1, 2); + }); + }); + + describe('toBeDefined', function() { + verifyPasses(function(env) { + env.expect({}).toBeDefined(); + }); + + verifyFails(function(env) { + env.expect(undefined).toBeDefined(); + }); + }); + + describe('toBeFalse', function() { + verifyPasses(function(env) { + env.expect(false).toBeFalse(); + }); + + verifyFails(function(env) { + env.expect(true).toBeFalse(); + }); + }); + + describe('toBeFalsy', function() { + verifyPasses(function(env) { + env.expect(false).toBeFalsy(); + }); + + verifyFails(function(env) { + env.expect(true).toBeFalsy(); + }); + }); + + describe('toBeGreaterThan', function() { + verifyPasses(function(env) { + env.expect(2).toBeGreaterThan(1); + }); + + verifyFails(function(env) { + env.expect(1).toBeGreaterThan(2); + }); + }); + + describe('toBeGreaterThanOrEqual', function() { + verifyPasses(function(env) { + env.expect(2).toBeGreaterThanOrEqual(1); + }); + + verifyFails(function(env) { + env.expect(1).toBeGreaterThanOrEqual(2); + }); + }); + + describe('toBeInstanceOf', function() { + function Ctor() {} + + verifyPasses(function(env) { + env.expect(new Ctor()).toBeInstanceOf(Ctor); + }); + + verifyFails(function(env) { + env.expect({}).toBeInstanceOf(Ctor); + }); + }); + + describe('toBeLessThan', function() { + verifyPasses(function(env) { + env.expect(1).toBeLessThan(2); + }); + + verifyFails(function(env) { + env.expect(2).toBeLessThan(1); + }); + }); + + describe('toBeLessThanOrEqual', function() { + verifyPasses(function(env) { + env.expect(1).toBeLessThanOrEqual(2); + }); + + verifyFails(function(env) { + env.expect(2).toBeLessThanOrEqual(1); + }); + }); + + describe('toBeNaN', function() { + verifyPasses(function(env) { + env.expect(NaN).toBeNaN(); + }); + + verifyFails(function(env) { + env.expect(2).toBeNaN(); + }); + }); + + describe('toBeNegativeInfinity', function() { + verifyPasses(function(env) { + env.expect(Number.NEGATIVE_INFINITY).toBeNegativeInfinity(); + }); + + verifyFails(function(env) { + env.expect(2).toBeNegativeInfinity(); + }); + }); + + describe('toBeNull', function() { + verifyPasses(function(env) { + env.expect(null).toBeNull(); + }); + + verifyFails(function(env) { + env.expect(2).toBeNull(); + }); + }); + + describe('toBePositiveInfinity', function() { + verifyPasses(function(env) { + env.expect(Number.POSITIVE_INFINITY).toBePositiveInfinity(); + }); + + verifyFails(function(env) { + env.expect(2).toBePositiveInfinity(); + }); + }); + + describe('toBeResolved', function() { + verifyPassesAsync(function(env) { + return env.expectAsync(Promise.resolve()).toBeResolved(); + }); + + verifyFailsAsync(function(env) { + return env.expectAsync(Promise.reject()).toBeResolved(); + }); + }); + + describe('toBeResolvedTo', function() { + verifyPassesAsync(function(env) { + return env.expectAsync(Promise.resolve('foo')).toBeResolvedTo('foo'); + }); + + verifyFailsAsync(function(env) { + return env.expectAsync(Promise.resolve('foo')).toBeResolvedTo('bar'); + }); + }); + + describe('toBeRejected', function() { + verifyPassesAsync(function(env) { + return env.expectAsync(Promise.reject('nope')).toBeRejected(); + }); + + verifyFailsAsync(function(env) { + return env.expectAsync(Promise.resolve()).toBeRejected(); + }); + }); + + describe('toBeRejectedWith', function() { + verifyPassesAsync(function(env) { + return env.expectAsync(Promise.reject('nope')).toBeRejectedWith('nope'); + }); + + verifyFailsAsync(function(env) { + return env.expectAsync(Promise.resolve()).toBeRejectedWith('nope'); + }); + }); + + describe('toBeRejectedWithError', function() { + function MyCustomError() {} + MyCustomError.prototype = new Error(); + + verifyPassesAsync(function(env) { + return env.expectAsync(Promise.reject(new MyCustomError())).toBeRejectedWithError(MyCustomError); + }); + + verifyFailsAsync(function(env) { + return env.expectAsync(Promise.resolve()).toBeRejectedWithError(MyCustomError); + }); + }); + + describe('toBeTrue', function() { + verifyPasses(function(env) { + env.expect(true).toBeTrue(); + }); + + verifyFails(function(env) { + env.expect(false).toBeTrue(); + }); + }); + + describe('toBeTruthy', function() { + verifyPasses(function(env) { + env.expect(true).toBeTruthy(); + }); + + verifyFails(function(env) { + env.expect(false).toBeTruthy(); + }); + }); + + describe('toBeUndefined', function() { + verifyPasses(function(env) { + env.expect(undefined).toBeUndefined(); + }); + + verifyFails(function(env) { + env.expect(1).toBeUndefined(); + }); + }); + + describe('toContain', function() { + verifyPasses(function(env) { + env.expect('foobar').toContain('oo'); + }); + + verifyFails(function(env) { + env.expect('bar').toContain('oo'); + }); + }); + + describe('toEqual', function() { + verifyPasses(function(env) { + env.expect('a').toEqual('a'); + }); + + verifyFails(function(env) { + env.expect('a').toEqual('b'); + }); + }); + + describe('toHaveBeenCalled', function() { + verifyPasses(function(env) { + var spy = env.createSpy('spy'); + spy(); + env.expect(spy).toHaveBeenCalled(); + }); + + verifyFails(function(env) { + var spy = env.createSpy('spy'); + env.expect(spy).toHaveBeenCalled(); + }); + }); + + describe('toHaveBeenCalledBefore', function() { + verifyPasses(function(env) { + var a = env.createSpy('a'), b = env.createSpy('b'); + a(); + b(); + env.expect(a).toHaveBeenCalledBefore(b); + }); + + verifyFails(function(env) { + var a = env.createSpy('a'), b = env.createSpy('b'); + b(); + a(); + env.expect(a).toHaveBeenCalledBefore(b); + }); + }); + + describe('toHaveBeenCalledTimes', function() { + verifyPasses(function(env) { + var spy = env.createSpy('spy'); + spy(); + env.expect(spy).toHaveBeenCalledTimes(1); + }); + + verifyFails(function(env) { + var spy = env.createSpy('spy'); + env.expect(spy).toHaveBeenCalledTimes(1); + }); + }); + + describe('toHaveBeenCalledWith', function() { + verifyPasses(function(env) { + var spy = env.createSpy(); + spy('foo'); + env.expect(spy).toHaveBeenCalledWith('foo'); + }); + + verifyFails(function(env) { + var spy = env.createSpy(); + env.expect(spy).toHaveBeenCalledWith('foo'); + }); + }); + + describe('toHaveClass', function() { + beforeEach(function() { + this.domHelpers = jasmine.getEnv().domHelpers(); + }); + + verifyPasses(function(env) { + var domHelpers = jasmine.getEnv().domHelpers(); + var el = domHelpers.createElementWithClassName('foo'); + env.expect(el).toHaveClass('foo'); + }); + + verifyFails(function(env) { + var domHelpers = jasmine.getEnv().domHelpers(); + var el = domHelpers.createElementWithClassName('foo'); + env.expect(el).toHaveClass('bar'); + }); + }); + + describe('toMatch', function() { + verifyPasses(function(env) { + env.expect('foo').toMatch(/oo$/); + }); + + verifyFails(function(env) { + env.expect('bar').toMatch(/oo$/); + }); + }); + + describe('toThrow', function() { + verifyPasses(function(env) { + env.expect(function() { throw new Error(); }).toThrow(); + }); + + verifyFails(function(env) { + env.expect(function() {}).toThrow(); + }); + }); + + describe('toThrowError', function() { + verifyPasses(function(env) { + env.expect(function() { throw new Error(); }).toThrowError(); + }); + + verifyFails(function(env) { + env.expect(function() { }).toThrowError(); + }); + }); + + describe('toThrowMatching', function() { + function throws() { + throw new Error('nope'); + } + + verifyPasses(function(env) { + env.expect(throws).toThrowMatching(function() { return true; }); + }); + + verifyFails(function(env) { + env.expect(throws).toThrowMatching(function() { return false; }); + }); + }); +}); diff --git a/spec/core/matchers/toHaveClassSpec.js b/spec/core/matchers/toHaveClassSpec.js index 4e4ef00d..109babbb 100644 --- a/spec/core/matchers/toHaveClassSpec.js +++ b/spec/core/matchers/toHaveClassSpec.js @@ -1,30 +1,18 @@ describe('toHaveClass', function() { beforeEach(function() { - this.createElementWithClassName = function(className) { - var el = this.doc.createElement('div'); - el.className = className; - return el; - }; - - if (typeof document !== 'undefined') { - this.doc = document; - } else { - var JSDOM = require('jsdom').JSDOM; - var dom = new JSDOM(); - this.doc = dom.window.document; - } + this.domHelpers = jasmine.getEnv().domHelpers(); }); it('fails for a DOM element that lacks the expected class', function() { var matcher = jasmineUnderTest.matchers.toHaveClass(), - result = matcher.compare(this.createElementWithClassName(''), 'foo'); + result = matcher.compare(this.domHelpers.createElementWithClassName(''), 'foo'); expect(result.pass).toBe(false); }); it('passes for a DOM element that has the expected class', function() { var matcher = jasmineUnderTest.matchers.toHaveClass(), - el = this.createElementWithClassName('foo bar baz'); + el = this.domHelpers.createElementWithClassName('foo bar baz'); expect(matcher.compare(el, 'foo').pass).toBe(true); expect(matcher.compare(el, 'bar').pass).toBe(true); @@ -33,7 +21,7 @@ describe('toHaveClass', function() { it('fails for a DOM element that only has other classes', function() { var matcher = jasmineUnderTest.matchers.toHaveClass(), - el = this.createElementWithClassName('foo bar'); + el = this.domHelpers.createElementWithClassName('foo bar'); expect(matcher.compare(el, 'fo').pass).toBe(false); }); @@ -49,7 +37,7 @@ describe('toHaveClass', function() { matcher.compare(undefined, 'foo'); }).toThrowError('undefined is not a DOM element'); - var textNode = this.doc.createTextNode(''); + var textNode = this.domHelpers.document.createTextNode(''); expect(function() { matcher.compare(textNode, 'foo') }).toThrowError('HTMLNode is not a DOM element'); diff --git a/spec/helpers/domHelpers.js b/spec/helpers/domHelpers.js new file mode 100644 index 00000000..79175df3 --- /dev/null +++ b/spec/helpers/domHelpers.js @@ -0,0 +1,24 @@ +(function(env) { + function domHelpers() { + var doc; + + if (typeof document !== 'undefined') { + doc = document; + } else { + var JSDOM = require('jsdom').JSDOM; + var dom = new JSDOM(); + doc = dom.window.document; + } + + return { + document: doc, + createElementWithClassName: function(className) { + var el = this.document.createElement('div'); + el.className = className; + return el; + } + }; + } + + env.domHelpers = domHelpers; +})(jasmine.getEnv()); diff --git a/spec/support/jasmine-browser.js b/spec/support/jasmine-browser.js index 9986ba08..41c9e703 100644 --- a/spec/support/jasmine-browser.js +++ b/spec/support/jasmine-browser.js @@ -23,6 +23,7 @@ module.exports = { 'helpers/checkForSet.js', 'helpers/checkForSymbol.js', 'helpers/checkForTypedArrays.js', + 'helpers/domHelpers.js', 'helpers/integrationMatchers.js', 'helpers/promises.js', 'helpers/defineJasmineUnderTest.js' diff --git a/spec/support/jasmine.json b/spec/support/jasmine.json index ffcd6b7d..033207ec 100644 --- a/spec/support/jasmine.json +++ b/spec/support/jasmine.json @@ -10,6 +10,7 @@ "helpers/checkForSet.js", "helpers/checkForSymbol.js", "helpers/checkForTypedArrays.js", + "helpers/domHelpers.js", "helpers/integrationMatchers.js", "helpers/promises.js", "helpers/nodeDefineJasmineUnderTest.js" From 2d3ac38df8ee556637915070371b3256789f6314 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Fri, 6 Sep 2019 14:17:52 -0700 Subject: [PATCH 078/201] toBeRejectedWithError can expect the error to be Error, not just a subtype --- spec/core/integration/MatchersSpec.js | 7 ++----- .../matchers/async/toBeRejectedWithErrorSpec.js | 15 +++++++++++++++ src/core/matchers/async/toBeRejectedWithError.js | 6 +++++- 3 files changed, 22 insertions(+), 6 deletions(-) diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js index 64c780cd..e1a1ada0 100644 --- a/spec/core/integration/MatchersSpec.js +++ b/spec/core/integration/MatchersSpec.js @@ -294,15 +294,12 @@ describe('Matchers (Integration)', function() { }); describe('toBeRejectedWithError', function() { - function MyCustomError() {} - MyCustomError.prototype = new Error(); - verifyPassesAsync(function(env) { - return env.expectAsync(Promise.reject(new MyCustomError())).toBeRejectedWithError(MyCustomError); + return env.expectAsync(Promise.reject(new Error())).toBeRejectedWithError(Error); }); verifyFailsAsync(function(env) { - return env.expectAsync(Promise.resolve()).toBeRejectedWithError(MyCustomError); + return env.expectAsync(Promise.resolve()).toBeRejectedWithError(Error); }); }); diff --git a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js index ebf2e9e6..3b207645 100644 --- a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js @@ -27,6 +27,21 @@ describe('#toBeRejectedWithError', function () { }); }); + it('passes when Error matches and is exactly Error', function() { + jasmine.getEnv().requirePromises(); + + var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + actual = Promise.reject(new Error()); + + return matcher.compare(actual, Error).then(function (result) { + expect(result).toEqual(jasmine.objectContaining({ + pass: true, + message: 'Expected a promise not to be rejected with Error, but it was.' + })); + }); + + }); + it('passes when Error message matches a string', function () { jasmine.getEnv().requirePromises(); diff --git a/src/core/matchers/async/toBeRejectedWithError.js b/src/core/matchers/async/toBeRejectedWithError.js index 43dd4bc9..8a578a60 100644 --- a/src/core/matchers/async/toBeRejectedWithError.js +++ b/src/core/matchers/async/toBeRejectedWithError.js @@ -76,7 +76,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { function getExpectedFromArgs(arg1, arg2) { var error, message; - if (typeof arg1 === 'function' && j$.isError_(arg1.prototype)) { + if (isErrorConstructor(arg1)) { error = arg1; message = arg2; } else { @@ -90,4 +90,8 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { printValue: j$.fnNameFor(error) + (typeof message === 'undefined' ? '' : ': ' + j$.pp(message)) }; } + + function isErrorConstructor(value) { + return typeof value === 'function' && (value === Error || j$.isError_(value.prototype)); + } }; From 65d9e93a88cfa0ab36ff803dc13ccf0403976f2f Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 10 Sep 2019 09:38:38 -0700 Subject: [PATCH 079/201] Removed broken & long-disabled JsApiReporter integration specs --- spec/core/JsApiReporterSpec.js | 77 ---------------------------------- 1 file changed, 77 deletions(-) diff --git a/spec/core/JsApiReporterSpec.js b/spec/core/JsApiReporterSpec.js index 2dcbdcff..d0985a31 100644 --- a/spec/core/JsApiReporterSpec.js +++ b/spec/core/JsApiReporterSpec.js @@ -1,80 +1,3 @@ -xdescribe('JsApiReporter (integration specs)', function() { - describe('results', function() { - var reporter, spec1, spec2; - var env; - - beforeEach(function() { - env = new jasmineUnderTest.Env(); - - env.describe('top-level suite', function() { - spec1 = env.it('spec 1', function() { - this.expect(true).toEqual(true); - }); - - spec2 = env.it('spec 2', function() { - this.expect(true).toEqual(false); - }); - - env.describe('nested suite', function() { - env.it('nested spec', function() { - expect(true).toEqual(true); - }); - }); - }); - - reporter = new jasmineUnderTest.JsApiReporter({}); - env.addReporter(reporter); - - env.execute(); - }); - - it('results() should return a hash of all results, indexed by spec id', function() { - expect(reporter.results()[spec1.id].result).toEqual('passed'); - expect(reporter.results()[spec2.id].result).toEqual('failed'); - }); - - it('should return nested suites as children of their parents', function() { - expect(reporter.suites()).toEqual([ - { - id: 0, - name: 'top-level suite', - type: 'suite', - children: [ - { id: 0, name: 'spec 1', type: 'spec', children: [] }, - { id: 1, name: 'spec 2', type: 'spec', children: [] }, - { - id: 1, - name: 'nested suite', - type: 'suite', - children: [ - { id: 2, name: 'nested spec', type: 'spec', children: [] } - ] - } - ] - } - ]); - }); - - describe('#summarizeResult_', function() { - it('should summarize a passing result', function() { - var result = reporter.results()[spec1.id]; - var summarizedResult = reporter.summarizeResult_(result); - expect(summarizedResult.result).toEqual('passed'); - expect(summarizedResult.messages.length).toEqual(0); - }); - - it('should have a stack trace for failing specs', function() { - var result = reporter.results()[spec2.id]; - var summarizedResult = reporter.summarizeResult_(result); - expect(summarizedResult.result).toEqual('failed'); - expect(summarizedResult.messages[0].trace.stack).toEqual( - result.messages[0].trace.stack - ); - }); - }); - }); -}); - describe('JsApiReporter', function() { it('knows when a full environment is started', function() { var reporter = new jasmineUnderTest.JsApiReporter({}); From ba4a8d1d0098a7fafe2451043afc551c0e2a5d43 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 10 Sep 2019 11:23:11 -0700 Subject: [PATCH 080/201] Fixed jsdocs --- src/core/base.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/core/base.js b/src/core/base.js index b962e129..3a2a097d 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -288,7 +288,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * that will succeed if every key/value pair in the sample passes the deep equality comparison * with at least one key/value pair in the actual value being compared * @name jasmine.mapContaining - * @since + * @since 3.5.0 * @function * @param {Map} sample - The subset of items that _must_ be in the actual. */ @@ -300,8 +300,8 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if every item in the sample passes the deep equality comparison * with at least one item in the actual value being compared - * @name jasmine.mapContaining - * @since + * @name jasmine.setContaining + * @since 3.5.0 * @function * @param {Set} sample - The subset of items that _must_ be in the actual. */ From 96ba66ad6012fbc99d003b5f2a70f2f67146b356 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 10 Sep 2019 11:23:27 -0700 Subject: [PATCH 081/201] Built distribution --- lib/jasmine-core/jasmine.js | 40 ++++++++++++++++++++----------------- 1 file changed, 22 insertions(+), 18 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index fc750714..2493bf4f 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -445,7 +445,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * that will succeed if every key/value pair in the sample passes the deep equality comparison * with at least one key/value pair in the actual value being compared * @name jasmine.mapContaining - * @since + * @since 3.5.0 * @function * @param {Map} sample - The subset of items that _must_ be in the actual. */ @@ -457,8 +457,8 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { * Get a matcher, usable in any {@link matchers|matcher} that uses Jasmine's equality (e.g. {@link matchers#toEqual|toEqual}, {@link matchers#toContain|toContain}, or {@link matchers#toHaveBeenCalledWith|toHaveBeenCalledWith}), * that will succeed if every item in the sample passes the deep equality comparison * with at least one item in the actual value being compared - * @name jasmine.mapContaining - * @since + * @name jasmine.setContaining + * @since 3.5.0 * @function * @param {Set} sample - The subset of items that _must_ be in the actual. */ @@ -3939,7 +3939,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { function getExpectedFromArgs(arg1, arg2) { var error, message; - if (typeof arg1 === 'function' && j$.isError_(arg1.prototype)) { + if (isErrorConstructor(arg1)) { error = arg1; message = arg2; } else { @@ -3953,6 +3953,10 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { printValue: j$.fnNameFor(error) + (typeof message === 'undefined' ? '' : ': ' + j$.pp(message)) }; } + + function isErrorConstructor(value) { + return typeof value === 'function' && (value === Error || j$.isError_(value.prototype)); + } }; getJasmineRequireObj().toBeResolved = function(j$) { @@ -4011,24 +4015,24 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { return actualPromise.then( function(actualValue) { - if (util.equals(actualValue, expectedValue, customEqualityTesters)) { - return { - pass: true, - message: prefix(true) + '.' - }; - } else { + if (util.equals(actualValue, expectedValue, customEqualityTesters)) { + return { + pass: true, + message: prefix(true) + '.' + }; + } else { + return { + pass: false, + message: prefix(false) + ' but it was resolved to ' + j$.pp(actualValue) + '.' + }; + } + }, + function() { return { pass: false, - message: prefix(false) + ' but it was resolved to ' + j$.pp(actualValue) + '.' + message: prefix(false) + ' but it was rejected.' }; } - }, - function() { - return { - pass: false, - message: prefix(false) + ' but it was rejected.' - }; - } ); } }; From 68f25a758da51388c1ef5845e539f79bc31d66cc Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 11 Sep 2019 13:21:38 -0700 Subject: [PATCH 082/201] Don't create env instances in beforeEach --- spec/core/integration/MatchersSpec.js | 12 ++++-------- 1 file changed, 4 insertions(+), 8 deletions(-) diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js index e1a1ada0..f75aae28 100644 --- a/spec/core/integration/MatchersSpec.js +++ b/spec/core/integration/MatchersSpec.js @@ -1,8 +1,7 @@ describe('Matchers (Integration)', function() { function verifyPasses(expectations) { - var env = new jasmineUnderTest.Env(); - it('passes', function(done) { + var env = new jasmineUnderTest.Env(); env.it('a spec', function() { expectations(env); }); @@ -26,9 +25,8 @@ describe('Matchers (Integration)', function() { } function verifyFails(expectations) { - var env = new jasmineUnderTest.Env(); - it('fails', function(done) { + var env = new jasmineUnderTest.Env(); env.it('a spec', function() { expectations(env); }); @@ -51,10 +49,9 @@ describe('Matchers (Integration)', function() { } function verifyPassesAsync(expectations) { - var env = new jasmineUnderTest.Env(); - it('passes', function(done) { jasmine.getEnv().requirePromises(); + var env = new jasmineUnderTest.Env(); env.it('a spec', function() { return expectations(env); @@ -79,9 +76,8 @@ describe('Matchers (Integration)', function() { } function verifyFailsAsync(expectations) { - var env = new jasmineUnderTest.Env(); - it('fails', function(done) { + var env = new jasmineUnderTest.Env(); jasmine.getEnv().requirePromises(); env.it('a spec', function() { From 53561ae71f8faa3ff4962c0f1d91ea5c7ef475ed Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 11 Sep 2019 13:27:59 -0700 Subject: [PATCH 083/201] Show details of syntax (etc) errors when loading Jasmine's own specs --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index f5cb97b9..1b340c27 100644 --- a/package.json +++ b/package.json @@ -14,7 +14,7 @@ ], "scripts": { "posttest": "eslint src/**/*.js spec/**/*.js && prettier --check src/**/*.js spec/**/*.js", - "test": "grunt execSpecsInNode", + "test": "grunt --stack execSpecsInNode", "cleanup": "prettier --write src/**/*.js spec/**/*.js", "build": "grunt buildDistribution", "serve": "node spec/support/localJasmineBrowser.js", From e8263e38aa5533c298b0b9a8176715a14c54a476 Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Fri, 20 Sep 2019 16:57:20 -0700 Subject: [PATCH 084/201] bump version to 3.5.0 --- lib/jasmine-core/jasmine.js | 2 +- lib/jasmine-core/version.rb | 2 +- package.json | 2 +- release_notes/3.5.0.md | 199 ++++++++++++++++++++++++++++++++++++ 4 files changed, 202 insertions(+), 3 deletions(-) create mode 100644 release_notes/3.5.0.md diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 2493bf4f..4875624e 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -8214,5 +8214,5 @@ getJasmineRequireObj().UserContext = function(j$) { }; getJasmineRequireObj().version = function() { - return '3.4.0'; + return '3.5.0'; }; diff --git a/lib/jasmine-core/version.rb b/lib/jasmine-core/version.rb index 0310ebe7..b757b251 100644 --- a/lib/jasmine-core/version.rb +++ b/lib/jasmine-core/version.rb @@ -4,6 +4,6 @@ # module Jasmine module Core - VERSION = "3.4.0" + VERSION = "3.5.0" end end diff --git a/package.json b/package.json index 1b340c27..e2ba236f 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "jasmine-core", "license": "MIT", - "version": "3.4.0", + "version": "3.5.0", "repository": { "type": "git", "url": "https://github.com/jasmine/jasmine.git" diff --git a/release_notes/3.5.0.md b/release_notes/3.5.0.md new file mode 100644 index 00000000..c1966796 --- /dev/null +++ b/release_notes/3.5.0.md @@ -0,0 +1,199 @@ +# Jasmine Core 3.5 Release Notes + +## Summary + +This is a maintenance release of Jasmine with a number of new features and fixes + +### Highlights + +* The output of toHaveBeenCalledWith should now be more readable + +This breaks each call out onto its own line, so that it's much easier to +see where each call starts and how they differ. E.g. previously the output +would be: + + Expected spy foo to have been called with [ 'bar', 'baz', 'qux' ] but actual calls were [ [ 42, 'wibble' ], [ 'bar' 'qux' ], [ 'grault '] ] + +Now it's: + + Expected spy foo to have been called with: + [ 'bar', 'baz', 'qux' ] + but actual calls were: + [ 42, 'wibble' ], + [ 'bar' 'qux' ], + [ 'grault ']. + +* Add new spy strategies to resolve and reject Promises `resolveTo` and `rejectWith` + +* Add the ability to have custom async matchers + +### Internal notes + +* Stop testing against PhantomJS + * PhantomJS is at end of life, and the last version of Selenium that supported it was 3.6.0, released almost three years ago. We can't test Jasmine against PhantomJS without pinning key pieces of the project to increasingly outdated versions of key libraries. + +* Fail Jasmine's CI build if the promise returned from `jasmineBrowser.runSpecs` is rejected + +* A bunch of other rejiggering of the Travis-CI builds to make them easier to work with + +* Also released a new browser runner that is being used by Jasmine + * See [jasmine-browser-runner](https://github.com/jasmine/jasmine-browser) + * This is a first pass at getting this to work for other projects as well. Please try it out and let us know what isn't working for you. + +* add prettier and eslint + + +## All Changes + +* Adds new configuration option to failSpecWithNoExpectations that will report specs without expectations as failures if enabled + * Merges [#1743](https://github.com/jasmine/jasmine/issues/1743) from @dtychshenko + * Fixes [#1740](https://github.com/jasmine/jasmine/issues/1740) + + +* Correctly propagate the `Error` object caught by the global error handler to reporters, etc. + - Merges [#1738](https://github.com/jasmine/jasmine/issues/1738) from @prantlf + - Fixes [#1728](https://github.com/jasmine/jasmine/issues/1728) + + +* Show argument diffs in toHaveBeenCalledWith failure messages + * Fixes [#1641](https://github.com/jasmine/jasmine/issues/1641) + + +* Updated arrayContaining to require actual values to be arrays + * Merges [#1746](https://github.com/jasmine/jasmine/issues/1746) from @divido + * Fixes [#1745](https://github.com/jasmine/jasmine/issues/1745) + + +* Add the ability to have custom async matchers + * Merges [#1732](https://github.com/jasmine/jasmine/issues/1732) from @UziTech + + +* Allow users to set a default spy strategy + - Merges [#1716](https://github.com/jasmine/jasmine/issues/1716) from @elliot-nelson + + +* Accept configurations with `Promise: undefined`. + + +* PrettyPrinter survives if objects throw in toString + - Merges [#1718](https://github.com/jasmine/jasmine/issues/1718) from @johnjbarton + - Fixes [#1726](https://github.com/jasmine/jasmine/issues/1726) + + +* Add `mapContaining` and `setContaining` asymmetric matchers + * Merges [#1741](https://github.com/jasmine/jasmine/issues/1741) from @eventlistener + + +* Use the same spec file pattern for both node and browser + + +* Gemspec: Drop EOL'd property rubyforge_project + * Merges [#1736](https://github.com/jasmine/jasmine/issues/1736) from @olleolleolle + + +* Updated async timeout message to include all of the ways that async code can be run in Jasmine + + +* Allow users to pass property names to createSpyObj + - Merges [#1722](https://github.com/jasmine/jasmine/issues/1722) from @elliot-nelson + - Closes [#1569](https://github.com/jasmine/jasmine/issues/1569) + - Fixes [#1442](https://github.com/jasmine/jasmine/issues/1442) + + +* don't attempt to normalize PNGs (gitattributes) + - Merges [#1721](https://github.com/jasmine/jasmine/issues/1721) from @elliot-nelson + + +* Add `@since` to most JSDoc comments + - See [jasmine/jasmine.github.io#117](https://github.com/jasmine/jasmine.github.io/issues/117) + + +* Make no expectations in HTML Reporter message a console warning + - Fixes [#1704](https://github.com/jasmine/jasmine/issues/1704) + + +* Prevent page overflow in HTML reporter under some situations by setting an explicit width + - Merges [#1713](https://github.com/jasmine/jasmine/issues/1713) from @pixelpax + + +* Cleanup: minor dead code removal and style fixes + - Merges [#1708](https://github.com/jasmine/jasmine/issues/1708) from @elliot-nelson + + +* Pretty Printer can now handle printing an object whose `toString` function has been spied upon + - Merges [#1712](https://github.com/jasmine/jasmine/issues/1712) from @johnjbarton + + +* PrettyPrinter handles objects with invalid toString implementations + - Merges [#1711](https://github.com/jasmine/jasmine/issues/1711) from @elliot-nelson + - Closes [#1700](https://github.com/jasmine/jasmine/issues/1700) + - Closes [#1575](https://github.com/jasmine/jasmine/issues/1575) + + +* Fix toBeCloseTo matcher for Node.js 12 and Chrome 74 + - Merges [#1710](https://github.com/jasmine/jasmine/issues/1710) from @paulvanbrenk + - Fixes [#1695](https://github.com/jasmine/jasmine/issues/1695) + + +* spyOnProperty jasmine-style error messages with usage note + - Merges [#1706](https://github.com/jasmine/jasmine/issues/1706) from @elliot-nelson + + +* spyOnProperty respects the allowRespy flag + - Merges [#1705](https://github.com/jasmine/jasmine/issues/1705) from @elliot-nelson + + +* Introduce matchers#toBeInstanceOf + - Merges [#1697](https://github.com/jasmine/jasmine/issues/1697) from @elliot-nelson + + +* Print global errors encountered during CI runs + - Merges [#1701](https://github.com/jasmine/jasmine/issues/1701) from @elliot-nelson + + +* Update contributing doc based on some of the newer tooling + - Fixes [#1702](https://github.com/jasmine/jasmine/issues/1702) + + +* Extend spyOnAllFunctions to include prototype and parent methods + - Merges [#1699](https://github.com/jasmine/jasmine/issues/1699) from @elliot-nelson + - Fixes [#1677](https://github.com/jasmine/jasmine/issues/1677) + + +* Improve error handling in CI test launcher + - Merges [#1598](https://github.com/jasmine/jasmine/issues/1598) from @elliot-nelson + + +* Add new spy strategies to resolve and reject Promises `resolveTo` and `rejectWith` + - Merges [#1688](https://github.com/jasmine/jasmine/issues/1688) from @enelson + - See [#1590](https://github.com/jasmine/jasmine/issues/1590) + - Fixes [#1715](https://github.com/jasmine/jasmine/issues/1715) + + +* Update deprecation messages to indicate _future_ removal + - Fixes [#1628](https://github.com/jasmine/jasmine/issues/1628) + +* Add toBeRejectedWithError matcher + - Merges [#1686](https://github.com/jasmine/jasmine/issues/1686) from @megahertz + - Fixes [#1625](https://github.com/jasmine/jasmine/issues/1625) + + +* Ignore internal ci.js from npm package + - See [#1684](https://github.com/jasmine/jasmine/issues/1684) + + +* Fix failure messages for positive/negative infinity matchers + - Fixes [#1674](https://github.com/jasmine/jasmine/issues/1674) + + +* nit: fix typo + - Merges [#1680](https://github.com/jasmine/jasmine/issues/1680) from @acinader + + +* added #toBeTrue and #toBeFalse matchers + - Merges [#1679](https://github.com/jasmine/jasmine/issues/1679) from @FelixRilling + + +------ + +_Release Notes generated with _[Anchorman](http://github.com/infews/anchorman)_ From 99799f72b3f25f38d39a807f986e2b9090fef0ec Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Fri, 20 Sep 2019 17:15:47 -0700 Subject: [PATCH 085/201] Still need some ruby stuff around to release the jasmine-core gem --- Rakefile | 2 ++ jasmine-core.gemspec | 1 + 2 files changed, 3 insertions(+) create mode 100644 Rakefile diff --git a/Rakefile b/Rakefile new file mode 100644 index 00000000..2480d0e6 --- /dev/null +++ b/Rakefile @@ -0,0 +1,2 @@ +require "bundler" +Bundler::GemHelper.install_tasks diff --git a/jasmine-core.gemspec b/jasmine-core.gemspec index 427d48c7..15999b31 100644 --- a/jasmine-core.gemspec +++ b/jasmine-core.gemspec @@ -15,4 +15,5 @@ Gem::Specification.new do |s| s.files = Dir.glob("./lib/**/*") s.require_paths = ["lib"] + s.add_development_dependency "rake" end From 223924a7a1eff78ad57a575fc98c163664a44f7a Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 21 Sep 2019 11:37:16 -0700 Subject: [PATCH 086/201] Fixed matchersUtil.contains test to fail correctly --- spec/core/matchers/matchersUtilSpec.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index 9dd42ce5..570f8f20 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -164,7 +164,7 @@ describe("matchersUtil", function() { expect(jasmineUnderTest.matchersUtil.equals(a,b)).toBe(true); }); - + it("passes for equivalent Promises (GitHub issue #1314)", function() { if (typeof Promise === 'undefined') { return; } @@ -620,7 +620,7 @@ describe("matchersUtil", function() { it("uses custom equality testers if passed in and actual is an Array", function() { var customTester = function(a, b) {return true;}; - expect(jasmineUnderTest.matchersUtil.contains([1, 2], 2, [customTester])).toBe(true); + expect(jasmineUnderTest.matchersUtil.contains([1, 2], 3, [customTester])).toBe(true); }); it("fails when actual is undefined", function() { From fc3eb0fbd89c5320fcdae493926de0e9ba910eed Mon Sep 17 00:00:00 2001 From: ivan baktsheev Date: Fri, 12 Apr 2019 18:46:12 +0300 Subject: [PATCH 087/201] Handle node.js `assert` as an error in your specs --- spec/core/ExpectationResultSpec.js | 33 ++++++++++++++++++++++++++++++ src/core/ExpectationResult.js | 18 +++++++++++++++- src/core/requireCore.js | 2 +- 3 files changed, 51 insertions(+), 2 deletions(-) diff --git a/spec/core/ExpectationResultSpec.js b/spec/core/ExpectationResultSpec.js index d9af2322..b28818aa 100644 --- a/spec/core/ExpectationResultSpec.js +++ b/spec/core/ExpectationResultSpec.js @@ -90,4 +90,37 @@ describe('buildExpectationResult', function() { }); expect(result.actual).toBe('some-value'); }); + + it('handles nodejs assertions', function() { + if (typeof require === 'undefined') { + return; + } + var assert = require('assert'); + var error; + var value = 8421; + var expectedValue = 'JasmineExpectationTestValue'; + try { + assert.equal(value, expectedValue); + } catch (e) { + error = e; + } + + expect(error.code).toEqual('ERR_ASSERTION'); + expect(error.actual).toEqual(value); + expect(error.expected).toEqual(expectedValue); + expect(error.operator).toEqual('=='); + + var result = jasmineUnderTest.buildExpectationResult({ + passed: false, + matcherName: '', + expected: '', + actual: '', + error: error + }); + + expect(result.code).toEqual('ERR_ASSERTION'); + expect(result.actual).toEqual(value); + expect(result.expected).toEqual(expectedValue); + expect(result.matcherName).toEqual('assert =='); + }); }); diff --git a/src/core/ExpectationResult.js b/src/core/ExpectationResult.js index 43545c43..7f298bc7 100644 --- a/src/core/ExpectationResult.js +++ b/src/core/ExpectationResult.js @@ -1,5 +1,5 @@ //TODO: expectation result may make more sense as a presentation of an expectation. -getJasmineRequireObj().buildExpectationResult = function() { +getJasmineRequireObj().buildExpectationResult = function(j$) { function buildExpectationResult(options) { var messageFormatter = options.messageFormatter || function() {}, stackFormatter = options.stackFormatter || function() {}; @@ -23,6 +23,22 @@ getJasmineRequireObj().buildExpectationResult = function() { if (!result.passed) { result.expected = options.expected; result.actual = options.actual; + + if (options.error && !j$.isString_(options.error)) { + if ('code' in options.error) { + result.code = options.error.code; + } + + if ( + options.error.code === 'ERR_ASSERTION' && + options.expected === '' && + options.actual === '' + ) { + result.expected = options.error.expected; + result.actual = options.error.actual; + result.matcherName = 'assert ' + options.error.operator; + } + } } return result; diff --git a/src/core/requireCore.js b/src/core/requireCore.js index a2c5f177..baacd713 100644 --- a/src/core/requireCore.js +++ b/src/core/requireCore.js @@ -48,7 +48,7 @@ var getJasmineRequireObj = (function(jasmineGlobal) { j$.ExpectationFilterChain = jRequire.ExpectationFilterChain(); j$.Expector = jRequire.Expector(j$); j$.Expectation = jRequire.Expectation(j$); - j$.buildExpectationResult = jRequire.buildExpectationResult(); + j$.buildExpectationResult = jRequire.buildExpectationResult(j$); j$.noopTimer = jRequire.noopTimer(); j$.JsApiReporter = jRequire.JsApiReporter(j$); j$.matchersUtil = jRequire.matchersUtil(j$); From a497d0942a0f32edba4c689a6ef504aff59386d6 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Fri, 27 Sep 2019 18:31:01 -0700 Subject: [PATCH 088/201] Report async expectations that complete after the runable completes It's very easy to forget to `await` or `return` the promise returned from `expectAsync`. When that happens, the expectation failure will occur after the spec or suite's result has been reported to reporters, and the failure will typically not be shown to the user. This change adds a top-level suite failure in that case, similar to the way we report unhandled exceptions or promise rejections that occur after the runable completes. Adding the error at the top level gives us the best chance of getting in before the set of failures we add it to is sent to reporters. See #1752. --- lib/jasmine-core/jasmine.js | 44 +++++++++++++-- spec/core/integration/EnvSpec.js | 91 +++++++++++++++++++++++++++++++- src/core/Env.js | 44 +++++++++++++-- 3 files changed, 170 insertions(+), 9 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index bd4a5c64..40713ef6 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1233,7 +1233,33 @@ getJasmineRequireObj().Env = function(j$) { } }; - var asyncExpectationFactory = function(actual, spec) { + function recordLateExpectation(runable, runableType, result) { + var delayedExpectationResult = {}; + Object.keys(result).forEach(function(k) { + delayedExpectationResult[k] = result[k]; + }); + delayedExpectationResult.passed = false; + delayedExpectationResult.globalErrorType = 'lateExpectation'; + delayedExpectationResult.message = + runableType + + ' "' + + runable.getFullName() + + '" ran a "' + + result.matcherName + + '" expectation after it finished.\n'; + + if (result.message) { + delayedExpectationResult.message += + 'Message: "' + result.message + '"\n'; + } + + delayedExpectationResult.message += + 'Did you forget to return or await the result of expectAsync?'; + + topSuite.result.failedExpectations.push(delayedExpectationResult); + } + + var asyncExpectationFactory = function(actual, spec, runableType) { return j$.Expectation.asyncFactory({ util: j$.matchersUtil, customEqualityTesters: runnableResources[spec.id].customEqualityTesters, @@ -1243,9 +1269,19 @@ getJasmineRequireObj().Env = function(j$) { }); function addExpectationResult(passed, result) { + if (currentRunnable() !== spec) { + recordLateExpectation(spec, runableType, result); + } return spec.addExpectationResult(passed, result); } }; + var suiteAsyncExpectationFactory = function(actual, suite) { + return asyncExpectationFactory(actual, suite, 'Suite'); + }; + + var specAsyncExpectationFactory = function(actual, suite) { + return asyncExpectationFactory(actual, suite, 'Spec'); + }; var defaultResourcesForRunnable = function(id, parentRunnableId) { var resources = { @@ -1463,7 +1499,7 @@ getJasmineRequireObj().Env = function(j$) { id: getNextSuiteId(), description: 'Jasmine__TopLevel__Suite', expectationFactory: expectationFactory, - asyncExpectationFactory: asyncExpectationFactory, + asyncExpectationFactory: suiteAsyncExpectationFactory, expectationResultFactory: expectationResultFactory }); defaultResourcesForRunnable(topSuite.id); @@ -1796,7 +1832,7 @@ getJasmineRequireObj().Env = function(j$) { description: description, parentSuite: currentDeclarationSuite, expectationFactory: expectationFactory, - asyncExpectationFactory: asyncExpectationFactory, + asyncExpectationFactory: suiteAsyncExpectationFactory, expectationResultFactory: expectationResultFactory, throwOnExpectationFailure: config.oneFailurePerSpec }); @@ -1890,7 +1926,7 @@ getJasmineRequireObj().Env = function(j$) { id: getNextSpecId(), beforeAndAfterFns: beforeAndAfterFns(suite), expectationFactory: expectationFactory, - asyncExpectationFactory: asyncExpectationFactory, + asyncExpectationFactory: specAsyncExpectationFactory, resultCallback: specResultCallback, getSpecName: function(spec) { return getSpecName(spec, suite); diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index e31f7d9d..eef02e6c 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -2149,7 +2149,7 @@ describe("Env integration", function() { env.it('is a spec without any expectations', function() { // does nothing, just a mock spec without expectations }); - + }); it('should report "failed" status if "failSpecWithNoExpectations" is enabled', function(done) { @@ -2556,4 +2556,93 @@ describe("Env integration", function() { env.execute(); }); + + it('reports an error when an async expectation occurs after the spec finishes', function(done) { + jasmine.getEnv().requirePromises(); + + var env = new jasmineUnderTest.Env(), + resolve, + promise = new Promise(function(res) { resolve = res; }); + + env.describe('a suite', function() { + env.it('does not wait', function() { + // Note: we intentionally don't return the result of each expectAsync. + // This causes the spec to finish before the expectations are evaluated. + env.expectAsync(promise).toBeResolved(); + env.expectAsync(promise).toBeResolvedTo('something else'); + }); + }); + + env.addReporter({ + specDone: function() { + resolve(); + }, + jasmineDone: function (result) { + expect(result.failedExpectations).toEqual([ + jasmine.objectContaining({ + passed: false, + globalErrorType: 'lateExpectation', + message: 'Spec "a suite does not wait" ran a "toBeResolved" expectation ' + + 'after it finished.\n' + + 'Did you forget to return or await the result of expectAsync?', + matcherName: 'toBeResolved' + }), + jasmine.objectContaining({ + passed: false, + globalErrorType: 'lateExpectation', + message: 'Spec "a suite does not wait" ran a "toBeResolvedTo" expectation ' + + 'after it finished.\n' + + 'Message: "Expected a promise to be resolved to \'something else\' ' + + 'but it was resolved to undefined."\n' + + 'Did you forget to return or await the result of expectAsync?', + matcherName: 'toBeResolvedTo' + }) + ]); + + done(); + } + }); + + env.execute(); + }); + + it('reports an error when an async expectation occurs after the suite finishes', function(done) { + jasmine.getEnv().requirePromises(); + + var env = new jasmineUnderTest.Env(), + resolve, + promise = new Promise(function(res) { resolve = res; }); + + env.describe('a suite', function() { + env.afterAll(function() { + // Note: we intentionally don't return the result of expectAsync. + // This causes the suite to finish before the expectations are evaluated. + env.expectAsync(promise).toBeResolved(); + }); + + env.it('is a spec', function() {}); + }); + + env.addReporter({ + suiteDone: function() { + resolve(); + }, + jasmineDone: function (result) { + expect(result.failedExpectations).toEqual([ + jasmine.objectContaining({ + passed: false, + globalErrorType: 'lateExpectation', + message: 'Suite "a suite" ran a "toBeResolved" expectation ' + + 'after it finished.\n' + + 'Did you forget to return or await the result of expectAsync?', + matcherName: 'toBeResolved' + }) + ]); + + done(); + } + }); + + env.execute(); + }); }); diff --git a/src/core/Env.js b/src/core/Env.js index 7d6a1210..dc652cd5 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -321,7 +321,33 @@ getJasmineRequireObj().Env = function(j$) { } }; - var asyncExpectationFactory = function(actual, spec) { + function recordLateExpectation(runable, runableType, result) { + var delayedExpectationResult = {}; + Object.keys(result).forEach(function(k) { + delayedExpectationResult[k] = result[k]; + }); + delayedExpectationResult.passed = false; + delayedExpectationResult.globalErrorType = 'lateExpectation'; + delayedExpectationResult.message = + runableType + + ' "' + + runable.getFullName() + + '" ran a "' + + result.matcherName + + '" expectation after it finished.\n'; + + if (result.message) { + delayedExpectationResult.message += + 'Message: "' + result.message + '"\n'; + } + + delayedExpectationResult.message += + 'Did you forget to return or await the result of expectAsync?'; + + topSuite.result.failedExpectations.push(delayedExpectationResult); + } + + var asyncExpectationFactory = function(actual, spec, runableType) { return j$.Expectation.asyncFactory({ util: j$.matchersUtil, customEqualityTesters: runnableResources[spec.id].customEqualityTesters, @@ -331,9 +357,19 @@ getJasmineRequireObj().Env = function(j$) { }); function addExpectationResult(passed, result) { + if (currentRunnable() !== spec) { + recordLateExpectation(spec, runableType, result); + } return spec.addExpectationResult(passed, result); } }; + var suiteAsyncExpectationFactory = function(actual, suite) { + return asyncExpectationFactory(actual, suite, 'Suite'); + }; + + var specAsyncExpectationFactory = function(actual, suite) { + return asyncExpectationFactory(actual, suite, 'Spec'); + }; var defaultResourcesForRunnable = function(id, parentRunnableId) { var resources = { @@ -551,7 +587,7 @@ getJasmineRequireObj().Env = function(j$) { id: getNextSuiteId(), description: 'Jasmine__TopLevel__Suite', expectationFactory: expectationFactory, - asyncExpectationFactory: asyncExpectationFactory, + asyncExpectationFactory: suiteAsyncExpectationFactory, expectationResultFactory: expectationResultFactory }); defaultResourcesForRunnable(topSuite.id); @@ -884,7 +920,7 @@ getJasmineRequireObj().Env = function(j$) { description: description, parentSuite: currentDeclarationSuite, expectationFactory: expectationFactory, - asyncExpectationFactory: asyncExpectationFactory, + asyncExpectationFactory: suiteAsyncExpectationFactory, expectationResultFactory: expectationResultFactory, throwOnExpectationFailure: config.oneFailurePerSpec }); @@ -978,7 +1014,7 @@ getJasmineRequireObj().Env = function(j$) { id: getNextSpecId(), beforeAndAfterFns: beforeAndAfterFns(suite), expectationFactory: expectationFactory, - asyncExpectationFactory: asyncExpectationFactory, + asyncExpectationFactory: specAsyncExpectationFactory, resultCallback: specResultCallback, getSpecName: function(spec) { return getSpecName(spec, suite); From 10dbf8be980b80d4b84e2db42f1fa879b427dc97 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 28 Sep 2019 12:31:00 -0700 Subject: [PATCH 089/201] Indent multiline failure messages in the output of `withContext` This makes it easier to see where each failure message begins and ends. Before: Some context: a multiline message After: Some context: a multiline message --- lib/jasmine-core/jasmine.js | 12 +++++++++++- spec/core/ExpectationSpec.js | 26 ++++++++++++++++++++++++++ src/core/Expectation.js | 12 +++++++++++- 3 files changed, 48 insertions(+), 2 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 40713ef6..a3f303b6 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -3495,9 +3495,19 @@ getJasmineRequireObj().Expectation = function(j$) { } ContextAddingFilter.prototype.modifyFailureMessage = function(msg) { - return this.message + ': ' + msg; + var nl = msg.indexOf('\n'); + + if (nl === -1) { + return this.message + ': ' + msg; + } else { + return this.message + ':\n' + indent(msg); + } }; + function indent(s) { + return s.replace(/^/gm, ' '); + } + return { factory: function(options) { return new Expectation(options || {}); diff --git a/spec/core/ExpectationSpec.js b/spec/core/ExpectationSpec.js index 45f69eb5..599b0558 100644 --- a/spec/core/ExpectationSpec.js +++ b/spec/core/ExpectationSpec.js @@ -589,6 +589,32 @@ describe('Expectation', function() { ); }); + it('indents a multiline failure message', function() { + var matchers = { + toFoo: function() { + return { + compare: function() { + return { pass: false, message: 'a\nmultiline\nmessage' }; + } + }; + } + }, + addExpectationResult = jasmine.createSpy('addExpectationResult'), + expectation = jasmineUnderTest.Expectation.factory({ + customMatchers: matchers, + actual: 'an actual', + addExpectationResult: addExpectationResult + }), + actualMessage; + + expectation.withContext('Some context').toFoo('hello'); + + actualMessage = addExpectationResult.calls.argsFor(0)[1].message; + expect(actualMessage).toEqual( + 'Some context:\n a\n multiline\n message' + ); + }); + it('prepends the context to a custom failure message from a function', function() { var matchers = { toFoo: function() { diff --git a/src/core/Expectation.js b/src/core/Expectation.js index add788cb..37e1b7d6 100644 --- a/src/core/Expectation.js +++ b/src/core/Expectation.js @@ -176,9 +176,19 @@ getJasmineRequireObj().Expectation = function(j$) { } ContextAddingFilter.prototype.modifyFailureMessage = function(msg) { - return this.message + ': ' + msg; + var nl = msg.indexOf('\n'); + + if (nl === -1) { + return this.message + ': ' + msg; + } else { + return this.message + ':\n' + indent(msg); + } }; + function indent(s) { + return s.replace(/^/gm, ' '); + } + return { factory: function(options) { return new Expectation(options || {}); From 472f61ab37984d977e5145e2346138f695ca286d Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 28 Sep 2019 17:50:17 -0700 Subject: [PATCH 090/201] Provide better diffs for object graphs that include `objectContaining` Turns this output: Expected $[0].foo = Object({ a: 4, b: 5 }) to equal . into this: Expected $[0].foo.a = 4 to equal 1. Expected $[0].foo.c = undefined to equal 3. And turns this output: Expected spy jasmineDone to have been called with: [ ... snipped very long expected call ] but actual calls were: [ ... snipped very long actual call ] Call 0: Expected $[0] = Object({ overallStatus: 'failed', totalTime: 1, incompleteReason: undefined, order: Order({ random: true, seed: '88732', sort: Function }), failedExpectations: [ Object({ matcherName: 'toBeResolved', passed: false, message: 'Suite "a suite" ran a "toBeResolved" expectation after it finished. Did you forget to return or await the result of expectAsync?', error: undefined, errorForStack: Error, actual: [object Promise], expected: [ ], globalErrorType: 'lateExpeztation' }) ], deprecationWarnings: [ ] }) to equal ] }))>. into this: Expected spy jasmineDone to have been called with: [ ... snipped very long expected call ] but actual calls were: [ ... snipped very long actual call ] Call 0: Expected $[0].failedExpectations[0].globalErrorType = 'lateExpeztation' to equal 'lateExpectation'. --- lib/jasmine-core/jasmine.js | 38 +++++++++++- .../ObjectContainingSpec.js | 61 +++++++++++++++++++ spec/core/matchers/matchersUtilSpec.js | 36 +++++++++++ spec/core/matchers/toEqualSpec.js | 14 +++++ .../asymmetric_equality/ObjectContaining.js | 21 +++++++ src/core/matchers/matchersUtil.js | 17 +++++- 6 files changed, 181 insertions(+), 6 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index a3f303b6..b442632e 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -2519,6 +2519,27 @@ getJasmineRequireObj().ObjectContaining = function(j$) { return true; }; + ObjectContaining.prototype.valuesForDiff_ = function(other) { + if (!j$.isObject_(other)) { + return { + self: this.jasmineToString(), + other: other + }; + } + + var filteredOther = {}; + Object.keys(this.sample).forEach(function (k) { + // eq short-circuits comparison of objects that have different key sets, + // so include all keys even if undefined. + filteredOther[k] = other[k]; + }); + + return { + self: this.sample, + other: filteredOther + }; + }; + ObjectContaining.prototype.jasmineToString = function() { return ''; }; @@ -4192,7 +4213,16 @@ getJasmineRequireObj().matchersUtil = function(j$) { return obj && j$.isA_('Function', obj.asymmetricMatch); } - function asymmetricMatch(a, b, customTesters, diffBuilder) { + function asymmetricDiff(a, b, aStack, bStack, customTesters, diffBuilder) { + if (j$.isFunction_(b.valuesForDiff_)) { + var values = b.valuesForDiff_(a); + eq(values.other, values.self, aStack, bStack, customTesters, diffBuilder); + } else { + diffBuilder.record(a, b); + } + } + + function asymmetricMatch(a, b, aStack, bStack, customTesters, diffBuilder) { var asymmetricA = isAsymmetric(a), asymmetricB = isAsymmetric(b), result; @@ -4204,6 +4234,8 @@ getJasmineRequireObj().matchersUtil = function(j$) { if (asymmetricA) { result = a.asymmetricMatch(b, customTesters); if (!result) { + // TODO: Do we want to build an asymmetric diff when the actual was an + // asymmeteric equality tester? Might be confusing. diffBuilder.record(a, b); } return result; @@ -4212,7 +4244,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { if (asymmetricB) { result = b.asymmetricMatch(a, customTesters); if (!result) { - diffBuilder.record(a, b); + asymmetricDiff(a, b, aStack, bStack, customTesters, diffBuilder); } return result; } @@ -4230,7 +4262,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { function eq(a, b, aStack, bStack, customTesters, diffBuilder) { var result = true, i; - var asymmetricResult = asymmetricMatch(a, b, customTesters, diffBuilder); + var asymmetricResult = asymmetricMatch(a, b, aStack, bStack, customTesters, diffBuilder); if (!j$.util.isUndefined(asymmetricResult)) { return asymmetricResult; } diff --git a/spec/core/asymmetric_equality/ObjectContainingSpec.js b/spec/core/asymmetric_equality/ObjectContainingSpec.js index e2741a9d..b17fd925 100644 --- a/spec/core/asymmetric_equality/ObjectContainingSpec.js +++ b/spec/core/asymmetric_equality/ObjectContainingSpec.js @@ -96,4 +96,65 @@ describe("ObjectContaining", function() { expect(containing.asymmetricMatch({foo: "fooBar"}, [tester])).toBe(true); }); + + describe("valuesForDiff_", function() { + describe("when other is not an object", function() { + it("sets self to jasmineToString()", function () { + var containing = new jasmineUnderTest.ObjectContaining({}), + result = containing.valuesForDiff_('a'); + + expect(result).toEqual({ + self: '', + other: 'a' + }); + }); + }); + + describe("when other is an object", function() { + it("includes keys that are present in both other and sample", function() { + var sample = {a: 1, b: 2}, + other = {a: 3, b: 4}, + containing = new jasmineUnderTest.ObjectContaining(sample), + result = containing.valuesForDiff_(other); + + expect(result.self).not.toBeInstanceOf(jasmineUnderTest.ObjectContaining); + expect(result).toEqual({ + self: sample, + other: other + }); + }); + + it("includes keys that are present in only sample", function() { + var sample = {a: 1, b: 2}, + other = {a: 3}, + containing = new jasmineUnderTest.ObjectContaining(sample), + result = containing.valuesForDiff_(other); + + expect(result.self).not.toBeInstanceOf(jasmineUnderTest.ObjectContaining); + expect(containing.valuesForDiff_(other)).toEqual({ + self: sample, + other: { + a: 3, + b: undefined + } + }); + }); + + it("omits keys that are present only in other", function() { + var sample = {a: 1, b: 2}, + other = {a: 3, b: 4, c: 5}, + containing = new jasmineUnderTest.ObjectContaining(sample), + result = containing.valuesForDiff_(other); + + expect(result.self).not.toBeInstanceOf(jasmineUnderTest.ObjectContaining); + expect(result).toEqual({ + self: sample, + other: { + a: 3, + b: 4 + } + }); + }); + }); + }); }); diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index 9dd42ce5..b2146e94 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -593,6 +593,42 @@ describe("matchersUtil", function() { expect(['foo']).toEqual(['foo']); }); }); + + describe("Building diffs for asymmetric equality testers", function() { + it("diffs the values returned by valuesForDiff_", function() { + var tester = { + asymmetricMatch: function() { return false; }, + valuesForDiff_: function() { + return { + self: 'asymmetric tester value', + other: 'other value' + } + } + }, + diffBuilder = jasmine.createSpyObj('diffBuilder', ['record', 'withPath']); + diffBuilder.withPath.and.callFake(function(p, block) { block() }); + debugger; + jasmineUnderTest.matchersUtil.equals({x: 42}, {x: tester}, [], diffBuilder); + + expect(diffBuilder.withPath).toHaveBeenCalledWith('x', jasmine.any(Function)); + expect(diffBuilder.record). toHaveBeenCalledWith( + 'other value', 'asymmetric tester value' + ); + }); + + it("records both objects when the tester does not implement valuesForDiff", function() { + var tester = { + asymmetricMatch: function() { return false; }, + }, + diffBuilder = jasmine.createSpyObj('diffBuilder', ['record', 'withPath']); + diffBuilder.withPath.and.callFake(function(p, block) { block() }); + debugger; + jasmineUnderTest.matchersUtil.equals({x: 42}, {x: tester}, [], diffBuilder); + + expect(diffBuilder.withPath).toHaveBeenCalledWith('x', jasmine.any(Function)); + expect(diffBuilder.record). toHaveBeenCalledWith(42, tester); + }); + }); }); describe("contains", function() { diff --git a/spec/core/matchers/toEqualSpec.js b/spec/core/matchers/toEqualSpec.js index 345eb724..ca23679f 100644 --- a/spec/core/matchers/toEqualSpec.js +++ b/spec/core/matchers/toEqualSpec.js @@ -350,6 +350,20 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); + it("reports mismatches involving objectContaining", function() { + var actual = {x: {a: 1, b: 4, c: 3, extra: 'ignored'}}; + var expected = {x: jasmineUnderTest.objectContaining({a: 1, b: 2, c: 3})}; + expect(compareEquals(actual, expected).message).toEqual('Expected $.x.b = 4 to equal 2.') + }); + + it("reports mismatches between a non-object and objectContaining", function() { + var actual = {x: 1}; + var expected = {x: jasmineUnderTest.objectContaining({a: 1})}; + expect(compareEquals(actual, expected).message).toEqual( + "Expected $.x = 1 to equal ''." + ); + }); + // == Sets == it("reports mismatches between Sets", function() { diff --git a/src/core/asymmetric_equality/ObjectContaining.js b/src/core/asymmetric_equality/ObjectContaining.js index 62e9bf17..9830fe90 100644 --- a/src/core/asymmetric_equality/ObjectContaining.js +++ b/src/core/asymmetric_equality/ObjectContaining.js @@ -41,6 +41,27 @@ getJasmineRequireObj().ObjectContaining = function(j$) { return true; }; + ObjectContaining.prototype.valuesForDiff_ = function(other) { + if (!j$.isObject_(other)) { + return { + self: this.jasmineToString(), + other: other + }; + } + + var filteredOther = {}; + Object.keys(this.sample).forEach(function (k) { + // eq short-circuits comparison of objects that have different key sets, + // so include all keys even if undefined. + filteredOther[k] = other[k]; + }); + + return { + self: this.sample, + other: filteredOther + }; + }; + ObjectContaining.prototype.jasmineToString = function() { return ''; }; diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index cfc0c749..522759a5 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -55,7 +55,16 @@ getJasmineRequireObj().matchersUtil = function(j$) { return obj && j$.isA_('Function', obj.asymmetricMatch); } - function asymmetricMatch(a, b, customTesters, diffBuilder) { + function asymmetricDiff(a, b, aStack, bStack, customTesters, diffBuilder) { + if (j$.isFunction_(b.valuesForDiff_)) { + var values = b.valuesForDiff_(a); + eq(values.other, values.self, aStack, bStack, customTesters, diffBuilder); + } else { + diffBuilder.record(a, b); + } + } + + function asymmetricMatch(a, b, aStack, bStack, customTesters, diffBuilder) { var asymmetricA = isAsymmetric(a), asymmetricB = isAsymmetric(b), result; @@ -67,6 +76,8 @@ getJasmineRequireObj().matchersUtil = function(j$) { if (asymmetricA) { result = a.asymmetricMatch(b, customTesters); if (!result) { + // TODO: Do we want to build an asymmetric diff when the actual was an + // asymmeteric equality tester? Might be confusing. diffBuilder.record(a, b); } return result; @@ -75,7 +86,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { if (asymmetricB) { result = b.asymmetricMatch(a, customTesters); if (!result) { - diffBuilder.record(a, b); + asymmetricDiff(a, b, aStack, bStack, customTesters, diffBuilder); } return result; } @@ -93,7 +104,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { function eq(a, b, aStack, bStack, customTesters, diffBuilder) { var result = true, i; - var asymmetricResult = asymmetricMatch(a, b, customTesters, diffBuilder); + var asymmetricResult = asymmetricMatch(a, b, aStack, bStack, customTesters, diffBuilder); if (!j$.util.isUndefined(asymmetricResult)) { return asymmetricResult; } From ef3f127d270ccbbd6dde3fe161e0e85474f19369 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 28 Sep 2019 18:39:43 -0700 Subject: [PATCH 091/201] Fixed comparison between ObjectContaining and non-objects on IE --- lib/jasmine-core/jasmine.js | 3 ++- src/core/asymmetric_equality/ObjectContaining.js | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index b442632e..64365dd2 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -2495,7 +2495,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } function hasProperty(obj, property) { - if (!obj) { + if (!obj || typeof(obj) !== 'object') { return false; } @@ -2508,6 +2508,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { ObjectContaining.prototype.asymmetricMatch = function(other, customTesters) { if (typeof(this.sample) !== 'object') { throw new Error('You must provide an object to objectContaining, not \''+this.sample+'\'.'); } + // TODO: This succeeds when sample is an empty object and other is a non-object, but should probably fail for (var property in this.sample) { if (!hasProperty(other, property) || diff --git a/src/core/asymmetric_equality/ObjectContaining.js b/src/core/asymmetric_equality/ObjectContaining.js index 9830fe90..d2da5c05 100644 --- a/src/core/asymmetric_equality/ObjectContaining.js +++ b/src/core/asymmetric_equality/ObjectContaining.js @@ -17,7 +17,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } function hasProperty(obj, property) { - if (!obj) { + if (!obj || typeof(obj) !== 'object') { return false; } @@ -30,6 +30,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { ObjectContaining.prototype.asymmetricMatch = function(other, customTesters) { if (typeof(this.sample) !== 'object') { throw new Error('You must provide an object to objectContaining, not \''+this.sample+'\'.'); } + // TODO: This succeeds when sample is an empty object and other is a non-object, but should probably fail for (var property in this.sample) { if (!hasProperty(other, property) || From 97fe2e7c95e92e185bc83591f589fe01f0859a64 Mon Sep 17 00:00:00 2001 From: Nicolas DUBIEN Date: Thu, 31 Oct 2019 00:27:20 +0100 Subject: [PATCH 092/201] Fix: Jasmine reports toEqual(0, Number.MIN_VALUE) to be true --- lib/jasmine-core/jasmine.js | 2 +- spec/core/matchers/toEqualSpec.js | 8 ++++++++ src/core/matchers/matchersUtil.js | 2 +- 3 files changed, 10 insertions(+), 2 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 64365dd2..5321f2d0 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -4321,7 +4321,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { case '[object Number]': // `NaN`s are equivalent, but non-reflexive. An `egal` comparison is performed for // other numeric values. - result = a != +a ? b != +b : (a === 0 ? 1 / a == 1 / b : a == +b); + result = a != +a ? b != +b : (a === 0 && b === 0 ? 1 / a == 1 / b : a == +b); if (!result) { diffBuilder.record(a, b); } diff --git a/spec/core/matchers/toEqualSpec.js b/spec/core/matchers/toEqualSpec.js index ca23679f..69651a81 100644 --- a/spec/core/matchers/toEqualSpec.js +++ b/spec/core/matchers/toEqualSpec.js @@ -334,6 +334,14 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); + it("reports mismatches between 0 and Number.MIN_VALUE", function() { + var actual = {x: 0}, + expected = {x: Number.MIN_VALUE}, + message = "Expected $.x = 0 to equal 5e-324."; + + expect(compareEquals(actual, expected).message).toEqual(message); + }); + it("reports mismatches between Errors", function() { var actual = {x: new Error("the error you got")}, expected = {x: new Error("the error you want")}, diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index 522759a5..7183d5e7 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -162,7 +162,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { case '[object Number]': // `NaN`s are equivalent, but non-reflexive. An `egal` comparison is performed for // other numeric values. - result = a != +a ? b != +b : (a === 0 ? 1 / a == 1 / b : a == +b); + result = a != +a ? b != +b : (a === 0 && b === 0 ? 1 / a == 1 / b : a == +b); if (!result) { diffBuilder.record(a, b); } From 71631a6529b7241a146b60cf0ce9623b1f219157 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 2 Nov 2019 13:14:49 -0700 Subject: [PATCH 093/201] Test IE before other browsers on Travis If the tests only fail on one browser, it's usually IE. So testing IE first gives us faster feedback in cases where we're actively watching the Travis build. --- .travis.yml | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/.travis.yml b/.travis.yml index b6b2209d..b0f0775f 100644 --- a/.travis.yml +++ b/.travis.yml @@ -18,6 +18,14 @@ env: matrix: include: + - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=11 SAUCE_OS="Windows 8.1" + if: type != pull_request + addons: + sauce_connect: true + - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=10 SAUCE_OS="Windows 8" + if: type != pull_request + addons: + sauce_connect: true - env: JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='' SAUCE_OS="Linux" if: type != pull_request addons: @@ -42,11 +50,3 @@ matrix: if: type != pull_request addons: sauce_connect: true - - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=11 SAUCE_OS="Windows 8.1" - if: type != pull_request - addons: - sauce_connect: true - - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=10 SAUCE_OS="Windows 8" - if: type != pull_request - addons: - sauce_connect: true From 8d53f4d202f86a11cbd3496469a1c5afd10cb836 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 2 Nov 2019 14:22:16 -0700 Subject: [PATCH 094/201] Fixed objectContaining to not match when the expected is the empty object and the actual is a non-object --- lib/jasmine-core/jasmine.js | 2 +- .../core/asymmetric_equality/ObjectContainingSpec.js | 12 ++++++++++-- src/core/asymmetric_equality/ObjectContaining.js | 2 +- 3 files changed, 12 insertions(+), 4 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 5321f2d0..25adbf80 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -2508,7 +2508,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { ObjectContaining.prototype.asymmetricMatch = function(other, customTesters) { if (typeof(this.sample) !== 'object') { throw new Error('You must provide an object to objectContaining, not \''+this.sample+'\'.'); } - // TODO: This succeeds when sample is an empty object and other is a non-object, but should probably fail + if (typeof(other) !== 'object') { return false; } for (var property in this.sample) { if (!hasProperty(other, property) || diff --git a/spec/core/asymmetric_equality/ObjectContainingSpec.js b/spec/core/asymmetric_equality/ObjectContainingSpec.js index b17fd925..cdcbf19f 100644 --- a/spec/core/asymmetric_equality/ObjectContainingSpec.js +++ b/spec/core/asymmetric_equality/ObjectContainingSpec.js @@ -1,9 +1,17 @@ describe("ObjectContaining", function() { - it("matches any actual to an empty object", function() { + it("matches any object actual to an empty object", function() { var containing = new jasmineUnderTest.ObjectContaining({}); - expect(containing.asymmetricMatch("foo")).toBe(true); + expect(containing.asymmetricMatch({foo: 1})).toBe(true); + }); + + it("does not match when the actual is not an object", function() { + var containing = new jasmineUnderTest.ObjectContaining({}); + + [1, true, undefined, "a string"].forEach(function(actual) { + expect(containing.asymmetricMatch(actual)).toBe(false); + }); }); it("does not match an empty object actual", function() { diff --git a/src/core/asymmetric_equality/ObjectContaining.js b/src/core/asymmetric_equality/ObjectContaining.js index d2da5c05..a0d69135 100644 --- a/src/core/asymmetric_equality/ObjectContaining.js +++ b/src/core/asymmetric_equality/ObjectContaining.js @@ -30,7 +30,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { ObjectContaining.prototype.asymmetricMatch = function(other, customTesters) { if (typeof(this.sample) !== 'object') { throw new Error('You must provide an object to objectContaining, not \''+this.sample+'\'.'); } - // TODO: This succeeds when sample is an empty object and other is a non-object, but should probably fail + if (typeof(other) !== 'object') { return false; } for (var property in this.sample) { if (!hasProperty(other, property) || From 076093c16c9641882c4089438de34554b343fd69 Mon Sep 17 00:00:00 2001 From: Adam Milligan Date: Mon, 4 Nov 2019 11:38:53 -0500 Subject: [PATCH 095/201] Properly import jasmineRequire object before using --- lib/jasmine-core/boot.js | 1 + lib/jasmine-core/jasmine-html.js | 3 +++ 2 files changed, 4 insertions(+) diff --git a/lib/jasmine-core/boot.js b/lib/jasmine-core/boot.js index aa501180..fcd11f1b 100644 --- a/lib/jasmine-core/boot.js +++ b/lib/jasmine-core/boot.js @@ -31,6 +31,7 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ (function() { + var jasmineRequire = window.jasmineRequire || require('./jasmine.js'); /** * ## Require & Instantiate diff --git a/lib/jasmine-core/jasmine-html.js b/lib/jasmine-core/jasmine-html.js index aecf2f1b..d08611de 100644 --- a/lib/jasmine-core/jasmine-html.js +++ b/lib/jasmine-core/jasmine-html.js @@ -20,6 +20,9 @@ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ + +var jasmineRequire = window.jasmineRequire || require('./jasmine.js'); + jasmineRequire.html = function(j$) { j$.ResultsNode = jasmineRequire.ResultsNode(); j$.HtmlReporter = jasmineRequire.HtmlReporter(j$); From 3d1a96e020e97ceb20d3944fdd42bad81509e0b2 Mon Sep 17 00:00:00 2001 From: Adam Milligan Date: Tue, 5 Nov 2019 10:54:46 -0500 Subject: [PATCH 096/201] Extend Jasmine env into correct global --- lib/jasmine-core/boot.js | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/lib/jasmine-core/boot.js b/lib/jasmine-core/boot.js index fcd11f1b..b46871cf 100644 --- a/lib/jasmine-core/boot.js +++ b/lib/jasmine-core/boot.js @@ -38,7 +38,9 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. * * Require Jasmine's core files. Specifically, this requires and attaches all of Jasmine's code to the `jasmine` reference. */ - window.jasmine = jasmineRequire.core(jasmineRequire); + var jasmine = jasmineRequire.core(jasmineRequire), + global = jasmine.getGlobal(); + global.jasmine = jasmine; /** * Since this is being run in a browser and the results should populate to an HTML page, require the HTML-specific Jasmine code, injecting the same reference. @@ -60,7 +62,7 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. /** * Add all of the Jasmine global/public interface to the global scope, so a project can use the public interface directly. For example, calling `describe` in specs instead of `jasmine.getEnv().describe`. */ - extend(window, jasmineInterface); + extend(global, jasmineInterface); /** * ## Runner Parameters From 795a80ec6663c496699e7f31bc70f13c13b5a256 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sun, 22 Sep 2019 12:07:23 -0700 Subject: [PATCH 097/201] Added integration tests for asymmetric equality testers --- .../AsymmetricEqualityTestersSpec.js | 222 ++++++++++++++++++ spec/core/integration/MatchersSpec.js | 27 ++- spec/helpers/checkForMap.js | 6 +- spec/helpers/checkForSet.js | 6 +- 4 files changed, 249 insertions(+), 12 deletions(-) create mode 100644 spec/core/integration/AsymmetricEqualityTestersSpec.js diff --git a/spec/core/integration/AsymmetricEqualityTestersSpec.js b/spec/core/integration/AsymmetricEqualityTestersSpec.js new file mode 100644 index 00000000..1ccf2801 --- /dev/null +++ b/spec/core/integration/AsymmetricEqualityTestersSpec.js @@ -0,0 +1,222 @@ +describe('Asymmetric equality testers (Integration)', function () { + function verifyPasses(expectations, setup) { + it('passes', function (done) { + var env = new jasmineUnderTest.Env(); + env.it('a spec', function () { + expectations(env); + }); + + var specExpectations = function (result) { + expect(result.status).toEqual('passed'); + expect(result.passedExpectations.length) + .withContext('Number of passed expectations') + .toEqual(1); + expect(result.failedExpectations.length) + .withContext('Number of failed expectations') + .toEqual(0); + expect(result.failedExpectations[0] && result.failedExpectations[0].message) + .withContext('Failure message') + .toBeUndefined(); + }; + + env.addReporter({specDone: specExpectations, jasmineDone: done}); + env.execute(); + }); + } + + function verifyFails(expectations) { + it('fails', function (done) { + var env = new jasmineUnderTest.Env(); + env.it('a spec', function () { + expectations(env); + }); + + var specExpectations = function (result) { + expect(result.status).toEqual('failed'); + expect(result.failedExpectations.length) + .withContext('Number of failed expectations') + .toEqual(1); + expect(result.failedExpectations[0].message) + .withContext('Failed with a thrown error rather than a matcher failure') + .not.toMatch(/^Error: /); + expect(result.failedExpectations[0].matcherName).withContext('Matcher name') + .not.toEqual(''); + }; + + env.addReporter({specDone: specExpectations, jasmineDone: done}); + env.execute(); + }); + } + + describe('any', function () { + verifyPasses(function (env) { + env.expect(5).toEqual(jasmineUnderTest.any(Number)); + }); + + verifyFails(function (env) { + env.expect("five").toEqual(jasmineUnderTest.any(Number)); + }); + }); + + describe('anything', function () { + verifyPasses(function (env) { + env.expect('').toEqual(jasmineUnderTest.anything()); + }); + + verifyFails(function (env) { + env.expect(null).toEqual(jasmineUnderTest.anything()); + }); + }); + + describe('arrayContaining', function () { + verifyPasses(function (env) { + env.addCustomEqualityTester(function (a, b) { + return a.toString() === b.toString(); + }); + env.expect([1, 2, 3]).toEqual(jasmineUnderTest.arrayContaining(["2"])); + }); + + verifyFails(function (env) { + env.expect(null).toEqual(jasmineUnderTest.arrayContaining([2])); + }); + }); + + describe('arrayWithExactContents', function () { + verifyPasses(function (env) { + env.addCustomEqualityTester(function (a, b) { + return a.toString() === b.toString(); + }); + env.expect([1, 2]).toEqual(jasmineUnderTest.arrayWithExactContents(["2", "1"])); + }); + + verifyFails(function (env) { + env.expect([]).toEqual(jasmineUnderTest.arrayWithExactContents([2])); + }); + }); + + describe('empty', function () { + verifyPasses(function (env) { + env.expect([]).toEqual(jasmineUnderTest.empty()); + }); + + verifyFails(function (env) { + env.expect([1]).toEqual(jasmineUnderTest.empty()); + }); + }); + + describe('falsy', function () { + verifyPasses(function (env) { + env.expect(false).toEqual(jasmineUnderTest.falsy()); + }); + + verifyFails(function (env) { + env.expect(true).toEqual(jasmineUnderTest.falsy()); + }); + }); + + describe('mapContaining', function () { + if (jasmine.getEnv().hasFunctioningMaps()) { + verifyPasses(function (env) { + var actual = new Map(); + actual.set('a', "2"); + var expected = new Map(); + expected.set('a', 2); + + env.addCustomEqualityTester(function (a, b) { + return a.toString() === b.toString(); + }); + + env.expect(actual).toEqual(jasmineUnderTest.mapContaining(expected)); + }); + } else { + it('passes', function() { + jasmine.getEnv().pending('Browser has incomplete or missing support for Maps'); + }); + } + + if (jasmine.getEnv().hasFunctioningMaps()) { + verifyFails(function (env) { + env.expect('something').toEqual(jasmineUnderTest.mapContaining(new Map())); + }); + } else { + it('fails', function() { + jasmine.getEnv().pending('Browser has incomplete or missing support for Maps'); + }); + } + }); + + describe('notEmpty', function () { + verifyPasses(function (env) { + env.expect([1]).toEqual(jasmineUnderTest.notEmpty()); + }); + + verifyFails(function (env) { + env.expect([]).toEqual(jasmineUnderTest.notEmpty()); + }); + }); + + describe('objectContaining', function () { + verifyPasses(function (env) { + env.addCustomEqualityTester(function (a, b) { + return a.toString() === b.toString(); + }); + + env.expect({a: 1, b: 2}).toEqual(jasmineUnderTest.objectContaining({a: "1"})); + }); + + verifyFails(function (env) { + env.expect({}).toEqual(jasmineUnderTest.objectContaining({a: "1"})); + }); + }); + + describe('setContaining', function () { + if (jasmine.getEnv().hasFunctioningSets()) { + verifyPasses(function (env) { + var actual = new Set(); + actual.add("1"); + var expected = new Set(); + actual.add(1); + + env.addCustomEqualityTester(function (a, b) { + return a.toString() === b.toString(); + }); + + env.expect(actual).toEqual(jasmineUnderTest.setContaining(expected)); + }); + } else { + it('pases', function() { + jasmine.getEnv().pending('Browser has incomplete or missing support for Sets'); + }); + } + + if (jasmine.getEnv().hasFunctioningSets()) { + verifyFails(function (env) { + env.expect('something').toEqual(jasmineUnderTest.setContaining(new Set())); + }); + } else { + it('fails', function() { + jasmine.getEnv().pending('Browser has incomplete or missing support for Sets'); + }); + } + }); + + describe('stringMatching', function () { + verifyPasses(function (env) { + env.expect('foo').toEqual(jasmineUnderTest.stringMatching(/o/)); + }); + + verifyFails(function (env) { + env.expect('bar').toEqual(jasmineUnderTest.stringMatching(/o/)); + }); + }); + + describe('truthy', function () { + verifyPasses(function (env) { + env.expect(true).toEqual(jasmineUnderTest.truthy()); + }); + + verifyFails(function (env) { + env.expect(false).toEqual(jasmineUnderTest.truthy()); + }); + }); +}); diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js index f75aae28..6f81ea04 100644 --- a/spec/core/integration/MatchersSpec.js +++ b/spec/core/integration/MatchersSpec.js @@ -261,7 +261,10 @@ describe('Matchers (Integration)', function() { describe('toBeResolvedTo', function() { verifyPassesAsync(function(env) { - return env.expectAsync(Promise.resolve('foo')).toBeResolvedTo('foo'); + env.addCustomEqualityTester(function(a, b) { + return a.toString() === b.toString(); + }); + return env.expectAsync(Promise.resolve('5')).toBeResolvedTo(5); }); verifyFailsAsync(function(env) { @@ -281,7 +284,10 @@ describe('Matchers (Integration)', function() { describe('toBeRejectedWith', function() { verifyPassesAsync(function(env) { - return env.expectAsync(Promise.reject('nope')).toBeRejectedWith('nope'); + env.addCustomEqualityTester(function(a, b) { + return a.toString() === b.toString(); + }); + return env.expectAsync(Promise.reject('5')).toBeRejectedWith(5); }); verifyFailsAsync(function(env) { @@ -331,7 +337,10 @@ describe('Matchers (Integration)', function() { describe('toContain', function() { verifyPasses(function(env) { - env.expect('foobar').toContain('oo'); + env.addCustomEqualityTester(function(a, b) { + return a.toString() === b.toString(); + }); + env.expect(['1', '2', '3']).toContain(2); }); verifyFails(function(env) { @@ -341,7 +350,10 @@ describe('Matchers (Integration)', function() { describe('toEqual', function() { verifyPasses(function(env) { - env.expect('a').toEqual('a'); + env.addCustomEqualityTester(function(a, b) { + return a.toString() === b.toString(); + }); + env.expect(5).toEqual('5'); }); verifyFails(function(env) { @@ -394,8 +406,11 @@ describe('Matchers (Integration)', function() { describe('toHaveBeenCalledWith', function() { verifyPasses(function(env) { var spy = env.createSpy(); - spy('foo'); - env.expect(spy).toHaveBeenCalledWith('foo'); + spy('5'); + env.addCustomEqualityTester(function(a, b) { + return a.toString() === b.toString(); + }); + env.expect(spy).toHaveBeenCalledWith(5); }); verifyFails(function(env) { diff --git a/spec/helpers/checkForMap.js b/spec/helpers/checkForMap.js index 64e32cdc..46e346a8 100644 --- a/spec/helpers/checkForMap.js +++ b/spec/helpers/checkForMap.js @@ -1,5 +1,5 @@ (function(env) { - function hasFunctioningMaps() { + env.hasFunctioningMaps = function() { if (typeof Map === 'undefined') { return false; } @@ -36,10 +36,10 @@ } catch (e) { return false; } - } + }; env.requireFunctioningMaps = function() { - if (!hasFunctioningMaps()) { + if (!env.hasFunctioningMaps()) { env.pending('Browser has incomplete or missing support for Maps'); } }; diff --git a/spec/helpers/checkForSet.js b/spec/helpers/checkForSet.js index 1be8de45..dacb06aa 100644 --- a/spec/helpers/checkForSet.js +++ b/spec/helpers/checkForSet.js @@ -1,5 +1,5 @@ (function(env) { - function hasFunctioningSets() { + env.hasFunctioningSets = function() { if (typeof Set === 'undefined') { return false; } @@ -40,10 +40,10 @@ } catch (e) { return false; } - } + }; env.requireFunctioningSets = function() { - if (!hasFunctioningSets()) { + if (!env.hasFunctioningSets()) { env.pending('Browser has incomplete or missing support for Sets'); } }; From a00f995c681a693c8117ce4ece96f186892a8d59 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 21 Sep 2019 14:18:32 -0700 Subject: [PATCH 098/201] Added integration tests for existing matcher interfaces --- .../integration/CustomAsyncMatchersSpec.js | 36 +++++++++++++++++ spec/core/integration/CustomMatchersSpec.js | 40 +++++++++++++++++-- 2 files changed, 72 insertions(+), 4 deletions(-) diff --git a/spec/core/integration/CustomAsyncMatchersSpec.js b/spec/core/integration/CustomAsyncMatchersSpec.js index 0849e42a..51ddef34 100644 --- a/spec/core/integration/CustomAsyncMatchersSpec.js +++ b/spec/core/integration/CustomAsyncMatchersSpec.js @@ -75,4 +75,40 @@ describe('Custom Async Matchers (Integration)', function() { env.addReporter({ specDone: specExpectations, jasmineDone: done }); env.execute(); }); + + // TODO: remove this in the next major release. + it("passes the jasmine utility and current equality testers to the matcher factory", function(done) { + jasmine.getEnv().requirePromises(); + + var matcherFactory = function () { + return { + compare: function () { + return Promise.resolve({pass: true}); + } + }; + }, + matcherFactorySpy = jasmine.createSpy("matcherFactorySpy").and.callFake(matcherFactory), + customEqualityFn = function () { + return true; + }; + + env.it("spec with expectation", function() { + env.addCustomEqualityTester(customEqualityFn); + env.addAsyncMatchers({ + toBeReal: matcherFactorySpy + }); + + return env.expectAsync(true).toBeReal(); + }); + + var specExpectations = function() { + expect(matcherFactorySpy).toHaveBeenCalledWith( + jasmine.any(jasmineUnderTest.MatchersUtil), + [customEqualityFn] + ); + }; + + env.addReporter({ specDone: specExpectations, jasmineDone: done }); + env.execute(); + }); }); diff --git a/spec/core/integration/CustomMatchersSpec.js b/spec/core/integration/CustomMatchersSpec.js index 17e66354..4bb0c352 100644 --- a/spec/core/integration/CustomMatchersSpec.js +++ b/spec/core/integration/CustomMatchersSpec.js @@ -81,6 +81,34 @@ describe("Custom Matchers (Integration)", function() { env.execute(); }); + it("supports asymmetric equality testers that take a list of custom equality testers", function(done) { + // TODO: remove this in the next major release. + env.it("spec using custom asymmetric equality tester", function() { + var customEqualityFn = function(a, b) { + if (a === 2 && b === "two") { + return true; + } + }; + var arrayWithFirstElement = function(sample) { + return { + asymmetricMatch: function (actual, customEqualityTesters) { + return jasmineUnderTest.matchersUtil.equals(sample, actual[0], customEqualityTesters); + } + }; + }; + + env.addCustomEqualityTester(customEqualityFn); + env.expect(["two"]).toEqual(arrayWithFirstElement(2)); + }); + + var specExpectations = function(result) { + expect(result.status).toEqual('passed'); + }; + + env.addReporter({ specDone: specExpectations, jasmineDone: done }); + env.execute(); + }); + it("displays an appropriate failure message if a custom equality matcher fails", function(done) { env.it("spec using custom equality matcher", function() { var customEqualityFn = function(a, b) { @@ -175,23 +203,27 @@ describe("Custom Matchers (Integration)", function() { env.execute(); }); - it("passes the jasmine utility and current equality matchers to the expectation factory", function(done) { + // TODO: remove this in the next major release. + it("passes the jasmine utility and current equality testers to the matcher factory", function(done) { var matcherFactory = function() { return { compare: function() { return {pass: true}; }}; }, - argumentSpy = jasmine.createSpy("argument spy").and.returnValue(matcherFactory), + matcherFactorySpy = jasmine.createSpy("matcherFactorySpy").and.callFake(matcherFactory), customEqualityFn = function() { return true; }; env.it("spec with expectation", function() { env.addCustomEqualityTester(customEqualityFn); env.addMatchers({ - toBeReal: argumentSpy + toBeReal: matcherFactorySpy }); env.expect(true).toBeReal(); }); var specExpectations = function() { - expect(argumentSpy).toHaveBeenCalledWith(jasmineUnderTest.matchersUtil, [customEqualityFn]); + expect(matcherFactorySpy).toHaveBeenCalledWith( + jasmine.any(jasmineUnderTest.MatchersUtil), + [customEqualityFn] + ); }; env.addReporter({ specDone: specExpectations, jasmineDone: done }); From 13ff1e037e86378a8aa49e7a0003c96c86a7a905 Mon Sep 17 00:00:00 2001 From: Adam Milligan Date: Fri, 22 Nov 2019 17:47:20 -0500 Subject: [PATCH 099/201] Make changes in source files --- lib/jasmine-core/boot/boot.js | 7 +++++-- lib/jasmine-core/jasmine-html.js | 1 - src/html/requireHtml.js | 2 ++ 3 files changed, 7 insertions(+), 3 deletions(-) diff --git a/lib/jasmine-core/boot/boot.js b/lib/jasmine-core/boot/boot.js index 2d684628..e1e20f1c 100644 --- a/lib/jasmine-core/boot/boot.js +++ b/lib/jasmine-core/boot/boot.js @@ -9,13 +9,16 @@ */ (function() { + var jasmineRequire = window.jasmineRequire || require('./jasmine.js'); /** * ## Require & Instantiate * * Require Jasmine's core files. Specifically, this requires and attaches all of Jasmine's code to the `jasmine` reference. */ - window.jasmine = jasmineRequire.core(jasmineRequire); + var jasmine = jasmineRequire.core(jasmineRequire), + global = jasmine.getGlobal(); + global.jasmine = jasmine; /** * Since this is being run in a browser and the results should populate to an HTML page, require the HTML-specific Jasmine code, injecting the same reference. @@ -37,7 +40,7 @@ /** * Add all of the Jasmine global/public interface to the global scope, so a project can use the public interface directly. For example, calling `describe` in specs instead of `jasmine.getEnv().describe`. */ - extend(window, jasmineInterface); + extend(global, jasmineInterface); /** * ## Runner Parameters diff --git a/lib/jasmine-core/jasmine-html.js b/lib/jasmine-core/jasmine-html.js index d08611de..a727d01e 100644 --- a/lib/jasmine-core/jasmine-html.js +++ b/lib/jasmine-core/jasmine-html.js @@ -20,7 +20,6 @@ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ - var jasmineRequire = window.jasmineRequire || require('./jasmine.js'); jasmineRequire.html = function(j$) { diff --git a/src/html/requireHtml.js b/src/html/requireHtml.js index b60c3ba5..a8fe2a1e 100644 --- a/src/html/requireHtml.js +++ b/src/html/requireHtml.js @@ -1,3 +1,5 @@ +var jasmineRequire = window.jasmineRequire || require('./jasmine.js'); + jasmineRequire.html = function(j$) { j$.ResultsNode = jasmineRequire.ResultsNode(); j$.HtmlReporter = jasmineRequire.HtmlReporter(j$); From 6c766b7785436fd7917647b86bbd8c573a5deab1 Mon Sep 17 00:00:00 2001 From: John Lin Date: Mon, 16 Dec 2019 12:21:59 +0800 Subject: [PATCH 100/201] Describe the naming for the function it() When I first saw it(), I was wondering if the name "it" is an abbreviation of anything. After some search, I finally realized that the name is only a pronoun. Therefore, I think it's worthwhile to include it in the documentation. --- src/core/requireInterface.js | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/core/requireInterface.js b/src/core/requireInterface.js index f8f15ac6..012f7303 100644 --- a/src/core/requireInterface.js +++ b/src/core/requireInterface.js @@ -60,6 +60,9 @@ getJasmineRequireObj().interface = function(jasmine, env) { * Define a single spec. A spec should contain one or more {@link expect|expectations} that test the state of the code. * * A spec whose expectations all succeed will be passing and a spec with any failures will fail. + * The name `it` is a pronoun for the test target, not an abbreviation of anything. It makes the + * spec more readable by connecting the function name `it` and the argument `description` as a + * complete sentence. * @name it * @since 1.3.0 * @function From 4eded6ab6107794d3068daee863655414d947d91 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 4 Jan 2020 14:25:25 -0800 Subject: [PATCH 101/201] Added basic property tests for matchersUtil.equals * See #1764 from @dubzzz * Property tests are only run in Node, not browser. * The Travis build sets JASMINE_LONG_PROPERTY_TESTS to enable much more thorough (but slow) testing. --- .travis.yml | 1 + package.json | 1 + spec/property/matchersUtilSpec.js | 69 +++++++++++++++++++++++++++++++ spec/support/jasmine-browser.js | 2 +- spec/support/jasmine.json | 1 + 5 files changed, 73 insertions(+), 1 deletion(-) create mode 100644 spec/property/matchersUtilSpec.js diff --git a/.travis.yml b/.travis.yml index b0f0775f..a4426161 100644 --- a/.travis.yml +++ b/.travis.yml @@ -50,3 +50,4 @@ matrix: if: type != pull_request addons: sauce_connect: true + - env: JASMINE_LONG_PROPERTY_TESTS=y diff --git a/package.json b/package.json index e2ba236f..bc602f6f 100644 --- a/package.json +++ b/package.json @@ -30,6 +30,7 @@ "ejs": "^2.5.5", "eslint": "^5.16.0", "express": "^4.16.4", + "fast-check": "^1.21.0", "fast-glob": "^2.2.6", "grunt": "^1.0.4", "grunt-cli": "^1.3.2", diff --git a/spec/property/matchersUtilSpec.js b/spec/property/matchersUtilSpec.js new file mode 100644 index 00000000..384a1f14 --- /dev/null +++ b/spec/property/matchersUtilSpec.js @@ -0,0 +1,69 @@ +describe('matchersUtil -- property tests', function() { + 'use strict'; + var fc = require('fast-check'); + + function basicAnythingSettings() { + return { + key: fc.oneof(fc.string(), fc.constantFrom('k1', 'k2', 'k3')), + // Limiting depth & number of keys allows fast-check to try + // a lot more scalar values. + maxDepth: 2, + maxKeys: 5, + withBoxedValues: true, + withMap: true, + withSet: true + }; + } + + function numRuns() { + var many = 5000000; + + // Be thorough but very slow when specified (usually on CI). + if (process.env.JASMINE_LONG_PROPERTY_TESTS) { + console.log( + 'Using', + many, + 'runs of fc.assert because JASMINE_LONG_PROPERTY_TESTS was set. This may take several minutes.' + ); + return many; + } else { + return undefined; + } + } + + describe('equals', function() { + it('is symmetric', function() { + fc.assert( + fc.property( + fc.anything(basicAnythingSettings()), + fc.anything(basicAnythingSettings()), + function(a, b) { + return ( + jasmineUnderTest.matchersUtil.equals(a, b) === + jasmineUnderTest.matchersUtil.equals(b, a) + ); + } + ), + { + numRuns: numRuns(), + examples: [[0, 5e-324]] + } + ); + }); + + it('is reflexive', function() { + var anythingSettings = basicAnythingSettings(); + anythingSettings.withMap = false; + fc.assert( + fc.property(fc.dedup(fc.anything(anythingSettings), 2), function( + values + ) { + return jasmineUnderTest.matchersUtil.equals(values[0], values[1]); + }), + { + numRuns: numRuns() + } + ); + }); + }); +}); diff --git a/spec/support/jasmine-browser.js b/spec/support/jasmine-browser.js index 41c9e703..bbc9c4ac 100644 --- a/spec/support/jasmine-browser.js +++ b/spec/support/jasmine-browser.js @@ -15,7 +15,7 @@ module.exports = { '**/*.js' ], specDir: 'spec', - specFiles: ['**/*[Ss]pec.js', '!npmPackage/**/*'], + specFiles: ['**/*[Ss]pec.js', '!npmPackage/**/*', '!property/**/*'], helpers: [ 'helpers/asyncAwait.js', 'helpers/BrowserFlags.js', diff --git a/spec/support/jasmine.json b/spec/support/jasmine.json index 033207ec..6ce73409 100644 --- a/spec/support/jasmine.json +++ b/spec/support/jasmine.json @@ -2,6 +2,7 @@ "spec_dir": "spec", "spec_files": [ "core/**/*[Ss]pec.js", + "property/**/*[Ss]pec.js", "npmPackage/**/*[Ss]pec.js" ], "helpers": [ From 88b98277bcf0d57463ceb5c1465cfe26b3aa2b73 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 4 Jan 2020 16:13:57 -0800 Subject: [PATCH 102/201] Fixed Travis build --- .travis.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index a4426161..4ad46565 100644 --- a/.travis.yml +++ b/.travis.yml @@ -10,6 +10,7 @@ env: global: - USE_SAUCE=true - TEST_COMMAND="bash travis-core-script.sh" + - JASMINE_LONG_PROPERTY_TESTS="y" - secure: WSPWhlnC4mWSnSPquX+m1/BCu5ch5NygkaHuM2Nea7lD8oS3XLX8QncZZAsQ4lnNfqoDDuBOizG0AESiqNvE4y6x5qvLLTS6q+ce255ZEMZ71TBdZgDEEvGMEjOPPsVXiXyTQOP1lwOPlrbZvaPgWV7e11KIBab6DfFcQpnvDgo= - secure: SW7CJhZnwaNT749Gdnhvqb5rbXlAOsygUAzh9qhtyvbqXKkmJdBIEsO01YF6pbju1X2twE9JvWCOxeZju43NgQChJlPsGbjY2j3k/TdQeTAJesQe2K7ytwghunI30gjEovtRH0T3w1EmcKPH8yj5eBIcB2OYoJHx8KEC7e68q1g= matrix: @@ -50,4 +51,3 @@ matrix: if: type != pull_request addons: sauce_connect: true - - env: JASMINE_LONG_PROPERTY_TESTS=y From 12fefa4b3dbb99a471531fbf2fffddcaef8f711d Mon Sep 17 00:00:00 2001 From: Valentin Hermann Date: Tue, 7 Jan 2020 15:23:37 +0100 Subject: [PATCH 103/201] Improves method messagePrefixLength. Now error messages like ReferenceError or TypeError are considered as well --- lib/jasmine-core/jasmine.js | 810 +++++++++++++++++++++++++----------- 1 file changed, 571 insertions(+), 239 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 25adbf80..522a69a2 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1,5 +1,5 @@ /* -Copyright (c) 2008-2019 Pivotal Labs +Copyright (c) 2008-2020 Pivotal Labs Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the @@ -2236,12 +2236,11 @@ getJasmineRequireObj().JsApiReporter = function(j$) { }; getJasmineRequireObj().Any = function(j$) { - function Any(expectedObject) { if (typeof expectedObject === 'undefined') { throw new TypeError( 'jasmine.any() expects to be passed a constructor function. ' + - 'Please pass one or use jasmine.anything() to match any object.' + 'Please pass one or use jasmine.anything() to match any object.' ); } this.expectedObject = expectedObject; @@ -2286,7 +2285,6 @@ getJasmineRequireObj().Any = function(j$) { }; getJasmineRequireObj().Anything = function(j$) { - function Anything() {} Anything.prototype.asymmetricMatch = function(other) { @@ -2307,7 +2305,11 @@ getJasmineRequireObj().ArrayContaining = function(j$) { ArrayContaining.prototype.asymmetricMatch = function(other, customTesters) { if (!j$.isArray_(this.sample)) { - throw new Error('You must provide an array to arrayContaining, not ' + j$.pp(this.sample) + '.'); + throw new Error( + 'You must provide an array to arrayContaining, not ' + + j$.pp(this.sample) + + '.' + ); } // If the actual parameter is not an array, we can fail immediately, since it couldn't @@ -2327,22 +2329,28 @@ getJasmineRequireObj().ArrayContaining = function(j$) { return true; }; - ArrayContaining.prototype.jasmineToString = function () { - return ''; + ArrayContaining.prototype.jasmineToString = function() { + return ''; }; return ArrayContaining; }; getJasmineRequireObj().ArrayWithExactContents = function(j$) { - function ArrayWithExactContents(sample) { this.sample = sample; } - ArrayWithExactContents.prototype.asymmetricMatch = function(other, customTesters) { + ArrayWithExactContents.prototype.asymmetricMatch = function( + other, + customTesters + ) { if (!j$.isArray_(this.sample)) { - throw new Error('You must provide an array to arrayWithExactContents, not ' + j$.pp(this.sample) + '.'); + throw new Error( + 'You must provide an array to arrayWithExactContents, not ' + + j$.pp(this.sample) + + '.' + ); } if (this.sample.length !== other.length) { @@ -2366,11 +2374,10 @@ getJasmineRequireObj().ArrayWithExactContents = function(j$) { return ArrayWithExactContents; }; -getJasmineRequireObj().Empty = function (j$) { - +getJasmineRequireObj().Empty = function(j$) { function Empty() {} - Empty.prototype.asymmetricMatch = function (other) { + Empty.prototype.asymmetricMatch = function(other) { if (j$.isString_(other) || j$.isArray_(other) || j$.isTypedArray_(other)) { return other.length === 0; } @@ -2385,7 +2392,7 @@ getJasmineRequireObj().Empty = function (j$) { return false; }; - Empty.prototype.jasmineToString = function () { + Empty.prototype.jasmineToString = function() { return ''; }; @@ -2393,7 +2400,6 @@ getJasmineRequireObj().Empty = function (j$) { }; getJasmineRequireObj().Falsy = function(j$) { - function Falsy() {} Falsy.prototype.asymmetricMatch = function(other) { @@ -2410,7 +2416,9 @@ getJasmineRequireObj().Falsy = function(j$) { getJasmineRequireObj().MapContaining = function(j$) { function MapContaining(sample) { if (!j$.isMap(sample)) { - throw new Error('You must provide a map to `mapContaining`, not ' + j$.pp(sample)); + throw new Error( + 'You must provide a map to `mapContaining`, not ' + j$.pp(sample) + ); } this.sample = sample; @@ -2426,8 +2434,8 @@ getJasmineRequireObj().MapContaining = function(j$) { var hasMatch = false; j$.util.forEachBreakable(other, function(oBreakLoop, oValue, oKey) { if ( - j$.matchersUtil.equals(oKey, key, customTesters) - && j$.matchersUtil.equals(oValue, value, customTesters) + j$.matchersUtil.equals(oKey, key, customTesters) && + j$.matchersUtil.equals(oValue, value, customTesters) ) { hasMatch = true; oBreakLoop(); @@ -2449,11 +2457,10 @@ getJasmineRequireObj().MapContaining = function(j$) { return MapContaining; }; -getJasmineRequireObj().NotEmpty = function (j$) { - +getJasmineRequireObj().NotEmpty = function(j$) { function NotEmpty() {} - NotEmpty.prototype.asymmetricMatch = function (other) { + NotEmpty.prototype.asymmetricMatch = function(other) { if (j$.isString_(other) || j$.isArray_(other) || j$.isTypedArray_(other)) { return other.length !== 0; } @@ -2469,7 +2476,7 @@ getJasmineRequireObj().NotEmpty = function (j$) { return false; }; - NotEmpty.prototype.jasmineToString = function () { + NotEmpty.prototype.jasmineToString = function() { return ''; }; @@ -2477,7 +2484,6 @@ getJasmineRequireObj().NotEmpty = function (j$) { }; getJasmineRequireObj().ObjectContaining = function(j$) { - function ObjectContaining(sample) { this.sample = sample; } @@ -2495,7 +2501,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } function hasProperty(obj, property) { - if (!obj || typeof(obj) !== 'object') { + if (!obj || typeof obj !== 'object') { return false; } @@ -2507,12 +2513,26 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } ObjectContaining.prototype.asymmetricMatch = function(other, customTesters) { - if (typeof(this.sample) !== 'object') { throw new Error('You must provide an object to objectContaining, not \''+this.sample+'\'.'); } - if (typeof(other) !== 'object') { return false; } + if (typeof this.sample !== 'object') { + throw new Error( + "You must provide an object to objectContaining, not '" + + this.sample + + "'." + ); + } + if (typeof other !== 'object') { + return false; + } for (var property in this.sample) { - if (!hasProperty(other, property) || - !j$.matchersUtil.equals(this.sample[property], other[property], customTesters)) { + if ( + !hasProperty(other, property) || + !j$.matchersUtil.equals( + this.sample[property], + other[property], + customTesters + ) + ) { return false; } } @@ -2529,7 +2549,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } var filteredOther = {}; - Object.keys(this.sample).forEach(function (k) { + Object.keys(this.sample).forEach(function(k) { // eq short-circuits comparison of objects that have different key sets, // so include all keys even if undefined. filteredOther[k] = other[k]; @@ -2551,7 +2571,9 @@ getJasmineRequireObj().ObjectContaining = function(j$) { getJasmineRequireObj().SetContaining = function(j$) { function SetContaining(sample) { if (!j$.isSet(sample)) { - throw new Error('You must provide a set to `setContaining`, not ' + j$.pp(sample)); + throw new Error( + 'You must provide a set to `setContaining`, not ' + j$.pp(sample) + ); } this.sample = sample; @@ -2589,7 +2611,6 @@ getJasmineRequireObj().SetContaining = function(j$) { }; getJasmineRequireObj().StringMatching = function(j$) { - function StringMatching(expected) { if (!j$.isString_(expected) && !j$.isA_('RegExp', expected)) { throw new Error('Expected is not a String or a RegExp'); @@ -2610,7 +2631,6 @@ getJasmineRequireObj().StringMatching = function(j$) { }; getJasmineRequireObj().Truthy = function(j$) { - function Truthy() {} Truthy.prototype.asymmetricMatch = function(other) { @@ -3885,8 +3905,12 @@ getJasmineRequireObj().toBeRejected = function(j$) { throw new Error('Expected toBeRejected to be called on a promise.'); } return actual.then( - function() { return {pass: false}; }, - function() { return {pass: true}; } + function() { + return { pass: false }; + }, + function() { + return { pass: true }; + } ); } }; @@ -3910,35 +3934,46 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { return { compare: function(actualPromise, expectedValue) { if (!j$.isPromiseLike(actualPromise)) { - throw new Error('Expected toBeRejectedWith to be called on a promise.'); + throw new Error( + 'Expected toBeRejectedWith to be called on a promise.' + ); } function prefix(passed) { - return 'Expected a promise ' + + return ( + 'Expected a promise ' + (passed ? 'not ' : '') + - 'to be rejected with ' + j$.pp(expectedValue); + 'to be rejected with ' + + j$.pp(expectedValue) + ); } return actualPromise.then( function() { - return { - pass: false, - message: prefix(false) + ' but it was resolved.' - }; - }, - function(actualValue) { - if (util.equals(actualValue, expectedValue, customEqualityTesters)) { - return { - pass: true, - message: prefix(true) + '.' - }; - } else { return { pass: false, - message: prefix(false) + ' but it was rejected with ' + j$.pp(actualValue) + '.' + message: prefix(false) + ' but it was resolved.' }; + }, + function(actualValue) { + if ( + util.equals(actualValue, expectedValue, customEqualityTesters) + ) { + return { + pass: true, + message: prefix(true) + '.' + }; + } else { + return { + pass: false, + message: + prefix(false) + + ' but it was rejected with ' + + j$.pp(actualValue) + + '.' + }; + } } - } ); } }; @@ -3965,7 +4000,9 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return { compare: function(actualPromise, arg1, arg2) { if (!j$.isPromiseLike(actualPromise)) { - throw new Error('Expected toBeRejectedWithError to be called on a promise.'); + throw new Error( + 'Expected toBeRejectedWithError to be called on a promise.' + ); } var expected = getExpectedFromArgs(arg1, arg2); @@ -3977,7 +4014,9 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { message: 'Expected a promise to be rejected but it was resolved.' }; }, - function(actualValue) { return matchError(actualValue, expected); } + function(actualValue) { + return matchError(actualValue, expected); + } ); } }; @@ -3989,16 +4028,25 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { } if (!(actual instanceof expected.error)) { - return fail(expected, 'rejected with type ' + j$.fnNameFor(actual.constructor)); + return fail( + expected, + 'rejected with type ' + j$.fnNameFor(actual.constructor) + ); } var actualMessage = actual.message; - if (actualMessage === expected.message || typeof expected.message === 'undefined') { + if ( + actualMessage === expected.message || + typeof expected.message === 'undefined' + ) { return pass(expected); } - if (expected.message instanceof RegExp && expected.message.test(actualMessage)) { + if ( + expected.message instanceof RegExp && + expected.message.test(actualMessage) + ) { return pass(expected); } @@ -4008,18 +4056,25 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { function pass(expected) { return { pass: true, - message: 'Expected a promise not to be rejected with ' + expected.printValue + ', but it was.' + message: + 'Expected a promise not to be rejected with ' + + expected.printValue + + ', but it was.' }; } function fail(expected, message) { return { pass: false, - message: 'Expected a promise to be rejected with ' + expected.printValue + ' but it was ' + message + '.' + message: + 'Expected a promise to be rejected with ' + + expected.printValue + + ' but it was ' + + message + + '.' }; } - function getExpectedFromArgs(arg1, arg2) { var error, message; @@ -4034,12 +4089,17 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return { error: error, message: message, - printValue: j$.fnNameFor(error) + (typeof message === 'undefined' ? '' : ': ' + j$.pp(message)) + printValue: + j$.fnNameFor(error) + + (typeof message === 'undefined' ? '' : ': ' + j$.pp(message)) }; } function isErrorConstructor(value) { - return typeof value === 'function' && (value === Error || j$.isError_(value.prototype)); + return ( + typeof value === 'function' && + (value === Error || j$.isError_(value.prototype)) + ); } }; @@ -4063,8 +4123,12 @@ getJasmineRequireObj().toBeResolved = function(j$) { } return actual.then( - function() { return {pass: true}; }, - function() { return {pass: false}; } + function() { + return { pass: true }; + }, + function() { + return { pass: false }; + } ); } }; @@ -4092,14 +4156,19 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { } function prefix(passed) { - return 'Expected a promise ' + + return ( + 'Expected a promise ' + (passed ? 'not ' : '') + - 'to be resolved to ' + j$.pp(expectedValue); + 'to be resolved to ' + + j$.pp(expectedValue) + ); } return actualPromise.then( function(actualValue) { - if (util.equals(actualValue, expectedValue, customEqualityTesters)) { + if ( + util.equals(actualValue, expectedValue, customEqualityTesters) + ) { return { pass: true, message: prefix(true) + '.' @@ -4107,7 +4176,11 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { } else { return { pass: false, - message: prefix(false) + ' but it was resolved to ' + j$.pp(actualValue) + '.' + message: + prefix(false) + + ' but it was resolved to ' + + j$.pp(actualValue) + + '.' }; } }, @@ -4126,19 +4199,19 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { getJasmineRequireObj().DiffBuilder = function(j$) { return function DiffBuilder() { var path = new j$.ObjectPath(), - mismatches = []; + mismatches = []; return { - record: function (actual, expected, formatter) { + record: function(actual, expected, formatter) { formatter = formatter || defaultFormatter; mismatches.push(formatter(actual, expected, path)); }, - getMessage: function () { + getMessage: function() { return mismatches.join('\n'); }, - withPath: function (pathComponent, block) { + withPath: function(pathComponent, block) { var oldPath = path; path = path.add(pathComponent); block(); @@ -4146,13 +4219,16 @@ getJasmineRequireObj().DiffBuilder = function(j$) { } }; - function defaultFormatter (actual, expected, path) { - return 'Expected ' + - path + (path.depth() ? ' = ' : '') + + function defaultFormatter(actual, expected, path) { + return ( + 'Expected ' + + path + + (path.depth() ? ' = ' : '') + j$.pp(actual) + ' to equal ' + j$.pp(expected) + - '.'; + '.' + ); } }; }; @@ -4170,9 +4246,10 @@ getJasmineRequireObj().matchersUtil = function(j$) { return haystack.has(needle); } - if ((Object.prototype.toString.apply(haystack) === '[object Array]') || - (!!haystack && !haystack.indexOf)) - { + if ( + Object.prototype.toString.apply(haystack) === '[object Array]' || + (!!haystack && !haystack.indexOf) + ) { for (var i = 0; i < haystack.length; i++) { if (equals(haystack[i], needle, customTesters)) { return true; @@ -4190,9 +4267,12 @@ getJasmineRequireObj().matchersUtil = function(j$) { isNot = args[1], actual = args[2], expected = args.slice(3), - englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { return ' ' + s.toLowerCase(); }); + englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { + return ' ' + s.toLowerCase(); + }); - var message = 'Expected ' + + var message = + 'Expected ' + j$.pp(actual) + (isNot ? ' not ' : ' ') + englishyPredicate; @@ -4225,8 +4305,8 @@ getJasmineRequireObj().matchersUtil = function(j$) { function asymmetricMatch(a, b, aStack, bStack, customTesters, diffBuilder) { var asymmetricA = isAsymmetric(a), - asymmetricB = isAsymmetric(b), - result; + asymmetricB = isAsymmetric(b), + result; if (asymmetricA && asymmetricB) { return undefined; @@ -4261,9 +4341,17 @@ getJasmineRequireObj().matchersUtil = function(j$) { // Equality function lovingly adapted from isEqual in // [Underscore](http://underscorejs.org) function eq(a, b, aStack, bStack, customTesters, diffBuilder) { - var result = true, i; + var result = true, + i; - var asymmetricResult = asymmetricMatch(a, b, aStack, bStack, customTesters, diffBuilder); + var asymmetricResult = asymmetricMatch( + a, + b, + aStack, + bStack, + customTesters, + diffBuilder + ); if (!j$.util.isUndefined(asymmetricResult)) { return asymmetricResult; } @@ -4321,7 +4409,8 @@ getJasmineRequireObj().matchersUtil = function(j$) { case '[object Number]': // `NaN`s are equivalent, but non-reflexive. An `egal` comparison is performed for // other numeric values. - result = a != +a ? b != +b : (a === 0 && b === 0 ? 1 / a == 1 / b : a == +b); + result = + a != +a ? b != +b : a === 0 && b === 0 ? 1 / a == 1 / b : a == +b; if (!result) { diffBuilder.record(a, b); } @@ -4338,10 +4427,12 @@ getJasmineRequireObj().matchersUtil = function(j$) { return result; // RegExps are compared by their source patterns and flags. case '[object RegExp]': - return a.source == b.source && + return ( + a.source == b.source && a.global == b.global && a.multiline == b.multiline && - a.ignoreCase == b.ignoreCase; + a.ignoreCase == b.ignoreCase + ); } if (typeof a != 'object' || typeof b != 'object') { diffBuilder.record(a, b); @@ -4375,7 +4466,9 @@ getJasmineRequireObj().matchersUtil = function(j$) { while (length--) { // Linear search. Performance is inversely proportional to the number of // unique nested structures. - if (aStack[length] == a) { return bStack[length] == b; } + if (aStack[length] == a) { + return bStack[length] == b; + } } // Add the first object to the stack of traversed objects. aStack.push(a); @@ -4400,7 +4493,15 @@ getJasmineRequireObj().matchersUtil = function(j$) { diffBuilder.record(a[i], void 0, actualArrayIsLongerFormatter); result = false; } else { - result = eq(i < aLength ? a[i] : void 0, i < bLength ? b[i] : void 0, aStack, bStack, customTesters, diffBuilder) && result; + result = + eq( + i < aLength ? a[i] : void 0, + i < bLength ? b[i] : void 0, + aStack, + bStack, + customTesters, + diffBuilder + ) && result; } }); } @@ -4415,11 +4516,11 @@ getJasmineRequireObj().matchersUtil = function(j$) { var keysA = []; var keysB = []; - a.forEach( function( valueA, keyA ) { - keysA.push( keyA ); + a.forEach(function(valueA, keyA) { + keysA.push(keyA); }); - b.forEach( function( valueB, keyB ) { - keysB.push( keyB ); + b.forEach(function(valueB, keyB) { + keysB.push(keyB); }); // For both sets of keys, check they map to equal values in both maps. @@ -4440,13 +4541,30 @@ getJasmineRequireObj().matchersUtil = function(j$) { // Only use the cmpKey when one of the keys is asymmetric and the corresponding key matches, // otherwise explicitly look up the mapKey in the other Map since we want keys with unique // obj identity (that are otherwise equal) to not match. - if (isAsymmetric(mapKey) || isAsymmetric(cmpKey) && - eq(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { + if ( + isAsymmetric(mapKey) || + (isAsymmetric(cmpKey) && + eq( + mapKey, + cmpKey, + aStack, + bStack, + customTesters, + j$.NullDiffBuilder() + )) + ) { mapValueB = b.get(cmpKey); } else { mapValueB = b.get(mapKey); } - result = eq(mapValueA, mapValueB, aStack, bStack, customTesters, j$.NullDiffBuilder()); + result = eq( + mapValueA, + mapValueB, + aStack, + bStack, + customTesters, + j$.NullDiffBuilder() + ); } } @@ -4461,12 +4579,12 @@ getJasmineRequireObj().matchersUtil = function(j$) { } var valuesA = []; - a.forEach( function( valueA ) { - valuesA.push( valueA ); + a.forEach(function(valueA) { + valuesA.push(valueA); }); var valuesB = []; - b.forEach( function( valueB ) { - valuesB.push( valueB ); + b.forEach(function(valueB) { + valuesB.push(valueB); }); // For both sets, check they are all contained in the other set @@ -4490,7 +4608,14 @@ getJasmineRequireObj().matchersUtil = function(j$) { otherValue = otherValues[l]; prevStackSize = baseStack.length; // compare by value equality - found = eq(baseValue, otherValue, baseStack, otherStack, customTesters, j$.NullDiffBuilder()); + found = eq( + baseValue, + otherValue, + baseStack, + otherStack, + customTesters, + j$.NullDiffBuilder() + ); if (!found && prevStackSize !== baseStack.length) { baseStack.splice(prevStackSize); otherStack.splice(prevStackSize); @@ -4505,22 +4630,26 @@ getJasmineRequireObj().matchersUtil = function(j$) { return false; } } else { - // Objects with different constructors are not equivalent, but `Object`s // or `Array`s from different frames are. - var aCtor = a.constructor, bCtor = b.constructor; - if (aCtor !== bCtor && - isFunction(aCtor) && isFunction(bCtor) && - a instanceof aCtor && b instanceof bCtor && - !(aCtor instanceof aCtor && bCtor instanceof bCtor)) { - + var aCtor = a.constructor, + bCtor = b.constructor; + if ( + aCtor !== bCtor && + isFunction(aCtor) && + isFunction(bCtor) && + a instanceof aCtor && + b instanceof bCtor && + !(aCtor instanceof aCtor && bCtor instanceof bCtor) + ) { diffBuilder.record(a, b, constructorsAreDifferentFormatter); return false; } } // Deep compare objects. - var aKeys = keys(a, className == '[object Array]'), key; + var aKeys = keys(a, className == '[object Array]'), + key; size = aKeys.length; // Ensure that both objects contain the same number of properties before comparing deep equality. @@ -4539,7 +4668,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { } diffBuilder.withPath(key, function() { - if(!eq(a[key], b[key], aStack, bStack, customTesters, diffBuilder)) { + if (!eq(a[key], b[key], aStack, bStack, customTesters, diffBuilder)) { result = false; } }); @@ -4557,23 +4686,24 @@ getJasmineRequireObj().matchersUtil = function(j$) { } function keys(obj, isArray) { - var allKeys = Object.keys ? Object.keys(obj) : - (function(o) { + var allKeys = Object.keys + ? Object.keys(obj) + : (function(o) { var keys = []; for (var key in o) { - if (j$.util.has(o, key)) { - keys.push(key); - } + if (j$.util.has(o, key)) { + keys.push(key); + } } return keys; - })(obj); + })(obj); if (!isArray) { return allKeys; } if (allKeys.length === 0) { - return allKeys; + return allKeys; } var extraKeys = []; @@ -4592,21 +4722,25 @@ getJasmineRequireObj().matchersUtil = function(j$) { function objectKeysAreDifferentFormatter(actual, expected, path) { var missingProperties = j$.util.objectDifference(expected, actual), - extraProperties = j$.util.objectDifference(actual, expected), - missingPropertiesMessage = formatKeyValuePairs(missingProperties), - extraPropertiesMessage = formatKeyValuePairs(extraProperties), - messages = []; + extraProperties = j$.util.objectDifference(actual, expected), + missingPropertiesMessage = formatKeyValuePairs(missingProperties), + extraPropertiesMessage = formatKeyValuePairs(extraProperties), + messages = []; if (!path.depth()) { path = 'object'; } if (missingPropertiesMessage.length) { - messages.push('Expected ' + path + ' to have properties' + missingPropertiesMessage); + messages.push( + 'Expected ' + path + ' to have properties' + missingPropertiesMessage + ); } if (extraPropertiesMessage.length) { - messages.push('Expected ' + path + ' not to have properties' + extraPropertiesMessage); + messages.push( + 'Expected ' + path + ' not to have properties' + extraPropertiesMessage + ); } return messages.join('\n'); @@ -4617,17 +4751,25 @@ getJasmineRequireObj().matchersUtil = function(j$) { path = 'object'; } - return 'Expected ' + - path + ' to be a kind of ' + + return ( + 'Expected ' + + path + + ' to be a kind of ' + j$.fnNameFor(expected.constructor) + - ', but was ' + j$.pp(actual) + '.'; + ', but was ' + + j$.pp(actual) + + '.' + ); } function actualArrayIsLongerFormatter(actual, expected, path) { - return 'Unexpected ' + - path + (path.depth() ? ' = ' : '') + + return ( + 'Unexpected ' + + path + + (path.depth() ? ' = ' : '') + j$.pp(actual) + - ' in array.'; + ' in array.' + ); } function formatKeyValuePairs(obj) { @@ -4702,7 +4844,7 @@ getJasmineRequireObj().ObjectPath = function(j$) { return '.' + prop; } - return '[\'' + prop + '\']'; + return "['" + prop + "']"; } function map(array, fn) { @@ -4749,7 +4891,8 @@ getJasmineRequireObj().toBe = function(j$) { * expect(thing).toBe(realThing); */ function toBe(util) { - var tip = ' Tip: To check for deep equality, use .toEqual() instead of .toBe().'; + var tip = + ' Tip: To check for deep equality, use .toEqual() instead of .toBe().'; return { compare: function(actual, expected) { @@ -4758,7 +4901,9 @@ getJasmineRequireObj().toBe = function(j$) { }; if (typeof expected === 'object') { - result.message = util.buildFailureMessage('toBe', result.pass, actual, expected) + tip; + result.message = + util.buildFailureMessage('toBe', result.pass, actual, expected) + + tip; } return result; @@ -4788,8 +4933,13 @@ getJasmineRequireObj().toBeCloseTo = function() { } if (expected === null || actual === null) { - throw new Error('Cannot use toBeCloseTo with null. Arguments evaluated to: ' + - 'expect(' + actual + ').toBeCloseTo(' + expected + ').' + throw new Error( + 'Cannot use toBeCloseTo with null. Arguments evaluated to: ' + + 'expect(' + + actual + + ').toBeCloseTo(' + + expected + + ').' ); } @@ -4820,7 +4970,7 @@ getJasmineRequireObj().toBeDefined = function() { return { compare: function(actual) { return { - pass: (void 0 !== actual) + pass: void 0 !== actual }; } }; @@ -4896,7 +5046,6 @@ getJasmineRequireObj().toBeGreaterThan = function() { return toBeGreaterThan; }; - getJasmineRequireObj().toBeGreaterThanOrEqual = function() { /** * {@link expect} the actual value to be greater than or equal to the expected value. @@ -4921,7 +5070,10 @@ getJasmineRequireObj().toBeGreaterThanOrEqual = function() { }; getJasmineRequireObj().toBeInstanceOf = function(j$) { - var usageError = j$.formatErrorMsg('', 'expect(value).toBeInstanceOf()'); + var usageError = j$.formatErrorMsg( + '', + 'expect(value).toBeInstanceOf()' + ); /** * {@link expect} the actual to be an instance of the expected class @@ -4937,27 +5089,40 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { function toBeInstanceOf(util, customEqualityTesters) { return { compare: function(actual, expected) { - var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : j$.pp(actual), - expectedType = expected ? j$.fnNameFor(expected) : j$.pp(expected), - expectedMatcher, - pass; + var actualType = + actual && actual.constructor + ? j$.fnNameFor(actual.constructor) + : j$.pp(actual), + expectedType = expected ? j$.fnNameFor(expected) : j$.pp(expected), + expectedMatcher, + pass; try { - expectedMatcher = new j$.Any(expected); - pass = expectedMatcher.asymmetricMatch(actual); + expectedMatcher = new j$.Any(expected); + pass = expectedMatcher.asymmetricMatch(actual); } catch (error) { - throw new Error(usageError('Expected value is not a constructor function')); + throw new Error( + usageError('Expected value is not a constructor function') + ); } if (pass) { return { pass: true, - message: 'Expected instance of ' + actualType + ' not to be an instance of ' + expectedType + message: + 'Expected instance of ' + + actualType + + ' not to be an instance of ' + + expectedType }; } else { return { pass: false, - message: 'Expected instance of ' + actualType + ' to be an instance of ' + expectedType + message: + 'Expected instance of ' + + actualType + + ' to be an instance of ' + + expectedType }; } } @@ -4979,7 +5144,6 @@ getJasmineRequireObj().toBeLessThan = function() { */ function toBeLessThan() { return { - compare: function(actual, expected) { return { pass: actual < expected @@ -5003,7 +5167,6 @@ getJasmineRequireObj().toBeLessThanOrEqual = function() { */ function toBeLessThanOrEqual() { return { - compare: function(actual, expected) { return { pass: actual <= expected @@ -5028,13 +5191,15 @@ getJasmineRequireObj().toBeNaN = function(j$) { return { compare: function(actual) { var result = { - pass: (actual !== actual) + pass: actual !== actual }; if (result.pass) { result.message = 'Expected actual not to be NaN.'; } else { - result.message = function() { return 'Expected ' + j$.pp(actual) + ' to be NaN.'; }; + result.message = function() { + return 'Expected ' + j$.pp(actual) + ' to be NaN.'; + }; } return result; @@ -5058,13 +5223,15 @@ getJasmineRequireObj().toBeNegativeInfinity = function(j$) { return { compare: function(actual) { var result = { - pass: (actual === Number.NEGATIVE_INFINITY) + pass: actual === Number.NEGATIVE_INFINITY }; if (result.pass) { result.message = 'Expected actual not to be -Infinity.'; } else { - result.message = function() { return 'Expected ' + j$.pp(actual) + ' to be -Infinity.'; }; + result.message = function() { + return 'Expected ' + j$.pp(actual) + ' to be -Infinity.'; + }; } return result; @@ -5110,13 +5277,15 @@ getJasmineRequireObj().toBePositiveInfinity = function(j$) { return { compare: function(actual) { var result = { - pass: (actual === Number.POSITIVE_INFINITY) + pass: actual === Number.POSITIVE_INFINITY }; if (result.pass) { result.message = 'Expected actual not to be Infinity.'; } else { - result.message = function() { return 'Expected ' + j$.pp(actual) + ' to be Infinity.'; }; + result.message = function() { + return 'Expected ' + j$.pp(actual) + ' to be Infinity.'; + }; } return result; @@ -5209,7 +5378,6 @@ getJasmineRequireObj().toContain = function() { return { compare: function(actual, expected) { - return { pass: util.contains(actual, expected, customEqualityTesters) }; @@ -5240,7 +5408,12 @@ getJasmineRequireObj().toEqual = function(j$) { }, diffBuilder = j$.DiffBuilder(); - result.pass = util.equals(actual, expected, customEqualityTesters, diffBuilder); + result.pass = util.equals( + actual, + expected, + customEqualityTesters, + diffBuilder + ); // TODO: only set error message if test fails result.message = diffBuilder.getMessage(); @@ -5254,8 +5427,10 @@ getJasmineRequireObj().toEqual = function(j$) { }; getJasmineRequireObj().toHaveBeenCalled = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalled()'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalled()' + ); /** * {@link expect} the actual (a {@link Spy}) to have been called. @@ -5272,18 +5447,22 @@ getJasmineRequireObj().toHaveBeenCalled = function(j$) { var result = {}; if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); + throw new Error( + getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.') + ); } if (arguments.length > 1) { - throw new Error(getErrorMsg('Does not take arguments, use toHaveBeenCalledWith')); + throw new Error( + getErrorMsg('Does not take arguments, use toHaveBeenCalledWith') + ); } result.pass = actual.calls.any(); - result.message = result.pass ? - 'Expected spy ' + actual.and.identity + ' not to have been called.' : - 'Expected spy ' + actual.and.identity + ' to have been called.'; + result.message = result.pass + ? 'Expected spy ' + actual.and.identity + ' not to have been called.' + : 'Expected spy ' + actual.and.identity + ' to have been called.'; return result; } @@ -5294,8 +5473,10 @@ getJasmineRequireObj().toHaveBeenCalled = function(j$) { }; getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledBefore()'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalledBefore()' + ); /** * {@link expect} the actual value (a {@link Spy}) to have been called before another {@link Spy}. @@ -5310,20 +5491,26 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { return { compare: function(firstSpy, latterSpy) { if (!j$.isSpy(firstSpy)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(firstSpy) + '.')); + throw new Error( + getErrorMsg('Expected a spy, but got ' + j$.pp(firstSpy) + '.') + ); } if (!j$.isSpy(latterSpy)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(latterSpy) + '.')); + throw new Error( + getErrorMsg('Expected a spy, but got ' + j$.pp(latterSpy) + '.') + ); } var result = { pass: false }; if (!firstSpy.calls.count()) { - result.message = 'Expected spy ' + firstSpy.and.identity + ' to have been called.'; + result.message = + 'Expected spy ' + firstSpy.and.identity + ' to have been called.'; return result; } if (!latterSpy.calls.count()) { - result.message = 'Expected spy ' + latterSpy.and.identity + ' to have been called.'; + result.message = + 'Expected spy ' + latterSpy.and.identity + ' to have been called.'; return result; } @@ -5333,17 +5520,36 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { result.pass = latest1stSpyCall < first2ndSpyCall; if (result.pass) { - result.message = 'Expected spy ' + firstSpy.and.identity + ' to not have been called before spy ' + latterSpy.and.identity + ', but it was'; + result.message = + 'Expected spy ' + + firstSpy.and.identity + + ' to not have been called before spy ' + + latterSpy.and.identity + + ', but it was'; } else { var first1stSpyCall = firstSpy.calls.first().invocationOrder; var latest2ndSpyCall = latterSpy.calls.mostRecent().invocationOrder; - if(first1stSpyCall < first2ndSpyCall) { - result.message = 'Expected latest call to spy ' + firstSpy.and.identity + ' to have been called before first call to spy ' + latterSpy.and.identity + ' (no interleaved calls)'; + if (first1stSpyCall < first2ndSpyCall) { + result.message = + 'Expected latest call to spy ' + + firstSpy.and.identity + + ' to have been called before first call to spy ' + + latterSpy.and.identity + + ' (no interleaved calls)'; } else if (latest2ndSpyCall > latest1stSpyCall) { - result.message = 'Expected first call to spy ' + latterSpy.and.identity + ' to have been called after latest call to spy ' + firstSpy.and.identity + ' (no interleaved calls)'; + result.message = + 'Expected first call to spy ' + + latterSpy.and.identity + + ' to have been called after latest call to spy ' + + firstSpy.and.identity + + ' (no interleaved calls)'; } else { - result.message = 'Expected spy ' + firstSpy.and.identity + ' to have been called before spy ' + latterSpy.and.identity; + result.message = + 'Expected spy ' + + firstSpy.and.identity + + ' to have been called before spy ' + + latterSpy.and.identity; } } @@ -5356,8 +5562,10 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { }; getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledTimes()'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalledTimes()' + ); /** * {@link expect} the actual (a {@link Spy}) to have been called the specified number of times. @@ -5372,23 +5580,41 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { return { compare: function(actual, expected) { if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); + throw new Error( + getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.') + ); } var args = Array.prototype.slice.call(arguments, 0), result = { pass: false }; if (!j$.isNumber_(expected)) { - throw new Error(getErrorMsg('The expected times failed is a required argument and must be a number.')); + throw new Error( + getErrorMsg( + 'The expected times failed is a required argument and must be a number.' + ) + ); } actual = args[0]; var calls = actual.calls.count(); var timesMessage = expected === 1 ? 'once' : expected + ' times'; result.pass = calls === expected; - result.message = result.pass ? - 'Expected spy ' + actual.and.identity + ' not to have been called ' + timesMessage + '. It was called ' + calls + ' times.' : - 'Expected spy ' + actual.and.identity + ' to have been called ' + timesMessage + '. It was called ' + calls + ' times.'; + result.message = result.pass + ? 'Expected spy ' + + actual.and.identity + + ' not to have been called ' + + timesMessage + + '. It was called ' + + calls + + ' times.' + : 'Expected spy ' + + actual.and.identity + + ' to have been called ' + + timesMessage + + '. It was called ' + + calls + + ' times.'; return result; } }; @@ -5398,8 +5624,10 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { }; getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledWith(...arguments)'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalledWith(...arguments)' + ); /** * {@link expect} the actual (a {@link Spy}) to have been called with particular arguments at least once. @@ -5419,43 +5647,82 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { result = { pass: false }; if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); + throw new Error( + getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.') + ); } if (!actual.calls.any()) { result.message = function() { - return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + - ' ' + j$.pp(expectedArgs) + - '\nbut it was never called.'; + return ( + 'Expected spy ' + + actual.and.identity + + ' to have been called with:\n' + + ' ' + + j$.pp(expectedArgs) + + '\nbut it was never called.' + ); }; return result; } - if (util.contains(actual.calls.allArgs(), expectedArgs, customEqualityTesters)) { + if ( + util.contains( + actual.calls.allArgs(), + expectedArgs, + customEqualityTesters + ) + ) { result.pass = true; result.message = function() { - return 'Expected spy ' + actual.and.identity + ' not to have been called with:\n' + - ' ' + j$.pp(expectedArgs) + - '\nbut it was.'; + return ( + 'Expected spy ' + + actual.and.identity + + ' not to have been called with:\n' + + ' ' + + j$.pp(expectedArgs) + + '\nbut it was.' + ); }; } else { result.message = function() { - var prettyPrintedCalls = actual.calls.allArgs().map(function(argsForCall) { - return ' ' + j$.pp(argsForCall); - }); + var prettyPrintedCalls = actual.calls + .allArgs() + .map(function(argsForCall) { + return ' ' + j$.pp(argsForCall); + }); - var diffs = actual.calls.allArgs().map(function(argsForCall, callIx) { - var diffBuilder = new j$.DiffBuilder(); - util.equals(argsForCall, expectedArgs, customEqualityTesters, diffBuilder); - return 'Call ' + callIx + ':\n' + - diffBuilder.getMessage().replace(/^/mg, ' '); - }); + var diffs = actual.calls + .allArgs() + .map(function(argsForCall, callIx) { + var diffBuilder = new j$.DiffBuilder(); + util.equals( + argsForCall, + expectedArgs, + customEqualityTesters, + diffBuilder + ); + return ( + 'Call ' + + callIx + + ':\n' + + diffBuilder.getMessage().replace(/^/gm, ' ') + ); + }); - return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + - ' ' + j$.pp(expectedArgs) + '\n' + '' + + return ( + 'Expected spy ' + + actual.and.identity + + ' to have been called with:\n' + + ' ' + + j$.pp(expectedArgs) + + '\n' + + '' + 'but actual calls were:\n' + - prettyPrintedCalls.join(',\n') + '.\n\n' + - diffs.join('\n'); + prettyPrintedCalls.join(',\n') + + '.\n\n' + + diffs.join('\n') + ); }; } @@ -5494,17 +5761,19 @@ getJasmineRequireObj().toHaveClass = function(j$) { } function isElement(maybeEl) { - return maybeEl && - maybeEl.classList && - j$.isFunction_(maybeEl.classList.contains); + return ( + maybeEl && maybeEl.classList && j$.isFunction_(maybeEl.classList.contains) + ); } return toHaveClass; }; getJasmineRequireObj().toMatch = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toMatch( || )'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toMatch( || )' + ); /** * {@link expect} the actual value to match a regular expression @@ -5536,8 +5805,10 @@ getJasmineRequireObj().toMatch = function(j$) { }; getJasmineRequireObj().toThrow = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect(function() {}).toThrow()'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect(function() {}).toThrow()' + ); /** * {@link expect} a function to `throw` something. @@ -5574,16 +5845,32 @@ getJasmineRequireObj().toThrow = function(j$) { if (arguments.length == 1) { result.pass = true; - result.message = function() { return 'Expected function not to throw, but it threw ' + j$.pp(thrown) + '.'; }; + result.message = function() { + return ( + 'Expected function not to throw, but it threw ' + + j$.pp(thrown) + + '.' + ); + }; return result; } if (util.equals(thrown, expected)) { result.pass = true; - result.message = function() { return 'Expected function not to throw ' + j$.pp(expected) + '.'; }; + result.message = function() { + return 'Expected function not to throw ' + j$.pp(expected) + '.'; + }; } else { - result.message = function() { return 'Expected function to throw ' + j$.pp(expected) + ', but it threw ' + j$.pp(thrown) + '.'; }; + result.message = function() { + return ( + 'Expected function to throw ' + + j$.pp(expected) + + ', but it threw ' + + j$.pp(thrown) + + '.' + ); + }; } return result; @@ -5595,8 +5882,10 @@ getJasmineRequireObj().toThrow = function(j$) { }; getJasmineRequireObj().toThrowError = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect(function() {}).toThrowError(, )'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect(function() {}).toThrowError(, )' + ); /** * {@link expect} a function to `throw` an `Error`. @@ -5612,7 +5901,7 @@ getJasmineRequireObj().toThrowError = function(j$) { * expect(function() { return 'other'; }).toThrowError(/foo/); * expect(function() { return 'other'; }).toThrowError(); */ - function toThrowError () { + function toThrowError() { return { compare: function(actual) { var errorMatcher = getMatcher.apply(null, arguments), @@ -5630,7 +5919,13 @@ getJasmineRequireObj().toThrowError = function(j$) { } if (!j$.isError_(thrown)) { - return fail(function() { return 'Expected function to throw an Error, but it threw ' + j$.pp(thrown) + '.'; }); + return fail(function() { + return ( + 'Expected function to throw an Error, but it threw ' + + j$.pp(thrown) + + '.' + ); + }); } return errorMatcher.match(thrown); @@ -5664,7 +5959,11 @@ getJasmineRequireObj().toThrowError = function(j$) { function anyMatcher() { return { match: function(error) { - return pass('Expected function not to throw an Error, but it threw ' + j$.fnNameFor(error) + '.'); + return pass( + 'Expected function not to throw an Error, but it threw ' + + j$.fnNameFor(error) + + '.' + ); } }; } @@ -5672,9 +5971,13 @@ getJasmineRequireObj().toThrowError = function(j$) { function exactMatcher(expected, errorType) { if (expected && !isStringOrRegExp(expected)) { if (errorType) { - throw new Error(getErrorMsg('Expected error message is not a string or RegExp.')); + throw new Error( + getErrorMsg('Expected error message is not a string or RegExp.') + ); } else { - throw new Error(getErrorMsg('Expected is not an Error, string, or RegExp.')); + throw new Error( + getErrorMsg('Expected is not an Error, string, or RegExp.') + ); } } @@ -5686,11 +5989,15 @@ getJasmineRequireObj().toThrowError = function(j$) { } } - var errorTypeDescription = errorType ? j$.fnNameFor(errorType) : 'an exception'; + var errorTypeDescription = errorType + ? j$.fnNameFor(errorType) + : 'an exception'; function thrownDescription(thrown) { - var thrownName = errorType ? j$.fnNameFor(thrown.constructor) : 'an exception', - thrownMessage = ''; + var thrownName = errorType + ? j$.fnNameFor(thrown.constructor) + : 'an exception', + thrownMessage = ''; if (expected) { thrownMessage = ' with message ' + j$.pp(thrown.message); @@ -5710,20 +6017,33 @@ getJasmineRequireObj().toThrowError = function(j$) { } function matches(error) { - return (errorType === null || error instanceof errorType) && - (expected === null || messageMatch(error.message)); + return ( + (errorType === null || error instanceof errorType) && + (expected === null || messageMatch(error.message)) + ); } return { match: function(thrown) { if (matches(thrown)) { return pass(function() { - return 'Expected function not to throw ' + errorTypeDescription + messageDescription() + '.'; + return ( + 'Expected function not to throw ' + + errorTypeDescription + + messageDescription() + + '.' + ); }); } else { return fail(function() { - return 'Expected function to throw ' + errorTypeDescription + messageDescription() + - ', but it threw ' + thrownDescription(thrown) + '.'; + return ( + 'Expected function to throw ' + + errorTypeDescription + + messageDescription() + + ', but it threw ' + + thrownDescription(thrown) + + '.' + ); }); } } @@ -5731,7 +6051,7 @@ getJasmineRequireObj().toThrowError = function(j$) { } function isStringOrRegExp(potential) { - return potential instanceof RegExp || (typeof potential == 'string'); + return potential instanceof RegExp || typeof potential == 'string'; } function isAnErrorType(type) { @@ -5763,7 +6083,10 @@ getJasmineRequireObj().toThrowError = function(j$) { }; getJasmineRequireObj().toThrowMatching = function(j$) { - var usageError = j$.formatErrorMsg('', 'expect(function() {}).toThrowMatching()'); + var usageError = j$.formatErrorMsg( + '', + 'expect(function() {}).toThrowMatching()' + ); /** * {@link expect} a function to `throw` something matching a predicate. @@ -5795,12 +6118,18 @@ getJasmineRequireObj().toThrowMatching = function(j$) { } if (predicate(thrown)) { - return pass('Expected function not to throw an exception matching a predicate.'); + return pass( + 'Expected function not to throw an exception matching a predicate.' + ); } else { - return fail(function() { - return 'Expected function to throw an exception matching a predicate, ' + - 'but it threw ' + thrownDescription(thrown) + '.'; - }); + return fail(function() { + return ( + 'Expected function to throw an exception matching a predicate, ' + + 'but it threw ' + + thrownDescription(thrown) + + '.' + ); + }); } } }; @@ -5808,8 +6137,11 @@ getJasmineRequireObj().toThrowMatching = function(j$) { function thrownDescription(thrown) { if (thrown && thrown.constructor) { - return j$.fnNameFor(thrown.constructor) + ' with message ' + - j$.pp(thrown.message); + return ( + j$.fnNameFor(thrown.constructor) + + ' with message ' + + j$.pp(thrown.message) + ); } else { return j$.pp(thrown); } @@ -7787,7 +8119,7 @@ getJasmineRequireObj().StackTrace = function(j$) { } function messagePrefixLength(message, stackLines) { - if (!stackLines[0].match(/^Error/)) { + if (!stackLines[0].match(/^w*Error/)) { return 0; } From c395c525dcb4dab6c030dce49557fb3faaa06b8f Mon Sep 17 00:00:00 2001 From: Valentin Hermann Date: Tue, 7 Jan 2020 15:41:02 +0100 Subject: [PATCH 104/201] Revert "Improves method messagePrefixLength. Now error messages like ReferenceError or TypeError are considered as well" This reverts commit 12fefa4b3dbb99a471531fbf2fffddcaef8f711d. --- lib/jasmine-core/jasmine.js | 810 +++++++++++------------------------- 1 file changed, 239 insertions(+), 571 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 522a69a2..25adbf80 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1,5 +1,5 @@ /* -Copyright (c) 2008-2020 Pivotal Labs +Copyright (c) 2008-2019 Pivotal Labs Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the @@ -2236,11 +2236,12 @@ getJasmineRequireObj().JsApiReporter = function(j$) { }; getJasmineRequireObj().Any = function(j$) { + function Any(expectedObject) { if (typeof expectedObject === 'undefined') { throw new TypeError( 'jasmine.any() expects to be passed a constructor function. ' + - 'Please pass one or use jasmine.anything() to match any object.' + 'Please pass one or use jasmine.anything() to match any object.' ); } this.expectedObject = expectedObject; @@ -2285,6 +2286,7 @@ getJasmineRequireObj().Any = function(j$) { }; getJasmineRequireObj().Anything = function(j$) { + function Anything() {} Anything.prototype.asymmetricMatch = function(other) { @@ -2305,11 +2307,7 @@ getJasmineRequireObj().ArrayContaining = function(j$) { ArrayContaining.prototype.asymmetricMatch = function(other, customTesters) { if (!j$.isArray_(this.sample)) { - throw new Error( - 'You must provide an array to arrayContaining, not ' + - j$.pp(this.sample) + - '.' - ); + throw new Error('You must provide an array to arrayContaining, not ' + j$.pp(this.sample) + '.'); } // If the actual parameter is not an array, we can fail immediately, since it couldn't @@ -2329,28 +2327,22 @@ getJasmineRequireObj().ArrayContaining = function(j$) { return true; }; - ArrayContaining.prototype.jasmineToString = function() { - return ''; + ArrayContaining.prototype.jasmineToString = function () { + return ''; }; return ArrayContaining; }; getJasmineRequireObj().ArrayWithExactContents = function(j$) { + function ArrayWithExactContents(sample) { this.sample = sample; } - ArrayWithExactContents.prototype.asymmetricMatch = function( - other, - customTesters - ) { + ArrayWithExactContents.prototype.asymmetricMatch = function(other, customTesters) { if (!j$.isArray_(this.sample)) { - throw new Error( - 'You must provide an array to arrayWithExactContents, not ' + - j$.pp(this.sample) + - '.' - ); + throw new Error('You must provide an array to arrayWithExactContents, not ' + j$.pp(this.sample) + '.'); } if (this.sample.length !== other.length) { @@ -2374,10 +2366,11 @@ getJasmineRequireObj().ArrayWithExactContents = function(j$) { return ArrayWithExactContents; }; -getJasmineRequireObj().Empty = function(j$) { +getJasmineRequireObj().Empty = function (j$) { + function Empty() {} - Empty.prototype.asymmetricMatch = function(other) { + Empty.prototype.asymmetricMatch = function (other) { if (j$.isString_(other) || j$.isArray_(other) || j$.isTypedArray_(other)) { return other.length === 0; } @@ -2392,7 +2385,7 @@ getJasmineRequireObj().Empty = function(j$) { return false; }; - Empty.prototype.jasmineToString = function() { + Empty.prototype.jasmineToString = function () { return ''; }; @@ -2400,6 +2393,7 @@ getJasmineRequireObj().Empty = function(j$) { }; getJasmineRequireObj().Falsy = function(j$) { + function Falsy() {} Falsy.prototype.asymmetricMatch = function(other) { @@ -2416,9 +2410,7 @@ getJasmineRequireObj().Falsy = function(j$) { getJasmineRequireObj().MapContaining = function(j$) { function MapContaining(sample) { if (!j$.isMap(sample)) { - throw new Error( - 'You must provide a map to `mapContaining`, not ' + j$.pp(sample) - ); + throw new Error('You must provide a map to `mapContaining`, not ' + j$.pp(sample)); } this.sample = sample; @@ -2434,8 +2426,8 @@ getJasmineRequireObj().MapContaining = function(j$) { var hasMatch = false; j$.util.forEachBreakable(other, function(oBreakLoop, oValue, oKey) { if ( - j$.matchersUtil.equals(oKey, key, customTesters) && - j$.matchersUtil.equals(oValue, value, customTesters) + j$.matchersUtil.equals(oKey, key, customTesters) + && j$.matchersUtil.equals(oValue, value, customTesters) ) { hasMatch = true; oBreakLoop(); @@ -2457,10 +2449,11 @@ getJasmineRequireObj().MapContaining = function(j$) { return MapContaining; }; -getJasmineRequireObj().NotEmpty = function(j$) { +getJasmineRequireObj().NotEmpty = function (j$) { + function NotEmpty() {} - NotEmpty.prototype.asymmetricMatch = function(other) { + NotEmpty.prototype.asymmetricMatch = function (other) { if (j$.isString_(other) || j$.isArray_(other) || j$.isTypedArray_(other)) { return other.length !== 0; } @@ -2476,7 +2469,7 @@ getJasmineRequireObj().NotEmpty = function(j$) { return false; }; - NotEmpty.prototype.jasmineToString = function() { + NotEmpty.prototype.jasmineToString = function () { return ''; }; @@ -2484,6 +2477,7 @@ getJasmineRequireObj().NotEmpty = function(j$) { }; getJasmineRequireObj().ObjectContaining = function(j$) { + function ObjectContaining(sample) { this.sample = sample; } @@ -2501,7 +2495,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } function hasProperty(obj, property) { - if (!obj || typeof obj !== 'object') { + if (!obj || typeof(obj) !== 'object') { return false; } @@ -2513,26 +2507,12 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } ObjectContaining.prototype.asymmetricMatch = function(other, customTesters) { - if (typeof this.sample !== 'object') { - throw new Error( - "You must provide an object to objectContaining, not '" + - this.sample + - "'." - ); - } - if (typeof other !== 'object') { - return false; - } + if (typeof(this.sample) !== 'object') { throw new Error('You must provide an object to objectContaining, not \''+this.sample+'\'.'); } + if (typeof(other) !== 'object') { return false; } for (var property in this.sample) { - if ( - !hasProperty(other, property) || - !j$.matchersUtil.equals( - this.sample[property], - other[property], - customTesters - ) - ) { + if (!hasProperty(other, property) || + !j$.matchersUtil.equals(this.sample[property], other[property], customTesters)) { return false; } } @@ -2549,7 +2529,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } var filteredOther = {}; - Object.keys(this.sample).forEach(function(k) { + Object.keys(this.sample).forEach(function (k) { // eq short-circuits comparison of objects that have different key sets, // so include all keys even if undefined. filteredOther[k] = other[k]; @@ -2571,9 +2551,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { getJasmineRequireObj().SetContaining = function(j$) { function SetContaining(sample) { if (!j$.isSet(sample)) { - throw new Error( - 'You must provide a set to `setContaining`, not ' + j$.pp(sample) - ); + throw new Error('You must provide a set to `setContaining`, not ' + j$.pp(sample)); } this.sample = sample; @@ -2611,6 +2589,7 @@ getJasmineRequireObj().SetContaining = function(j$) { }; getJasmineRequireObj().StringMatching = function(j$) { + function StringMatching(expected) { if (!j$.isString_(expected) && !j$.isA_('RegExp', expected)) { throw new Error('Expected is not a String or a RegExp'); @@ -2631,6 +2610,7 @@ getJasmineRequireObj().StringMatching = function(j$) { }; getJasmineRequireObj().Truthy = function(j$) { + function Truthy() {} Truthy.prototype.asymmetricMatch = function(other) { @@ -3905,12 +3885,8 @@ getJasmineRequireObj().toBeRejected = function(j$) { throw new Error('Expected toBeRejected to be called on a promise.'); } return actual.then( - function() { - return { pass: false }; - }, - function() { - return { pass: true }; - } + function() { return {pass: false}; }, + function() { return {pass: true}; } ); } }; @@ -3934,46 +3910,35 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { return { compare: function(actualPromise, expectedValue) { if (!j$.isPromiseLike(actualPromise)) { - throw new Error( - 'Expected toBeRejectedWith to be called on a promise.' - ); + throw new Error('Expected toBeRejectedWith to be called on a promise.'); } function prefix(passed) { - return ( - 'Expected a promise ' + + return 'Expected a promise ' + (passed ? 'not ' : '') + - 'to be rejected with ' + - j$.pp(expectedValue) - ); + 'to be rejected with ' + j$.pp(expectedValue); } return actualPromise.then( function() { + return { + pass: false, + message: prefix(false) + ' but it was resolved.' + }; + }, + function(actualValue) { + if (util.equals(actualValue, expectedValue, customEqualityTesters)) { + return { + pass: true, + message: prefix(true) + '.' + }; + } else { return { pass: false, - message: prefix(false) + ' but it was resolved.' + message: prefix(false) + ' but it was rejected with ' + j$.pp(actualValue) + '.' }; - }, - function(actualValue) { - if ( - util.equals(actualValue, expectedValue, customEqualityTesters) - ) { - return { - pass: true, - message: prefix(true) + '.' - }; - } else { - return { - pass: false, - message: - prefix(false) + - ' but it was rejected with ' + - j$.pp(actualValue) + - '.' - }; - } } + } ); } }; @@ -4000,9 +3965,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return { compare: function(actualPromise, arg1, arg2) { if (!j$.isPromiseLike(actualPromise)) { - throw new Error( - 'Expected toBeRejectedWithError to be called on a promise.' - ); + throw new Error('Expected toBeRejectedWithError to be called on a promise.'); } var expected = getExpectedFromArgs(arg1, arg2); @@ -4014,9 +3977,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { message: 'Expected a promise to be rejected but it was resolved.' }; }, - function(actualValue) { - return matchError(actualValue, expected); - } + function(actualValue) { return matchError(actualValue, expected); } ); } }; @@ -4028,25 +3989,16 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { } if (!(actual instanceof expected.error)) { - return fail( - expected, - 'rejected with type ' + j$.fnNameFor(actual.constructor) - ); + return fail(expected, 'rejected with type ' + j$.fnNameFor(actual.constructor)); } var actualMessage = actual.message; - if ( - actualMessage === expected.message || - typeof expected.message === 'undefined' - ) { + if (actualMessage === expected.message || typeof expected.message === 'undefined') { return pass(expected); } - if ( - expected.message instanceof RegExp && - expected.message.test(actualMessage) - ) { + if (expected.message instanceof RegExp && expected.message.test(actualMessage)) { return pass(expected); } @@ -4056,25 +4008,18 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { function pass(expected) { return { pass: true, - message: - 'Expected a promise not to be rejected with ' + - expected.printValue + - ', but it was.' + message: 'Expected a promise not to be rejected with ' + expected.printValue + ', but it was.' }; } function fail(expected, message) { return { pass: false, - message: - 'Expected a promise to be rejected with ' + - expected.printValue + - ' but it was ' + - message + - '.' + message: 'Expected a promise to be rejected with ' + expected.printValue + ' but it was ' + message + '.' }; } + function getExpectedFromArgs(arg1, arg2) { var error, message; @@ -4089,17 +4034,12 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return { error: error, message: message, - printValue: - j$.fnNameFor(error) + - (typeof message === 'undefined' ? '' : ': ' + j$.pp(message)) + printValue: j$.fnNameFor(error) + (typeof message === 'undefined' ? '' : ': ' + j$.pp(message)) }; } function isErrorConstructor(value) { - return ( - typeof value === 'function' && - (value === Error || j$.isError_(value.prototype)) - ); + return typeof value === 'function' && (value === Error || j$.isError_(value.prototype)); } }; @@ -4123,12 +4063,8 @@ getJasmineRequireObj().toBeResolved = function(j$) { } return actual.then( - function() { - return { pass: true }; - }, - function() { - return { pass: false }; - } + function() { return {pass: true}; }, + function() { return {pass: false}; } ); } }; @@ -4156,19 +4092,14 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { } function prefix(passed) { - return ( - 'Expected a promise ' + + return 'Expected a promise ' + (passed ? 'not ' : '') + - 'to be resolved to ' + - j$.pp(expectedValue) - ); + 'to be resolved to ' + j$.pp(expectedValue); } return actualPromise.then( function(actualValue) { - if ( - util.equals(actualValue, expectedValue, customEqualityTesters) - ) { + if (util.equals(actualValue, expectedValue, customEqualityTesters)) { return { pass: true, message: prefix(true) + '.' @@ -4176,11 +4107,7 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { } else { return { pass: false, - message: - prefix(false) + - ' but it was resolved to ' + - j$.pp(actualValue) + - '.' + message: prefix(false) + ' but it was resolved to ' + j$.pp(actualValue) + '.' }; } }, @@ -4199,19 +4126,19 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { getJasmineRequireObj().DiffBuilder = function(j$) { return function DiffBuilder() { var path = new j$.ObjectPath(), - mismatches = []; + mismatches = []; return { - record: function(actual, expected, formatter) { + record: function (actual, expected, formatter) { formatter = formatter || defaultFormatter; mismatches.push(formatter(actual, expected, path)); }, - getMessage: function() { + getMessage: function () { return mismatches.join('\n'); }, - withPath: function(pathComponent, block) { + withPath: function (pathComponent, block) { var oldPath = path; path = path.add(pathComponent); block(); @@ -4219,16 +4146,13 @@ getJasmineRequireObj().DiffBuilder = function(j$) { } }; - function defaultFormatter(actual, expected, path) { - return ( - 'Expected ' + - path + - (path.depth() ? ' = ' : '') + + function defaultFormatter (actual, expected, path) { + return 'Expected ' + + path + (path.depth() ? ' = ' : '') + j$.pp(actual) + ' to equal ' + j$.pp(expected) + - '.' - ); + '.'; } }; }; @@ -4246,10 +4170,9 @@ getJasmineRequireObj().matchersUtil = function(j$) { return haystack.has(needle); } - if ( - Object.prototype.toString.apply(haystack) === '[object Array]' || - (!!haystack && !haystack.indexOf) - ) { + if ((Object.prototype.toString.apply(haystack) === '[object Array]') || + (!!haystack && !haystack.indexOf)) + { for (var i = 0; i < haystack.length; i++) { if (equals(haystack[i], needle, customTesters)) { return true; @@ -4267,12 +4190,9 @@ getJasmineRequireObj().matchersUtil = function(j$) { isNot = args[1], actual = args[2], expected = args.slice(3), - englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { - return ' ' + s.toLowerCase(); - }); + englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { return ' ' + s.toLowerCase(); }); - var message = - 'Expected ' + + var message = 'Expected ' + j$.pp(actual) + (isNot ? ' not ' : ' ') + englishyPredicate; @@ -4305,8 +4225,8 @@ getJasmineRequireObj().matchersUtil = function(j$) { function asymmetricMatch(a, b, aStack, bStack, customTesters, diffBuilder) { var asymmetricA = isAsymmetric(a), - asymmetricB = isAsymmetric(b), - result; + asymmetricB = isAsymmetric(b), + result; if (asymmetricA && asymmetricB) { return undefined; @@ -4341,17 +4261,9 @@ getJasmineRequireObj().matchersUtil = function(j$) { // Equality function lovingly adapted from isEqual in // [Underscore](http://underscorejs.org) function eq(a, b, aStack, bStack, customTesters, diffBuilder) { - var result = true, - i; + var result = true, i; - var asymmetricResult = asymmetricMatch( - a, - b, - aStack, - bStack, - customTesters, - diffBuilder - ); + var asymmetricResult = asymmetricMatch(a, b, aStack, bStack, customTesters, diffBuilder); if (!j$.util.isUndefined(asymmetricResult)) { return asymmetricResult; } @@ -4409,8 +4321,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { case '[object Number]': // `NaN`s are equivalent, but non-reflexive. An `egal` comparison is performed for // other numeric values. - result = - a != +a ? b != +b : a === 0 && b === 0 ? 1 / a == 1 / b : a == +b; + result = a != +a ? b != +b : (a === 0 && b === 0 ? 1 / a == 1 / b : a == +b); if (!result) { diffBuilder.record(a, b); } @@ -4427,12 +4338,10 @@ getJasmineRequireObj().matchersUtil = function(j$) { return result; // RegExps are compared by their source patterns and flags. case '[object RegExp]': - return ( - a.source == b.source && + return a.source == b.source && a.global == b.global && a.multiline == b.multiline && - a.ignoreCase == b.ignoreCase - ); + a.ignoreCase == b.ignoreCase; } if (typeof a != 'object' || typeof b != 'object') { diffBuilder.record(a, b); @@ -4466,9 +4375,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { while (length--) { // Linear search. Performance is inversely proportional to the number of // unique nested structures. - if (aStack[length] == a) { - return bStack[length] == b; - } + if (aStack[length] == a) { return bStack[length] == b; } } // Add the first object to the stack of traversed objects. aStack.push(a); @@ -4493,15 +4400,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { diffBuilder.record(a[i], void 0, actualArrayIsLongerFormatter); result = false; } else { - result = - eq( - i < aLength ? a[i] : void 0, - i < bLength ? b[i] : void 0, - aStack, - bStack, - customTesters, - diffBuilder - ) && result; + result = eq(i < aLength ? a[i] : void 0, i < bLength ? b[i] : void 0, aStack, bStack, customTesters, diffBuilder) && result; } }); } @@ -4516,11 +4415,11 @@ getJasmineRequireObj().matchersUtil = function(j$) { var keysA = []; var keysB = []; - a.forEach(function(valueA, keyA) { - keysA.push(keyA); + a.forEach( function( valueA, keyA ) { + keysA.push( keyA ); }); - b.forEach(function(valueB, keyB) { - keysB.push(keyB); + b.forEach( function( valueB, keyB ) { + keysB.push( keyB ); }); // For both sets of keys, check they map to equal values in both maps. @@ -4541,30 +4440,13 @@ getJasmineRequireObj().matchersUtil = function(j$) { // Only use the cmpKey when one of the keys is asymmetric and the corresponding key matches, // otherwise explicitly look up the mapKey in the other Map since we want keys with unique // obj identity (that are otherwise equal) to not match. - if ( - isAsymmetric(mapKey) || - (isAsymmetric(cmpKey) && - eq( - mapKey, - cmpKey, - aStack, - bStack, - customTesters, - j$.NullDiffBuilder() - )) - ) { + if (isAsymmetric(mapKey) || isAsymmetric(cmpKey) && + eq(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { mapValueB = b.get(cmpKey); } else { mapValueB = b.get(mapKey); } - result = eq( - mapValueA, - mapValueB, - aStack, - bStack, - customTesters, - j$.NullDiffBuilder() - ); + result = eq(mapValueA, mapValueB, aStack, bStack, customTesters, j$.NullDiffBuilder()); } } @@ -4579,12 +4461,12 @@ getJasmineRequireObj().matchersUtil = function(j$) { } var valuesA = []; - a.forEach(function(valueA) { - valuesA.push(valueA); + a.forEach( function( valueA ) { + valuesA.push( valueA ); }); var valuesB = []; - b.forEach(function(valueB) { - valuesB.push(valueB); + b.forEach( function( valueB ) { + valuesB.push( valueB ); }); // For both sets, check they are all contained in the other set @@ -4608,14 +4490,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { otherValue = otherValues[l]; prevStackSize = baseStack.length; // compare by value equality - found = eq( - baseValue, - otherValue, - baseStack, - otherStack, - customTesters, - j$.NullDiffBuilder() - ); + found = eq(baseValue, otherValue, baseStack, otherStack, customTesters, j$.NullDiffBuilder()); if (!found && prevStackSize !== baseStack.length) { baseStack.splice(prevStackSize); otherStack.splice(prevStackSize); @@ -4630,26 +4505,22 @@ getJasmineRequireObj().matchersUtil = function(j$) { return false; } } else { + // Objects with different constructors are not equivalent, but `Object`s // or `Array`s from different frames are. - var aCtor = a.constructor, - bCtor = b.constructor; - if ( - aCtor !== bCtor && - isFunction(aCtor) && - isFunction(bCtor) && - a instanceof aCtor && - b instanceof bCtor && - !(aCtor instanceof aCtor && bCtor instanceof bCtor) - ) { + var aCtor = a.constructor, bCtor = b.constructor; + if (aCtor !== bCtor && + isFunction(aCtor) && isFunction(bCtor) && + a instanceof aCtor && b instanceof bCtor && + !(aCtor instanceof aCtor && bCtor instanceof bCtor)) { + diffBuilder.record(a, b, constructorsAreDifferentFormatter); return false; } } // Deep compare objects. - var aKeys = keys(a, className == '[object Array]'), - key; + var aKeys = keys(a, className == '[object Array]'), key; size = aKeys.length; // Ensure that both objects contain the same number of properties before comparing deep equality. @@ -4668,7 +4539,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { } diffBuilder.withPath(key, function() { - if (!eq(a[key], b[key], aStack, bStack, customTesters, diffBuilder)) { + if(!eq(a[key], b[key], aStack, bStack, customTesters, diffBuilder)) { result = false; } }); @@ -4686,24 +4557,23 @@ getJasmineRequireObj().matchersUtil = function(j$) { } function keys(obj, isArray) { - var allKeys = Object.keys - ? Object.keys(obj) - : (function(o) { + var allKeys = Object.keys ? Object.keys(obj) : + (function(o) { var keys = []; for (var key in o) { - if (j$.util.has(o, key)) { - keys.push(key); - } + if (j$.util.has(o, key)) { + keys.push(key); + } } return keys; - })(obj); + })(obj); if (!isArray) { return allKeys; } if (allKeys.length === 0) { - return allKeys; + return allKeys; } var extraKeys = []; @@ -4722,25 +4592,21 @@ getJasmineRequireObj().matchersUtil = function(j$) { function objectKeysAreDifferentFormatter(actual, expected, path) { var missingProperties = j$.util.objectDifference(expected, actual), - extraProperties = j$.util.objectDifference(actual, expected), - missingPropertiesMessage = formatKeyValuePairs(missingProperties), - extraPropertiesMessage = formatKeyValuePairs(extraProperties), - messages = []; + extraProperties = j$.util.objectDifference(actual, expected), + missingPropertiesMessage = formatKeyValuePairs(missingProperties), + extraPropertiesMessage = formatKeyValuePairs(extraProperties), + messages = []; if (!path.depth()) { path = 'object'; } if (missingPropertiesMessage.length) { - messages.push( - 'Expected ' + path + ' to have properties' + missingPropertiesMessage - ); + messages.push('Expected ' + path + ' to have properties' + missingPropertiesMessage); } if (extraPropertiesMessage.length) { - messages.push( - 'Expected ' + path + ' not to have properties' + extraPropertiesMessage - ); + messages.push('Expected ' + path + ' not to have properties' + extraPropertiesMessage); } return messages.join('\n'); @@ -4751,25 +4617,17 @@ getJasmineRequireObj().matchersUtil = function(j$) { path = 'object'; } - return ( - 'Expected ' + - path + - ' to be a kind of ' + + return 'Expected ' + + path + ' to be a kind of ' + j$.fnNameFor(expected.constructor) + - ', but was ' + - j$.pp(actual) + - '.' - ); + ', but was ' + j$.pp(actual) + '.'; } function actualArrayIsLongerFormatter(actual, expected, path) { - return ( - 'Unexpected ' + - path + - (path.depth() ? ' = ' : '') + + return 'Unexpected ' + + path + (path.depth() ? ' = ' : '') + j$.pp(actual) + - ' in array.' - ); + ' in array.'; } function formatKeyValuePairs(obj) { @@ -4844,7 +4702,7 @@ getJasmineRequireObj().ObjectPath = function(j$) { return '.' + prop; } - return "['" + prop + "']"; + return '[\'' + prop + '\']'; } function map(array, fn) { @@ -4891,8 +4749,7 @@ getJasmineRequireObj().toBe = function(j$) { * expect(thing).toBe(realThing); */ function toBe(util) { - var tip = - ' Tip: To check for deep equality, use .toEqual() instead of .toBe().'; + var tip = ' Tip: To check for deep equality, use .toEqual() instead of .toBe().'; return { compare: function(actual, expected) { @@ -4901,9 +4758,7 @@ getJasmineRequireObj().toBe = function(j$) { }; if (typeof expected === 'object') { - result.message = - util.buildFailureMessage('toBe', result.pass, actual, expected) + - tip; + result.message = util.buildFailureMessage('toBe', result.pass, actual, expected) + tip; } return result; @@ -4933,13 +4788,8 @@ getJasmineRequireObj().toBeCloseTo = function() { } if (expected === null || actual === null) { - throw new Error( - 'Cannot use toBeCloseTo with null. Arguments evaluated to: ' + - 'expect(' + - actual + - ').toBeCloseTo(' + - expected + - ').' + throw new Error('Cannot use toBeCloseTo with null. Arguments evaluated to: ' + + 'expect(' + actual + ').toBeCloseTo(' + expected + ').' ); } @@ -4970,7 +4820,7 @@ getJasmineRequireObj().toBeDefined = function() { return { compare: function(actual) { return { - pass: void 0 !== actual + pass: (void 0 !== actual) }; } }; @@ -5046,6 +4896,7 @@ getJasmineRequireObj().toBeGreaterThan = function() { return toBeGreaterThan; }; + getJasmineRequireObj().toBeGreaterThanOrEqual = function() { /** * {@link expect} the actual value to be greater than or equal to the expected value. @@ -5070,10 +4921,7 @@ getJasmineRequireObj().toBeGreaterThanOrEqual = function() { }; getJasmineRequireObj().toBeInstanceOf = function(j$) { - var usageError = j$.formatErrorMsg( - '', - 'expect(value).toBeInstanceOf()' - ); + var usageError = j$.formatErrorMsg('', 'expect(value).toBeInstanceOf()'); /** * {@link expect} the actual to be an instance of the expected class @@ -5089,40 +4937,27 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { function toBeInstanceOf(util, customEqualityTesters) { return { compare: function(actual, expected) { - var actualType = - actual && actual.constructor - ? j$.fnNameFor(actual.constructor) - : j$.pp(actual), - expectedType = expected ? j$.fnNameFor(expected) : j$.pp(expected), - expectedMatcher, - pass; + var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : j$.pp(actual), + expectedType = expected ? j$.fnNameFor(expected) : j$.pp(expected), + expectedMatcher, + pass; try { - expectedMatcher = new j$.Any(expected); - pass = expectedMatcher.asymmetricMatch(actual); + expectedMatcher = new j$.Any(expected); + pass = expectedMatcher.asymmetricMatch(actual); } catch (error) { - throw new Error( - usageError('Expected value is not a constructor function') - ); + throw new Error(usageError('Expected value is not a constructor function')); } if (pass) { return { pass: true, - message: - 'Expected instance of ' + - actualType + - ' not to be an instance of ' + - expectedType + message: 'Expected instance of ' + actualType + ' not to be an instance of ' + expectedType }; } else { return { pass: false, - message: - 'Expected instance of ' + - actualType + - ' to be an instance of ' + - expectedType + message: 'Expected instance of ' + actualType + ' to be an instance of ' + expectedType }; } } @@ -5144,6 +4979,7 @@ getJasmineRequireObj().toBeLessThan = function() { */ function toBeLessThan() { return { + compare: function(actual, expected) { return { pass: actual < expected @@ -5167,6 +5003,7 @@ getJasmineRequireObj().toBeLessThanOrEqual = function() { */ function toBeLessThanOrEqual() { return { + compare: function(actual, expected) { return { pass: actual <= expected @@ -5191,15 +5028,13 @@ getJasmineRequireObj().toBeNaN = function(j$) { return { compare: function(actual) { var result = { - pass: actual !== actual + pass: (actual !== actual) }; if (result.pass) { result.message = 'Expected actual not to be NaN.'; } else { - result.message = function() { - return 'Expected ' + j$.pp(actual) + ' to be NaN.'; - }; + result.message = function() { return 'Expected ' + j$.pp(actual) + ' to be NaN.'; }; } return result; @@ -5223,15 +5058,13 @@ getJasmineRequireObj().toBeNegativeInfinity = function(j$) { return { compare: function(actual) { var result = { - pass: actual === Number.NEGATIVE_INFINITY + pass: (actual === Number.NEGATIVE_INFINITY) }; if (result.pass) { result.message = 'Expected actual not to be -Infinity.'; } else { - result.message = function() { - return 'Expected ' + j$.pp(actual) + ' to be -Infinity.'; - }; + result.message = function() { return 'Expected ' + j$.pp(actual) + ' to be -Infinity.'; }; } return result; @@ -5277,15 +5110,13 @@ getJasmineRequireObj().toBePositiveInfinity = function(j$) { return { compare: function(actual) { var result = { - pass: actual === Number.POSITIVE_INFINITY + pass: (actual === Number.POSITIVE_INFINITY) }; if (result.pass) { result.message = 'Expected actual not to be Infinity.'; } else { - result.message = function() { - return 'Expected ' + j$.pp(actual) + ' to be Infinity.'; - }; + result.message = function() { return 'Expected ' + j$.pp(actual) + ' to be Infinity.'; }; } return result; @@ -5378,6 +5209,7 @@ getJasmineRequireObj().toContain = function() { return { compare: function(actual, expected) { + return { pass: util.contains(actual, expected, customEqualityTesters) }; @@ -5408,12 +5240,7 @@ getJasmineRequireObj().toEqual = function(j$) { }, diffBuilder = j$.DiffBuilder(); - result.pass = util.equals( - actual, - expected, - customEqualityTesters, - diffBuilder - ); + result.pass = util.equals(actual, expected, customEqualityTesters, diffBuilder); // TODO: only set error message if test fails result.message = diffBuilder.getMessage(); @@ -5427,10 +5254,8 @@ getJasmineRequireObj().toEqual = function(j$) { }; getJasmineRequireObj().toHaveBeenCalled = function(j$) { - var getErrorMsg = j$.formatErrorMsg( - '', - 'expect().toHaveBeenCalled()' - ); + + var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalled()'); /** * {@link expect} the actual (a {@link Spy}) to have been called. @@ -5447,22 +5272,18 @@ getJasmineRequireObj().toHaveBeenCalled = function(j$) { var result = {}; if (!j$.isSpy(actual)) { - throw new Error( - getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.') - ); + throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); } if (arguments.length > 1) { - throw new Error( - getErrorMsg('Does not take arguments, use toHaveBeenCalledWith') - ); + throw new Error(getErrorMsg('Does not take arguments, use toHaveBeenCalledWith')); } result.pass = actual.calls.any(); - result.message = result.pass - ? 'Expected spy ' + actual.and.identity + ' not to have been called.' - : 'Expected spy ' + actual.and.identity + ' to have been called.'; + result.message = result.pass ? + 'Expected spy ' + actual.and.identity + ' not to have been called.' : + 'Expected spy ' + actual.and.identity + ' to have been called.'; return result; } @@ -5473,10 +5294,8 @@ getJasmineRequireObj().toHaveBeenCalled = function(j$) { }; getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { - var getErrorMsg = j$.formatErrorMsg( - '', - 'expect().toHaveBeenCalledBefore()' - ); + + var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledBefore()'); /** * {@link expect} the actual value (a {@link Spy}) to have been called before another {@link Spy}. @@ -5491,26 +5310,20 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { return { compare: function(firstSpy, latterSpy) { if (!j$.isSpy(firstSpy)) { - throw new Error( - getErrorMsg('Expected a spy, but got ' + j$.pp(firstSpy) + '.') - ); + throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(firstSpy) + '.')); } if (!j$.isSpy(latterSpy)) { - throw new Error( - getErrorMsg('Expected a spy, but got ' + j$.pp(latterSpy) + '.') - ); + throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(latterSpy) + '.')); } var result = { pass: false }; if (!firstSpy.calls.count()) { - result.message = - 'Expected spy ' + firstSpy.and.identity + ' to have been called.'; + result.message = 'Expected spy ' + firstSpy.and.identity + ' to have been called.'; return result; } if (!latterSpy.calls.count()) { - result.message = - 'Expected spy ' + latterSpy.and.identity + ' to have been called.'; + result.message = 'Expected spy ' + latterSpy.and.identity + ' to have been called.'; return result; } @@ -5520,36 +5333,17 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { result.pass = latest1stSpyCall < first2ndSpyCall; if (result.pass) { - result.message = - 'Expected spy ' + - firstSpy.and.identity + - ' to not have been called before spy ' + - latterSpy.and.identity + - ', but it was'; + result.message = 'Expected spy ' + firstSpy.and.identity + ' to not have been called before spy ' + latterSpy.and.identity + ', but it was'; } else { var first1stSpyCall = firstSpy.calls.first().invocationOrder; var latest2ndSpyCall = latterSpy.calls.mostRecent().invocationOrder; - if (first1stSpyCall < first2ndSpyCall) { - result.message = - 'Expected latest call to spy ' + - firstSpy.and.identity + - ' to have been called before first call to spy ' + - latterSpy.and.identity + - ' (no interleaved calls)'; + if(first1stSpyCall < first2ndSpyCall) { + result.message = 'Expected latest call to spy ' + firstSpy.and.identity + ' to have been called before first call to spy ' + latterSpy.and.identity + ' (no interleaved calls)'; } else if (latest2ndSpyCall > latest1stSpyCall) { - result.message = - 'Expected first call to spy ' + - latterSpy.and.identity + - ' to have been called after latest call to spy ' + - firstSpy.and.identity + - ' (no interleaved calls)'; + result.message = 'Expected first call to spy ' + latterSpy.and.identity + ' to have been called after latest call to spy ' + firstSpy.and.identity + ' (no interleaved calls)'; } else { - result.message = - 'Expected spy ' + - firstSpy.and.identity + - ' to have been called before spy ' + - latterSpy.and.identity; + result.message = 'Expected spy ' + firstSpy.and.identity + ' to have been called before spy ' + latterSpy.and.identity; } } @@ -5562,10 +5356,8 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { }; getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { - var getErrorMsg = j$.formatErrorMsg( - '', - 'expect().toHaveBeenCalledTimes()' - ); + + var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledTimes()'); /** * {@link expect} the actual (a {@link Spy}) to have been called the specified number of times. @@ -5580,41 +5372,23 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { return { compare: function(actual, expected) { if (!j$.isSpy(actual)) { - throw new Error( - getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.') - ); + throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); } var args = Array.prototype.slice.call(arguments, 0), result = { pass: false }; if (!j$.isNumber_(expected)) { - throw new Error( - getErrorMsg( - 'The expected times failed is a required argument and must be a number.' - ) - ); + throw new Error(getErrorMsg('The expected times failed is a required argument and must be a number.')); } actual = args[0]; var calls = actual.calls.count(); var timesMessage = expected === 1 ? 'once' : expected + ' times'; result.pass = calls === expected; - result.message = result.pass - ? 'Expected spy ' + - actual.and.identity + - ' not to have been called ' + - timesMessage + - '. It was called ' + - calls + - ' times.' - : 'Expected spy ' + - actual.and.identity + - ' to have been called ' + - timesMessage + - '. It was called ' + - calls + - ' times.'; + result.message = result.pass ? + 'Expected spy ' + actual.and.identity + ' not to have been called ' + timesMessage + '. It was called ' + calls + ' times.' : + 'Expected spy ' + actual.and.identity + ' to have been called ' + timesMessage + '. It was called ' + calls + ' times.'; return result; } }; @@ -5624,10 +5398,8 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { }; getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { - var getErrorMsg = j$.formatErrorMsg( - '', - 'expect().toHaveBeenCalledWith(...arguments)' - ); + + var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledWith(...arguments)'); /** * {@link expect} the actual (a {@link Spy}) to have been called with particular arguments at least once. @@ -5647,82 +5419,43 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { result = { pass: false }; if (!j$.isSpy(actual)) { - throw new Error( - getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.') - ); + throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); } if (!actual.calls.any()) { result.message = function() { - return ( - 'Expected spy ' + - actual.and.identity + - ' to have been called with:\n' + - ' ' + - j$.pp(expectedArgs) + - '\nbut it was never called.' - ); + return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + + ' ' + j$.pp(expectedArgs) + + '\nbut it was never called.'; }; return result; } - if ( - util.contains( - actual.calls.allArgs(), - expectedArgs, - customEqualityTesters - ) - ) { + if (util.contains(actual.calls.allArgs(), expectedArgs, customEqualityTesters)) { result.pass = true; result.message = function() { - return ( - 'Expected spy ' + - actual.and.identity + - ' not to have been called with:\n' + - ' ' + - j$.pp(expectedArgs) + - '\nbut it was.' - ); + return 'Expected spy ' + actual.and.identity + ' not to have been called with:\n' + + ' ' + j$.pp(expectedArgs) + + '\nbut it was.'; }; } else { result.message = function() { - var prettyPrintedCalls = actual.calls - .allArgs() - .map(function(argsForCall) { - return ' ' + j$.pp(argsForCall); - }); + var prettyPrintedCalls = actual.calls.allArgs().map(function(argsForCall) { + return ' ' + j$.pp(argsForCall); + }); - var diffs = actual.calls - .allArgs() - .map(function(argsForCall, callIx) { - var diffBuilder = new j$.DiffBuilder(); - util.equals( - argsForCall, - expectedArgs, - customEqualityTesters, - diffBuilder - ); - return ( - 'Call ' + - callIx + - ':\n' + - diffBuilder.getMessage().replace(/^/gm, ' ') - ); - }); + var diffs = actual.calls.allArgs().map(function(argsForCall, callIx) { + var diffBuilder = new j$.DiffBuilder(); + util.equals(argsForCall, expectedArgs, customEqualityTesters, diffBuilder); + return 'Call ' + callIx + ':\n' + + diffBuilder.getMessage().replace(/^/mg, ' '); + }); - return ( - 'Expected spy ' + - actual.and.identity + - ' to have been called with:\n' + - ' ' + - j$.pp(expectedArgs) + - '\n' + - '' + + return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + + ' ' + j$.pp(expectedArgs) + '\n' + '' + 'but actual calls were:\n' + - prettyPrintedCalls.join(',\n') + - '.\n\n' + - diffs.join('\n') - ); + prettyPrintedCalls.join(',\n') + '.\n\n' + + diffs.join('\n'); }; } @@ -5761,19 +5494,17 @@ getJasmineRequireObj().toHaveClass = function(j$) { } function isElement(maybeEl) { - return ( - maybeEl && maybeEl.classList && j$.isFunction_(maybeEl.classList.contains) - ); + return maybeEl && + maybeEl.classList && + j$.isFunction_(maybeEl.classList.contains); } return toHaveClass; }; getJasmineRequireObj().toMatch = function(j$) { - var getErrorMsg = j$.formatErrorMsg( - '', - 'expect().toMatch( || )' - ); + + var getErrorMsg = j$.formatErrorMsg('', 'expect().toMatch( || )'); /** * {@link expect} the actual value to match a regular expression @@ -5805,10 +5536,8 @@ getJasmineRequireObj().toMatch = function(j$) { }; getJasmineRequireObj().toThrow = function(j$) { - var getErrorMsg = j$.formatErrorMsg( - '', - 'expect(function() {}).toThrow()' - ); + + var getErrorMsg = j$.formatErrorMsg('', 'expect(function() {}).toThrow()'); /** * {@link expect} a function to `throw` something. @@ -5845,32 +5574,16 @@ getJasmineRequireObj().toThrow = function(j$) { if (arguments.length == 1) { result.pass = true; - result.message = function() { - return ( - 'Expected function not to throw, but it threw ' + - j$.pp(thrown) + - '.' - ); - }; + result.message = function() { return 'Expected function not to throw, but it threw ' + j$.pp(thrown) + '.'; }; return result; } if (util.equals(thrown, expected)) { result.pass = true; - result.message = function() { - return 'Expected function not to throw ' + j$.pp(expected) + '.'; - }; + result.message = function() { return 'Expected function not to throw ' + j$.pp(expected) + '.'; }; } else { - result.message = function() { - return ( - 'Expected function to throw ' + - j$.pp(expected) + - ', but it threw ' + - j$.pp(thrown) + - '.' - ); - }; + result.message = function() { return 'Expected function to throw ' + j$.pp(expected) + ', but it threw ' + j$.pp(thrown) + '.'; }; } return result; @@ -5882,10 +5595,8 @@ getJasmineRequireObj().toThrow = function(j$) { }; getJasmineRequireObj().toThrowError = function(j$) { - var getErrorMsg = j$.formatErrorMsg( - '', - 'expect(function() {}).toThrowError(, )' - ); + + var getErrorMsg = j$.formatErrorMsg('', 'expect(function() {}).toThrowError(, )'); /** * {@link expect} a function to `throw` an `Error`. @@ -5901,7 +5612,7 @@ getJasmineRequireObj().toThrowError = function(j$) { * expect(function() { return 'other'; }).toThrowError(/foo/); * expect(function() { return 'other'; }).toThrowError(); */ - function toThrowError() { + function toThrowError () { return { compare: function(actual) { var errorMatcher = getMatcher.apply(null, arguments), @@ -5919,13 +5630,7 @@ getJasmineRequireObj().toThrowError = function(j$) { } if (!j$.isError_(thrown)) { - return fail(function() { - return ( - 'Expected function to throw an Error, but it threw ' + - j$.pp(thrown) + - '.' - ); - }); + return fail(function() { return 'Expected function to throw an Error, but it threw ' + j$.pp(thrown) + '.'; }); } return errorMatcher.match(thrown); @@ -5959,11 +5664,7 @@ getJasmineRequireObj().toThrowError = function(j$) { function anyMatcher() { return { match: function(error) { - return pass( - 'Expected function not to throw an Error, but it threw ' + - j$.fnNameFor(error) + - '.' - ); + return pass('Expected function not to throw an Error, but it threw ' + j$.fnNameFor(error) + '.'); } }; } @@ -5971,13 +5672,9 @@ getJasmineRequireObj().toThrowError = function(j$) { function exactMatcher(expected, errorType) { if (expected && !isStringOrRegExp(expected)) { if (errorType) { - throw new Error( - getErrorMsg('Expected error message is not a string or RegExp.') - ); + throw new Error(getErrorMsg('Expected error message is not a string or RegExp.')); } else { - throw new Error( - getErrorMsg('Expected is not an Error, string, or RegExp.') - ); + throw new Error(getErrorMsg('Expected is not an Error, string, or RegExp.')); } } @@ -5989,15 +5686,11 @@ getJasmineRequireObj().toThrowError = function(j$) { } } - var errorTypeDescription = errorType - ? j$.fnNameFor(errorType) - : 'an exception'; + var errorTypeDescription = errorType ? j$.fnNameFor(errorType) : 'an exception'; function thrownDescription(thrown) { - var thrownName = errorType - ? j$.fnNameFor(thrown.constructor) - : 'an exception', - thrownMessage = ''; + var thrownName = errorType ? j$.fnNameFor(thrown.constructor) : 'an exception', + thrownMessage = ''; if (expected) { thrownMessage = ' with message ' + j$.pp(thrown.message); @@ -6017,33 +5710,20 @@ getJasmineRequireObj().toThrowError = function(j$) { } function matches(error) { - return ( - (errorType === null || error instanceof errorType) && - (expected === null || messageMatch(error.message)) - ); + return (errorType === null || error instanceof errorType) && + (expected === null || messageMatch(error.message)); } return { match: function(thrown) { if (matches(thrown)) { return pass(function() { - return ( - 'Expected function not to throw ' + - errorTypeDescription + - messageDescription() + - '.' - ); + return 'Expected function not to throw ' + errorTypeDescription + messageDescription() + '.'; }); } else { return fail(function() { - return ( - 'Expected function to throw ' + - errorTypeDescription + - messageDescription() + - ', but it threw ' + - thrownDescription(thrown) + - '.' - ); + return 'Expected function to throw ' + errorTypeDescription + messageDescription() + + ', but it threw ' + thrownDescription(thrown) + '.'; }); } } @@ -6051,7 +5731,7 @@ getJasmineRequireObj().toThrowError = function(j$) { } function isStringOrRegExp(potential) { - return potential instanceof RegExp || typeof potential == 'string'; + return potential instanceof RegExp || (typeof potential == 'string'); } function isAnErrorType(type) { @@ -6083,10 +5763,7 @@ getJasmineRequireObj().toThrowError = function(j$) { }; getJasmineRequireObj().toThrowMatching = function(j$) { - var usageError = j$.formatErrorMsg( - '', - 'expect(function() {}).toThrowMatching()' - ); + var usageError = j$.formatErrorMsg('', 'expect(function() {}).toThrowMatching()'); /** * {@link expect} a function to `throw` something matching a predicate. @@ -6118,18 +5795,12 @@ getJasmineRequireObj().toThrowMatching = function(j$) { } if (predicate(thrown)) { - return pass( - 'Expected function not to throw an exception matching a predicate.' - ); + return pass('Expected function not to throw an exception matching a predicate.'); } else { - return fail(function() { - return ( - 'Expected function to throw an exception matching a predicate, ' + - 'but it threw ' + - thrownDescription(thrown) + - '.' - ); - }); + return fail(function() { + return 'Expected function to throw an exception matching a predicate, ' + + 'but it threw ' + thrownDescription(thrown) + '.'; + }); } } }; @@ -6137,11 +5808,8 @@ getJasmineRequireObj().toThrowMatching = function(j$) { function thrownDescription(thrown) { if (thrown && thrown.constructor) { - return ( - j$.fnNameFor(thrown.constructor) + - ' with message ' + - j$.pp(thrown.message) - ); + return j$.fnNameFor(thrown.constructor) + ' with message ' + + j$.pp(thrown.message); } else { return j$.pp(thrown); } @@ -8119,7 +7787,7 @@ getJasmineRequireObj().StackTrace = function(j$) { } function messagePrefixLength(message, stackLines) { - if (!stackLines[0].match(/^w*Error/)) { + if (!stackLines[0].match(/^Error/)) { return 0; } From 913ad50a76fb6c12f087cea6ece7c7cd5d2bb777 Mon Sep 17 00:00:00 2001 From: Valentin Hermann Date: Tue, 7 Jan 2020 15:49:43 +0100 Subject: [PATCH 105/201] Improves method messagePrefixLength. Now error messages like ReferenceError or TypeError are considered, too --- lib/jasmine-core/jasmine.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 25adbf80..f8bb0602 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -7787,7 +7787,7 @@ getJasmineRequireObj().StackTrace = function(j$) { } function messagePrefixLength(message, stackLines) { - if (!stackLines[0].match(/^Error/)) { + if (!stackLines[0].match(/^\w*Error/)) { return 0; } From e02c24d15148319036af414aeea9cdb35ffdb2fd Mon Sep 17 00:00:00 2001 From: Valentin Hermann Date: Wed, 8 Jan 2020 08:47:08 +0100 Subject: [PATCH 106/201] Revert "Improves method messagePrefixLength. Now error messages like ReferenceError or TypeError are considered, too" This reverts commit 913ad50a76fb6c12f087cea6ece7c7cd5d2bb777. --- lib/jasmine-core/jasmine.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index f8bb0602..25adbf80 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -7787,7 +7787,7 @@ getJasmineRequireObj().StackTrace = function(j$) { } function messagePrefixLength(message, stackLines) { - if (!stackLines[0].match(/^\w*Error/)) { + if (!stackLines[0].match(/^Error/)) { return 0; } From 0b4a9edff864a3e192d3aea3600766d07b8dc8cd Mon Sep 17 00:00:00 2001 From: Valentin Hermann Date: Wed, 8 Jan 2020 10:55:14 +0100 Subject: [PATCH 107/201] Added some tests and modified the source code instead of the build product --- spec/core/StackTraceSpec.js | 42 +++++++++++++++++++++++++++++++++++++ src/core/StackTrace.js | 2 +- 2 files changed, 43 insertions(+), 1 deletion(-) diff --git a/spec/core/StackTraceSpec.js b/spec/core/StackTraceSpec.js index 9cbffe33..d041c8e7 100644 --- a/spec/core/StackTraceSpec.js +++ b/spec/core/StackTraceSpec.js @@ -213,4 +213,46 @@ describe('StackTrace', function() { } ]); }); + + it('consideres different types of errors', function() { + var error = { + message: 'nope', + stack: + 'TypeError: nope\n' + + ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)\n' + + ' at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)' + }; + + var result = new jasmineUnderTest.StackTrace(error); + + expect(result.message).toEqual('TypeError: nope'); + expect(result.frames).toEqual([ + { + raw: + ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)', + func: 'UserContext.', + file: 'http://localhost:8888/__spec__/core/UtilSpec.js', + line: 115 + }, + { + raw: + ' at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)', + func: 'QueueRunner.run', + file: 'http://localhost:8888/__jasmine__/jasmine.js', + line: 4320 + } + ]); + + var no_error = { + message: 'nope', + stack: + 'Type Error: nope\n' + + ' at UserContext. (http://localhost:8888/__spec__/core/UtilSpec.js:115:19)\n' + + ' at QueueRunner.run (http://localhost:8888/__jasmine__/jasmine.js:4320:20)' + }; + + var result_no_error = new jasmineUnderTest.StackTrace(no_error); + + expect(result_no_error.message).not.toEqual(jasmine.anything()); + }); }); diff --git a/src/core/StackTrace.js b/src/core/StackTrace.js index 3382751d..44db4ff1 100644 --- a/src/core/StackTrace.js +++ b/src/core/StackTrace.js @@ -104,7 +104,7 @@ getJasmineRequireObj().StackTrace = function(j$) { } function messagePrefixLength(message, stackLines) { - if (!stackLines[0].match(/^Error/)) { + if (!stackLines[0].match(/^\w*Error/)) { return 0; } From fffb8abb244ee95551b42ace75ff6f21428ce157 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 11 Jan 2020 10:49:37 -0800 Subject: [PATCH 108/201] Moved property tests to the main suite Property tests can only run in Node, so they were previously in another directory that only gets run in Node. Now they're next to the related non-property tests and marked pending in the browser. This makes it more likely that a developer who normally only runs tests in the browser will notice and run them. --- spec/core/matchers/matchersUtilSpec.js | 73 +++++++++++++++++++++++++- spec/helpers/requireFastCheck.js | 16 ++++++ spec/property/matchersUtilSpec.js | 69 ------------------------ spec/support/jasmine-browser.js | 3 +- spec/support/jasmine.json | 2 +- 5 files changed, 91 insertions(+), 72 deletions(-) create mode 100644 spec/helpers/requireFastCheck.js delete mode 100644 spec/property/matchersUtilSpec.js diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index b2146e94..508a5bfd 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -1,5 +1,76 @@ describe("matchersUtil", function() { describe("equals", function() { + describe('Properties', function() { + var fc; + + beforeEach(function() { + fc = jasmine.getEnv().requireFastCheck(); + }); + + function basicAnythingSettings() { + return { + key: fc.oneof(fc.string(), fc.constantFrom('k1', 'k2', 'k3')), + // Limiting depth & number of keys allows fast-check to try + // a lot more scalar values. + maxDepth: 2, + maxKeys: 5, + withBoxedValues: true, + withMap: true, + withSet: true + }; + } + + function numRuns() { + var many = 5000000; + + // Be thorough but very slow when specified (usually on CI). + if (process.env.JASMINE_LONG_PROPERTY_TESTS) { + console.log( + 'Using', + many, + 'runs of fc.assert because JASMINE_LONG_PROPERTY_TESTS was set. This may take several minutes.' + ); + return many; + } else { + return undefined; + } + } + + it('is symmetric', function() { + fc.assert( + fc.property( + fc.anything(basicAnythingSettings()), + fc.anything(basicAnythingSettings()), + function(a, b) { + return ( + jasmineUnderTest.matchersUtil.equals(a, b) === + jasmineUnderTest.matchersUtil.equals(b, a) + ); + } + ), + { + numRuns: numRuns(), + examples: [[0, 5e-324]] + } + ); + }); + + it('is reflexive', function() { + var anythingSettings = basicAnythingSettings(); + anythingSettings.withMap = false; + fc.assert( + fc.property(fc.dedup(fc.anything(anythingSettings), 2), function( + values + ) { + return jasmineUnderTest.matchersUtil.equals(values[0], values[1]); + }), + { + numRuns: numRuns() + } + ); + }); + }); + it("passes for literals that are triple-equal", function() { expect(jasmineUnderTest.matchersUtil.equals(null, null)).toBe(true); expect(jasmineUnderTest.matchersUtil.equals(void 0, void 0)).toBe(true); @@ -164,7 +235,7 @@ describe("matchersUtil", function() { expect(jasmineUnderTest.matchersUtil.equals(a,b)).toBe(true); }); - + it("passes for equivalent Promises (GitHub issue #1314)", function() { if (typeof Promise === 'undefined') { return; } diff --git a/spec/helpers/requireFastCheck.js b/spec/helpers/requireFastCheck.js new file mode 100644 index 00000000..140b8e80 --- /dev/null +++ b/spec/helpers/requireFastCheck.js @@ -0,0 +1,16 @@ +(function(env) { + var NODE_JS = + typeof process !== 'undefined' && + process.versions && + typeof process.versions.node === 'string'; + + env.requireFastCheck = function() { + if (!NODE_JS) { + env.pending( + "Property tests don't run in the browser. Use `npm test` to run them." + ); + } + + return require('fast-check'); + }; +})(jasmine.getEnv()); diff --git a/spec/property/matchersUtilSpec.js b/spec/property/matchersUtilSpec.js deleted file mode 100644 index 384a1f14..00000000 --- a/spec/property/matchersUtilSpec.js +++ /dev/null @@ -1,69 +0,0 @@ -describe('matchersUtil -- property tests', function() { - 'use strict'; - var fc = require('fast-check'); - - function basicAnythingSettings() { - return { - key: fc.oneof(fc.string(), fc.constantFrom('k1', 'k2', 'k3')), - // Limiting depth & number of keys allows fast-check to try - // a lot more scalar values. - maxDepth: 2, - maxKeys: 5, - withBoxedValues: true, - withMap: true, - withSet: true - }; - } - - function numRuns() { - var many = 5000000; - - // Be thorough but very slow when specified (usually on CI). - if (process.env.JASMINE_LONG_PROPERTY_TESTS) { - console.log( - 'Using', - many, - 'runs of fc.assert because JASMINE_LONG_PROPERTY_TESTS was set. This may take several minutes.' - ); - return many; - } else { - return undefined; - } - } - - describe('equals', function() { - it('is symmetric', function() { - fc.assert( - fc.property( - fc.anything(basicAnythingSettings()), - fc.anything(basicAnythingSettings()), - function(a, b) { - return ( - jasmineUnderTest.matchersUtil.equals(a, b) === - jasmineUnderTest.matchersUtil.equals(b, a) - ); - } - ), - { - numRuns: numRuns(), - examples: [[0, 5e-324]] - } - ); - }); - - it('is reflexive', function() { - var anythingSettings = basicAnythingSettings(); - anythingSettings.withMap = false; - fc.assert( - fc.property(fc.dedup(fc.anything(anythingSettings), 2), function( - values - ) { - return jasmineUnderTest.matchersUtil.equals(values[0], values[1]); - }), - { - numRuns: numRuns() - } - ); - }); - }); -}); diff --git a/spec/support/jasmine-browser.js b/spec/support/jasmine-browser.js index bbc9c4ac..61076dbb 100644 --- a/spec/support/jasmine-browser.js +++ b/spec/support/jasmine-browser.js @@ -15,7 +15,7 @@ module.exports = { '**/*.js' ], specDir: 'spec', - specFiles: ['**/*[Ss]pec.js', '!npmPackage/**/*', '!property/**/*'], + specFiles: ['**/*[Ss]pec.js', '!npmPackage/**/*'], helpers: [ 'helpers/asyncAwait.js', 'helpers/BrowserFlags.js', @@ -26,6 +26,7 @@ module.exports = { 'helpers/domHelpers.js', 'helpers/integrationMatchers.js', 'helpers/promises.js', + 'helpers/requireFastCheck.js', 'helpers/defineJasmineUnderTest.js' ], random: true, diff --git a/spec/support/jasmine.json b/spec/support/jasmine.json index 6ce73409..b48efde5 100644 --- a/spec/support/jasmine.json +++ b/spec/support/jasmine.json @@ -2,7 +2,6 @@ "spec_dir": "spec", "spec_files": [ "core/**/*[Ss]pec.js", - "property/**/*[Ss]pec.js", "npmPackage/**/*[Ss]pec.js" ], "helpers": [ @@ -14,6 +13,7 @@ "helpers/domHelpers.js", "helpers/integrationMatchers.js", "helpers/promises.js", + "helpers/requireFastCheck.js", "helpers/nodeDefineJasmineUnderTest.js" ], "random": true From 8a5216401f706812aacc0624ad94d2065ae1f20a Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 11 Jan 2020 14:29:24 -0800 Subject: [PATCH 109/201] Built distribution --- lib/jasmine-core/boot.js | 2 +- lib/jasmine-core/jasmine-html.js | 2 +- lib/jasmine-core/jasmine.js | 7 +++++-- lib/jasmine-core/node_boot.js | 2 +- 4 files changed, 8 insertions(+), 5 deletions(-) diff --git a/lib/jasmine-core/boot.js b/lib/jasmine-core/boot.js index aa501180..f3354fb2 100644 --- a/lib/jasmine-core/boot.js +++ b/lib/jasmine-core/boot.js @@ -1,5 +1,5 @@ /* -Copyright (c) 2008-2019 Pivotal Labs +Copyright (c) 2008-2020 Pivotal Labs Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the diff --git a/lib/jasmine-core/jasmine-html.js b/lib/jasmine-core/jasmine-html.js index aecf2f1b..c53a1e36 100644 --- a/lib/jasmine-core/jasmine-html.js +++ b/lib/jasmine-core/jasmine-html.js @@ -1,5 +1,5 @@ /* -Copyright (c) 2008-2019 Pivotal Labs +Copyright (c) 2008-2020 Pivotal Labs Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 25adbf80..a126c89b 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1,5 +1,5 @@ /* -Copyright (c) 2008-2019 Pivotal Labs +Copyright (c) 2008-2020 Pivotal Labs Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the @@ -6658,6 +6658,9 @@ getJasmineRequireObj().interface = function(jasmine, env) { * Define a single spec. A spec should contain one or more {@link expect|expectations} that test the state of the code. * * A spec whose expectations all succeed will be passing and a spec with any failures will fail. + * The name `it` is a pronoun for the test target, not an abbreviation of anything. It makes the + * spec more readable by connecting the function name `it` and the argument `description` as a + * complete sentence. * @name it * @since 1.3.0 * @function @@ -7787,7 +7790,7 @@ getJasmineRequireObj().StackTrace = function(j$) { } function messagePrefixLength(message, stackLines) { - if (!stackLines[0].match(/^Error/)) { + if (!stackLines[0].match(/^\w*Error/)) { return 0; } diff --git a/lib/jasmine-core/node_boot.js b/lib/jasmine-core/node_boot.js index 921d3434..d62c7d36 100644 --- a/lib/jasmine-core/node_boot.js +++ b/lib/jasmine-core/node_boot.js @@ -1,5 +1,5 @@ /* -Copyright (c) 2008-2019 Pivotal Labs +Copyright (c) 2008-2020 Pivotal Labs Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the From 1545112744bc06afb105e78799ceadda62bae391 Mon Sep 17 00:00:00 2001 From: johnjbarton Date: Tue, 14 Jan 2020 09:38:59 -0800 Subject: [PATCH 110/201] feat(GlobalErrors): Route unhandledrejections to onerror Fixes #1777 --- spec/core/GlobalErrorsSpec.js | 30 ++++++++++++++++++++++++++++++ src/core/GlobalErrors.js | 17 +++++++++++++++++ 2 files changed, 47 insertions(+) diff --git a/spec/core/GlobalErrorsSpec.js b/spec/core/GlobalErrorsSpec.js index 3880b041..42f9f37c 100644 --- a/spec/core/GlobalErrorsSpec.js +++ b/spec/core/GlobalErrorsSpec.js @@ -193,4 +193,34 @@ describe('GlobalErrors', function() { 'foo' ); }); + + it('reports unhandledRejection in browser', function() { + var fakeGlobal = { + addEventListener: jasmine.createSpy('addEventListener'), + removeEventListener: jasmine.createSpy('removeEventListener'), + onerror: jasmine.createSpy('onerror') + }, + handler = jasmine.createSpy('errorHandler'), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); + + errors.install(); + expect(fakeGlobal.addEventListener).toHaveBeenCalledWith( + 'unhandledrejection', + jasmine.any(Function) + ); + + errors.pushListener(handler); + + var addedListener = fakeGlobal.addEventListener.calls.argsFor(0)[1]; + addedListener({ reason: new Error('bar') }); + + expect(handler).toHaveBeenCalledWith('Unhandled Rejection: Error: bar'); + + errors.uninstall(); + + expect(fakeGlobal.removeEventListener).toHaveBeenCalledWith( + 'unhandledrejection', + addedListener + ); + }); }); diff --git a/src/core/GlobalErrors.js b/src/core/GlobalErrors.js index 2c58e684..2fe4725d 100644 --- a/src/core/GlobalErrors.js +++ b/src/core/GlobalErrors.js @@ -63,8 +63,25 @@ getJasmineRequireObj().GlobalErrors = function(j$) { var originalHandler = global.onerror; global.onerror = onerror; + var browserRejectionHandler = function browserRejectionHandler(event) { + onerror('Unhandled Rejection: ' + event.reason); + }; + + if (global.addEventListener) { + global.addEventListener( + 'unhandledrejection', + browserRejectionHandler + ); + } + this.uninstall = function uninstall() { global.onerror = originalHandler; + if (global.removeEventListener) { + global.removeEventListener( + 'unhandledrejection', + browserRejectionHandler + ); + } }; } }; From 7f392d188ea9a41faad9033c372031327c694690 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Mon, 20 Jan 2020 10:18:29 -0800 Subject: [PATCH 111/201] Don't leak global error handlers between Jasmine's own tests --- lib/jasmine-core/jasmine.js | 6 + spec/core/EnvSpec.js | 10 +- spec/core/ExceptionsSpec.js | 4 + spec/core/PrettyPrintSpec.js | 90 ++++--- spec/core/SpySpec.js | 4 + spec/core/SuiteSpec.js | 52 ++-- .../integration/CustomAsyncMatchersSpec.js | 4 + spec/core/integration/CustomMatchersSpec.js | 4 + .../integration/CustomSpyStrategiesSpec.js | 4 + .../integration/DefaultSpyStrategySpec.js | 4 + spec/core/integration/EnvSpec.js | 255 +++++++----------- spec/core/integration/MatchersSpec.js | 14 +- spec/core/integration/SpecRunningSpec.js | 4 + spec/core/matchers/matchersUtilSpec.js | 2 - .../matchers/toHaveBeenCalledBeforeSpec.js | 68 ++--- spec/core/matchers/toHaveBeenCalledSpec.js | 8 +- .../matchers/toHaveBeenCalledTimesSpec.js | 14 +- .../core/matchers/toHaveBeenCalledWithSpec.js | 8 +- spec/html/HtmlReporterSpec.js | 126 ++++----- spec/html/MatchersHtmlSpec.js | 4 + src/core/Env.js | 6 + 21 files changed, 339 insertions(+), 352 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index cf2a8adc..e1e7615a 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -2100,6 +2100,12 @@ getJasmineRequireObj().Env = function(j$) { throw new Error(message); } }; + + this.cleanup_ = function() { + if (globalErrors) { + globalErrors.uninstall(); + } + }; } return Env; diff --git a/spec/core/EnvSpec.js b/spec/core/EnvSpec.js index aa87a997..61b962b1 100644 --- a/spec/core/EnvSpec.js +++ b/spec/core/EnvSpec.js @@ -5,6 +5,10 @@ describe('Env', function() { env = new jasmineUnderTest.Env(); }); + afterEach(function() { + env.cleanup_(); + }); + describe('#pending', function() { it('throws the Pending Spec exception', function() { expect(function() { @@ -281,11 +285,13 @@ describe('Env', function() { it('installs a global error handler on construction', function() { var globalErrors = jasmine.createSpyObj('globalErrors', [ 'install', + 'uninstall', 'pushListener', 'popListener' ]); spyOn(jasmineUnderTest, 'GlobalErrors').and.returnValue(globalErrors); - new jasmineUnderTest.Env(); + env.cleanup_(); + env = new jasmineUnderTest.Env(); expect(globalErrors.install).toHaveBeenCalled(); }); }); @@ -294,10 +300,12 @@ describe('Env', function() { it('does not install a global error handler until execute is called', function() { var globalErrors = jasmine.createSpyObj('globalErrors', [ 'install', + 'uninstall', 'pushListener', 'popListener' ]); spyOn(jasmineUnderTest, 'GlobalErrors').and.returnValue(globalErrors); + env.cleanup_(); env = new jasmineUnderTest.Env({ suppressLoadErrors: true }); expect(globalErrors.install).not.toHaveBeenCalled(); env.execute(); diff --git a/spec/core/ExceptionsSpec.js b/spec/core/ExceptionsSpec.js index 538c682d..c5e65754 100644 --- a/spec/core/ExceptionsSpec.js +++ b/spec/core/ExceptionsSpec.js @@ -5,6 +5,10 @@ describe('Exceptions:', function() { env = new jasmineUnderTest.Env(); }); + afterEach(function() { + env.cleanup_(); + }); + it('should handle exceptions thrown, but continue', function(done) { var secondTest = jasmine.createSpy('second test'); env.describe('Suite for handles exceptions', function() { diff --git a/spec/core/PrettyPrintSpec.js b/spec/core/PrettyPrintSpec.js index 1249d8c6..5c397eb5 100644 --- a/spec/core/PrettyPrintSpec.js +++ b/spec/core/PrettyPrintSpec.js @@ -327,52 +327,62 @@ describe('jasmineUnderTest.pp', function() { expect(jasmineUnderTest.pp(now)).toEqual('Date(' + now.toString() + ')'); }); - it('should stringify spy objects properly', function() { - var TestObject = { - someFunction: function() {} - }, - env = new jasmineUnderTest.Env(); + describe('with a spy object', function() { + var env; - var spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() { - return []; - }, - createSpy: function(name, originalFn) { - return jasmineUnderTest.Spy(name, originalFn); - } + beforeEach(function() { + env = new jasmineUnderTest.Env(); }); - spyRegistry.spyOn(TestObject, 'someFunction'); - expect(jasmineUnderTest.pp(TestObject.someFunction)).toEqual( - 'spy on someFunction' - ); - - expect(jasmineUnderTest.pp(env.createSpy('something'))).toEqual( - 'spy on something' - ); - }); - - it('should stringify spyOn toString properly', function() { - var TestObject = { - someFunction: function() {} - }, - env = new jasmineUnderTest.Env(); - - var spyRegistry = new jasmineUnderTest.SpyRegistry({ - currentSpies: function() { - return []; - }, - createSpy: function(name, originalFn) { - return jasmineUnderTest.Spy(name, originalFn); - } + afterEach(function() { + env.cleanup_(); }); - spyRegistry.spyOn(TestObject, 'toString'); - var testSpyObj = env.createSpyObj('TheClassName', ['toString']); + it('should stringify spy objects properly', function() { + var TestObject = { + someFunction: function() {} + }; - expect(jasmineUnderTest.pp(testSpyObj)).toEqual( - 'spy on TheClassName.toString' - ); + var spyRegistry = new jasmineUnderTest.SpyRegistry({ + currentSpies: function() { + return []; + }, + createSpy: function(name, originalFn) { + return jasmineUnderTest.Spy(name, originalFn); + } + }); + + spyRegistry.spyOn(TestObject, 'someFunction'); + expect(jasmineUnderTest.pp(TestObject.someFunction)).toEqual( + 'spy on someFunction' + ); + + expect(jasmineUnderTest.pp(env.createSpy('something'))).toEqual( + 'spy on something' + ); + }); + + it('should stringify spyOn toString properly', function() { + var TestObject = { + someFunction: function() {} + }; + + var spyRegistry = new jasmineUnderTest.SpyRegistry({ + currentSpies: function() { + return []; + }, + createSpy: function(name, originalFn) { + return jasmineUnderTest.Spy(name, originalFn); + } + }); + + spyRegistry.spyOn(TestObject, 'toString'); + var testSpyObj = env.createSpyObj('TheClassName', ['toString']); + + expect(jasmineUnderTest.pp(testSpyObj)).toEqual( + 'spy on TheClassName.toString' + ); + }); }); it('should stringify objects that implement jasmineToString', function() { diff --git a/spec/core/SpySpec.js b/spec/core/SpySpec.js index b1165dd3..97d9f03b 100644 --- a/spec/core/SpySpec.js +++ b/spec/core/SpySpec.js @@ -5,6 +5,10 @@ describe('Spies', function() { env = new jasmineUnderTest.Env(); }); + afterEach(function() { + env.cleanup_(); + }); + describe('createSpy', function() { var TestClass; diff --git a/spec/core/SuiteSpec.js b/spec/core/SuiteSpec.js index 8470bad7..2a1cd757 100644 --- a/spec/core/SuiteSpec.js +++ b/spec/core/SuiteSpec.js @@ -1,28 +1,35 @@ describe('Suite', function() { + var env; + + beforeEach(function() { + env = new jasmineUnderTest.Env(); + }); + + afterEach(function() { + env.cleanup_(); + }); + it('keeps its id', function() { - var env = new jasmineUnderTest.Env(), - suite = new jasmineUnderTest.Suite({ - env: env, - id: 456, - description: 'I am a suite' - }); + var suite = new jasmineUnderTest.Suite({ + env: env, + id: 456, + description: 'I am a suite' + }); expect(suite.id).toEqual(456); }); it('returns blank full name for top level suite', function() { - var env = new jasmineUnderTest.Env(), - suite = new jasmineUnderTest.Suite({ - env: env, - description: 'I am a suite' - }); + var suite = new jasmineUnderTest.Suite({ + env: env, + description: 'I am a suite' + }); expect(suite.getFullName()).toEqual(''); }); it('returns its full name when it has parent suites', function() { - var env = new jasmineUnderTest.Env(), - parentSuite = new jasmineUnderTest.Suite({ + var parentSuite = new jasmineUnderTest.Suite({ env: env, description: 'I am a parent suite', parentSuite: jasmine.createSpy('pretend top level suite') @@ -37,8 +44,7 @@ describe('Suite', function() { }); it('adds before functions in order of needed execution', function() { - var env = new jasmineUnderTest.Env(), - suite = new jasmineUnderTest.Suite({ + var suite = new jasmineUnderTest.Suite({ env: env, description: 'I am a suite' }), @@ -52,8 +58,7 @@ describe('Suite', function() { }); it('adds after functions in order of needed execution', function() { - var env = new jasmineUnderTest.Env(), - suite = new jasmineUnderTest.Suite({ + var suite = new jasmineUnderTest.Suite({ env: env, description: 'I am a suite' }), @@ -115,13 +120,12 @@ describe('Suite', function() { }); it('calls timer to compute duration', function() { - var env = new jasmineUnderTest.Env(), - suite = new jasmineUnderTest.Suite({ - env: env, - id: 456, - description: 'I am a suite', - timer: jasmine.createSpyObj('timer', { start: null, elapsed: 77000 }) - }); + var suite = new jasmineUnderTest.Suite({ + env: env, + id: 456, + description: 'I am a suite', + timer: jasmine.createSpyObj('timer', { start: null, elapsed: 77000 }) + }); suite.startTimer(); suite.endTimer(); expect(suite.getResult().duration).toEqual(77000); diff --git a/spec/core/integration/CustomAsyncMatchersSpec.js b/spec/core/integration/CustomAsyncMatchersSpec.js index 0849e42a..a38ad472 100644 --- a/spec/core/integration/CustomAsyncMatchersSpec.js +++ b/spec/core/integration/CustomAsyncMatchersSpec.js @@ -6,6 +6,10 @@ describe('Custom Async Matchers (Integration)', function() { env.configure({random: false}); }); + afterEach(function() { + env.cleanup_(); + }); + it('passes the spec if the custom async matcher passes', function(done) { jasmine.getEnv().requirePromises(); diff --git a/spec/core/integration/CustomMatchersSpec.js b/spec/core/integration/CustomMatchersSpec.js index 17e66354..184c89be 100644 --- a/spec/core/integration/CustomMatchersSpec.js +++ b/spec/core/integration/CustomMatchersSpec.js @@ -7,6 +7,10 @@ describe("Custom Matchers (Integration)", function() { env.configure({random: false}); }); + afterEach(function() { + env.cleanup_(); + }); + it("allows adding more matchers local to a spec", function(done) { env.it('spec defining a custom matcher', function() { env.addMatchers({ diff --git a/spec/core/integration/CustomSpyStrategiesSpec.js b/spec/core/integration/CustomSpyStrategiesSpec.js index 796d3478..7ab4d28d 100644 --- a/spec/core/integration/CustomSpyStrategiesSpec.js +++ b/spec/core/integration/CustomSpyStrategiesSpec.js @@ -6,6 +6,10 @@ describe('Custom Spy Strategies (Integration)', function() { env.configure({random: false}); }); + afterEach(function() { + env.cleanup_(); + }); + it('allows adding more strategies local to a suite', function(done) { var plan = jasmine.createSpy('custom strategy plan') .and.returnValue(42); diff --git a/spec/core/integration/DefaultSpyStrategySpec.js b/spec/core/integration/DefaultSpyStrategySpec.js index 0b02c572..584b25b2 100644 --- a/spec/core/integration/DefaultSpyStrategySpec.js +++ b/spec/core/integration/DefaultSpyStrategySpec.js @@ -6,6 +6,10 @@ describe('Default Spy Strategy (Integration)', function() { env.configure({random: false}); }); + afterEach(function() { + env.cleanup_(); + }); + it('allows defining a default spy strategy', function(done) { env.describe('suite with default strategy', function() { env.beforeEach(function() { diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index eef02e6c..490e9d94 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -1,11 +1,17 @@ describe("Env integration", function() { + var env; + beforeEach(function() { jasmine.getEnv().registerIntegrationMatchers(); + env = new jasmineUnderTest.Env(); + }); + + afterEach(function() { + env.cleanup_(); }); it("Suites execute as expected (no nesting)", function(done) { - var env = new jasmineUnderTest.Env(), - calls = []; + var calls = []; var assertions = function() { expect(calls).toEqual([ @@ -32,8 +38,7 @@ describe("Env integration", function() { }); it("Nested Suites execute as expected", function(done) { - var env = new jasmineUnderTest.Env(), - calls = []; + var calls = []; var assertions = function() { expect(calls).toEqual([ @@ -66,8 +71,7 @@ describe("Env integration", function() { }); it("Multiple top-level Suites execute as expected", function(done) { - var env = new jasmineUnderTest.Env(), - calls = []; + var calls = []; var assertions = function() { expect(calls).toEqual([ @@ -108,8 +112,7 @@ describe("Env integration", function() { }); it('explicitly fails a spec', function(done) { - var env = new jasmineUnderTest.Env(), - specDone = jasmine.createSpy('specDone'); + var specDone = jasmine.createSpy('specDone'); env.addReporter({ specDone: specDone, @@ -179,8 +182,7 @@ describe("Env integration", function() { }); it("produces an understandable error message when 'fail' is used outside of a current spec", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', ['jasmineDone']); + var reporter = jasmine.createSpyObj('fakeReporter', ['jasmineDone']); reporter.jasmineDone.and.callFake(done); env.addReporter(reporter); @@ -197,8 +199,6 @@ describe("Env integration", function() { it("calls associated befores/specs/afters with the same 'this'", function(done) { - var env = new jasmineUnderTest.Env(); - env.addReporter({jasmineDone: done}); env.configure({random: false}); env.describe("tests", function() { @@ -235,8 +235,6 @@ describe("Env integration", function() { }); it("calls associated befores/its/afters with the same 'this' for an async spec", function(done) { - var env = new jasmineUnderTest.Env(); - env.addReporter({jasmineDone: done}); env.describe("with an async spec", function() { @@ -261,8 +259,7 @@ describe("Env integration", function() { }); it("calls associated beforeAlls/afterAlls only once per suite", function(done) { - var env = new jasmineUnderTest.Env(), - before = jasmine.createSpy('beforeAll'), + var before = jasmine.createSpy('beforeAll'), after = jasmine.createSpy('afterAll'); env.addReporter({ @@ -293,8 +290,7 @@ describe("Env integration", function() { }); it("calls associated beforeAlls/afterAlls only once per suite for async", function(done) { - var env = new jasmineUnderTest.Env(), - before = jasmine.createSpy('beforeAll'), + var before = jasmine.createSpy('beforeAll'), after = jasmine.createSpy('afterAll'); env.addReporter({ @@ -332,8 +328,6 @@ describe("Env integration", function() { }); it("calls associated beforeAlls/afterAlls with the cascaded 'this'", function(done) { - var env = new jasmineUnderTest.Env(); - env.addReporter({jasmineDone: done}); env.describe("with beforeAll and afterAll", function() { @@ -386,8 +380,6 @@ describe("Env integration", function() { }); it("tags top-level afterAll failures with a type", function(done) { - var env = new jasmineUnderTest.Env(); - env.addReporter({jasmineDone: function(result) { expect(result.failedExpectations[0].globalErrorType).toEqual('afterAll'); done(); @@ -403,8 +395,7 @@ describe("Env integration", function() { }); it("does not tag suite afterAll failures with a type", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = { + var reporter = { jasmineDone: function() { expect(reporter.suiteDone).toHaveBeenCalled(); done(); @@ -428,8 +419,7 @@ describe("Env integration", function() { }); it("when the beforeAll fails, error at suite level", function (done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "suiteDone", "jasmineDone" ]); + var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "suiteDone", "jasmineDone" ]); reporter.jasmineDone.and.callFake(function() { expect(reporter.specDone.calls.count()).toEqual(2); @@ -465,8 +455,9 @@ describe("Env integration", function() { clearTimeout: function(fn, delay) { clearTimeout(fn, delay) }, }; spyOn(jasmineUnderTest, 'getGlobal').and.returnValue(global); - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "jasmineDone", "suiteDone" ]); + env.cleanup_(); + env = new jasmineUnderTest.Env(); + var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "jasmineDone", "suiteDone" ]); reporter.jasmineDone.and.callFake(function() { expect(reporter.specDone).not.toHaveFailedExpectationsForRunnable('A suite fails', ['fail thrown']); @@ -498,8 +489,7 @@ describe("Env integration", function() { describe('suiteDone reporting', function(){ it("reports when an afterAll fails an expectation", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); + var reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); reporter.jasmineDone.and.callFake(function() { expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('my suite', [ @@ -525,8 +515,7 @@ describe("Env integration", function() { }); it("if there are no specs, it still reports correctly", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); + var reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); reporter.jasmineDone.and.callFake(function() { expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('outer suite', [ @@ -553,8 +542,7 @@ describe("Env integration", function() { }); it("reports when afterAll throws an exception", function(done) { - var env = new jasmineUnderTest.Env(), - error = new Error('After All Exception'), + var error = new Error('After All Exception'), reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); reporter.jasmineDone.and.callFake(function() { @@ -579,8 +567,7 @@ describe("Env integration", function() { }); it("reports when an async afterAll fails an expectation", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); + var reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); reporter.jasmineDone.and.callFake(function() { expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('my suite', [ @@ -605,8 +592,7 @@ describe("Env integration", function() { }); it("reports when an async afterAll throws an exception", function(done) { - var env = new jasmineUnderTest.Env(), - error = new Error('After All Exception'), + var error = new Error('After All Exception'), reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); @@ -633,8 +619,7 @@ describe("Env integration", function() { }); it('reports expectation failures in global beforeAll', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj(['specDone', 'jasmineDone']); + var reporter = jasmine.createSpyObj(['specDone', 'jasmineDone']); reporter.jasmineDone.and.callFake(function(results) { expect(results.failedExpectations).toEqual([jasmine.objectContaining({ message: 'Expected 1 to be 0.' })]); @@ -656,8 +641,7 @@ describe("Env integration", function() { }); it('reports expectation failures in global afterAll', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj(['jasmineDone']); + var reporter = jasmine.createSpyObj(['jasmineDone']); reporter.jasmineDone.and.callFake(function(results) { expect(results.failedExpectations).toEqual([jasmine.objectContaining({ message: 'Expected 1 to be 0.' })]); @@ -678,8 +662,7 @@ describe("Env integration", function() { }); it("Allows specifying which specs and suites to run", function(done) { - var env = new jasmineUnderTest.Env(), - calls = [], + var calls = [], suiteCallback = jasmine.createSpy('suite callback'), firstSpec, secondSuite; @@ -714,8 +697,7 @@ describe("Env integration", function() { }); it('runs before and after all functions for runnables provided to .execute()', function(done) { - var env = new jasmineUnderTest.Env(), - calls = [], + var calls = [], first_spec, second_spec; @@ -750,8 +732,7 @@ describe("Env integration", function() { }); it("Allows filtering out specs and suites to run programmatically", function(done) { - var env = new jasmineUnderTest.Env(), - calls = [], + var calls = [], suiteCallback = jasmine.createSpy('suite callback'), firstSpec, secondSuite; @@ -793,8 +774,6 @@ describe("Env integration", function() { }); it("Functions can be spied on and have their calls tracked", function (done) { - var env = new jasmineUnderTest.Env(); - var originalFunctionWasCalled = false; var subject = { spiedFunc: function() { @@ -833,8 +812,7 @@ describe("Env integration", function() { }); it('can be configured to allow respying on functions', function (done) { - var env = new jasmineUnderTest.Env(), - foo = { + var foo = { bar: function () { return 1; } @@ -859,8 +837,7 @@ describe("Env integration", function() { }); it('removes all spies added in a spec after the spec is complete', function(done) { - var env = new jasmineUnderTest.Env(), - originalFoo = function() {}, + var originalFoo = function() {}, testObj = { foo: originalFoo }, @@ -887,8 +864,7 @@ describe("Env integration", function() { }); it('removes all spies added in a suite after the suite is complete', function(done) { - var env = new jasmineUnderTest.Env(), - originalFoo = function() {}, + var originalFoo = function() {}, testObj = { foo: originalFoo }; @@ -917,8 +893,7 @@ describe("Env integration", function() { }); it('removes a spy from the top suite after the run is complete', function(done) { - var env = new jasmineUnderTest.Env(), - originalFoo = function() {}, + var originalFoo = function() {}, testObj = { foo: originalFoo }; @@ -944,8 +919,10 @@ describe("Env integration", function() { it("Mock clock can be installed and used in tests", function(done) { var globalSetTimeout = jasmine.createSpy('globalSetTimeout').and.callFake(function(cb, t) { setTimeout(cb, t); }), delayedFunctionForGlobalClock = jasmine.createSpy('delayedFunctionForGlobalClock'), - delayedFunctionForMockClock = jasmine.createSpy('delayedFunctionForMockClock'), - env = new jasmineUnderTest.Env({global: { setTimeout: globalSetTimeout, clearTimeout: clearTimeout, setImmediate: function(cb) { setTimeout(cb, 0); } }}); + delayedFunctionForMockClock = jasmine.createSpy('delayedFunctionForMockClock'); + + env.cleanup_(); + env = new jasmineUnderTest.Env({global: { setTimeout: globalSetTimeout, clearTimeout: clearTimeout, setImmediate: function(cb) { setTimeout(cb, 0); } }}); var assertions = function() { expect(delayedFunctionForMockClock).toHaveBeenCalled(); @@ -976,8 +953,7 @@ describe("Env integration", function() { }); it("should run async specs in order, waiting for them to complete", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone']), + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone']), mutatedVar; reporter.jasmineDone.and.callFake(function() { @@ -1008,9 +984,10 @@ describe("Env integration", function() { describe("with a mock clock", function() { var realSetTimeout; function createMockedEnv() { + env.cleanup_(); // explicitly pass in timing functions so we can make sure that clear stack always works // no matter how long the suite in the spec is - return new jasmineUnderTest.Env({ global: { + env = new jasmineUnderTest.Env({ global: { setTimeout: function(cb, t) { var stack = jasmine.util.errorWithStack().stack; if (stack.indexOf('ClearStack') >= 0) { @@ -1040,8 +1017,8 @@ describe("Env integration", function() { }); it("should wait a default interval before failing specs that haven't called done yet", function(done) { - var env = createMockedEnv(), - reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "jasmineDone" ]); + createMockedEnv(); + var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "jasmineDone" ]); reporter.specDone.and.callFake(function(result) { expect(result).toEqual(jasmine.objectContaining({status: 'failed'})); @@ -1069,8 +1046,8 @@ describe("Env integration", function() { }); it("should not use the mock clock for asynchronous timeouts", function(done){ - var env = createMockedEnv(), - reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "jasmineDone" ]), + createMockedEnv(); + var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "jasmineDone" ]), clock = env.clock; reporter.specDone.and.callFake(function() { @@ -1107,8 +1084,8 @@ describe("Env integration", function() { }); it('should wait a custom interval before reporting async functions that fail to complete', function(done) { - var env = createMockedEnv(), - reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone', 'suiteDone', 'specDone']); + createMockedEnv(); + var reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(r) { expect(r.failedExpectations).toEqual([]); @@ -1207,8 +1184,7 @@ describe("Env integration", function() { }); it('explicitly fails an async spec', function(done) { - var env = new jasmineUnderTest.Env(), - specDone = jasmine.createSpy('specDone'); + var specDone = jasmine.createSpy('specDone'); env.addReporter({ specDone: specDone, @@ -1273,8 +1249,7 @@ describe("Env integration", function() { describe('focused tests', function() { it('should only run the focused tests', function(done) { - var env = new jasmineUnderTest.Env(), - calls = []; + var calls = []; var assertions = function() { expect(calls).toEqual(['focused']); @@ -1297,8 +1272,7 @@ describe("Env integration", function() { }); it('should only run focused suites', function(done){ - var env = new jasmineUnderTest.Env(), - calls = []; + var calls = []; var assertions = function() { expect(calls).toEqual(['focused']); @@ -1323,8 +1297,7 @@ describe("Env integration", function() { }); it('should run focused tests inside an xdescribe', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ + var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineStarted", "jasmineDone", "suiteStarted", @@ -1359,8 +1332,7 @@ describe("Env integration", function() { }); it('should run focused suites inside an xdescribe', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ + var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineStarted", "jasmineDone", "suiteStarted", @@ -1398,8 +1370,7 @@ describe("Env integration", function() { }); it("should report as expected", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ + var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineStarted", "jasmineDone", "suiteStarted", @@ -1472,8 +1443,7 @@ describe("Env integration", function() { }); it("should report the random seed at the beginning and end of execution", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ + var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineStarted", "jasmineDone", "suiteStarted", @@ -1500,8 +1470,7 @@ describe("Env integration", function() { }); it('should report pending spec messages', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ + var reporter = jasmine.createSpyObj('fakeReporter', [ 'specDone', 'jasmineDone' ]); @@ -1537,8 +1506,7 @@ describe("Env integration", function() { reject(this.exception); }; - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ + var reporter = jasmine.createSpyObj('fakeReporter', [ 'specDone', 'jasmineDone' ]); @@ -1564,8 +1532,7 @@ describe("Env integration", function() { }); it('should report using fallback reporter', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ + var reporter = jasmine.createSpyObj('fakeReporter', [ 'specDone', 'jasmineDone' ]); @@ -1586,8 +1553,7 @@ describe("Env integration", function() { }); it('should report xdescribes as expected', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ + var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineStarted", "jasmineDone", "suiteStarted", @@ -1627,8 +1593,7 @@ describe("Env integration", function() { }); it("should be possible to get full name from a spec", function() { - var env = new jasmineUnderTest.Env(), - topLevelSpec, nestedSpec, doublyNestedSpec; + var topLevelSpec, nestedSpec, doublyNestedSpec; env.describe("my tests", function() { topLevelSpec = env.it("are sometimes top level", function() { @@ -1649,8 +1614,7 @@ describe("Env integration", function() { }); it("Custom equality testers should be per spec", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ + var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineDone", "specDone" ]); @@ -1683,8 +1647,7 @@ describe("Env integration", function() { }); it("Custom equality testers should be per suite", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ + var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineDone", "specDone" ]); @@ -1726,8 +1689,7 @@ describe("Env integration", function() { }); it("Custom equality testers for toContain should be per spec", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ + var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineDone", "specDone" ]); @@ -1760,8 +1722,7 @@ describe("Env integration", function() { }); it("produces an understandable error message when an 'expect' is used outside of a current spec", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', ['jasmineDone']); + var reporter = jasmine.createSpyObj('fakeReporter', ['jasmineDone']); reporter.jasmineDone.and.callFake(done); env.addReporter(reporter); @@ -1777,8 +1738,7 @@ describe("Env integration", function() { }); it("Custom equality testers for toContain should be per suite", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReporter', [ + var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineDone", "specDone" ]); @@ -1820,8 +1780,7 @@ describe("Env integration", function() { }); it("Custom matchers should be per spec", function(done) { - var env = new jasmineUnderTest.Env(), - matchers = { + var matchers = { toFoo: function() {} }; @@ -1842,8 +1801,7 @@ describe("Env integration", function() { }); it("Custom matchers should be per suite", function(done) { - var env = new jasmineUnderTest.Env(), - matchers = { + var matchers = { toFoo: function() {} }; @@ -1871,8 +1829,7 @@ describe("Env integration", function() { }); it('throws an exception if you try to create a spy outside of a runnable', function (done) { - var env = new jasmineUnderTest.Env(), - obj = {fn: function () {}}, + var obj = {fn: function () {}}, exception; env.describe("a suite", function () { @@ -1894,8 +1851,7 @@ describe("Env integration", function() { }); it('throws an exception if you try to add a matcher outside of a runnable', function (done) { - var env = new jasmineUnderTest.Env(), - obj = {fn: function () {}}, + var obj = {fn: function () {}}, exception; env.describe("a suite", function () { @@ -1917,8 +1873,7 @@ describe("Env integration", function() { }); it('throws an exception if you try to add a custom equality outside of a runnable', function (done) { - var env = new jasmineUnderTest.Env(), - obj = {fn: function () {}}, + var obj = {fn: function () {}}, exception; env.describe("a suite", function () { @@ -1940,8 +1895,7 @@ describe("Env integration", function() { }); it("should associate errors thrown from async code with the correct runnable", function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone','specDone']); + var reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone','specDone']); reporter.jasmineDone.and.callFake(function() { expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('async suite', [ @@ -1973,8 +1927,7 @@ describe("Env integration", function() { }); it('should throw on suites/specs/befores/afters nested in methods other than \'describe\'', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function() { var msg = /\'.*\' should only be used in \'describe\' function/; @@ -2037,11 +1990,13 @@ describe("Env integration", function() { var global = { setTimeout: function(fn, delay) { setTimeout(fn, delay) }, clearTimeout: function(fn, delay) { clearTimeout(fn, delay) }, + onerror: function() {} }; spyOn(jasmineUnderTest, 'getGlobal').and.returnValue(global); - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + env.cleanup_(); + env = new jasmineUnderTest.Env(); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { expect(e.failedExpectations).toEqual([ @@ -2087,8 +2042,9 @@ describe("Env integration", function() { globalErrors.pushListener(onerror); spyOn(jasmineUnderTest, 'GlobalErrors').and.returnValue(globalErrors); - var env = new jasmineUnderTest.Env({suppressLoadErrors: true}); - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + env.cleanup_(); + env = new jasmineUnderTest.Env({suppressLoadErrors: true}); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { expect(e.failedExpectations).toEqual([]); @@ -2106,8 +2062,7 @@ describe("Env integration", function() { describe('Overall status in the jasmineDone event', function() { describe('When everything passes', function() { it('is "passed"', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { expect(e.overallStatus).toEqual('passed'); @@ -2122,8 +2077,7 @@ describe("Env integration", function() { describe('When a spec fails', function() { it('is "failed"', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { expect(e.overallStatus).toEqual('failed'); @@ -2139,10 +2093,9 @@ describe("Env integration", function() { }); describe('when spec has no expectations', function() { - var env, reporter; + var reporter; beforeEach(function() { - env = new jasmineUnderTest.Env(); reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); env.addReporter(reporter); @@ -2175,8 +2128,7 @@ describe("Env integration", function() { describe('When a top-level beforeAll fails', function() { it('is "failed"', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { expect(e.overallStatus).toEqual('failed'); @@ -2194,8 +2146,7 @@ describe("Env integration", function() { describe('When a suite beforeAll fails', function() { it('is "failed"', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { expect(e.overallStatus).toEqual('failed'); @@ -2215,8 +2166,7 @@ describe("Env integration", function() { describe('When a top-level afterAll fails', function() { it('is "failed"', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { expect(e.overallStatus).toEqual('failed'); @@ -2234,8 +2184,7 @@ describe("Env integration", function() { describe('When a suite afterAll fails', function() { it('is "failed"', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { expect(e.overallStatus).toEqual('failed'); @@ -2261,7 +2210,8 @@ describe("Env integration", function() { }; spyOn(jasmineUnderTest, 'getGlobal').and.returnValue(global); - var env = new jasmineUnderTest.Env(); + env.cleanup_(); + env = new jasmineUnderTest.Env(); var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { @@ -2278,8 +2228,7 @@ describe("Env integration", function() { describe('When there are no specs', function() { it('is "incomplete"', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { expect(e.overallStatus).toEqual('incomplete'); @@ -2294,8 +2243,7 @@ describe("Env integration", function() { describe('When a spec is focused', function() { it('is "incomplete"', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { expect(e.overallStatus).toEqual('incomplete'); @@ -2311,8 +2259,7 @@ describe("Env integration", function() { describe('When a suite is focused', function() { it('is "incomplete"', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { expect(e.overallStatus).toEqual('incomplete'); @@ -2330,8 +2277,7 @@ describe("Env integration", function() { describe('When there are both failures and focused specs', function() { it('is "failed"', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); reporter.jasmineDone.and.callFake(function(e) { expect(e.overallStatus).toEqual('failed'); @@ -2349,8 +2295,7 @@ describe("Env integration", function() { }); it('should report deprecation warnings on the correct specs and suites', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); // prevent deprecation from being displayed spyOn(console, "error"); @@ -2395,8 +2340,7 @@ describe("Env integration", function() { }); it('should report deprecation stack with an error object', function(done) { - var env = new jasmineUnderTest.Env(), - exceptionFormatter = new jasmineUnderTest.ExceptionFormatter(), + var exceptionFormatter = new jasmineUnderTest.ExceptionFormatter(), reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']), topLevelError, suiteLevelError, specLevelError; @@ -2458,8 +2402,7 @@ describe("Env integration", function() { it('supports async matchers', function(done) { jasmine.getEnv().requirePromises(); - var env = new jasmineUnderTest.Env(), - specDone = jasmine.createSpy('specDone'), + var specDone = jasmine.createSpy('specDone'), suiteDone = jasmine.createSpy('suiteDone'); env.addReporter({ @@ -2507,8 +2450,7 @@ describe("Env integration", function() { it('provides custom equality testers to async matchers', function(done) { jasmine.getEnv().requirePromises(); - var env = new jasmineUnderTest.Env(), - specDone = jasmine.createSpy('specDone'); + var specDone = jasmine.createSpy('specDone'); env.addReporter({ specDone: specDone, @@ -2533,8 +2475,7 @@ describe("Env integration", function() { it('includes useful stack frames in async matcher failures', function(done) { jasmine.getEnv().requirePromises(); - var env = new jasmineUnderTest.Env(), - specDone = jasmine.createSpy('specDone'); + var specDone = jasmine.createSpy('specDone'); env.addReporter({ specDone: specDone, @@ -2560,8 +2501,7 @@ describe("Env integration", function() { it('reports an error when an async expectation occurs after the spec finishes', function(done) { jasmine.getEnv().requirePromises(); - var env = new jasmineUnderTest.Env(), - resolve, + var resolve, promise = new Promise(function(res) { resolve = res; }); env.describe('a suite', function() { @@ -2609,8 +2549,7 @@ describe("Env integration", function() { it('reports an error when an async expectation occurs after the suite finishes', function(done) { jasmine.getEnv().requirePromises(); - var env = new jasmineUnderTest.Env(), - resolve, + var resolve, promise = new Promise(function(res) { resolve = res; }); env.describe('a suite', function() { diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js index f75aae28..95eaf041 100644 --- a/spec/core/integration/MatchersSpec.js +++ b/spec/core/integration/MatchersSpec.js @@ -1,7 +1,16 @@ describe('Matchers (Integration)', function() { + var env; + + beforeEach(function() { + env = new jasmineUnderTest.Env(); + }); + + afterEach(function() { + env.cleanup_(); + }); + function verifyPasses(expectations) { it('passes', function(done) { - var env = new jasmineUnderTest.Env(); env.it('a spec', function() { expectations(env); }); @@ -26,7 +35,6 @@ describe('Matchers (Integration)', function() { function verifyFails(expectations) { it('fails', function(done) { - var env = new jasmineUnderTest.Env(); env.it('a spec', function() { expectations(env); }); @@ -51,7 +59,6 @@ describe('Matchers (Integration)', function() { function verifyPassesAsync(expectations) { it('passes', function(done) { jasmine.getEnv().requirePromises(); - var env = new jasmineUnderTest.Env(); env.it('a spec', function() { return expectations(env); @@ -77,7 +84,6 @@ describe('Matchers (Integration)', function() { function verifyFailsAsync(expectations) { it('fails', function(done) { - var env = new jasmineUnderTest.Env(); jasmine.getEnv().requirePromises(); env.it('a spec', function() { diff --git a/spec/core/integration/SpecRunningSpec.js b/spec/core/integration/SpecRunningSpec.js index 1bd670b4..d522cf86 100644 --- a/spec/core/integration/SpecRunningSpec.js +++ b/spec/core/integration/SpecRunningSpec.js @@ -7,6 +7,10 @@ describe("spec running", function () { env.configure({random: false}); }); + afterEach(function() { + env.cleanup_(); + }); + it('should assign spec ids sequentially', function() { var it0, it1, it2, it3, it4; env.describe('test suite', function() { diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index 508a5bfd..d5d88ab3 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -678,7 +678,6 @@ describe("matchersUtil", function() { }, diffBuilder = jasmine.createSpyObj('diffBuilder', ['record', 'withPath']); diffBuilder.withPath.and.callFake(function(p, block) { block() }); - debugger; jasmineUnderTest.matchersUtil.equals({x: 42}, {x: tester}, [], diffBuilder); expect(diffBuilder.withPath).toHaveBeenCalledWith('x', jasmine.any(Function)); @@ -693,7 +692,6 @@ describe("matchersUtil", function() { }, diffBuilder = jasmine.createSpyObj('diffBuilder', ['record', 'withPath']); diffBuilder.withPath.and.callFake(function(p, block) { block() }); - debugger; jasmineUnderTest.matchersUtil.equals({x: 42}, {x: tester}, [], diffBuilder); expect(diffBuilder.withPath).toHaveBeenCalledWith('x', jasmine.any(Function)); diff --git a/spec/core/matchers/toHaveBeenCalledBeforeSpec.js b/spec/core/matchers/toHaveBeenCalledBeforeSpec.js index f2e89c2f..53aa3fdb 100644 --- a/spec/core/matchers/toHaveBeenCalledBeforeSpec.js +++ b/spec/core/matchers/toHaveBeenCalledBeforeSpec.js @@ -1,24 +1,30 @@ -describe("toHaveBeenCalledBefore", function() { - it("throws an exception when the actual is not a spy", function() { +describe("toHaveBeenCalledBefore", function () { + it("throws an exception when the actual is not a spy", function () { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), - fn = function() {}, - secondSpy = new jasmineUnderTest.Env().createSpy('second spy'); + fn = function () { + }, + spy = new jasmineUnderTest.Spy('a spy'); - expect(function() { matcher.compare(fn, secondSpy) }).toThrowError(Error, /Expected a spy, but got Function./); + expect(function () { + matcher.compare(fn, spy) + }).toThrowError(Error, /Expected a spy, but got Function./); }); - it("throws an exception when the expected is not a spy", function() { + it("throws an exception when the expected is not a spy", function () { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), - firstSpy = new jasmineUnderTest.Env().createSpy('first spy'), - fn = function() {}; + spy = new jasmineUnderTest.Spy('a spy'), + fn = function () { + }; - expect(function() { matcher.compare(firstSpy, fn) }).toThrowError(Error, /Expected a spy, but got Function./); + expect(function () { + matcher.compare(spy, fn) + }).toThrowError(Error, /Expected a spy, but got Function./); }); - it("fails when the actual was not called", function() { + it("fails when the actual was not called", function () { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), - firstSpy = new jasmineUnderTest.Env().createSpy('first spy'), - secondSpy = new jasmineUnderTest.Env().createSpy('second spy'); + firstSpy = new jasmineUnderTest.Spy('first spy'), + secondSpy = new jasmineUnderTest.Spy('second spy'); secondSpy(); @@ -27,10 +33,10 @@ describe("toHaveBeenCalledBefore", function() { expect(result.message).toMatch(/Expected spy first spy to have been called./); }); - it("fails when the expected was not called", function() { + it("fails when the expected was not called", function () { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), - firstSpy = new jasmineUnderTest.Env().createSpy('first spy'), - secondSpy = new jasmineUnderTest.Env().createSpy('second spy'); + firstSpy = new jasmineUnderTest.Spy('first spy'), + secondSpy = new jasmineUnderTest.Spy('second spy'); firstSpy(); @@ -39,11 +45,11 @@ describe("toHaveBeenCalledBefore", function() { expect(result.message).toMatch(/Expected spy second spy to have been called./); }); - it("fails when the actual is called after the expected", function() { + it("fails when the actual is called after the expected", function () { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), - firstSpy = new jasmineUnderTest.Env().createSpy('first spy'), - secondSpy = new jasmineUnderTest.Env().createSpy('second spy'), - result; + firstSpy = new jasmineUnderTest.Spy('first spy'), + secondSpy = new jasmineUnderTest.Spy('second spy'), + result; secondSpy(); firstSpy(); @@ -53,11 +59,11 @@ describe("toHaveBeenCalledBefore", function() { expect(result.message).toEqual('Expected spy first spy to have been called before spy second spy'); }); - it("fails when the actual is called before and after the expected", function() { + it("fails when the actual is called before and after the expected", function () { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), - firstSpy = new jasmineUnderTest.Env().createSpy('first spy'), - secondSpy = new jasmineUnderTest.Env().createSpy('second spy'), - result; + firstSpy = new jasmineUnderTest.Spy('first spy'), + secondSpy = new jasmineUnderTest.Spy('second spy'), + result; firstSpy(); secondSpy(); @@ -68,11 +74,11 @@ describe("toHaveBeenCalledBefore", function() { expect(result.message).toEqual('Expected latest call to spy first spy to have been called before first call to spy second spy (no interleaved calls)'); }); - it("fails when the expected is called before and after the actual", function() { + it("fails when the expected is called before and after the actual", function () { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), - firstSpy = new jasmineUnderTest.Env().createSpy('first spy'), - secondSpy = new jasmineUnderTest.Env().createSpy('second spy'), - result; + firstSpy = new jasmineUnderTest.Spy('first spy'), + secondSpy = new jasmineUnderTest.Spy('second spy'), + result; secondSpy(); firstSpy(); @@ -83,11 +89,11 @@ describe("toHaveBeenCalledBefore", function() { expect(result.message).toEqual('Expected first call to spy second spy to have been called after latest call to spy first spy (no interleaved calls)'); }); - it("passes when the actual is called before the expected", function() { + it("passes when the actual is called before the expected", function () { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), - firstSpy = new jasmineUnderTest.Env().createSpy('first spy'), - secondSpy = new jasmineUnderTest.Env().createSpy('second spy'), - result; + firstSpy = new jasmineUnderTest.Spy('first spy'), + secondSpy = new jasmineUnderTest.Spy('second spy'), + result; firstSpy(); secondSpy(); diff --git a/spec/core/matchers/toHaveBeenCalledSpec.js b/spec/core/matchers/toHaveBeenCalledSpec.js index b14116f0..d39236c0 100644 --- a/spec/core/matchers/toHaveBeenCalledSpec.js +++ b/spec/core/matchers/toHaveBeenCalledSpec.js @@ -1,7 +1,7 @@ describe("toHaveBeenCalled", function() { it("passes when the actual was called, with a custom .not fail message", function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalled(), - calledSpy = new jasmineUnderTest.Env().createSpy('called-spy'), + calledSpy = new jasmineUnderTest.Spy('called-spy'), result; calledSpy(); @@ -13,7 +13,7 @@ describe("toHaveBeenCalled", function() { it("fails when the actual was not called", function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalled(), - uncalledSpy = new jasmineUnderTest.Env().createSpy('uncalled spy'), + uncalledSpy = new jasmineUnderTest.Spy('uncalled spy'), result; result = matcher.compare(uncalledSpy); @@ -29,14 +29,14 @@ describe("toHaveBeenCalled", function() { it("throws an exception when invoked with any arguments", function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalled(), - spy = new jasmineUnderTest.Env().createSpy('sample spy'); + spy = new jasmineUnderTest.Spy('sample spy'); expect(function() { matcher.compare(spy, 'foo') }).toThrowError(Error, /Does not take arguments, use toHaveBeenCalledWith/); }); it("has a custom message on failure", function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalled(), - spy = new jasmineUnderTest.Env().createSpy('sample-spy'), + spy = new jasmineUnderTest.Spy('sample-spy'), result; result = matcher.compare(spy); diff --git a/spec/core/matchers/toHaveBeenCalledTimesSpec.js b/spec/core/matchers/toHaveBeenCalledTimesSpec.js index 62778fbd..7b3ad2b5 100644 --- a/spec/core/matchers/toHaveBeenCalledTimesSpec.js +++ b/spec/core/matchers/toHaveBeenCalledTimesSpec.js @@ -1,14 +1,14 @@ describe("toHaveBeenCalledTimes", function() { it("passes when the actual 0 matches the expected 0 ", function () { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), - calledSpy = new jasmineUnderTest.Env().createSpy('called-spy'), + calledSpy = new jasmineUnderTest.Spy('called-spy'), result; result = matcher.compare(calledSpy, 0); expect(result.pass).toBeTruthy(); }); it("passes when the actual matches the expected", function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), - calledSpy = new jasmineUnderTest.Env().createSpy('called-spy'), + calledSpy = new jasmineUnderTest.Spy('called-spy'), result; calledSpy(); @@ -18,7 +18,7 @@ describe("toHaveBeenCalledTimes", function() { it("fails when expected numbers is not supplied", function(){ var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), - spy = new jasmineUnderTest.Env().createSpy('spy'), + spy = new jasmineUnderTest.Spy('spy'), result; spy(); @@ -29,7 +29,7 @@ describe("toHaveBeenCalledTimes", function() { it("fails when the actual was called less than the expected", function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), - uncalledSpy = new jasmineUnderTest.Env().createSpy('uncalled spy'), + uncalledSpy = new jasmineUnderTest.Spy('uncalled spy'), result; result = matcher.compare(uncalledSpy, 2); @@ -38,7 +38,7 @@ describe("toHaveBeenCalledTimes", function() { it("fails when the actual was called more than expected", function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), - uncalledSpy = new jasmineUnderTest.Env().createSpy('uncalled spy'), + uncalledSpy = new jasmineUnderTest.Spy('uncalled spy'), result; uncalledSpy(); @@ -59,7 +59,7 @@ describe("toHaveBeenCalledTimes", function() { it("has a custom message on failure that tells it was called only once", function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), - spy = new jasmineUnderTest.Env().createSpy('sample-spy'), + spy = new jasmineUnderTest.Spy('sample-spy'), result; spy(); spy(); @@ -72,7 +72,7 @@ describe("toHaveBeenCalledTimes", function() { it("has a custom message on failure that tells how many times it was called", function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), - spy = new jasmineUnderTest.Env().createSpy('sample-spy'), + spy = new jasmineUnderTest.Spy('sample-spy'), result; spy(); spy(); diff --git a/spec/core/matchers/toHaveBeenCalledWithSpec.js b/spec/core/matchers/toHaveBeenCalledWithSpec.js index 4ac7e074..9cc3415b 100644 --- a/spec/core/matchers/toHaveBeenCalledWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledWithSpec.js @@ -5,7 +5,7 @@ describe("toHaveBeenCalledWith", function() { contains: jasmine.createSpy('delegated-contains').and.returnValue(true) }, matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util), - calledSpy = new jasmineUnderTest.Env().createSpy('called-spy'), + calledSpy = new jasmineUnderTest.Spy('called-spy'), result; calledSpy('a', 'b'); @@ -21,7 +21,7 @@ describe("toHaveBeenCalledWith", function() { }, customEqualityTesters = [function() { return true; }], matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util, customEqualityTesters), - calledSpy = new jasmineUnderTest.Env().createSpy('called-spy'); + calledSpy = new jasmineUnderTest.Spy('called-spy'); calledSpy('a', 'b'); matcher.compare(calledSpy, 'a', 'b'); @@ -34,7 +34,7 @@ describe("toHaveBeenCalledWith", function() { contains: jasmine.createSpy('delegated-contains').and.returnValue(false) }, matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util), - uncalledSpy = new jasmineUnderTest.Env().createSpy('uncalled spy'), + uncalledSpy = new jasmineUnderTest.Spy('uncalled spy'), result; result = matcher.compare(uncalledSpy); @@ -45,7 +45,7 @@ describe("toHaveBeenCalledWith", function() { it("fails when the actual was called with different parameters", function() { var util = jasmineUnderTest.matchersUtil, matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util), - calledSpy = new jasmineUnderTest.Env().createSpy('called spy'), + calledSpy = new jasmineUnderTest.Spy('called spy'), result; calledSpy('a'); diff --git a/spec/html/HtmlReporterSpec.js b/spec/html/HtmlReporterSpec.js index 526fa76c..3b4f20e5 100644 --- a/spec/html/HtmlReporterSpec.js +++ b/spec/html/HtmlReporterSpec.js @@ -1,7 +1,16 @@ describe('HtmlReporter', function() { + var env; + + beforeEach(function() { + env = new jasmineUnderTest.Env(); + }); + + afterEach(function() { + env.cleanup_(); + }); + it('builds the initial DOM elements, including the title banner', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -37,8 +46,7 @@ describe('HtmlReporter', function() { }); it('builds a single reporter even if initialized multiple times', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -71,7 +79,7 @@ describe('HtmlReporter', function() { container = document.createElement('div'); reporter = new jasmineUnderTest.HtmlReporter({ - env: new jasmineUnderTest.Env(), + env: env, getContainer: function() { return container; }, @@ -119,8 +127,7 @@ describe('HtmlReporter', function() { }); it('reports the status symbol of a excluded spec', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -152,8 +159,7 @@ describe('HtmlReporter', function() { }); it('reports the status symbol of a pending spec', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -182,8 +188,7 @@ describe('HtmlReporter', function() { }); it('reports the status symbol of a passing spec', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -213,8 +218,7 @@ describe('HtmlReporter', function() { }); it('reports the status symbol of a failing spec', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -246,8 +250,7 @@ describe('HtmlReporter', function() { describe('when there are deprecation warnings', function() { it('displays the messages in their own alert bars', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -298,8 +301,7 @@ describe('HtmlReporter', function() { if (!window.console) { window.console = { error: function() {} }; } - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -343,8 +345,7 @@ describe('HtmlReporter', function() { }); it('reports the run time', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -372,8 +373,7 @@ describe('HtmlReporter', function() { }); it('reports the suite and spec names with status', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -490,8 +490,7 @@ describe('HtmlReporter', function() { }); it('has an options menu', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -529,8 +528,7 @@ describe('HtmlReporter', function() { describe('when there are global errors', function() { it('displays the exceptions in their own alert bars', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -576,8 +574,7 @@ describe('HtmlReporter', function() { }); it('displays file and line information if available', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -619,8 +616,7 @@ describe('HtmlReporter', function() { describe('UI for stop on spec failure', function() { it('should be unchecked for full execution', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -643,8 +639,7 @@ describe('HtmlReporter', function() { }); it('should be checked if stopping short', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -669,8 +664,7 @@ describe('HtmlReporter', function() { }); it('should navigate and turn the setting on', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), navigationHandler = jasmine.createSpy('navigate'), getContainer = function() { return container; @@ -697,8 +691,7 @@ describe('HtmlReporter', function() { }); it('should navigate and turn the setting off', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), navigationHandler = jasmine.createSpy('navigate'), getContainer = function() { return container; @@ -729,8 +722,7 @@ describe('HtmlReporter', function() { describe('UI for throwing errors on expectation failures', function() { it('should be unchecked if not throwing', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -753,8 +745,7 @@ describe('HtmlReporter', function() { }); it('should be checked if throwing', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -779,8 +770,7 @@ describe('HtmlReporter', function() { }); it('should navigate and change the setting to on', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), navigateHandler = jasmine.createSpy('navigate'), getContainer = function() { return container; @@ -807,8 +797,7 @@ describe('HtmlReporter', function() { }); it('should navigate and change the setting to off', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), navigateHandler = jasmine.createSpy('navigate'), getContainer = function() { return container; @@ -838,8 +827,7 @@ describe('HtmlReporter', function() { }); describe('UI for hiding disabled specs', function() { it('should be unchecked if not hiding disabled specs', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -863,8 +851,7 @@ describe('HtmlReporter', function() { }); it('should be checked if hiding disabled', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -888,8 +875,7 @@ describe('HtmlReporter', function() { }); it('should not display specs that have been disabled', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -922,8 +908,7 @@ describe('HtmlReporter', function() { }); describe('UI for running tests in random order', function() { it('should be unchecked if not randomizing', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -947,8 +932,7 @@ describe('HtmlReporter', function() { }); it('should be checked if randomizing', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -972,8 +956,7 @@ describe('HtmlReporter', function() { }); it('should navigate and change the setting to on', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), navigateHandler = jasmine.createSpy('navigate'), getContainer = function() { return container; @@ -1001,8 +984,7 @@ describe('HtmlReporter', function() { }); it('should navigate and change the setting to off', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), navigateHandler = jasmine.createSpy('navigate'), getContainer = function() { return container; @@ -1030,8 +1012,7 @@ describe('HtmlReporter', function() { }); it('should show the seed bar if randomizing', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -1061,8 +1042,7 @@ describe('HtmlReporter', function() { }); it('should not show the current seed bar if not randomizing', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -1085,8 +1065,7 @@ describe('HtmlReporter', function() { }); it('should include non-spec query params in the jasmine-skipped link when present', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), reporter = new jasmineUnderTest.HtmlReporter({ env: env, getContainer: function() { @@ -1113,9 +1092,8 @@ describe('HtmlReporter', function() { }); describe('and all specs pass', function() { - var env, container; + var container; beforeEach(function() { - env = new jasmineUnderTest.Env(); container = document.createElement('div'); var getContainer = function() { return container; @@ -1175,9 +1153,8 @@ describe('HtmlReporter', function() { }); describe('and there are excluded specs', function() { - var env, container, reporter, reporterConfig, specStatus; + var container, reporter, reporterConfig, specStatus; beforeEach(function() { - env = new jasmineUnderTest.Env(); container = document.createElement('div'); reporterConfig = { env: env, @@ -1239,9 +1216,8 @@ describe('HtmlReporter', function() { }); describe('and there are pending specs', function() { - var env, container, reporter; + var container, reporter; beforeEach(function() { - env = new jasmineUnderTest.Env(); container = document.createElement('div'); var getContainer = function() { return container; @@ -1297,10 +1273,9 @@ describe('HtmlReporter', function() { }); describe('and some tests fail', function() { - var env, container, reporter; + var container, reporter; beforeEach(function() { - env = new jasmineUnderTest.Env(); container = document.createElement('div'); var getContainer = function() { return container; @@ -1469,8 +1444,7 @@ describe('HtmlReporter', function() { describe('The overall result bar', function() { describe("When the jasmineDone event's overallStatus is 'passed'", function() { it('has class jasmine-passed', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -1500,8 +1474,7 @@ describe('HtmlReporter', function() { describe("When the jasmineDone event's overallStatus is 'failed'", function() { it('has class jasmine-failed', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, @@ -1531,8 +1504,7 @@ describe('HtmlReporter', function() { describe("When the jasmineDone event's overallStatus is 'incomplete'", function() { it('has class jasmine-incomplete', function() { - var env = new jasmineUnderTest.Env(), - container = document.createElement('div'), + var container = document.createElement('div'), getContainer = function() { return container; }, diff --git a/spec/html/MatchersHtmlSpec.js b/spec/html/MatchersHtmlSpec.js index 75256f9d..a1cb8d24 100644 --- a/spec/html/MatchersHtmlSpec.js +++ b/spec/html/MatchersHtmlSpec.js @@ -19,6 +19,10 @@ describe('MatchersSpec - HTML Dependent', function() { }); }); + afterEach(function() { + env.cleanup_(); + }); + function match(value) { return spec.expect(value); } diff --git a/src/core/Env.js b/src/core/Env.js index dc652cd5..6cc9329c 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -1188,6 +1188,12 @@ getJasmineRequireObj().Env = function(j$) { throw new Error(message); } }; + + this.cleanup_ = function() { + if (globalErrors) { + globalErrors.uninstall(); + } + }; } return Env; From 58c63e98bb32a37fe4eb3e0644b262f64ec8fa07 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Mon, 20 Jan 2020 10:50:42 -0800 Subject: [PATCH 112/201] Include stack traces in unhandled promise rejection messages --- lib/jasmine-core/jasmine.js | 7 ++- spec/core/GlobalErrorsSpec.js | 83 +++++++++++++++++++++++++---------- src/core/GlobalErrors.js | 8 +++- 3 files changed, 74 insertions(+), 24 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index e1e7615a..6761367b 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -3855,7 +3855,12 @@ getJasmineRequireObj().GlobalErrors = function(j$) { global.onerror = onerror; var browserRejectionHandler = function browserRejectionHandler(event) { - onerror('Unhandled Rejection: ' + event.reason); + if (j$.isError_(event.reason)) { + event.reason.jasmineMessage = 'Unhandled promise rejection: ' + event.reason; + onerror(event.reason); + } else { + onerror('Unhandled promise rejection: ' + event.reason); + } }; if (global.addEventListener) { diff --git a/spec/core/GlobalErrorsSpec.js b/spec/core/GlobalErrorsSpec.js index 42f9f37c..16ca8371 100644 --- a/spec/core/GlobalErrorsSpec.js +++ b/spec/core/GlobalErrorsSpec.js @@ -194,33 +194,72 @@ describe('GlobalErrors', function() { ); }); - it('reports unhandledRejection in browser', function() { - var fakeGlobal = { - addEventListener: jasmine.createSpy('addEventListener'), - removeEventListener: jasmine.createSpy('removeEventListener'), - onerror: jasmine.createSpy('onerror') - }, - handler = jasmine.createSpy('errorHandler'), - errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); + describe('Reporting unhandled promise rejections in the browser', function() { + it('subscribes and unsubscribes from the unhandledrejection event', function() { + var fakeGlobal = jasmine.createSpyObj('globalErrors', [ + 'addEventListener', + 'removeEventListener', + 'onerror' + ]), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); - errors.install(); - expect(fakeGlobal.addEventListener).toHaveBeenCalledWith( - 'unhandledrejection', - jasmine.any(Function) - ); + errors.install(); + expect(fakeGlobal.addEventListener).toHaveBeenCalledWith( + 'unhandledrejection', + jasmine.any(Function) + ); - errors.pushListener(handler); + var addedListener = fakeGlobal.addEventListener.calls.argsFor(0)[1]; + errors.uninstall(); - var addedListener = fakeGlobal.addEventListener.calls.argsFor(0)[1]; - addedListener({ reason: new Error('bar') }); + expect(fakeGlobal.removeEventListener).toHaveBeenCalledWith( + 'unhandledrejection', + addedListener + ); + }); - expect(handler).toHaveBeenCalledWith('Unhandled Rejection: Error: bar'); + it('reports rejections whose reason is a string', function() { + var fakeGlobal = jasmine.createSpyObj('globalErrors', [ + 'addEventListener', + 'removeEventListener', + 'onerror' + ]), + handler = jasmine.createSpy('errorHandler'), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); - errors.uninstall(); + errors.install(); + errors.pushListener(handler); - expect(fakeGlobal.removeEventListener).toHaveBeenCalledWith( - 'unhandledrejection', - addedListener - ); + var addedListener = fakeGlobal.addEventListener.calls.argsFor(0)[1]; + addedListener({ reason: 'nope' }); + + expect(handler).toHaveBeenCalledWith('Unhandled promise rejection: nope'); + }); + + it('reports rejections whose reason is an Error', function() { + var fakeGlobal = jasmine.createSpyObj('globalErrors', [ + 'addEventListener', + 'removeEventListener', + 'onerror' + ]), + handler = jasmine.createSpy('errorHandler'), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); + + errors.install(); + errors.pushListener(handler); + + var addedListener = fakeGlobal.addEventListener.calls.argsFor(0)[1]; + var reason = new Error('bar'); + addedListener({ reason: reason }); + + var expectedError = Object.create(reason); + expectedError.jasmineMessage = expect(handler).toHaveBeenCalledWith( + jasmine.objectContaining({ + jasmineMessage: 'Unhandled promise rejection: Error: bar', + message: reason.message, + stack: reason.stack + }) + ); + }); }); }); diff --git a/src/core/GlobalErrors.js b/src/core/GlobalErrors.js index 2fe4725d..282eb262 100644 --- a/src/core/GlobalErrors.js +++ b/src/core/GlobalErrors.js @@ -64,7 +64,13 @@ getJasmineRequireObj().GlobalErrors = function(j$) { global.onerror = onerror; var browserRejectionHandler = function browserRejectionHandler(event) { - onerror('Unhandled Rejection: ' + event.reason); + if (j$.isError_(event.reason)) { + event.reason.jasmineMessage = + 'Unhandled promise rejection: ' + event.reason; + onerror(event.reason); + } else { + onerror('Unhandled promise rejection: ' + event.reason); + } }; if (global.addEventListener) { From fd5b9ce1aebf9e71107e5c07a71c776c01da0775 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Mon, 20 Jan 2020 11:40:26 -0800 Subject: [PATCH 113/201] Fixed spec failure in IE --- spec/core/GlobalErrorsSpec.js | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/spec/core/GlobalErrorsSpec.js b/spec/core/GlobalErrorsSpec.js index 16ca8371..3effa537 100644 --- a/spec/core/GlobalErrorsSpec.js +++ b/spec/core/GlobalErrorsSpec.js @@ -249,11 +249,18 @@ describe('GlobalErrors', function() { errors.pushListener(handler); var addedListener = fakeGlobal.addEventListener.calls.argsFor(0)[1]; - var reason = new Error('bar'); + var reason; + + try { + // Throwing ensures that we get a stack property in all browsers + throw new Error('bar'); + } catch (e) { + reason = e; + } + addedListener({ reason: reason }); - var expectedError = Object.create(reason); - expectedError.jasmineMessage = expect(handler).toHaveBeenCalledWith( + expect(handler).toHaveBeenCalledWith( jasmine.objectContaining({ jasmineMessage: 'Unhandled promise rejection: Error: bar', message: reason.message, From 5e98ee951cf8724061daab4cde2a3721ad5e7cf7 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Mon, 20 Jan 2020 12:08:01 -0800 Subject: [PATCH 114/201] Realign the browser testing matrix to match current reality * Use Windows instead of Linux so we can get current browsers from Sauce. * Test against the version of Firefox that corresponds to ESR as well as latest. * Test the latest Edge rather than a specific older version. * Test Safari 8 and 13 instead of 8, 9 and 10. What works in those versions is likely to work in the ones in between. --- .travis.yml | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/.travis.yml b/.travis.yml index 4ad46565..3a2cb0db 100644 --- a/.travis.yml +++ b/.travis.yml @@ -27,19 +27,19 @@ matrix: if: type != pull_request addons: sauce_connect: true - - env: JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='' SAUCE_OS="Linux" + - env: JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='' SAUCE_OS="Windows 10" if: type != pull_request addons: sauce_connect: true - - env: JASMINE_BROWSER="chrome" SAUCE_BROWSER_VERSION='' SAUCE_OS="Linux" + - env: JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='68' SAUCE_OS="Windows 10" if: type != pull_request addons: sauce_connect: true - - env: JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="10" SAUCE_OS="OS X 10.12" + - env: JASMINE_BROWSER="chrome" SAUCE_BROWSER_VERSION='' SAUCE_OS="Windows 10" if: type != pull_request addons: sauce_connect: true - - env: JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="9" SAUCE_OS="OS X 10.11" + - env: JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="13" SAUCE_OS="OS X 10.13" if: type != pull_request addons: sauce_connect: true @@ -47,7 +47,7 @@ matrix: if: type != pull_request addons: sauce_connect: true - - env: JASMINE_BROWSER="MicrosoftEdge" SAUCE_BROWSER_VERSION="15" SAUCE_OS="Windows 10" + - env: JASMINE_BROWSER="MicrosoftEdge" SAUCE_BROWSER_VERSION="" SAUCE_OS="Windows 10" if: type != pull_request addons: sauce_connect: true From 9febe3159d729bdf9459274216ffe4cbf3588dd7 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Tue, 28 Jan 2020 19:40:44 -0500 Subject: [PATCH 115/201] Allow callThrough to call constructor functions without errors --- spec/core/integration/EnvSpec.js | 19 +++++++++++ src/core/Spy.js | 56 ++++++++++++++++---------------- src/core/SpyStrategy.js | 11 +++++-- 3 files changed, 56 insertions(+), 30 deletions(-) diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index 490e9d94..58f06014 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -808,6 +808,25 @@ describe("Env integration", function() { expect(originalFunctionWasCalled).toEqual(true); }); + env.it("works with constructors when using callThrough spy strategy", function() { + function MyClass(foo) { + if (!(this instanceof MyClass)) throw new Error('You must use the new keyword.'); + this.foo = foo; + } + var subject = { MyClass: MyClass }; + var spy = env.spyOn(subject, 'MyClass').and.callThrough(); + + expect(function() { + var result = new spy('hello world'); + expect(result instanceof MyClass).toBeTruthy(); + expect(result.foo).toEqual('hello world'); + }).not.toThrow(); + + expect(function() { + spy('hello world'); + }).toThrowError('You must use the new keyword.'); + }); + env.execute(); }); diff --git a/src/core/Spy.js b/src/core/Spy.js index ffbb0103..01c772fe 100644 --- a/src/core/Spy.js +++ b/src/core/Spy.js @@ -20,8 +20,8 @@ getJasmineRequireObj().Spy = function(j$) { getPromise ) { var numArgs = typeof originalFn === 'function' ? originalFn.length : 0, - wrapper = makeFunc(numArgs, function() { - return spy.apply(this, Array.prototype.slice.call(arguments)); + wrapper = makeFunc(numArgs, function(context, args, isConstructor) { + return spy(context, args, isConstructor); }), strategyDispatcher = new SpyStrategyDispatcher({ name: name, @@ -33,7 +33,7 @@ getJasmineRequireObj().Spy = function(j$) { getPromise: getPromise }), callTracker = new j$.CallTracker(), - spy = function() { + spy = function(context, args, isConstructor) { /** * @name Spy.callData * @property {object} object - `this` context for the invocation. @@ -41,13 +41,13 @@ getJasmineRequireObj().Spy = function(j$) { * @property {Array} args - The arguments passed for this invocation. */ var callData = { - object: this, + object: context, invocationOrder: nextOrder(), - args: Array.prototype.slice.apply(arguments) + args: Array.prototype.slice.apply(args) }; callTracker.track(callData); - var returnValue = strategyDispatcher.exec(this, arguments); + var returnValue = strategyDispatcher.exec(this, args, isConstructor); callData.returnValue = returnValue; return returnValue; @@ -56,44 +56,44 @@ getJasmineRequireObj().Spy = function(j$) { function makeFunc(length, fn) { switch (length) { case 1: - return function(a) { - return fn.apply(this, arguments); + return function fnargs(a) { + return fn(this, arguments, this instanceof fnargs); }; case 2: - return function(a, b) { - return fn.apply(this, arguments); + return function fnargs(a, b) { + return fn(this, arguments, this instanceof fnargs); }; case 3: - return function(a, b, c) { - return fn.apply(this, arguments); + return function fnargs(a, b, c) { + return fn(this, arguments, this instanceof fnargs); }; case 4: - return function(a, b, c, d) { - return fn.apply(this, arguments); + return function fnargs(a, b, c, d) { + return fn(this, arguments, this instanceof fnargs); }; case 5: - return function(a, b, c, d, e) { - return fn.apply(this, arguments); + return function fnargs(a, b, c, d, e) { + return fn(this, arguments, this instanceof fnargs); }; case 6: - return function(a, b, c, d, e, f) { - return fn.apply(this, arguments); + return function fnargs(a, b, c, d, e, f) { + return fn(this, arguments, this instanceof fnargs); }; case 7: - return function(a, b, c, d, e, f, g) { - return fn.apply(this, arguments); + return function fnargs(a, b, c, d, e, f, g) { + return fn(this, arguments, this instanceof fnargs); }; case 8: - return function(a, b, c, d, e, f, g, h) { - return fn.apply(this, arguments); + return function fnargs(a, b, c, d, e, f, g, h) { + return fn(this, arguments, this instanceof fnargs); }; case 9: - return function(a, b, c, d, e, f, g, h, i) { - return fn.apply(this, arguments); + return function fnargs(a, b, c, d, e, f, g, h, i) { + return fn(this, arguments, this instanceof fnargs); }; default: - return function() { - return fn.apply(this, arguments); + return function fnargs() { + return fn(this, arguments, this instanceof fnargs); }; } } @@ -150,7 +150,7 @@ getJasmineRequireObj().Spy = function(j$) { this.and = baseStrategy; - this.exec = function(spy, args) { + this.exec = function(spy, args, isConstructor) { var strategy = argsStrategies.get(args); if (!strategy) { @@ -167,7 +167,7 @@ getJasmineRequireObj().Spy = function(j$) { } } - return strategy.exec(spy, args); + return strategy.exec(spy, args, isConstructor); }; this.withArgs = function() { diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index 83985967..252de41e 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -96,8 +96,15 @@ getJasmineRequireObj().SpyStrategy = function(j$) { * @since 2.0.0 * @function */ - SpyStrategy.prototype.exec = function(context, args) { - return this.plan.apply(context, args); + SpyStrategy.prototype.exec = function(context, args, isConstructor) { + var list = [context].concat(args ? Array.prototype.slice.call(args) : []); + var target = this.plan.bind.apply(this.plan, list); + + if (isConstructor) { + return new target(); + } else { + return target(); + } }; /** From bf4694333cde39049818e7f4768a47d345275a94 Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Thu, 6 Feb 2020 10:29:02 -0500 Subject: [PATCH 116/201] Improve wrapper function and parameter naming --- spec/core/integration/EnvSpec.js | 10 ++++-- src/core/Spy.js | 52 ++++++++++++++++---------------- src/core/SpyStrategy.js | 4 +-- 3 files changed, 36 insertions(+), 30 deletions(-) diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index 58f06014..d3d347fc 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -822,6 +822,12 @@ describe("Env integration", function() { expect(result.foo).toEqual('hello world'); }).not.toThrow(); + expect(function() { + var result = new spy('passing', 'extra', 'arguments', 'to', 'constructor'); + expect(result instanceof MyClass).toBeTruthy(); + expect(result.foo).toEqual('passing'); + }).not.toThrow(); + expect(function() { spy('hello world'); }).toThrowError('You must use the new keyword.'); @@ -840,8 +846,8 @@ describe("Env integration", function() { env.allowRespy(true); env.addReporter({ jasmineDone: done }); - env.describe('test suite', function(){ - env.it('spec 0', function(){ + env.describe('test suite', function() { + env.it('spec 0', function() { env.spyOn(foo,'bar'); var error = null; diff --git a/src/core/Spy.js b/src/core/Spy.js index 01c772fe..377b3f57 100644 --- a/src/core/Spy.js +++ b/src/core/Spy.js @@ -20,8 +20,8 @@ getJasmineRequireObj().Spy = function(j$) { getPromise ) { var numArgs = typeof originalFn === 'function' ? originalFn.length : 0, - wrapper = makeFunc(numArgs, function(context, args, isConstructor) { - return spy(context, args, isConstructor); + wrapper = makeFunc(numArgs, function(context, args, invokeNew) { + return spy(context, args, invokeNew); }), strategyDispatcher = new SpyStrategyDispatcher({ name: name, @@ -33,7 +33,7 @@ getJasmineRequireObj().Spy = function(j$) { getPromise: getPromise }), callTracker = new j$.CallTracker(), - spy = function(context, args, isConstructor) { + spy = function(context, args, invokeNew) { /** * @name Spy.callData * @property {object} object - `this` context for the invocation. @@ -47,7 +47,7 @@ getJasmineRequireObj().Spy = function(j$) { }; callTracker.track(callData); - var returnValue = strategyDispatcher.exec(this, args, isConstructor); + var returnValue = strategyDispatcher.exec(context, args, invokeNew); callData.returnValue = returnValue; return returnValue; @@ -56,44 +56,44 @@ getJasmineRequireObj().Spy = function(j$) { function makeFunc(length, fn) { switch (length) { case 1: - return function fnargs(a) { - return fn(this, arguments, this instanceof fnargs); + return function wrap1(a) { + return fn(this, arguments, this instanceof wrap1); }; case 2: - return function fnargs(a, b) { - return fn(this, arguments, this instanceof fnargs); + return function wrap2(a, b) { + return fn(this, arguments, this instanceof wrap2); }; case 3: - return function fnargs(a, b, c) { - return fn(this, arguments, this instanceof fnargs); + return function wrap3(a, b, c) { + return fn(this, arguments, this instanceof wrap3); }; case 4: - return function fnargs(a, b, c, d) { - return fn(this, arguments, this instanceof fnargs); + return function wrap4(a, b, c, d) { + return fn(this, arguments, this instanceof wrap4); }; case 5: - return function fnargs(a, b, c, d, e) { - return fn(this, arguments, this instanceof fnargs); + return function wrap5(a, b, c, d, e) { + return fn(this, arguments, this instanceof wrap5); }; case 6: - return function fnargs(a, b, c, d, e, f) { - return fn(this, arguments, this instanceof fnargs); + return function wrap6(a, b, c, d, e, f) { + return fn(this, arguments, this instanceof wrap6); }; case 7: - return function fnargs(a, b, c, d, e, f, g) { - return fn(this, arguments, this instanceof fnargs); + return function wrap7(a, b, c, d, e, f, g) { + return fn(this, arguments, this instanceof wrap7); }; case 8: - return function fnargs(a, b, c, d, e, f, g, h) { - return fn(this, arguments, this instanceof fnargs); + return function wrap8(a, b, c, d, e, f, g, h) { + return fn(this, arguments, this instanceof wrap8); }; case 9: - return function fnargs(a, b, c, d, e, f, g, h, i) { - return fn(this, arguments, this instanceof fnargs); + return function wrap9(a, b, c, d, e, f, g, h, i) { + return fn(this, arguments, this instanceof wrap9); }; default: - return function fnargs() { - return fn(this, arguments, this instanceof fnargs); + return function wrap() { + return fn(this, arguments, this instanceof wrap); }; } } @@ -150,7 +150,7 @@ getJasmineRequireObj().Spy = function(j$) { this.and = baseStrategy; - this.exec = function(spy, args, isConstructor) { + this.exec = function(spy, args, invokeNew) { var strategy = argsStrategies.get(args); if (!strategy) { @@ -167,7 +167,7 @@ getJasmineRequireObj().Spy = function(j$) { } } - return strategy.exec(spy, args, isConstructor); + return strategy.exec(spy, args, invokeNew); }; this.withArgs = function() { diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index 252de41e..43f89831 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -96,11 +96,11 @@ getJasmineRequireObj().SpyStrategy = function(j$) { * @since 2.0.0 * @function */ - SpyStrategy.prototype.exec = function(context, args, isConstructor) { + SpyStrategy.prototype.exec = function(context, args, invokeNew) { var list = [context].concat(args ? Array.prototype.slice.call(args) : []); var target = this.plan.bind.apply(this.plan, list); - if (isConstructor) { + if (invokeNew) { return new target(); } else { return target(); From be3c8275d480e843f49cb64179022b2e0a86059a Mon Sep 17 00:00:00 2001 From: Elliot Nelson Date: Thu, 6 Feb 2020 10:34:55 -0500 Subject: [PATCH 117/201] Tidy up SpyStrategy#exec --- src/core/SpyStrategy.js | 12 +++++------- 1 file changed, 5 insertions(+), 7 deletions(-) diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index 43f89831..7e86abd6 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -97,14 +97,12 @@ getJasmineRequireObj().SpyStrategy = function(j$) { * @function */ SpyStrategy.prototype.exec = function(context, args, invokeNew) { - var list = [context].concat(args ? Array.prototype.slice.call(args) : []); - var target = this.plan.bind.apply(this.plan, list); + var contextArgs = [context].concat( + args ? Array.prototype.slice.call(args) : [] + ); + var target = this.plan.bind.apply(this.plan, contextArgs); - if (invokeNew) { - return new target(); - } else { - return target(); - } + return invokeNew ? new target() : target(); }; /** From dec67bd535bfeeb9e4953f14c35ff56874aabcf9 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 21 Sep 2019 10:58:09 -0700 Subject: [PATCH 118/201] Don't require matchers and asymmetric equality testers to pass custom object formatters back to Jasmine This makes it easier to write high quality matchers and asymmetric equality testers, and is also a step toward supporting custom object formatters. Previously, Jasmine passed custom object formatters as the second argument to matcher factories and as and the second argument to asymmetric equality testers' `asymmetricMatch` method. Matchers and asymmetric equality testers were responsible for passing the custom object formatters to methods like `matchersUtil#equals`: function toEqual(util, customEqualityTesters) { return { compare: function(actual, expected) { // ... result.pass = util.equals(actual, expected, customEqualityTesters, diffBuilder); And: ArrayContaining.prototype.asymmetricMatch = function(other, customTesters) { // ... for (var i = 0; i < this.sample.length; i++) { var item = this.sample[i]; if (!j$.matchersUtil.contains(other, item, customTesters)) { return false; } } With this change, that is no longer necessary. Matchers and asymmetric equality testers can ignore the existence of custom equality testers and still fully support them: function toEqual(util) { return { compare: function(actual, expected) { // ... result.pass = util.equals(actual, expected, diffBuilder); And: ArrayContaining.prototype.asymmetricMatch = function(other, matchersUtil) { // ... for (var i = 0; i < this.sample.length; i++) { var item = this.sample[i]; if (!matchersUtil.contains(other, item)) { return false; } } The old interfaces are still supported, for now, but will be deprecated in a future commit and removed in the next major release after that. In addition to making matchers and custom equality testers simpler, this change sets the stage for adding support for custom object formatters. Those will be architecturally similar to custom equality testers, and by injecting a `MatchersUtil` instance everywhere we can add them without requiring user code to pass them around as used to be the case with custom object formatters. --- lib/jasmine-core/jasmine.js | 332 ++++++++++---- spec/core/AsyncExpectationSpec.js | 8 +- spec/core/EnvSpec.js | 58 +++ spec/core/ExpectationSpec.js | 2 +- ...ymmetricEqualityTesterArgCompatShimSpec.js | 101 ++++ .../ArrayContainingSpec.js | 15 +- .../ArrayWithExactContentsSpec.js | 14 +- .../asymmetric_equality/MapContainingSpec.js | 36 +- .../ObjectContainingSpec.js | 30 +- .../asymmetric_equality/SetContainingSpec.js | 22 +- .../integration/CustomAsyncMatchersSpec.js | 32 ++ spec/core/integration/CustomMatchersSpec.js | 46 +- spec/core/integration/EnvSpec.js | 31 +- spec/core/integration/MatchersSpec.js | 5 +- spec/core/matchers/async/toBeRejectedSpec.js | 9 +- .../async/toBeRejectedWithErrorSpec.js | 36 +- .../matchers/async/toBeRejectedWithSpec.js | 18 +- spec/core/matchers/async/toBeResolvedSpec.js | 9 +- .../core/matchers/async/toBeResolvedToSpec.js | 18 +- spec/core/matchers/matchersUtilSpec.js | 433 ++++++++++++------ spec/core/matchers/toBeSpec.js | 18 +- spec/core/matchers/toContainSpec.js | 15 +- spec/core/matchers/toEqualSpec.js | 23 +- .../core/matchers/toHaveBeenCalledWithSpec.js | 20 +- spec/helpers/integrationMatchers.js | 5 +- spec/npmPackage/npmPackageSpec.js | 2 +- src/core/Env.js | 14 +- src/core/Spy.js | 4 +- .../asymmetricEqualityTesterArgCompatShim.js | 105 +++++ .../asymmetric_equality/ArrayContaining.js | 4 +- .../ArrayWithExactContents.js | 4 +- src/core/asymmetric_equality/MapContaining.js | 6 +- .../asymmetric_equality/ObjectContaining.js | 4 +- src/core/asymmetric_equality/SetContaining.js | 6 +- src/core/matchers/async/toBeRejectedWith.js | 4 +- src/core/matchers/async/toBeResolvedTo.js | 4 +- src/core/matchers/matchersUtil.js | 147 +++--- src/core/matchers/toBeInstanceOf.js | 2 +- src/core/matchers/toContain.js | 6 +- src/core/matchers/toEqual.js | 6 +- src/core/matchers/toHaveBeenCalledWith.js | 6 +- src/core/matchers/toHaveClass.js | 2 +- src/core/requireCore.js | 7 +- 43 files changed, 1214 insertions(+), 455 deletions(-) create mode 100644 spec/core/asymmetricEqualityTesterArgCompatShimSpec.js create mode 100644 src/core/asymmetricEqualityTesterArgCompatShim.js diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 4875624e..555cb046 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -73,7 +73,12 @@ var getJasmineRequireObj = (function(jasmineGlobal) { j$.buildExpectationResult = jRequire.buildExpectationResult(); j$.noopTimer = jRequire.noopTimer(); j$.JsApiReporter = jRequire.JsApiReporter(j$); - j$.matchersUtil = jRequire.matchersUtil(j$); + j$.asymmetricEqualityTesterArgCompatShim = jRequire.asymmetricEqualityTesterArgCompatShim( + j$ + ); + j$.MatchersUtil = jRequire.MatchersUtil(j$); + j$.matchersUtil = new j$.MatchersUtil({ customTesters: [] }); + j$.ObjectContaining = jRequire.ObjectContaining(j$); j$.ArrayContaining = jRequire.ArrayContaining(j$); j$.ArrayWithExactContents = jRequire.ArrayWithExactContents(j$); @@ -1188,6 +1193,7 @@ getJasmineRequireObj().Env = function(j$) { } var customMatchers = runnableResources[currentRunnable().id].customMatchers; + for (var matcherName in matchersToAdd) { customMatchers[matcherName] = matchersToAdd[matcherName]; } @@ -1201,6 +1207,7 @@ getJasmineRequireObj().Env = function(j$) { } var customAsyncMatchers = runnableResources[currentRunnable().id].customAsyncMatchers; + for (var matcherName in matchersToAdd) { customAsyncMatchers[matcherName] = matchersToAdd[matcherName]; } @@ -1220,9 +1227,12 @@ getJasmineRequireObj().Env = function(j$) { }; var expectationFactory = function(actual, spec) { + var customEqualityTesters = + runnableResources[spec.id].customEqualityTesters; + return j$.Expectation.factory({ - util: j$.matchersUtil, - customEqualityTesters: runnableResources[spec.id].customEqualityTesters, + util: new j$.MatchersUtil({ customTesters: customEqualityTesters }), + customEqualityTesters: customEqualityTesters, customMatchers: runnableResources[spec.id].customMatchers, actual: actual, addExpectationResult: addExpectationResult @@ -1234,8 +1244,11 @@ getJasmineRequireObj().Env = function(j$) { }; var asyncExpectationFactory = function(actual, spec) { + var customEqualityTesters = + runnableResources[spec.id].customEqualityTesters; + return j$.Expectation.asyncFactory({ - util: j$.matchersUtil, + util: new j$.MatchersUtil({ customTesters: customEqualityTesters }), customEqualityTesters: runnableResources[spec.id].customEqualityTesters, customAsyncMatchers: runnableResources[spec.id].customAsyncMatchers, actual: actual, @@ -2269,7 +2282,7 @@ getJasmineRequireObj().ArrayContaining = function(j$) { this.sample = sample; } - ArrayContaining.prototype.asymmetricMatch = function(other, customTesters) { + ArrayContaining.prototype.asymmetricMatch = function(other, matchersUtil) { if (!j$.isArray_(this.sample)) { throw new Error('You must provide an array to arrayContaining, not ' + j$.pp(this.sample) + '.'); } @@ -2283,7 +2296,7 @@ getJasmineRequireObj().ArrayContaining = function(j$) { for (var i = 0; i < this.sample.length; i++) { var item = this.sample[i]; - if (!j$.matchersUtil.contains(other, item, customTesters)) { + if (!matchersUtil.contains(other, item)) { return false; } } @@ -2304,7 +2317,7 @@ getJasmineRequireObj().ArrayWithExactContents = function(j$) { this.sample = sample; } - ArrayWithExactContents.prototype.asymmetricMatch = function(other, customTesters) { + ArrayWithExactContents.prototype.asymmetricMatch = function(other, matchersUtil) { if (!j$.isArray_(this.sample)) { throw new Error('You must provide an array to arrayWithExactContents, not ' + j$.pp(this.sample) + '.'); } @@ -2315,7 +2328,7 @@ getJasmineRequireObj().ArrayWithExactContents = function(j$) { for (var i = 0; i < this.sample.length; i++) { var item = this.sample[i]; - if (!j$.matchersUtil.contains(other, item, customTesters)) { + if (!matchersUtil.contains(other, item)) { return false; } } @@ -2380,7 +2393,7 @@ getJasmineRequireObj().MapContaining = function(j$) { this.sample = sample; } - MapContaining.prototype.asymmetricMatch = function(other, customTesters) { + MapContaining.prototype.asymmetricMatch = function(other, matchersUtil) { if (!j$.isMap(other)) return false; var hasAllMatches = true; @@ -2390,8 +2403,8 @@ getJasmineRequireObj().MapContaining = function(j$) { var hasMatch = false; j$.util.forEachBreakable(other, function(oBreakLoop, oValue, oKey) { if ( - j$.matchersUtil.equals(oKey, key, customTesters) - && j$.matchersUtil.equals(oValue, value, customTesters) + matchersUtil.equals(oKey, key) + && matchersUtil.equals(oValue, value) ) { hasMatch = true; oBreakLoop(); @@ -2470,12 +2483,12 @@ getJasmineRequireObj().ObjectContaining = function(j$) { return hasProperty(getPrototype(obj), property); } - ObjectContaining.prototype.asymmetricMatch = function(other, customTesters) { + ObjectContaining.prototype.asymmetricMatch = function(other, matchersUtil) { if (typeof(this.sample) !== 'object') { throw new Error('You must provide an object to objectContaining, not \''+this.sample+'\'.'); } for (var property in this.sample) { if (!hasProperty(other, property) || - !j$.matchersUtil.equals(this.sample[property], other[property], customTesters)) { + !matchersUtil.equals(this.sample[property], other[property])) { return false; } } @@ -2499,17 +2512,17 @@ getJasmineRequireObj().SetContaining = function(j$) { this.sample = sample; } - SetContaining.prototype.asymmetricMatch = function(other, customTesters) { + SetContaining.prototype.asymmetricMatch = function(other, matchersUtil) { if (!j$.isSet(other)) return false; var hasAllMatches = true; j$.util.forEachBreakable(this.sample, function(breakLoop, item) { // for each item in `sample` there should be at least one matching item in `other` - // (not using `j$.matchersUtil.contains` because it compares set members by reference, + // (not using `matchersUtil.contains` because it compares set members by reference, // not by deep value equality) var hasMatch = false; j$.util.forEachBreakable(other, function(oBreakLoop, oItem) { - if (j$.matchersUtil.equals(oItem, item, customTesters)) { + if (matchersUtil.equals(oItem, item)) { hasMatch = true; oBreakLoop(); } @@ -2566,6 +2579,112 @@ getJasmineRequireObj().Truthy = function(j$) { return Truthy; }; +getJasmineRequireObj().asymmetricEqualityTesterArgCompatShim = function(j$) { + /* + Older versions of Jasmine passed an array of custom equality testers as the + second argument to each asymmetric equality tester's `asymmetricMatch` + method. Newer versions will pass a `MatchersUtil` instance. The + asymmetricEqualityTesterArgCompatShim allows for a graceful migration from + the old interface to the new by "being" both an array of custom equality + testers and a `MatchersUtil` at the same time. + + This code should be removed in the next major release. + */ + + var likelyArrayProps = [ + 'concat', + 'constructor', + 'copyWithin', + 'entries', + 'every', + 'fill', + 'filter', + 'find', + 'findIndex', + 'flat', + 'flatMap', + 'forEach', + 'includes', + 'indexOf', + 'join', + 'keys', + 'lastIndexOf', + 'length', + 'map', + 'pop', + 'push', + 'reduce', + 'reduceRight', + 'reverse', + 'shift', + 'slice', + 'some', + 'sort', + 'splice', + 'toLocaleString', + 'toSource', + 'toString', + 'unshift', + 'values' + ]; + + function asymmetricEqualityTesterArgCompatShim( + matchersUtil, + customEqualityTesters + ) { + var self = Object.create(matchersUtil), + props, + i, + k; + + copy(self, customEqualityTesters, 'length'); + + for (i = 0; i < customEqualityTesters.length; i++) { + copy(self, customEqualityTesters, i); + } + + var props = arrayProps(); + + for (i = 0; i < props.length; i++) { + k = props[i]; + if (k !== 'length') { + copy(self, Array.prototype, k); + } + } + + return self; + } + + function copy(dest, src, propName) { + Object.defineProperty(dest, propName, { + get: function() { + return src[propName]; + } + }); + } + + function arrayProps() { + var props, a, k; + + if (!Object.getOwnPropertyDescriptors) { + return likelyArrayProps.filter(function(k) { + return Array.prototype.hasOwnProperty(k); + }); + } + + props = Object.getOwnPropertyDescriptors(Array.prototype); + a = []; + + for (k in props) { + a.push(k); + } + + return a; + } + + return asymmetricEqualityTesterArgCompatShim; +}; + getJasmineRequireObj().CallTracker = function(j$) { /** * @namespace Spy#calls @@ -3822,7 +3941,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { * @example * return expectAsync(aPromise).toBeRejectedWith({prop: 'value'}); */ - return function toBeRejectedWith(util, customEqualityTesters) { + return function toBeRejectedWith(util) { return { compare: function(actualPromise, expectedValue) { if (!j$.isPromiseLike(actualPromise)) { @@ -3843,7 +3962,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { }; }, function(actualValue) { - if (util.equals(actualValue, expectedValue, customEqualityTesters)) { + if (util.equals(actualValue, expectedValue)) { return { pass: true, message: prefix(true) + '.' @@ -4000,7 +4119,7 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { * @example * return expectAsync(aPromise).toBeResolvedTo({prop: 'value'}); */ - return function toBeResolvedTo(util, customEqualityTesters) { + return function toBeResolvedTo(util) { return { compare: function(actualPromise, expectedValue) { if (!j$.isPromiseLike(actualPromise)) { @@ -4015,7 +4134,7 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { return actualPromise.then( function(actualValue) { - if (util.equals(actualValue, expectedValue, customEqualityTesters)) { + if (util.equals(actualValue, expectedValue)) { return { pass: true, message: prefix(true) + '.' @@ -4073,66 +4192,70 @@ getJasmineRequireObj().DiffBuilder = function(j$) { }; }; -getJasmineRequireObj().matchersUtil = function(j$) { +getJasmineRequireObj().MatchersUtil = function(j$) { // TODO: what to do about jasmine.pp not being inject? move to JSON.stringify? gut PrettyPrinter? - return { - equals: equals, + function MatchersUtil(options) { + options = options || {}; + this.customTesters_ = options.customTesters || []; - contains: function(haystack, needle, customTesters) { - customTesters = customTesters || []; - - if (j$.isSet(haystack)) { - return haystack.has(needle); - } - - if ((Object.prototype.toString.apply(haystack) === '[object Array]') || - (!!haystack && !haystack.indexOf)) - { - for (var i = 0; i < haystack.length; i++) { - if (equals(haystack[i], needle, customTesters)) { - return true; - } - } - return false; - } - - return !!haystack && haystack.indexOf(needle) >= 0; - }, - - buildFailureMessage: function() { - var args = Array.prototype.slice.call(arguments, 0), - matcherName = args[0], - isNot = args[1], - actual = args[2], - expected = args.slice(3), - englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { return ' ' + s.toLowerCase(); }); - - var message = 'Expected ' + - j$.pp(actual) + - (isNot ? ' not ' : ' ') + - englishyPredicate; - - if (expected.length > 0) { - for (var i = 0; i < expected.length; i++) { - if (i > 0) { - message += ','; - } - message += ' ' + j$.pp(expected[i]); - } - } - - return message + '.'; + if (!j$.isArray_(this.customTesters_)) { + throw new Error("MatchersUtil requires custom equality testers"); } + } + + MatchersUtil.prototype.contains = function(haystack, needle, customTesters) { + if (j$.isSet(haystack)) { + return haystack.has(needle); + } + + if ((Object.prototype.toString.apply(haystack) === '[object Array]') || + (!!haystack && !haystack.indexOf)) + { + for (var i = 0; i < haystack.length; i++) { + if (this.equals(haystack[i], needle, customTesters)) { + return true; + } + } + return false; + } + + return !!haystack && haystack.indexOf(needle) >= 0; + }; + + MatchersUtil.prototype.buildFailureMessage = function() { + var args = Array.prototype.slice.call(arguments, 0), + matcherName = args[0], + isNot = args[1], + actual = args[2], + expected = args.slice(3), + englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { return ' ' + s.toLowerCase(); }); + + var message = 'Expected ' + + j$.pp(actual) + + (isNot ? ' not ' : ' ') + + englishyPredicate; + + if (expected.length > 0) { + for (var i = 0; i < expected.length; i++) { + if (i > 0) { + message += ','; + } + message += ' ' + j$.pp(expected[i]); + } + } + + return message + '.'; }; function isAsymmetric(obj) { return obj && j$.isA_('Function', obj.asymmetricMatch); } - function asymmetricMatch(a, b, customTesters, diffBuilder) { + MatchersUtil.prototype.asymmetricMatch_ = function(a, b, customTesters, diffBuilder) { var asymmetricA = isAsymmetric(a), asymmetricB = isAsymmetric(b), + shim = j$.asymmetricEqualityTesterArgCompatShim(this, customTesters), result; if (asymmetricA && asymmetricB) { @@ -4140,7 +4263,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { } if (asymmetricA) { - result = a.asymmetricMatch(b, customTesters); + result = a.asymmetricMatch(b, shim); if (!result) { diffBuilder.record(a, b); } @@ -4148,27 +4271,36 @@ getJasmineRequireObj().matchersUtil = function(j$) { } if (asymmetricB) { - result = b.asymmetricMatch(a, customTesters); + result = b.asymmetricMatch(a, shim); if (!result) { diffBuilder.record(a, b); } return result; } - } + }; - function equals(a, b, customTesters, diffBuilder) { - customTesters = customTesters || []; + MatchersUtil.prototype.equals = function(a, b, customTestersOrDiffBuilder, diffBuilderOrNothing) { + var customTesters, diffBuilder; + + if (isDiffBuilder(customTestersOrDiffBuilder)) { + diffBuilder = customTestersOrDiffBuilder; + } else { + customTesters = customTestersOrDiffBuilder; + diffBuilder = diffBuilderOrNothing; + } + + customTesters = customTesters || this.customTesters_; diffBuilder = diffBuilder || j$.NullDiffBuilder(); - return eq(a, b, [], [], customTesters, diffBuilder); - } + return this.eq_(a, b, [], [], customTesters, diffBuilder); + }; // Equality function lovingly adapted from isEqual in // [Underscore](http://underscorejs.org) - function eq(a, b, aStack, bStack, customTesters, diffBuilder) { - var result = true, i; + MatchersUtil.prototype.eq_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { + var result = true, self = this, i; - var asymmetricResult = asymmetricMatch(a, b, customTesters, diffBuilder); + var asymmetricResult = this.asymmetricMatch_(a, b, customTesters, diffBuilder); if (!j$.util.isUndefined(asymmetricResult)) { return asymmetricResult; } @@ -4305,7 +4437,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { diffBuilder.record(a[i], void 0, actualArrayIsLongerFormatter); result = false; } else { - result = eq(i < aLength ? a[i] : void 0, i < bLength ? b[i] : void 0, aStack, bStack, customTesters, diffBuilder) && result; + result = self.eq_(i < aLength ? a[i] : void 0, i < bLength ? b[i] : void 0, aStack, bStack, customTesters, diffBuilder) && result; } }); } @@ -4346,12 +4478,12 @@ getJasmineRequireObj().matchersUtil = function(j$) { // otherwise explicitly look up the mapKey in the other Map since we want keys with unique // obj identity (that are otherwise equal) to not match. if (isAsymmetric(mapKey) || isAsymmetric(cmpKey) && - eq(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { + this.eq_(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { mapValueB = b.get(cmpKey); } else { mapValueB = b.get(mapKey); } - result = eq(mapValueA, mapValueB, aStack, bStack, customTesters, j$.NullDiffBuilder()); + result = this.eq_(mapValueA, mapValueB, aStack, bStack, customTesters, j$.NullDiffBuilder()); } } @@ -4395,7 +4527,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { otherValue = otherValues[l]; prevStackSize = baseStack.length; // compare by value equality - found = eq(baseValue, otherValue, baseStack, otherStack, customTesters, j$.NullDiffBuilder()); + found = this.eq_(baseValue, otherValue, baseStack, otherStack, customTesters, j$.NullDiffBuilder()); if (!found && prevStackSize !== baseStack.length) { baseStack.splice(prevStackSize); otherStack.splice(prevStackSize); @@ -4444,7 +4576,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { } diffBuilder.withPath(key, function() { - if(!eq(a[key], b[key], aStack, bStack, customTesters, diffBuilder)) { + if(!self.eq_(a[key], b[key], aStack, bStack, customTesters, diffBuilder)) { result = false; } }); @@ -4459,7 +4591,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { bStack.pop(); return result; - } + }; function keys(obj, isArray) { var allKeys = Object.keys ? Object.keys(obj) : @@ -4542,6 +4674,12 @@ getJasmineRequireObj().matchersUtil = function(j$) { } return formatted; } + + function isDiffBuilder(obj) { + return obj && typeof obj.record === 'function'; + } + + return MatchersUtil; }; getJasmineRequireObj().nothing = function() { @@ -4839,7 +4977,7 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { * expect(3).toBeInstanceOf(Number); * expect(new Error()).toBeInstanceOf(Error); */ - function toBeInstanceOf(util, customEqualityTesters) { + function toBeInstanceOf() { return { compare: function(actual, expected) { var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : j$.pp(actual), @@ -5109,14 +5247,12 @@ getJasmineRequireObj().toContain = function() { * expect(array).toContain(anElement); * expect(string).toContain(substring); */ - function toContain(util, customEqualityTesters) { - customEqualityTesters = customEqualityTesters || []; - + function toContain(util) { return { compare: function(actual, expected) { return { - pass: util.contains(actual, expected, customEqualityTesters) + pass: util.contains(actual, expected) }; } }; @@ -5135,9 +5271,7 @@ getJasmineRequireObj().toEqual = function(j$) { * @example * expect(bigObject).toEqual({"foo": ['bar', 'baz']}); */ - function toEqual(util, customEqualityTesters) { - customEqualityTesters = customEqualityTesters || []; - + function toEqual(util) { return { compare: function(actual, expected) { var result = { @@ -5145,7 +5279,7 @@ getJasmineRequireObj().toEqual = function(j$) { }, diffBuilder = j$.DiffBuilder(); - result.pass = util.equals(actual, expected, customEqualityTesters, diffBuilder); + result.pass = util.equals(actual, expected, diffBuilder); // TODO: only set error message if test fails result.message = diffBuilder.getMessage(); @@ -5315,7 +5449,7 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { * @example * expect(mySpy).toHaveBeenCalledWith('foo', 'bar', 2); */ - function toHaveBeenCalledWith(util, customEqualityTesters) { + function toHaveBeenCalledWith(util) { return { compare: function() { var args = Array.prototype.slice.call(arguments, 0), @@ -5336,7 +5470,7 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { return result; } - if (util.contains(actual.calls.allArgs(), expectedArgs, customEqualityTesters)) { + if (util.contains(actual.calls.allArgs(), expectedArgs)) { result.pass = true; result.message = function() { return 'Expected spy ' + actual.and.identity + ' not to have been called with:\n' + @@ -5351,7 +5485,7 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { var diffs = actual.calls.allArgs().map(function(argsForCall, callIx) { var diffBuilder = new j$.DiffBuilder(); - util.equals(argsForCall, expectedArgs, customEqualityTesters, diffBuilder); + util.equals(argsForCall, expectedArgs, diffBuilder); return 'Call ' + callIx + ':\n' + diffBuilder.getMessage().replace(/^/mg, ' '); }); @@ -5384,7 +5518,7 @@ getJasmineRequireObj().toHaveClass = function(j$) { * el.className = 'foo bar baz'; * expect(el).toHaveClass('bar'); */ - function toHaveClass(util, customEqualityTesters) { + function toHaveClass() { return { compare: function(actual, expected) { if (!isElement(actual)) { @@ -6899,6 +7033,8 @@ getJasmineRequireObj().Spy = function(j$) { }; })(); + var matchersUtil = new j$.MatchersUtil(); + /** * _Note:_ Do not construct this directly, use {@link spyOn}, {@link spyOnProperty}, {@link jasmine.createSpy}, or {@link jasmine.createSpyObj} * @constructor @@ -7094,7 +7230,7 @@ getJasmineRequireObj().Spy = function(j$) { var i; for (i = 0; i < this.strategies.length; i++) { - if (j$.matchersUtil.equals(args, this.strategies[i].args)) { + if (matchersUtil.equals(args, this.strategies[i].args)) { return this.strategies[i].strategy; } } diff --git a/spec/core/AsyncExpectationSpec.js b/spec/core/AsyncExpectationSpec.js index 9b2e3f26..23d145e1 100644 --- a/spec/core/AsyncExpectationSpec.js +++ b/spec/core/AsyncExpectationSpec.js @@ -25,7 +25,7 @@ describe('AsyncExpectation', function() { var addExpectationResult = jasmine.createSpy('addExpectationResult'), actual = Promise.resolve(), expectation = jasmineUnderTest.Expectation.asyncFactory({ - util: jasmineUnderTest.matchersUtil, + util: new jasmineUnderTest.MatchersUtil(), actual: actual, addExpectationResult: addExpectationResult }); @@ -47,7 +47,7 @@ describe('AsyncExpectation', function() { var addExpectationResult = jasmine.createSpy('addExpectationResult'), actual = Promise.reject(), expectation = jasmineUnderTest.Expectation.asyncFactory({ - util: jasmineUnderTest.matchersUtil, + util: new jasmineUnderTest.MatchersUtil(), actual: actual, addExpectationResult: addExpectationResult }); @@ -183,7 +183,7 @@ describe('AsyncExpectation', function() { expectation = jasmineUnderTest.Expectation.asyncFactory({ actual: actual, addExpectationResult: addExpectationResult, - util: jasmineUnderTest.matchersUtil + util: new jasmineUnderTest.MatchersUtil() }); return expectation @@ -208,7 +208,7 @@ describe('AsyncExpectation', function() { expectation = jasmineUnderTest.Expectation.asyncFactory({ actual: actual, addExpectationResult: addExpectationResult, - util: jasmineUnderTest.matchersUtil + util: new jasmineUnderTest.MatchersUtil() }); return expectation diff --git a/spec/core/EnvSpec.js b/spec/core/EnvSpec.js index aa87a997..dc7233c8 100644 --- a/spec/core/EnvSpec.js +++ b/spec/core/EnvSpec.js @@ -304,4 +304,62 @@ describe('Env', function() { expect(globalErrors.install).toHaveBeenCalled(); }); }); + + it('creates an expectationFactory that uses the current custom equality testers', function(done) { + function customEqualityTester() {} + var RealSpec = jasmineUnderTest.Spec, + specInstance, + expectationFactory; + spyOn(jasmineUnderTest, 'MatchersUtil'); + spyOn(jasmineUnderTest, 'Spec').and.callFake(function(options) { + expectationFactory = options.expectationFactory; + specInstance = new RealSpec(options); + return specInstance; + }); + + env.it('spec', function() { + env.addCustomEqualityTester(customEqualityTester); + expectationFactory('actual', specInstance); + }); + + env.addReporter({ + jasmineDone: function() { + expect(jasmineUnderTest.MatchersUtil).toHaveBeenCalledWith({ + customTesters: [customEqualityTester] + }); + done(); + } + }); + + env.execute(); + }); + + it('creates an asyncExpectationFactory that uses the current custom equality testers', function(done) { + function customEqualityTester() {} + var RealSpec = jasmineUnderTest.Spec, + specInstance, + asyncExpectationFactory; + spyOn(jasmineUnderTest, 'MatchersUtil'); + spyOn(jasmineUnderTest, 'Spec').and.callFake(function(options) { + asyncExpectationFactory = options.asyncExpectationFactory; + specInstance = new RealSpec(options); + return specInstance; + }); + + env.it('spec', function() { + env.addCustomEqualityTester(customEqualityTester); + asyncExpectationFactory('actual', specInstance); + }); + + env.addReporter({ + jasmineDone: function() { + expect(jasmineUnderTest.MatchersUtil).toHaveBeenCalledWith({ + customTesters: [customEqualityTester] + }); + done(); + } + }); + + env.execute(); + }); }); diff --git a/spec/core/ExpectationSpec.js b/spec/core/ExpectationSpec.js index 45f69eb5..361224ab 100644 --- a/spec/core/ExpectationSpec.js +++ b/spec/core/ExpectationSpec.js @@ -634,7 +634,7 @@ describe('Expectation', function() { addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - util: jasmineUnderTest.matchersUtil, + util: new jasmineUnderTest.MatchersUtil(), actual: 'an actual', addExpectationResult: addExpectationResult }); diff --git a/spec/core/asymmetricEqualityTesterArgCompatShimSpec.js b/spec/core/asymmetricEqualityTesterArgCompatShimSpec.js new file mode 100644 index 00000000..c7c4d9b6 --- /dev/null +++ b/spec/core/asymmetricEqualityTesterArgCompatShimSpec.js @@ -0,0 +1,101 @@ +describe('asymmetricEqualityTesterArgCompatShim', function() { + it('provides all the properties of the MatchersUtil', function() { + var matchersUtil = { + foo: function() {}, + bar: function() {} + }, + shim = jasmineUnderTest.asymmetricEqualityTesterArgCompatShim( + matchersUtil, + [] + ); + + expect(shim.foo).toBe(matchersUtil.foo); + expect(shim.bar).toBe(matchersUtil.bar); + }); + + it('provides all the properties of the customEqualityTesters', function() { + var customEqualityTesters = [function() {}, function() {}], + shim = jasmineUnderTest.asymmetricEqualityTesterArgCompatShim( + {}, + customEqualityTesters + ); + + expect(shim.length).toBe(2); + expect(shim[0]).toBe(customEqualityTesters[0]); + expect(shim[1]).toBe(customEqualityTesters[1]); + }); + + it('provides all the properties of Array.prototype', function() { + var shim = jasmineUnderTest.asymmetricEqualityTesterArgCompatShim({}, []); + + expect(shim.filter).toBe(Array.prototype.filter); + expect(shim.forEach).toBe(Array.prototype.forEach); + expect(shim.map).toBe(Array.prototype.map); + }); + + it('provides properties of Array.prototype', function() { + var keys = [ + 'concat', + 'constructor', + 'every', + 'filter', + 'forEach', + 'indexOf', + 'join', + 'lastIndexOf', + 'length', + 'map', + 'pop', + 'push', + 'reduce', + 'reduceRight', + 'reverse', + 'shift', + 'slice', + 'some', + 'sort', + 'splice', + 'toLocaleString', + 'toString', + 'unshift' + ], + optionalKeys = [ + 'copyWithin', + 'entries', + 'fill', + 'find', + 'findIndex', + 'flat', + 'flatMap', + 'includes', + 'keys', + 'toSource', + 'values' + ], + shim = jasmineUnderTest.asymmetricEqualityTesterArgCompatShim({}, []), + i, + k; + + // Properties that are present on all supported runtimes + for (i = 0; i < keys.length; i++) { + k = keys[i]; + expect(shim[k]) + .withContext(k) + .not.toBeUndefined(); + expect(shim[k]) + .withContext(k) + .toBe(Array.prototype[k]); + } + + // Properties that are present on only some supported runtimes + for (i = 0; i < optionalKeys.length; i++) { + k = optionalKeys[i]; + + if (shim[k] !== undefined) { + expect(shim[k]) + .withContext(k) + .toBe(Array.prototype[k]); + } + } + }); +}); diff --git a/spec/core/asymmetric_equality/ArrayContainingSpec.js b/spec/core/asymmetric_equality/ArrayContainingSpec.js index 30b5aaad..4cbfa66d 100644 --- a/spec/core/asymmetric_equality/ArrayContainingSpec.js +++ b/spec/core/asymmetric_equality/ArrayContainingSpec.js @@ -15,26 +15,30 @@ describe("ArrayContaining", function() { it("matches when the item is in the actual", function() { var containing = new jasmineUnderTest.ArrayContaining(["foo"]); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(["foo"])).toBe(true); + expect(containing.asymmetricMatch(["foo"], matchersUtil)).toBe(true); }); it("matches when additional items are in the actual", function() { var containing = new jasmineUnderTest.ArrayContaining(["foo"]); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(["foo", "bar"])).toBe(true); + expect(containing.asymmetricMatch(["foo", "bar"], matchersUtil)).toBe(true); }); it("does not match when the item is not in the actual", function() { var containing = new jasmineUnderTest.ArrayContaining(["foo"]); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(["bar"])).toBe(false); + expect(containing.asymmetricMatch(["bar"], matchersUtil)).toBe(false); }); it("does not match when the actual is not an array", function() { var containing = new jasmineUnderTest.ArrayContaining(["foo"]); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch("foo")).toBe(false); + expect(containing.asymmetricMatch("foo", matchersUtil)).toBe(false); }); it("jasmineToStrings itself", function() { @@ -52,7 +56,8 @@ describe("ArrayContaining", function() { } }; var containing = new jasmineUnderTest.ArrayContaining(["fooVal"]); + var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); - expect(containing.asymmetricMatch(["fooBar"], [tester])).toBe(true); + expect(containing.asymmetricMatch(["fooBar"], matchersUtil)).toBe(true); }); }); diff --git a/spec/core/asymmetric_equality/ArrayWithExactContentsSpec.js b/spec/core/asymmetric_equality/ArrayWithExactContentsSpec.js index 1cae0a0b..5f8795d6 100644 --- a/spec/core/asymmetric_equality/ArrayWithExactContentsSpec.js +++ b/spec/core/asymmetric_equality/ArrayWithExactContentsSpec.js @@ -1,8 +1,9 @@ describe("ArrayWithExactContents", function() { it("matches an array with the same items in a different order", function() { var matcher = new jasmineUnderTest.ArrayWithExactContents(['a', 2, /a/]); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matcher.asymmetricMatch([2, 'a', /a/])).toBe(true); + expect(matcher.asymmetricMatch([2, 'a', /a/], matchersUtil)).toBe(true); }); it("does not work when not passed an array", function() { @@ -15,15 +16,17 @@ describe("ArrayWithExactContents", function() { it("does not match when an item is missing", function() { var matcher = new jasmineUnderTest.ArrayWithExactContents(['a', 2, /a/]); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matcher.asymmetricMatch(['a', 2])).toBe(false); - expect(matcher.asymmetricMatch(['a', 2, undefined])).toBe(false); + expect(matcher.asymmetricMatch(['a', 2], matchersUtil)).toBe(false); + expect(matcher.asymmetricMatch(['a', 2, undefined], matchersUtil)).toBe(false); }); it("does not match when there is an extra item", function() { var matcher = new jasmineUnderTest.ArrayWithExactContents(['a']); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matcher.asymmetricMatch(['a', 2])).toBe(false); + expect(matcher.asymmetricMatch(['a', 2], matchersUtil)).toBe(false); }); it("jasmineToStrings itself", function() { @@ -41,7 +44,8 @@ describe("ArrayWithExactContents", function() { } }; var matcher = new jasmineUnderTest.ArrayWithExactContents(["fooVal"]); + var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); - expect(matcher.asymmetricMatch(["fooBar"], [tester])).toBe(true); + expect(matcher.asymmetricMatch(["fooBar"], matchersUtil)).toBe(true); }); }); diff --git a/spec/core/asymmetric_equality/MapContainingSpec.js b/spec/core/asymmetric_equality/MapContainingSpec.js index a214dce8..f264e693 100644 --- a/spec/core/asymmetric_equality/MapContainingSpec.js +++ b/spec/core/asymmetric_equality/MapContainingSpec.js @@ -31,8 +31,9 @@ describe('MapContaining', function() { ['foo', [1, 2, 3]], ]); var containing = new jasmineUnderTest.MapContaining(containingMap); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(actualMap)).toBe(true); + expect(containing.asymmetricMatch(actualMap, matchersUtil)).toBe(true); }); it('does not match when a key is not in actual', function() { @@ -46,8 +47,9 @@ describe('MapContaining', function() { ['foo', [1, 2, 3]], ]); var containing = new jasmineUnderTest.MapContaining(containingMap); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(actualMap)).toBe(false); + expect(containing.asymmetricMatch(actualMap, matchersUtil)).toBe(false); }); it('does not match when a value is not in actual', function() { @@ -61,8 +63,9 @@ describe('MapContaining', function() { ['foo', [1, 2]], ]); var containing = new jasmineUnderTest.MapContaining(containingMap); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(actualMap)).toBe(false); + expect(containing.asymmetricMatch(actualMap, matchersUtil)).toBe(false); }); it('matches when all the key/value pairs in sample have asymmetric matches in actual', function() { @@ -74,17 +77,18 @@ describe('MapContaining', function() { var containingMap = new MapI([ [ - jasmine.stringMatching(/^foo\d/), + jasmineUnderTest.stringMatching(/^foo\d/), 'bar' ], [ 'baz', - jasmine.arrayContaining([2, 3]) + jasmineUnderTest.arrayContaining([2, 3]) ], ]); var containing = new jasmineUnderTest.MapContaining(containingMap); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(actualMap)).toBe(true); + expect(containing.asymmetricMatch(actualMap, matchersUtil)).toBe(true); }); it('does not match when a key in sample has no asymmetric matches in actual', function() { @@ -95,17 +99,18 @@ describe('MapContaining', function() { var containingMap = new MapI([ [ - jasmine.stringMatching(/^foo\d/), + jasmineUnderTest.stringMatching(/^foo\d/), 'bar' ], [ 'baz', - jasmine.arrayContaining([2, 3]) + jasmineUnderTest.arrayContaining([2, 3]) ], ]); var containing = new jasmineUnderTest.MapContaining(containingMap); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(actualMap)).toBe(false); + expect(containing.asymmetricMatch(actualMap, matchersUtil)).toBe(false); }); it('does not match when a value in sample has no asymmetric matches in actual', function() { @@ -116,17 +121,18 @@ describe('MapContaining', function() { var containingMap = new MapI([ [ - jasmine.stringMatching(/^foo\d/), + jasmineUnderTest.stringMatching(/^foo\d/), 'bar' ], [ 'baz', - jasmine.arrayContaining([4, 5]) + jasmineUnderTest.arrayContaining([4, 5]) ], ]); var containing = new jasmineUnderTest.MapContaining(containingMap); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(actualMap)).toBe(false); + expect(containing.asymmetricMatch(actualMap, matchersUtil)).toBe(false); }); it('matches recursively', function() { @@ -147,8 +153,9 @@ describe('MapContaining', function() { ], ]); var containing = new jasmineUnderTest.MapContaining(containingMap); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(actualMap)).toBe(true); + expect(containing.asymmetricMatch(actualMap, matchersUtil)).toBe(true); }); it('uses custom equality testers', function() { @@ -158,8 +165,9 @@ describe('MapContaining', function() { } var actualMap = new MapI([['foo', -1]]); var containing = new jasmineUnderTest.MapContaining(new MapI([['foo', -2]])); + var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); - expect(containing.asymmetricMatch(actualMap, [tester])).toBe(true); + expect(containing.asymmetricMatch(actualMap, matchersUtil)).toBe(true); }); it('does not match when actual is not a map', function() { diff --git a/spec/core/asymmetric_equality/ObjectContainingSpec.js b/spec/core/asymmetric_equality/ObjectContainingSpec.js index e2741a9d..13fa0a90 100644 --- a/spec/core/asymmetric_equality/ObjectContainingSpec.js +++ b/spec/core/asymmetric_equality/ObjectContainingSpec.js @@ -2,8 +2,9 @@ describe("ObjectContaining", function() { it("matches any actual to an empty object", function() { var containing = new jasmineUnderTest.ObjectContaining({}); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch("foo")).toBe(true); + expect(containing.asymmetricMatch("foo", matchersUtil)).toBe(true); }); it("does not match an empty object actual", function() { @@ -16,20 +17,23 @@ describe("ObjectContaining", function() { it("matches when the key/value pair is present in the actual", function() { var containing = new jasmineUnderTest.ObjectContaining({foo: "fooVal"}); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch({foo: "fooVal", bar: "barVal"})).toBe(true); + expect(containing.asymmetricMatch({foo: "fooVal", bar: "barVal"}, matchersUtil)).toBe(true); }); it("does not match when the key/value pair is not present in the actual", function() { var containing = new jasmineUnderTest.ObjectContaining({foo: "fooVal"}); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch({bar: "barVal", quux: "quuxVal"})).toBe(false); + expect(containing.asymmetricMatch({bar: "barVal", quux: "quuxVal"}, matchersUtil)).toBe(false); }); it("does not match when the key is present but the value is different in the actual", function() { var containing = new jasmineUnderTest.ObjectContaining({foo: "other"}); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch({foo: "fooVal", bar: "barVal"})).toBe(false); + expect(containing.asymmetricMatch({foo: "fooVal", bar: "barVal"}, matchersUtil)).toBe(false); }); it("jasmineToString's itself", function() { @@ -40,34 +44,39 @@ describe("ObjectContaining", function() { it("matches recursively", function() { var containing = new jasmineUnderTest.ObjectContaining({one: new jasmineUnderTest.ObjectContaining({two: {}})}); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch({one: {two: {}}})).toBe(true); + expect(containing.asymmetricMatch({one: {two: {}}}, matchersUtil)).toBe(true); }); it("matches when key is present with undefined value", function() { var containing = new jasmineUnderTest.ObjectContaining({ one: undefined }); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch({ one: undefined })).toBe(true); + expect(containing.asymmetricMatch({ one: undefined }, matchersUtil)).toBe(true); }); it("does not match when key with undefined value is not present", function() { var containing = new jasmineUnderTest.ObjectContaining({ one: undefined }); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch({})).toBe(false); + expect(containing.asymmetricMatch({}, matchersUtil)).toBe(false); }); it("matches defined properties", function(){ var containing = new jasmineUnderTest.ObjectContaining({ foo: "fooVal" }); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var definedPropertyObject = {}; Object.defineProperty(definedPropertyObject, "foo", { get: function() { return "fooVal" } }); - expect(containing.asymmetricMatch(definedPropertyObject)).toBe(true); + expect(containing.asymmetricMatch(definedPropertyObject, matchersUtil)).toBe(true); }); it("matches prototype properties", function(){ var containing = new jasmineUnderTest.ObjectContaining({ foo: "fooVal" }); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var prototypeObject = {foo: "fooVal"}; var obj; @@ -81,7 +90,7 @@ describe("ObjectContaining", function() { obj = new Foo(); } - expect(containing.asymmetricMatch(obj)).toBe(true); + expect(containing.asymmetricMatch(obj, matchersUtil)).toBe(true); }); it("uses custom equality testers", function() { @@ -93,7 +102,8 @@ describe("ObjectContaining", function() { } }; var containing = new jasmineUnderTest.ObjectContaining({foo: "fooVal"}); + var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); - expect(containing.asymmetricMatch({foo: "fooBar"}, [tester])).toBe(true); + expect(containing.asymmetricMatch({foo: "fooBar"}, matchersUtil)).toBe(true); }); }); diff --git a/spec/core/asymmetric_equality/SetContainingSpec.js b/spec/core/asymmetric_equality/SetContainingSpec.js index d1ae7a5a..f882621f 100644 --- a/spec/core/asymmetric_equality/SetContainingSpec.js +++ b/spec/core/asymmetric_equality/SetContainingSpec.js @@ -28,8 +28,9 @@ describe('SetContaining', function() { [1, 2, 3], {'foo': 'bar'} ]); var containing = new jasmineUnderTest.SetContaining(containingSet); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(actualSet)).toBe(true); + expect(containing.asymmetricMatch(actualSet, matchersUtil)).toBe(true); }); it('does not match when a value is not in actual', function() { @@ -41,8 +42,9 @@ describe('SetContaining', function() { [1, 2], {'foo': 'bar'} ]); var containing = new jasmineUnderTest.SetContaining(containingSet); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(actualSet)).toBe(false); + expect(containing.asymmetricMatch(actualSet, matchersUtil)).toBe(false); }); it('matches when all the values in sample have asymmetric matches in actual', function() { @@ -51,12 +53,13 @@ describe('SetContaining', function() { ]); var containingSet = new SetI([ - jasmine.stringMatching(/^foo\d/), - jasmine.arrayContaining([2, 3]), + jasmineUnderTest.stringMatching(/^foo\d/), + jasmineUnderTest.arrayContaining([2, 3]), ]); var containing = new jasmineUnderTest.SetContaining(containingSet); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(actualSet)).toBe(true); + expect(containing.asymmetricMatch(actualSet, matchersUtil)).toBe(true); }); it('does not match when a value in sample has no asymmetric matches in actual', function() { @@ -69,8 +72,9 @@ describe('SetContaining', function() { jasmine.arrayContaining([2, 3]), ]); var containing = new jasmineUnderTest.SetContaining(containingSet); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(actualSet)).toBe(false); + expect(containing.asymmetricMatch(actualSet, matchersUtil)).toBe(false); }); it('matches recursively', function() { @@ -82,8 +86,9 @@ describe('SetContaining', function() { new jasmineUnderTest.SetContaining(new SetI(['bar'])), 'foo' ]); var containing = new jasmineUnderTest.SetContaining(containingSet); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(actualSet)).toBe(true); + expect(containing.asymmetricMatch(actualSet, matchersUtil)).toBe(true); }); it('uses custom equality testers', function() { @@ -93,8 +98,9 @@ describe('SetContaining', function() { } var actualSet = new SetI(['foo', -1]); var containing = new jasmineUnderTest.SetContaining(new SetI([-2, 'foo'])); + var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); - expect(containing.asymmetricMatch(actualSet, [tester])).toBe(true); + expect(containing.asymmetricMatch(actualSet, matchersUtil)).toBe(true); }); it('does not match when actual is not a set', function() { diff --git a/spec/core/integration/CustomAsyncMatchersSpec.js b/spec/core/integration/CustomAsyncMatchersSpec.js index 51ddef34..de4806c3 100644 --- a/spec/core/integration/CustomAsyncMatchersSpec.js +++ b/spec/core/integration/CustomAsyncMatchersSpec.js @@ -111,4 +111,36 @@ describe('Custom Async Matchers (Integration)', function() { env.addReporter({ specDone: specExpectations, jasmineDone: done }); env.execute(); }); + + it("provides custom equality testers to the matcher factory via matchersUtil", function(done) { + jasmine.getEnv().requirePromises(); + + var matcherFactory = function (matchersUtil) { + return { + compare: function (actual, expected) { + return Promise.resolve({pass: matchersUtil.equals(actual[0], expected)}); + } + }; + }, + customEqualityFn = jasmine.createSpy("customEqualityFn").and.callFake(function (a, b) { + return a.toString() === b; + }); + + env.it("spec with expectation", function() { + env.addCustomEqualityTester(customEqualityFn); + env.addAsyncMatchers({ + toBeArrayWithFirstElement: matcherFactory + }); + + return env.expectAsync([1, 2]).toBeArrayWithFirstElement("1"); + }); + + var specExpectations = function(result) { + expect(customEqualityFn).toHaveBeenCalledWith(1, "1"); + expect(result.failedExpectations).toEqual([]); + }; + + env.addReporter({ specDone: specExpectations, jasmineDone: done }); + env.execute(); + }); }); diff --git a/spec/core/integration/CustomMatchersSpec.js b/spec/core/integration/CustomMatchersSpec.js index 4bb0c352..dfca7a78 100644 --- a/spec/core/integration/CustomMatchersSpec.js +++ b/spec/core/integration/CustomMatchersSpec.js @@ -1,19 +1,19 @@ -describe("Custom Matchers (Integration)", function() { +describe("Custom Matchers (Integration)", function () { var env; var fakeTimer; - beforeEach(function() { + beforeEach(function () { env = new jasmineUnderTest.Env(); env.configure({random: false}); }); - it("allows adding more matchers local to a spec", function(done) { - env.it('spec defining a custom matcher', function() { + it("allows adding more matchers local to a spec", function (done) { + env.it('spec defining a custom matcher', function () { env.addMatchers({ - matcherForSpec: function() { + matcherForSpec: function () { return { - compare: function(actual, expected) { - return { pass: false, message: "matcherForSpec: actual: " + actual + "; expected: " + expected }; + compare: function (actual, expected) { + return {pass: false, message: "matcherForSpec: actual: " + actual + "; expected: " + expected}; } } } @@ -83,6 +83,8 @@ describe("Custom Matchers (Integration)", function() { it("supports asymmetric equality testers that take a list of custom equality testers", function(done) { // TODO: remove this in the next major release. + spyOn(jasmineUnderTest, 'getEnv').and.returnValue(env); + env.it("spec using custom asymmetric equality tester", function() { var customEqualityFn = function(a, b) { if (a === 2 && b === "two") { @@ -229,4 +231,34 @@ describe("Custom Matchers (Integration)", function() { env.addReporter({ specDone: specExpectations, jasmineDone: done }); env.execute(); }); + + it("provides custom equality testers to the matcher factory via matchersUtil", function (done) { + var matcherFactory = function (matchersUtil) { + return { + compare: function (actual, expected) { + return {pass: matchersUtil.equals(actual[0], expected)}; + } + }; + }, + customEqualityFn = jasmine.createSpy("customEqualityFn").and.callFake(function (a, b) { + return a.toString() === b; + }); + + env.it("spec with expectation", function () { + env.addCustomEqualityTester(customEqualityFn); + env.addMatchers({ + toBeArrayWithFirstElement: matcherFactory + }); + + env.expect([1, 2]).toBeArrayWithFirstElement("1"); + }); + + var specExpectations = function (result) { + expect(customEqualityFn).toHaveBeenCalledWith(1, "1"); + expect(result.failedExpectations).toEqual([]); + }; + + env.addReporter({specDone: specExpectations, jasmineDone: done}); + env.execute(); + }); }); diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index e31f7d9d..2536fa07 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -2149,7 +2149,7 @@ describe("Env integration", function() { env.it('is a spec without any expectations', function() { // does nothing, just a mock spec without expectations }); - + }); it('should report "failed" status if "failSpecWithNoExpectations" is enabled', function(done) { @@ -2556,4 +2556,33 @@ describe("Env integration", function() { env.execute(); }); + + it("supports asymmetric equality testers that take a matchersUtil", function(done) { + var env = new jasmineUnderTest.Env(); + + env.it("spec using custom asymmetric equality tester", function() { + var customEqualityFn = function(a, b) { + if (a === 2 && b === "two") { + return true; + } + }; + var arrayWithFirstElement = function(sample) { + return { + asymmetricMatch: function (actual, matchersUtil) { + return matchersUtil.equals(sample, actual[0]); + } + }; + }; + + env.addCustomEqualityTester(customEqualityFn); + env.expect(["two"]).toEqual(arrayWithFirstElement(2)); + }); + + var specExpectations = function(result) { + expect(result.status).toEqual('passed'); + }; + + env.addReporter({ specDone: specExpectations, jasmineDone: done }); + env.execute(); + }); }); diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js index 6f81ea04..b21208d5 100644 --- a/spec/core/integration/MatchersSpec.js +++ b/spec/core/integration/MatchersSpec.js @@ -449,7 +449,10 @@ describe('Matchers (Integration)', function() { describe('toThrow', function() { verifyPasses(function(env) { - env.expect(function() { throw new Error(); }).toThrow(); + env.addCustomEqualityTester(function(a, b) { + return a.toString() === b.toString(); + }); + env.expect(function() { throw '5'; }).toThrow(5); }); verifyFails(function(env) { diff --git a/spec/core/matchers/async/toBeRejectedSpec.js b/spec/core/matchers/async/toBeRejectedSpec.js index 442ddba2..61bd2a5a 100644 --- a/spec/core/matchers/async/toBeRejectedSpec.js +++ b/spec/core/matchers/async/toBeRejectedSpec.js @@ -2,7 +2,8 @@ describe('toBeRejected', function() { it('passes if the actual is rejected', function() { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejected(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejected(matchersUtil), actual = Promise.reject('AsyncExpectationSpec rejection'); return matcher.compare(actual).then(function(result) { @@ -13,7 +14,8 @@ describe('toBeRejected', function() { it('fails if the actual is resolved', function() { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejected(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejected(matchersUtil), actual = Promise.resolve(); return matcher.compare(actual).then(function(result) { @@ -22,7 +24,8 @@ describe('toBeRejected', function() { }); it('fails if actual is not a promise', function() { - var matcher = jasmineUnderTest.asyncMatchers.toBeRejected(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejected(matchersUtil), actual = 'not a promise'; function f() { diff --git a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js index 3b207645..03a337b0 100644 --- a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js @@ -2,7 +2,8 @@ describe('#toBeRejectedWithError', function () { it('passes when Error type matches', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new TypeError('foo')); return matcher.compare(actual, TypeError).then(function (result) { @@ -16,7 +17,8 @@ describe('#toBeRejectedWithError', function () { it('passes when Error type and message matches', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new TypeError('foo')); return matcher.compare(actual, TypeError, 'foo').then(function (result) { @@ -30,7 +32,8 @@ describe('#toBeRejectedWithError', function () { it('passes when Error matches and is exactly Error', function() { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error()); return matcher.compare(actual, Error).then(function (result) { @@ -45,7 +48,8 @@ describe('#toBeRejectedWithError', function () { it('passes when Error message matches a string', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error('foo')); return matcher.compare(actual, 'foo').then(function (result) { @@ -59,7 +63,8 @@ describe('#toBeRejectedWithError', function () { it('passes when Error message matches a RegExp', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error('foo')); return matcher.compare(actual, /foo/).then(function (result) { @@ -73,7 +78,8 @@ describe('#toBeRejectedWithError', function () { it('passes when Error message is empty', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error()); return matcher.compare(actual, '').then(function (result) { @@ -87,7 +93,8 @@ describe('#toBeRejectedWithError', function () { it('passes when no arguments', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error()); return matcher.compare(actual, void 0).then(function (result) { @@ -101,7 +108,8 @@ describe('#toBeRejectedWithError', function () { it('fails when resolved', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.resolve(new Error('foo')); return matcher.compare(actual, 'foo').then(function (result) { @@ -115,7 +123,8 @@ describe('#toBeRejectedWithError', function () { it('fails when rejected with non Error type', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject('foo'); return matcher.compare(actual, 'foo').then(function (result) { @@ -129,7 +138,8 @@ describe('#toBeRejectedWithError', function () { it('fails when Error type mismatches', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error('foo')); return matcher.compare(actual, TypeError, 'foo').then(function (result) { @@ -143,7 +153,8 @@ describe('#toBeRejectedWithError', function () { it('fails when Error message mismatches', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error('foo')); return matcher.compare(actual, 'bar').then(function (result) { @@ -155,7 +166,8 @@ describe('#toBeRejectedWithError', function () { }); it('fails if actual is not a promise', function() { - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = 'not a promise'; function f() { diff --git a/spec/core/matchers/async/toBeRejectedWithSpec.js b/spec/core/matchers/async/toBeRejectedWithSpec.js index ea927c20..c1d22d0b 100644 --- a/spec/core/matchers/async/toBeRejectedWithSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithSpec.js @@ -2,7 +2,8 @@ describe('#toBeRejectedWith', function () { it('should return true if the promise is rejected with the expected value', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = Promise.reject({error: 'PEBCAK'}); return matcher.compare(actual, {error: 'PEBCAK'}).then(function (result) { @@ -13,7 +14,8 @@ describe('#toBeRejectedWith', function () { it('should fail if the promise resolves', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = Promise.resolve(); return matcher.compare(actual, '').then(function (result) { @@ -24,7 +26,8 @@ describe('#toBeRejectedWith', function () { it('should fail if the promise is rejected with a different value', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = Promise.reject('A Bad Apple'); return matcher.compare(actual, 'Some Cool Thing').then(function (result) { @@ -38,7 +41,8 @@ describe('#toBeRejectedWith', function () { it('should build its error correctly when negated', function () { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = Promise.reject(true); return matcher.compare(actual, true).then(function (result) { @@ -53,7 +57,8 @@ describe('#toBeRejectedWith', function () { jasmine.getEnv().requirePromises(); var customEqualityTesters = [function() { return true; }], - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(jasmineUnderTest.matchersUtil, customEqualityTesters), + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: customEqualityTesters}), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = Promise.reject('actual'); return matcher.compare(actual, 'expected').then(function(result) { @@ -62,7 +67,8 @@ describe('#toBeRejectedWith', function () { }); it('fails if actual is not a promise', function() { - var matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = 'not a promise'; function f() { diff --git a/spec/core/matchers/async/toBeResolvedSpec.js b/spec/core/matchers/async/toBeResolvedSpec.js index 28297e30..a6ab25ba 100644 --- a/spec/core/matchers/async/toBeResolvedSpec.js +++ b/spec/core/matchers/async/toBeResolvedSpec.js @@ -2,7 +2,8 @@ describe('toBeResolved', function() { it('passes if the actual is resolved', function() { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeResolved(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeResolved(matchersUtil), actual = Promise.resolve(); return matcher.compare(actual).then(function(result) { @@ -13,7 +14,8 @@ describe('toBeResolved', function() { it('fails if the actual is rejected', function() { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeResolved(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeResolved(matchersUtil), actual = Promise.reject('AsyncExpectationSpec rejection'); return matcher.compare(actual).then(function(result) { @@ -22,7 +24,8 @@ describe('toBeResolved', function() { }); it('fails if actual is not a promise', function() { - var matcher = jasmineUnderTest.asyncMatchers.toBeResolved(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeResolved(matchersUtil), actual = 'not a promise'; function f() { diff --git a/spec/core/matchers/async/toBeResolvedToSpec.js b/spec/core/matchers/async/toBeResolvedToSpec.js index dc330920..426f9f12 100644 --- a/spec/core/matchers/async/toBeResolvedToSpec.js +++ b/spec/core/matchers/async/toBeResolvedToSpec.js @@ -2,7 +2,8 @@ describe('#toBeResolvedTo', function() { it('passes if the promise is resolved to the expected value', function() { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.resolve({foo: 42}); return matcher.compare(actual, {foo: 42}).then(function(result) { @@ -13,7 +14,8 @@ describe('#toBeResolvedTo', function() { it('fails if the promise is rejected', function() { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.reject('AsyncExpectationSpec error'); return matcher.compare(actual, '').then(function(result) { @@ -27,7 +29,8 @@ describe('#toBeResolvedTo', function() { it('fails if the promise is resolved to a different value', function() { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.resolve({foo: 17}); return matcher.compare(actual, {foo: 42}).then(function(result) { @@ -41,7 +44,8 @@ describe('#toBeResolvedTo', function() { it('builds its message correctly when negated', function() { jasmine.getEnv().requirePromises(); - var matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.resolve(true); return matcher.compare(actual, true).then(function(result) { @@ -56,7 +60,8 @@ describe('#toBeResolvedTo', function() { jasmine.getEnv().requirePromises(); var customEqualityTesters = [function() { return true; }], - matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(jasmineUnderTest.matchersUtil, customEqualityTesters), + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: customEqualityTesters}), + matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.resolve('actual'); return matcher.compare(actual, 'expected').then(function(result) { @@ -65,7 +70,8 @@ describe('#toBeResolvedTo', function() { }); it('fails if actual is not a promise', function() { - var matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(jasmineUnderTest.matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = 'not a promise'; function f() { diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index 570f8f20..096d7c86 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -1,178 +1,210 @@ describe("matchersUtil", function() { describe("equals", function() { it("passes for literals that are triple-equal", function() { - expect(jasmineUnderTest.matchersUtil.equals(null, null)).toBe(true); - expect(jasmineUnderTest.matchersUtil.equals(void 0, void 0)).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(null, null)).toBe(true); + expect(matchersUtil.equals(void 0, void 0)).toBe(true); }); it("fails for things that are not equivalent", function() { - expect(jasmineUnderTest.matchersUtil.equals({a: "foo"}, 1)).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals({a: "foo"}, 1)).toBe(false); }); it("passes for Strings that are equivalent", function() { - expect(jasmineUnderTest.matchersUtil.equals("foo", "foo")).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals("foo", "foo")).toBe(true); }); it("fails for Strings that are not equivalent", function() { - expect(jasmineUnderTest.matchersUtil.equals("foo", "bar")).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals("foo", "bar")).toBe(false); }); it("passes for Numbers that are equivalent", function() { - expect(jasmineUnderTest.matchersUtil.equals(123, 123)).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(123, 123)).toBe(true); }); it("fails for Numbers that are not equivalent", function() { - expect(jasmineUnderTest.matchersUtil.equals(123, 456)).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(123, 456)).toBe(false); }); it("passes for Dates that are equivalent", function() { - expect(jasmineUnderTest.matchersUtil.equals(new Date("Jan 1, 1970"), new Date("Jan 1, 1970"))).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(new Date("Jan 1, 1970"), new Date("Jan 1, 1970"))).toBe(true); }); it("fails for Dates that are not equivalent", function() { - expect(jasmineUnderTest.matchersUtil.equals(new Date("Jan 1, 1970"), new Date("Feb 3, 1991"))).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(new Date("Jan 1, 1970"), new Date("Feb 3, 1991"))).toBe(false); }); it("passes for Booleans that are equivalent", function() { - expect(jasmineUnderTest.matchersUtil.equals(true, true)).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(true, true)).toBe(true); }); it("fails for Booleans that are not equivalent", function() { - expect(jasmineUnderTest.matchersUtil.equals(true, false)).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(true, false)).toBe(false); }); it("passes for RegExps that are equivalent", function() { - expect(jasmineUnderTest.matchersUtil.equals(/foo/, /foo/)).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(/foo/, /foo/)).toBe(true); }); it("fails for RegExps that are not equivalent", function() { - expect(jasmineUnderTest.matchersUtil.equals(/foo/, /bar/)).toBe(false); - expect(jasmineUnderTest.matchersUtil.equals(new RegExp("foo", "i"), new RegExp("foo"))).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(/foo/, /bar/)).toBe(false); + expect(matchersUtil.equals(new RegExp("foo", "i"), new RegExp("foo"))).toBe(false); }); it("passes for Arrays that are equivalent", function() { - expect(jasmineUnderTest.matchersUtil.equals([1, 2], [1, 2])).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals([1, 2], [1, 2])).toBe(true); }); it("passes for Arrays that are equivalent, with elements added by changing length", function() { - var foo = []; + var foo = [], + matchersUtil = new jasmineUnderTest.MatchersUtil(); foo.length = 1; - expect(jasmineUnderTest.matchersUtil.equals(foo, [undefined])).toBe(true); + expect(matchersUtil.equals(foo, [undefined])).toBe(true); }); it("fails for Arrays that have different lengths", function() { - expect(jasmineUnderTest.matchersUtil.equals([1, 2], [1, 2, 3])).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals([1, 2], [1, 2, 3])).toBe(false); }); it("fails for Arrays that have different elements", function() { - expect(jasmineUnderTest.matchersUtil.equals([1, 2, 3], [1, 5, 3])).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals([1, 2, 3], [1, 5, 3])).toBe(false); }); it("fails for Arrays whose contents are equivalent, but have differing properties", function() { var one = [1,2,3], - two = [1,2,3]; + two = [1,2,3], + matchersUtil = new jasmineUnderTest.MatchersUtil(); one.foo = 'bar'; two.foo = 'baz'; - expect(jasmineUnderTest.matchersUtil.equals(one, two)).toBe(false); + expect(matchersUtil.equals(one, two)).toBe(false); }); it("passes for Arrays with equivalent contents and properties", function() { var one = [1,2,3], - two = [1,2,3]; + two = [1,2,3], + matchersUtil = new jasmineUnderTest.MatchersUtil(); one.foo = 'bar'; two.foo = 'bar'; - expect(jasmineUnderTest.matchersUtil.equals(one, two)).toBe(true); + expect(matchersUtil.equals(one, two)).toBe(true); }); it("passes for Errors that are the same type and have the same message", function() { - expect(jasmineUnderTest.matchersUtil.equals(new Error("foo"), new Error("foo"))).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(new Error("foo"), new Error("foo"))).toBe(true); }); it("fails for Errors that are the same type and have different messages", function() { - expect(jasmineUnderTest.matchersUtil.equals(new Error("foo"), new Error("bar"))).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(new Error("foo"), new Error("bar"))).toBe(false); }); it("fails for objects with different constructors", function() { + var matchersUtil = new jasmineUnderTest.MatchersUtil(); function One() {} function Two() {} - expect(jasmineUnderTest.matchersUtil.equals(new One(), new Two())).toBe(false); + expect(matchersUtil.equals(new One(), new Two())).toBe(false); }); it("passes for Objects that are equivalent (simple case)", function() { - expect(jasmineUnderTest.matchersUtil.equals({a: "foo"}, {a: "foo"})).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals({a: "foo"}, {a: "foo"})).toBe(true); }); it("fails for Objects that are not equivalent (simple case)", function() { - expect(jasmineUnderTest.matchersUtil.equals({a: "foo"}, {a: "bar"})).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals({a: "foo"}, {a: "bar"})).toBe(false); }); it("passes for Objects that are equivalent (deep case)", function() { - expect(jasmineUnderTest.matchersUtil.equals({a: "foo", b: { c: "bar"}}, {a: "foo", b: { c: "bar"}})).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals({a: "foo", b: { c: "bar"}}, {a: "foo", b: { c: "bar"}})).toBe(true); }); it("fails for Objects that are not equivalent (deep case)", function() { - expect(jasmineUnderTest.matchersUtil.equals({a: "foo", b: { c: "baz"}}, {a: "foo", b: { c: "bar"}})).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals({a: "foo", b: { c: "baz"}}, {a: "foo", b: { c: "bar"}})).toBe(false); }); it("passes for Objects that are equivalent (with cycles)", function() { var actual = { a: "foo" }, - expected = { a: "foo" }; + expected = { a: "foo" }, + matchersUtil = new jasmineUnderTest.MatchersUtil(); actual.b = actual; expected.b = actual; - expect(jasmineUnderTest.matchersUtil.equals(actual, expected)).toBe(true); + expect(matchersUtil.equals(actual, expected)).toBe(true); }); it("fails for Objects that are not equivalent (with cycles)", function() { var actual = { a: "foo" }, - expected = { a: "bar" }; + expected = { a: "bar" }, + matchersUtil = new jasmineUnderTest.MatchersUtil(); actual.b = actual; expected.b = actual; - expect(jasmineUnderTest.matchersUtil.equals(actual, expected)).toBe(false); + expect(matchersUtil.equals(actual, expected)).toBe(false); }); it("fails for Objects that have the same number of keys, but different keys/values", function () { var expected = { a: undefined }, - actual = { b: 1 }; + actual = { b: 1 }, + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.equals(actual, expected)).toBe(false); + expect(matchersUtil.equals(actual, expected)).toBe(false); }); it("fails when comparing an empty object to an empty array (issue #114)", function() { var emptyObject = {}, - emptyArray = []; + emptyArray = [], + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.equals(emptyObject, emptyArray)).toBe(false); - expect(jasmineUnderTest.matchersUtil.equals(emptyArray, emptyObject)).toBe(false); + + expect(matchersUtil.equals(emptyObject, emptyArray)).toBe(false); + expect(matchersUtil.equals(emptyArray, emptyObject)).toBe(false); }); it("passes for equivalent frozen objects (GitHub issue #266)", function() { var a = { foo: 1 }, - b = {foo: 1 }; + b = {foo: 1 }, + matchersUtil = new jasmineUnderTest.MatchersUtil(); Object.freeze(a); Object.freeze(b); - expect(jasmineUnderTest.matchersUtil.equals(a,b)).toBe(true); + expect(matchersUtil.equals(a,b)).toBe(true); }); it("passes for equivalent Promises (GitHub issue #1314)", function() { if (typeof Promise === 'undefined') { return; } var p1 = new Promise(function () {}), - p2 = new Promise(function () {}); + p2 = new Promise(function () {}), + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.equals(p1, p1)).toBe(true); - expect(jasmineUnderTest.matchersUtil.equals(p1, p2)).toBe(false); + expect(matchersUtil.equals(p1, p1)).toBe(true); + expect(matchersUtil.equals(p1, p2)).toBe(false); }); describe("when running in a browser", function() { @@ -185,6 +217,8 @@ describe("matchersUtil", function() { return; } var a = document.createElement("div"); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + a.setAttribute("test-attr", "attr-value"); a.appendChild(document.createTextNode('test')); @@ -192,17 +226,18 @@ describe("matchersUtil", function() { b.setAttribute("test-attr", "attr-value"); b.appendChild(document.createTextNode('test')); - expect(jasmineUnderTest.matchersUtil.equals(a,b)).toBe(true); + expect(matchersUtil.equals(a,b)).toBe(true); }); it("passes for equivalent objects from different frames", function() { if (isNotRunningInBrowser()) { return; } + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var iframe = document.createElement('iframe'); document.body.appendChild(iframe); iframe.contentWindow.eval('window.testObject = {}'); - expect(jasmineUnderTest.matchersUtil.equals({}, iframe.contentWindow.testObject)).toBe(true); + expect(matchersUtil.equals({}, iframe.contentWindow.testObject)).toBe(true); document.body.removeChild(iframe); }); @@ -210,6 +245,7 @@ describe("matchersUtil", function() { if (isNotRunningInBrowser()) { return; } + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var a = document.createElement("div"); a.setAttribute("test-attr", "attr-value"); a.appendChild(document.createTextNode('test')); @@ -218,16 +254,16 @@ describe("matchersUtil", function() { b.setAttribute("test-attr", "attr-value2"); b.appendChild(document.createTextNode('test')); - expect(jasmineUnderTest.matchersUtil.equals(a,b)).toBe(false); + expect(matchersUtil.equals(a,b)).toBe(false); b.setAttribute("test-attr", "attr-value"); - expect(jasmineUnderTest.matchersUtil.equals(a,b)).toBe(true); + expect(matchersUtil.equals(a,b)).toBe(true); b.appendChild(document.createTextNode('2')); - expect(jasmineUnderTest.matchersUtil.equals(a,b)).toBe(false); + expect(matchersUtil.equals(a,b)).toBe(false); a.appendChild(document.createTextNode('2')); - expect(jasmineUnderTest.matchersUtil.equals(a,b)).toBe(true); + expect(matchersUtil.equals(a,b)).toBe(true); }); }); @@ -240,43 +276,47 @@ describe("matchersUtil", function() { if (isNotRunningInNode()) { return; } + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var vm = require('vm'); var sandbox = { obj: null }; vm.runInNewContext('obj = {a: 1, b: 2}', sandbox); - expect(jasmineUnderTest.matchersUtil.equals(sandbox.obj, {a: 1, b: 2})).toBe(true); + expect(matchersUtil.equals(sandbox.obj, {a: 1, b: 2})).toBe(true); }); it("passes for equivalent arrays from different vm contexts", function() { if (isNotRunningInNode()) { return; } + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var vm = require('vm'); var sandbox = { arr: null }; vm.runInNewContext('arr = [1, 2]', sandbox); - expect(jasmineUnderTest.matchersUtil.equals(sandbox.arr, [1, 2])).toBe(true); + expect(matchersUtil.equals(sandbox.arr, [1, 2])).toBe(true); }); }); it("passes when Any is used", function() { var number = 3, - anyNumber = new jasmineUnderTest.Any(Number); + anyNumber = new jasmineUnderTest.Any(Number), + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.equals(number, anyNumber)).toBe(true); - expect(jasmineUnderTest.matchersUtil.equals(anyNumber, number)).toBe(true); + expect(matchersUtil.equals(number, anyNumber)).toBe(true); + expect(matchersUtil.equals(anyNumber, number)).toBe(true); }); it("fails when Any is compared to something unexpected", function() { var number = 3, - anyString = new jasmineUnderTest.Any(String); + anyString = new jasmineUnderTest.Any(String), + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.equals(number, anyString)).toBe(false); - expect(jasmineUnderTest.matchersUtil.equals(anyString, number)).toBe(false); + expect(matchersUtil.equals(number, anyString)).toBe(false); + expect(matchersUtil.equals(anyString, number)).toBe(false); }); it("passes when ObjectContaining is used", function() { @@ -284,135 +324,209 @@ describe("matchersUtil", function() { foo: 3, bar: 7 }, - containing = new jasmineUnderTest.ObjectContaining({foo: 3}); + containing = new jasmineUnderTest.ObjectContaining({foo: 3}), + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.equals(obj, containing)).toBe(true); - expect(jasmineUnderTest.matchersUtil.equals(containing, obj)).toBe(true); + expect(matchersUtil.equals(obj, containing)).toBe(true); + expect(matchersUtil.equals(containing, obj)).toBe(true); }); it("passes when MapContaining is used", function() { jasmine.getEnv().requireFunctioningMaps(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var obj = new Map(); obj.set(1, 2); obj.set('foo', 'bar'); var containing = new jasmineUnderTest.MapContaining(new Map()); containing.sample.set('foo', 'bar'); - expect(jasmineUnderTest.matchersUtil.equals(obj, containing)).toBe(true); - expect(jasmineUnderTest.matchersUtil.equals(containing, obj)).toBe(true); + expect(matchersUtil.equals(obj, containing)).toBe(true); + expect(matchersUtil.equals(containing, obj)).toBe(true); }); it("passes when SetContaining is used", function() { jasmine.getEnv().requireFunctioningSets(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var obj = new Set(); obj.add(1); obj.add('foo'); var containing = new jasmineUnderTest.SetContaining(new Set()); containing.sample.add(1); - expect(jasmineUnderTest.matchersUtil.equals(obj, containing)).toBe(true); - expect(jasmineUnderTest.matchersUtil.equals(containing, obj)).toBe(true); + expect(matchersUtil.equals(obj, containing)).toBe(true); + expect(matchersUtil.equals(containing, obj)).toBe(true); }); it("passes when an asymmetric equality tester returns true", function() { - var tester = { asymmetricMatch: function(other) { return true; } }; + var tester = { asymmetricMatch: function(other) { return true; } }, + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.equals(false, tester)).toBe(true); - expect(jasmineUnderTest.matchersUtil.equals(tester, false)).toBe(true); + expect(matchersUtil.equals(false, tester)).toBe(true); + expect(matchersUtil.equals(tester, false)).toBe(true); }); it("fails when an asymmetric equality tester returns false", function() { - var tester = { asymmetricMatch: function(other) { return false; } }; + var tester = { asymmetricMatch: function(other) { return false; } }, + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.equals(true, tester)).toBe(false); - expect(jasmineUnderTest.matchersUtil.equals(tester, true)).toBe(false); + expect(matchersUtil.equals(true, tester)).toBe(false); + expect(matchersUtil.equals(tester, true)).toBe(false); }); it("passes when ArrayContaining is used", function() { - var arr = ["foo", "bar"]; + var arr = ["foo", "bar"], + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.equals(arr, new jasmineUnderTest.ArrayContaining(["bar"]))).toBe(true); + expect(matchersUtil.equals(arr, new jasmineUnderTest.ArrayContaining(["bar"]))).toBe(true); }); - it("passes when a custom equality matcher returns true", function() { - var tester = function(a, b) { return true; }; + it("passes when a custom equality matcher passed to equals returns true", function() { + // TODO: remove this in the next major release. + var tester = function(a, b) { return true; }, + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.equals(1, 2, [tester])).toBe(true); + expect(matchersUtil.equals(1, 2, [tester])).toBe(true); + }); + + it("passes when a custom equality matcher passed to the constructor returns true", function() { + var tester = function(a, b) { return true; }, + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); + + expect(matchersUtil.equals(1, 2)).toBe(true); }); it("passes for two empty Objects", function () { - expect(jasmineUnderTest.matchersUtil.equals({}, {})).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals({}, {})).toBe(true); }); - describe("when a custom equality matcher is installed that returns 'undefined'", function () { + describe("when a custom equality matcher is passed to equals that returns 'undefined'", function () { + // TODO: remove this in the next major release. var tester = function(a, b) { return jasmine.undefined; }; it("passes for two empty Objects", function () { - expect(jasmineUnderTest.matchersUtil.equals({}, {}, [tester])).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals({}, {}, [tester])).toBe(true); }); }); - it("fails for equivalents when a custom equality matcher returns false", function() { - var tester = function(a, b) { return false; }; + describe("when a custom equality matcher is passed to the constructor that returns 'undefined'", function () { + var tester = function(a, b) { return jasmine.undefined; }; - expect(jasmineUnderTest.matchersUtil.equals(1, 1, [tester])).toBe(false); + it("passes for two empty Objects", function () { + var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); + expect(matchersUtil.equals({}, {})).toBe(true); + }); }); - it("passes for an asymmetric equality tester that returns true when a custom equality tester return false", function() { + it("fails for equivalents when a custom equality matcher passed to equals returns false", function() { + // TODO: remove this in the next major release. + var tester = function(a, b) { return false; }, + matchersUtil = new jasmineUnderTest.MatchersUtil(); + + expect(matchersUtil.equals(1, 1, [tester])).toBe(false); + }); + + it("fails for equivalents when a custom equality matcher passed to the constructor returns false", function() { + var tester = function(a, b) { return false; }, + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); + + expect(matchersUtil.equals(1, 1)).toBe(false); + }); + + it("passes for an asymmetric equality tester that returns true when a custom equality tester passed to equals return false", function() { + // TODO: remove this in the next major release. var asymmetricTester = { asymmetricMatch: function(other) { return true; } }, - symmetricTester = function(a, b) { return false; }; + symmetricTester = function(a, b) { return false; }, + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.equals(asymmetricTester, true, [symmetricTester])).toBe(true); - expect(jasmineUnderTest.matchersUtil.equals(true, asymmetricTester, [symmetricTester])).toBe(true); + expect(matchersUtil.equals(asymmetricTester, true, [symmetricTester])).toBe(true); + expect(matchersUtil.equals(true, asymmetricTester, [symmetricTester])).toBe(true); }); - it("passes custom equality matchers to asymmetric equality testers", function() { - var tester = function(a, b) {}; - var asymmetricTester = { asymmetricMatch: jasmine.createSpy('asymmetricMatch') }; - asymmetricTester.asymmetricMatch.and.returnValue(true); - var other = {}; + it("passes for an asymmetric equality tester that returns true when a custom equality tester passed to the constructor return false", function() { + var asymmetricTester = { asymmetricMatch: function(other) { return true; } }, + symmetricTester = function(a, b) { return false; }, + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [symmetricTester()]}); - expect(jasmineUnderTest.matchersUtil.equals(asymmetricTester, other, [tester])).toBe(true); - expect(asymmetricTester.asymmetricMatch).toHaveBeenCalledWith(other, [tester]); + expect(matchersUtil.equals(asymmetricTester, true)).toBe(true); + expect(matchersUtil.equals(true, asymmetricTester)).toBe(true); + }); + + describe("The compatibility shim passed to asymmetric equality testers", function() { + describe("When equals is called with custom equality testers", function() { + it("is both a matchersUtil and the custom equality testers passed to equals", function() { + var asymmetricTester = jasmine.createSpyObj('tester', ['asymmetricMatch']), + symmetricTester = function() { } , + matchersUtil = new jasmineUnderTest.MatchersUtil(), + shim; + + matchersUtil.equals(true, asymmetricTester, [symmetricTester]); + shim = asymmetricTester.asymmetricMatch.calls.argsFor(0)[1]; + expect(shim).toEqual(jasmine.any(jasmineUnderTest.MatchersUtil)); + expect(shim.length).toEqual(1); + expect(shim[0]).toEqual(symmetricTester); + }); + }); + + describe("When equals is called with custom equality testers", function() { + it("is both a matchersUtil and the custom equality testers passed to the constructor", function() { + var asymmetricTester = jasmine.createSpyObj('tester', ['asymmetricMatch']), + symmetricTester = function() { } , + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [symmetricTester]}), + shim; + + matchersUtil.equals(true, asymmetricTester); + shim = asymmetricTester.asymmetricMatch.calls.argsFor(0)[1]; + expect(shim).toEqual(jasmine.any(jasmineUnderTest.MatchersUtil)); + expect(shim.length).toEqual(1); + expect(shim[0]).toEqual(symmetricTester); + }); + }); }); it("passes when an Any is compared to an Any that checks for the same type", function() { var any1 = new jasmineUnderTest.Any(Function), - any2 = new jasmineUnderTest.Any(Function); + any2 = new jasmineUnderTest.Any(Function), + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.equals(any1, any2)).toBe(true); + expect(matchersUtil.equals(any1, any2)).toBe(true); }); it("passes for null prototype objects with same properties", function () { var objA = Object.create(null), - objB = Object.create(null); + objB = Object.create(null), + matchersUtil = new jasmineUnderTest.MatchersUtil(); objA.name = 'test'; objB.name = 'test'; - expect(jasmineUnderTest.matchersUtil.equals(objA, objB)).toBe(true); + expect(matchersUtil.equals(objA, objB)).toBe(true); }); it("fails for null prototype objects with different properties", function () { var objA = Object.create(null), - objB = Object.create(null); + objB = Object.create(null), + matchersUtil = new jasmineUnderTest.MatchersUtil(); objA.name = 'test'; objB.test = 'name'; - expect(jasmineUnderTest.matchersUtil.equals(objA, objB)).toBe(false); + expect(matchersUtil.equals(objA, objB)).toBe(false); }); it("passes when comparing two empty sets", function() { jasmine.getEnv().requireFunctioningSets(); - expect(jasmineUnderTest.matchersUtil.equals(new Set(), new Set())).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(new Set(), new Set())).toBe(true); }); it("passes when comparing identical sets", function() { jasmine.getEnv().requireFunctioningSets(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var setA = new Set(); setA.add(6); setA.add(5); @@ -420,12 +534,13 @@ describe("matchersUtil", function() { setB.add(6); setB.add(5); - expect(jasmineUnderTest.matchersUtil.equals(setA, setB)).toBe(true); + expect(matchersUtil.equals(setA, setB)).toBe(true); }); it("passes when comparing identical sets with different insertion order and simple elements", function() { jasmine.getEnv().requireFunctioningSets(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var setA = new Set(); setA.add(3); setA.add(6); @@ -433,12 +548,13 @@ describe("matchersUtil", function() { setB.add(6); setB.add(3); - expect(jasmineUnderTest.matchersUtil.equals(setA, setB)).toBe(true); + expect(matchersUtil.equals(setA, setB)).toBe(true); }); it("passes when comparing identical sets with different insertion order and complex elements 1", function() { jasmine.getEnv().requireFunctioningSets(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var setA1 = new Set(); setA1.add(['a',3]); setA1.add([6,1]); @@ -460,12 +576,13 @@ describe("matchersUtil", function() { setB.add(setB1); setB.add(setB2); - expect(jasmineUnderTest.matchersUtil.equals(setA, setB)).toBe(true); + expect(matchersUtil.equals(setA, setB)).toBe(true); }); it("passes when comparing identical sets with different insertion order and complex elements 2", function() { jasmine.getEnv().requireFunctioningSets(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var setA = new Set(); setA.add([[1,2], [3,4]]); setA.add([[5,6], [7,8]]); @@ -473,11 +590,12 @@ describe("matchersUtil", function() { setB.add([[5,6], [7,8]]); setB.add([[1,2], [3,4]]); - expect(jasmineUnderTest.matchersUtil.equals(setA, setB)).toBe(true); + expect(matchersUtil.equals(setA, setB)).toBe(true); }); it("fails for sets with different elements", function() { jasmine.getEnv().requireFunctioningSets(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var setA = new Set(); setA.add(6); setA.add(3); @@ -487,11 +605,12 @@ describe("matchersUtil", function() { setB.add(4); setB.add(5); - expect(jasmineUnderTest.matchersUtil.equals(setA, setB)).toBe(false); + expect(matchersUtil.equals(setA, setB)).toBe(false); }); it("fails for sets of different size", function() { jasmine.getEnv().requireFunctioningSets(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var setA = new Set(); setA.add(6); setA.add(3); @@ -500,36 +619,40 @@ describe("matchersUtil", function() { setB.add(4); setB.add(5); - expect(jasmineUnderTest.matchersUtil.equals(setA, setB)).toBe(false); + expect(matchersUtil.equals(setA, setB)).toBe(false); }); it("passes when comparing two empty maps", function() { jasmine.getEnv().requireFunctioningMaps(); - expect(jasmineUnderTest.matchersUtil.equals(new Map(), new Map())).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(new Map(), new Map())).toBe(true); }); it("passes when comparing identical maps", function() { jasmine.getEnv().requireFunctioningMaps(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var mapA = new Map(); mapA.set(6, 5); var mapB = new Map(); mapB.set(6, 5); - expect(jasmineUnderTest.matchersUtil.equals(mapA, mapB)).toBe(true); + expect(matchersUtil.equals(mapA, mapB)).toBe(true); }); it("passes when comparing identical maps with different insertion order", function() { jasmine.getEnv().requireFunctioningMaps(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var mapA = new Map(); mapA.set("a", 3); mapA.set(6, 1); var mapB = new Map(); mapB.set(6, 1); mapB.set("a", 3); - expect(jasmineUnderTest.matchersUtil.equals(mapA, mapB)).toBe(true); + expect(matchersUtil.equals(mapA, mapB)).toBe(true); }); it("fails for maps with different elements", function() { jasmine.getEnv().requireFunctioningMaps(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var mapA = new Map(); mapA.set(6, 3); mapA.set(5, 1); @@ -537,17 +660,18 @@ describe("matchersUtil", function() { mapB.set(6, 4); mapB.set(5, 1); - expect(jasmineUnderTest.matchersUtil.equals(mapA, mapB)).toBe(false); + expect(matchersUtil.equals(mapA, mapB)).toBe(false); }); it("fails for maps of different size", function() { jasmine.getEnv().requireFunctioningMaps(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var mapA = new Map(); mapA.set(6, 3); var mapB = new Map(); mapB.set(6, 4); mapB.set(5, 1); - expect(jasmineUnderTest.matchersUtil.equals(mapA, mapB)).toBe(false); + expect(matchersUtil.equals(mapA, mapB)).toBe(false); }); describe("when running in an environment with array polyfills", function() { @@ -593,71 +717,119 @@ describe("matchersUtil", function() { expect(['foo']).toEqual(['foo']); }); }); + + it('uses a diffBuilder if one is provided as the fourth argument', function() { + // TODO: remove this in the next major release. + var diffBuilder = new jasmineUnderTest.DiffBuilder(), + matchersUtil = new jasmineUnderTest.MatchersUtil(); + + spyOn(diffBuilder, 'record'); + spyOn(diffBuilder, 'withPath').and.callThrough(); + + matchersUtil.equals([1], [2], [], diffBuilder); + expect(diffBuilder.withPath).toHaveBeenCalledWith('length', jasmine.any(Function)); + expect(diffBuilder.withPath).toHaveBeenCalledWith(0, jasmine.any(Function)); + expect(diffBuilder.record).toHaveBeenCalledWith(1, 2); + }); + + it('uses a diffBuilder if one is provided as the third argument', function() { + var diffBuilder = new jasmineUnderTest.DiffBuilder(), + matchersUtil = new jasmineUnderTest.MatchersUtil(); + + spyOn(diffBuilder, 'record'); + spyOn(diffBuilder, 'withPath').and.callThrough(); + + matchersUtil.equals([1], [2], diffBuilder); + expect(diffBuilder.withPath).toHaveBeenCalledWith('length', jasmine.any(Function)); + expect(diffBuilder.withPath).toHaveBeenCalledWith(0, jasmine.any(Function)); + expect(diffBuilder.record).toHaveBeenCalledWith(1, 2); + }); }); describe("contains", function() { it("passes when expected is a substring of actual", function() { - expect(jasmineUnderTest.matchersUtil.contains("ABC", "BC")).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.contains("ABC", "BC")).toBe(true); }); it("fails when expected is a not substring of actual", function() { - expect(jasmineUnderTest.matchersUtil.contains("ABC", "X")).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.contains("ABC", "X")).toBe(false); }); it("passes when expected is an element in an actual array", function() { - expect(jasmineUnderTest.matchersUtil.contains(['foo', 'bar'], 'foo')).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.contains(['foo', 'bar'], 'foo')).toBe(true); }); it("fails when expected is not an element in an actual array", function() { - expect(jasmineUnderTest.matchersUtil.contains(['foo', 'bar'], 'baz')).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.contains(['foo', 'bar'], 'baz')).toBe(false); }); it("passes with mixed-element arrays", function() { - expect(jasmineUnderTest.matchersUtil.contains(["foo", {some: "bar"}], "foo")).toBe(true); - expect(jasmineUnderTest.matchersUtil.contains(["foo", {some: "bar"}], {some: "bar"})).toBe(true); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.contains(["foo", {some: "bar"}], "foo")).toBe(true); + expect(matchersUtil.contains(["foo", {some: "bar"}], {some: "bar"})).toBe(true); }); - it("uses custom equality testers if passed in and actual is an Array", function() { - var customTester = function(a, b) {return true;}; + it("uses custom equality testers if passed to contains and actual is an Array", function() { + // TODO: remove this in the next major release. + var customTester = function(a, b) {return true;}, + matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(jasmineUnderTest.matchersUtil.contains([1, 2], 3, [customTester])).toBe(true); + expect(matchersUtil.contains([1, 2], 3, [customTester])).toBe(true); + }); + + it("uses custom equality testers if passed to the constructor and actual is an Array", function() { + var customTester = function(a, b) {return true;}, + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [customTester]}); + + expect(matchersUtil.contains([1, 2], 3)).toBe(true); }); it("fails when actual is undefined", function() { - expect(jasmineUnderTest.matchersUtil.contains(undefined, 'A')).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.contains(undefined, 'A')).toBe(false); }); it("fails when actual is null", function() { - expect(jasmineUnderTest.matchersUtil.contains(null, 'A')).toBe(false); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.contains(null, 'A')).toBe(false); }); it("passes with array-like objects", function() { - var capturedArgs = null; + var capturedArgs = null, + matchersUtil = new jasmineUnderTest.MatchersUtil(); + function testFunction(){ capturedArgs = arguments; } + testFunction('foo', 'bar'); - expect(jasmineUnderTest.matchersUtil.contains(capturedArgs, 'bar')).toBe(true); + expect(matchersUtil.contains(capturedArgs, 'bar')).toBe(true); }); it("passes for set members", function() { jasmine.getEnv().requireFunctioningSets(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var setItem = {'foo': 'bar'}; var set = new Set(); set.add(setItem); - expect(jasmineUnderTest.matchersUtil.contains(set, setItem)).toBe(true); + expect(matchersUtil.contains(set, setItem)).toBe(true); }); // documenting current behavior it("fails (!) for objects that equal to a set member", function() { jasmine.getEnv().requireFunctioningSets(); + var matchersUtil = new jasmineUnderTest.MatchersUtil(); var set = new Set(); set.add({'foo': 'bar'}); - expect(jasmineUnderTest.matchersUtil.contains(set, {'foo': 'bar'})).toBe(false); + expect(matchersUtil.contains(set, {'foo': 'bar'})).toBe(false); }); }); @@ -666,7 +838,8 @@ describe("matchersUtil", function() { it("builds an English sentence for a failure case", function() { var actual = "foo", name = "toBar", - message = jasmineUnderTest.matchersUtil.buildFailureMessage(name, false, actual); + matchersUtil = new jasmineUnderTest.MatchersUtil(), + message = matchersUtil.buildFailureMessage(name, false, actual); expect(message).toEqual("Expected 'foo' to bar."); }); @@ -675,7 +848,8 @@ describe("matchersUtil", function() { var actual = "foo", name = "toBar", isNot = true, - message = message = jasmineUnderTest.matchersUtil.buildFailureMessage(name, isNot, actual); + matchersUtil = new jasmineUnderTest.MatchersUtil(), + message = message = matchersUtil.buildFailureMessage(name, isNot, actual); expect(message).toEqual("Expected 'foo' not to bar."); }); @@ -683,7 +857,8 @@ describe("matchersUtil", function() { it("builds an English sentence for an arbitrary array of expected arguments", function() { var actual = "foo", name = "toBar", - message = jasmineUnderTest.matchersUtil.buildFailureMessage(name, false, actual, "quux", "corge"); + matchersUtil = new jasmineUnderTest.MatchersUtil(), + message = matchersUtil.buildFailureMessage(name, false, actual, "quux", "corge"); expect(message).toEqual("Expected 'foo' to bar 'quux', 'corge'."); }); diff --git a/spec/core/matchers/toBeSpec.js b/spec/core/matchers/toBeSpec.js index e065af57..8e27b992 100644 --- a/spec/core/matchers/toBeSpec.js +++ b/spec/core/matchers/toBeSpec.js @@ -1,6 +1,7 @@ describe("toBe", function() { it("passes with no message when actual === expected", function() { - var matcher = jasmineUnderTest.matchers.toBe(jasmineUnderTest.matchersUtil), + var util = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.matchers.toBe(util), result; result = matcher.compare(1, 1); @@ -8,7 +9,8 @@ describe("toBe", function() { }); it("passes with a custom message when expected is an array", function() { - var matcher = jasmineUnderTest.matchers.toBe(jasmineUnderTest.matchersUtil), + var util = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.matchers.toBe(util), result, array = [1]; @@ -18,7 +20,8 @@ describe("toBe", function() { }); it("passes with a custom message when expected is an object", function() { - var matcher = jasmineUnderTest.matchers.toBe(jasmineUnderTest.matchersUtil), + var util = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.matchers.toBe(util), result, obj = {foo: "bar"}; @@ -28,7 +31,8 @@ describe("toBe", function() { }); it("fails with no message when actual !== expected", function() { - var matcher = jasmineUnderTest.matchers.toBe(jasmineUnderTest.matchersUtil), + var util = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.matchers.toBe(util), result; result = matcher.compare(1, 2); @@ -37,7 +41,8 @@ describe("toBe", function() { }); it("fails with a custom message when expected is an array", function() { - var matcher = jasmineUnderTest.matchers.toBe(jasmineUnderTest.matchersUtil), + var util = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.matchers.toBe(util), result; result = matcher.compare([1], [1]); @@ -46,7 +51,8 @@ describe("toBe", function() { }); it("fails with a custom message when expected is an object", function() { - var matcher = jasmineUnderTest.matchers.toBe(jasmineUnderTest.matchersUtil), + var util = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.matchers.toBe(util), result; result = matcher.compare({foo: "bar"}, {foo: "bar"}); diff --git a/spec/core/matchers/toContainSpec.js b/spec/core/matchers/toContainSpec.js index a56d05e4..effe5862 100644 --- a/spec/core/matchers/toContainSpec.js +++ b/spec/core/matchers/toContainSpec.js @@ -7,20 +7,19 @@ describe("toContain", function() { result; result = matcher.compare("ABC", "B"); - expect(util.contains).toHaveBeenCalledWith("ABC", "B", []); + expect(util.contains).toHaveBeenCalledWith("ABC", "B"); expect(result.pass).toBe(true); }); - it("delegates to jasmineUnderTest.matchersUtil.contains, passing in equality testers if present", function() { - var util = { - contains: jasmine.createSpy('delegated-contains').and.returnValue(true) + it("works with custom equality testers", function() { + var tester = function (a, b) { + return a.toString() === b.toString(); }, - customEqualityTesters = ['a', 'b'], - matcher = jasmineUnderTest.matchers.toContain(util, customEqualityTesters), + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}), + matcher = jasmineUnderTest.matchers.toContain(matchersUtil), result; - result = matcher.compare("ABC", "B"); - expect(util.contains).toHaveBeenCalledWith("ABC", "B", ['a', 'b']); + result = matcher.compare(['1', '2'], 2); expect(result.pass).toBe(true); }); }); diff --git a/spec/core/matchers/toEqualSpec.js b/spec/core/matchers/toEqualSpec.js index 345eb724..2bd2f077 100644 --- a/spec/core/matchers/toEqualSpec.js +++ b/spec/core/matchers/toEqualSpec.js @@ -2,7 +2,7 @@ describe("toEqual", function() { "use strict"; function compareEquals(actual, expected) { - var util = jasmineUnderTest.matchersUtil, + var util = new jasmineUnderTest.MatchersUtil(), matcher = jasmineUnderTest.matchers.toEqual(util); var result = matcher.compare(actual, expected); @@ -16,32 +16,27 @@ describe("toEqual", function() { buildFailureMessage: function() { return 'does not matter' }, - DiffBuilder: jasmineUnderTest.matchersUtil.DiffBuilder + DiffBuilder: new jasmineUnderTest.DiffBuilder() }, matcher = jasmineUnderTest.matchers.toEqual(util), result; result = matcher.compare(1, 1); - expect(util.equals).toHaveBeenCalledWith(1, 1, [], jasmine.anything()); + expect(util.equals).toHaveBeenCalledWith(1, 1, jasmine.anything()); expect(result.pass).toBe(true); }); - it("delegates custom equality testers, if present", function() { - var util = { - equals: jasmine.createSpy('delegated-equals').and.returnValue(true), - buildFailureMessage: function() { - return 'does not matter' - }, - DiffBuilder: jasmineUnderTest.matchersUtil.DiffBuilder + it("works with custom equality testers", function() { + var tester = function (a, b) { + return a.toString() === b.toString(); }, - customEqualityTesters = ['a', 'b'], - matcher = jasmineUnderTest.matchers.toEqual(util, customEqualityTesters), + util = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}), + matcher = jasmineUnderTest.matchers.toEqual(util), result; - result = matcher.compare(1, 1); + result = matcher.compare(1, '1'); - expect(util.equals).toHaveBeenCalledWith(1, 1, ['a', 'b'], jasmine.anything()); expect(result.pass).toBe(true); }); diff --git a/spec/core/matchers/toHaveBeenCalledWithSpec.js b/spec/core/matchers/toHaveBeenCalledWithSpec.js index 4ac7e074..a57bc4a4 100644 --- a/spec/core/matchers/toHaveBeenCalledWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledWithSpec.js @@ -15,18 +15,16 @@ describe("toHaveBeenCalledWith", function() { expect(result.message()).toEqual("Expected spy called-spy not to have been called with:\n [ 'a', 'b' ]\nbut it was."); }); - it("passes through the custom equality testers", function() { - var util = { - contains: jasmine.createSpy('delegated-contains').and.returnValue(true) - }, - customEqualityTesters = [function() { return true; }], - matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util, customEqualityTesters), - calledSpy = new jasmineUnderTest.Env().createSpy('called-spy'); + it("supports custom equality testers", function() { + var customEqualityTesters = [function() { return true; }], + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: customEqualityTesters}), + matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(matchersUtil), + calledSpy = new jasmineUnderTest.Env().createSpy('called-spy'), + result; calledSpy('a', 'b'); - matcher.compare(calledSpy, 'a', 'b'); - - expect(util.contains).toHaveBeenCalledWith([['a', 'b']], ['a', 'b'], customEqualityTesters); + result = matcher.compare(calledSpy, 'a', 'b'); + expect(result.pass).toBe(true); }); it("fails when the actual was not called", function() { @@ -43,7 +41,7 @@ describe("toHaveBeenCalledWith", function() { }); it("fails when the actual was called with different parameters", function() { - var util = jasmineUnderTest.matchersUtil, + var util = new jasmineUnderTest.MatchersUtil(), matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util), calledSpy = new jasmineUnderTest.Env().createSpy('called spy'), result; diff --git a/spec/helpers/integrationMatchers.js b/spec/helpers/integrationMatchers.js index 694ccd6e..f473385c 100644 --- a/spec/helpers/integrationMatchers.js +++ b/spec/helpers/integrationMatchers.js @@ -1,10 +1,7 @@ (function(env) { env.registerIntegrationMatchers = function() { jasmine.addMatchers({ - toHaveFailedExpectationsForRunnable: function( - util, - customeEqualityTesters - ) { + toHaveFailedExpectationsForRunnable: function(util) { return { compare: function(actual, fullName, expectedFailures) { var foundRunnable = false, diff --git a/spec/npmPackage/npmPackageSpec.js b/spec/npmPackage/npmPackageSpec.js index 5248d88c..908b1c06 100644 --- a/spec/npmPackage/npmPackageSpec.js +++ b/spec/npmPackage/npmPackageSpec.js @@ -23,7 +23,7 @@ describe('npm package', function() { beforeEach(function() { jasmine.addMatchers({ - toExistInPath: function(util, customEquality) { + toExistInPath: function(util) { return { compare: function(actual, expected) { var fullPath = path.resolve(expected, actual); diff --git a/src/core/Env.js b/src/core/Env.js index 7d6a1210..e3c5f5c6 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -276,6 +276,7 @@ getJasmineRequireObj().Env = function(j$) { } var customMatchers = runnableResources[currentRunnable().id].customMatchers; + for (var matcherName in matchersToAdd) { customMatchers[matcherName] = matchersToAdd[matcherName]; } @@ -289,6 +290,7 @@ getJasmineRequireObj().Env = function(j$) { } var customAsyncMatchers = runnableResources[currentRunnable().id].customAsyncMatchers; + for (var matcherName in matchersToAdd) { customAsyncMatchers[matcherName] = matchersToAdd[matcherName]; } @@ -308,9 +310,12 @@ getJasmineRequireObj().Env = function(j$) { }; var expectationFactory = function(actual, spec) { + var customEqualityTesters = + runnableResources[spec.id].customEqualityTesters; + return j$.Expectation.factory({ - util: j$.matchersUtil, - customEqualityTesters: runnableResources[spec.id].customEqualityTesters, + util: new j$.MatchersUtil({ customTesters: customEqualityTesters }), + customEqualityTesters: customEqualityTesters, customMatchers: runnableResources[spec.id].customMatchers, actual: actual, addExpectationResult: addExpectationResult @@ -322,8 +327,11 @@ getJasmineRequireObj().Env = function(j$) { }; var asyncExpectationFactory = function(actual, spec) { + var customEqualityTesters = + runnableResources[spec.id].customEqualityTesters; + return j$.Expectation.asyncFactory({ - util: j$.matchersUtil, + util: new j$.MatchersUtil({ customTesters: customEqualityTesters }), customEqualityTesters: runnableResources[spec.id].customEqualityTesters, customAsyncMatchers: runnableResources[spec.id].customAsyncMatchers, actual: actual, diff --git a/src/core/Spy.js b/src/core/Spy.js index ffbb0103..3d4aca21 100644 --- a/src/core/Spy.js +++ b/src/core/Spy.js @@ -7,6 +7,8 @@ getJasmineRequireObj().Spy = function(j$) { }; })(); + var matchersUtil = new j$.MatchersUtil(); + /** * _Note:_ Do not construct this directly, use {@link spyOn}, {@link spyOnProperty}, {@link jasmine.createSpy}, or {@link jasmine.createSpyObj} * @constructor @@ -202,7 +204,7 @@ getJasmineRequireObj().Spy = function(j$) { var i; for (i = 0; i < this.strategies.length; i++) { - if (j$.matchersUtil.equals(args, this.strategies[i].args)) { + if (matchersUtil.equals(args, this.strategies[i].args)) { return this.strategies[i].strategy; } } diff --git a/src/core/asymmetricEqualityTesterArgCompatShim.js b/src/core/asymmetricEqualityTesterArgCompatShim.js new file mode 100644 index 00000000..faa4bf79 --- /dev/null +++ b/src/core/asymmetricEqualityTesterArgCompatShim.js @@ -0,0 +1,105 @@ +getJasmineRequireObj().asymmetricEqualityTesterArgCompatShim = function(j$) { + /* + Older versions of Jasmine passed an array of custom equality testers as the + second argument to each asymmetric equality tester's `asymmetricMatch` + method. Newer versions will pass a `MatchersUtil` instance. The + asymmetricEqualityTesterArgCompatShim allows for a graceful migration from + the old interface to the new by "being" both an array of custom equality + testers and a `MatchersUtil` at the same time. + + This code should be removed in the next major release. + */ + + var likelyArrayProps = [ + 'concat', + 'constructor', + 'copyWithin', + 'entries', + 'every', + 'fill', + 'filter', + 'find', + 'findIndex', + 'flat', + 'flatMap', + 'forEach', + 'includes', + 'indexOf', + 'join', + 'keys', + 'lastIndexOf', + 'length', + 'map', + 'pop', + 'push', + 'reduce', + 'reduceRight', + 'reverse', + 'shift', + 'slice', + 'some', + 'sort', + 'splice', + 'toLocaleString', + 'toSource', + 'toString', + 'unshift', + 'values' + ]; + + function asymmetricEqualityTesterArgCompatShim( + matchersUtil, + customEqualityTesters + ) { + var self = Object.create(matchersUtil), + props, + i, + k; + + copy(self, customEqualityTesters, 'length'); + + for (i = 0; i < customEqualityTesters.length; i++) { + copy(self, customEqualityTesters, i); + } + + var props = arrayProps(); + + for (i = 0; i < props.length; i++) { + k = props[i]; + if (k !== 'length') { + copy(self, Array.prototype, k); + } + } + + return self; + } + + function copy(dest, src, propName) { + Object.defineProperty(dest, propName, { + get: function() { + return src[propName]; + } + }); + } + + function arrayProps() { + var props, a, k; + + if (!Object.getOwnPropertyDescriptors) { + return likelyArrayProps.filter(function(k) { + return Array.prototype.hasOwnProperty(k); + }); + } + + props = Object.getOwnPropertyDescriptors(Array.prototype); + a = []; + + for (k in props) { + a.push(k); + } + + return a; + } + + return asymmetricEqualityTesterArgCompatShim; +}; diff --git a/src/core/asymmetric_equality/ArrayContaining.js b/src/core/asymmetric_equality/ArrayContaining.js index 92a85ed0..95c9f3f1 100644 --- a/src/core/asymmetric_equality/ArrayContaining.js +++ b/src/core/asymmetric_equality/ArrayContaining.js @@ -3,7 +3,7 @@ getJasmineRequireObj().ArrayContaining = function(j$) { this.sample = sample; } - ArrayContaining.prototype.asymmetricMatch = function(other, customTesters) { + ArrayContaining.prototype.asymmetricMatch = function(other, matchersUtil) { if (!j$.isArray_(this.sample)) { throw new Error('You must provide an array to arrayContaining, not ' + j$.pp(this.sample) + '.'); } @@ -17,7 +17,7 @@ getJasmineRequireObj().ArrayContaining = function(j$) { for (var i = 0; i < this.sample.length; i++) { var item = this.sample[i]; - if (!j$.matchersUtil.contains(other, item, customTesters)) { + if (!matchersUtil.contains(other, item)) { return false; } } diff --git a/src/core/asymmetric_equality/ArrayWithExactContents.js b/src/core/asymmetric_equality/ArrayWithExactContents.js index 37b8ee95..9bdba8d4 100644 --- a/src/core/asymmetric_equality/ArrayWithExactContents.js +++ b/src/core/asymmetric_equality/ArrayWithExactContents.js @@ -4,7 +4,7 @@ getJasmineRequireObj().ArrayWithExactContents = function(j$) { this.sample = sample; } - ArrayWithExactContents.prototype.asymmetricMatch = function(other, customTesters) { + ArrayWithExactContents.prototype.asymmetricMatch = function(other, matchersUtil) { if (!j$.isArray_(this.sample)) { throw new Error('You must provide an array to arrayWithExactContents, not ' + j$.pp(this.sample) + '.'); } @@ -15,7 +15,7 @@ getJasmineRequireObj().ArrayWithExactContents = function(j$) { for (var i = 0; i < this.sample.length; i++) { var item = this.sample[i]; - if (!j$.matchersUtil.contains(other, item, customTesters)) { + if (!matchersUtil.contains(other, item)) { return false; } } diff --git a/src/core/asymmetric_equality/MapContaining.js b/src/core/asymmetric_equality/MapContaining.js index 061c2666..7c8e3c5b 100644 --- a/src/core/asymmetric_equality/MapContaining.js +++ b/src/core/asymmetric_equality/MapContaining.js @@ -7,7 +7,7 @@ getJasmineRequireObj().MapContaining = function(j$) { this.sample = sample; } - MapContaining.prototype.asymmetricMatch = function(other, customTesters) { + MapContaining.prototype.asymmetricMatch = function(other, matchersUtil) { if (!j$.isMap(other)) return false; var hasAllMatches = true; @@ -17,8 +17,8 @@ getJasmineRequireObj().MapContaining = function(j$) { var hasMatch = false; j$.util.forEachBreakable(other, function(oBreakLoop, oValue, oKey) { if ( - j$.matchersUtil.equals(oKey, key, customTesters) - && j$.matchersUtil.equals(oValue, value, customTesters) + matchersUtil.equals(oKey, key) + && matchersUtil.equals(oValue, value) ) { hasMatch = true; oBreakLoop(); diff --git a/src/core/asymmetric_equality/ObjectContaining.js b/src/core/asymmetric_equality/ObjectContaining.js index 62e9bf17..93069b25 100644 --- a/src/core/asymmetric_equality/ObjectContaining.js +++ b/src/core/asymmetric_equality/ObjectContaining.js @@ -28,12 +28,12 @@ getJasmineRequireObj().ObjectContaining = function(j$) { return hasProperty(getPrototype(obj), property); } - ObjectContaining.prototype.asymmetricMatch = function(other, customTesters) { + ObjectContaining.prototype.asymmetricMatch = function(other, matchersUtil) { if (typeof(this.sample) !== 'object') { throw new Error('You must provide an object to objectContaining, not \''+this.sample+'\'.'); } for (var property in this.sample) { if (!hasProperty(other, property) || - !j$.matchersUtil.equals(this.sample[property], other[property], customTesters)) { + !matchersUtil.equals(this.sample[property], other[property])) { return false; } } diff --git a/src/core/asymmetric_equality/SetContaining.js b/src/core/asymmetric_equality/SetContaining.js index d9dd8fd2..00627935 100644 --- a/src/core/asymmetric_equality/SetContaining.js +++ b/src/core/asymmetric_equality/SetContaining.js @@ -7,17 +7,17 @@ getJasmineRequireObj().SetContaining = function(j$) { this.sample = sample; } - SetContaining.prototype.asymmetricMatch = function(other, customTesters) { + SetContaining.prototype.asymmetricMatch = function(other, matchersUtil) { if (!j$.isSet(other)) return false; var hasAllMatches = true; j$.util.forEachBreakable(this.sample, function(breakLoop, item) { // for each item in `sample` there should be at least one matching item in `other` - // (not using `j$.matchersUtil.contains` because it compares set members by reference, + // (not using `matchersUtil.contains` because it compares set members by reference, // not by deep value equality) var hasMatch = false; j$.util.forEachBreakable(other, function(oBreakLoop, oItem) { - if (j$.matchersUtil.equals(oItem, item, customTesters)) { + if (matchersUtil.equals(oItem, item)) { hasMatch = true; oBreakLoop(); } diff --git a/src/core/matchers/async/toBeRejectedWith.js b/src/core/matchers/async/toBeRejectedWith.js index 031230a1..621daf0b 100644 --- a/src/core/matchers/async/toBeRejectedWith.js +++ b/src/core/matchers/async/toBeRejectedWith.js @@ -11,7 +11,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { * @example * return expectAsync(aPromise).toBeRejectedWith({prop: 'value'}); */ - return function toBeRejectedWith(util, customEqualityTesters) { + return function toBeRejectedWith(util) { return { compare: function(actualPromise, expectedValue) { if (!j$.isPromiseLike(actualPromise)) { @@ -32,7 +32,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { }; }, function(actualValue) { - if (util.equals(actualValue, expectedValue, customEqualityTesters)) { + if (util.equals(actualValue, expectedValue)) { return { pass: true, message: prefix(true) + '.' diff --git a/src/core/matchers/async/toBeResolvedTo.js b/src/core/matchers/async/toBeResolvedTo.js index 9d5aa370..a0295c8a 100644 --- a/src/core/matchers/async/toBeResolvedTo.js +++ b/src/core/matchers/async/toBeResolvedTo.js @@ -11,7 +11,7 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { * @example * return expectAsync(aPromise).toBeResolvedTo({prop: 'value'}); */ - return function toBeResolvedTo(util, customEqualityTesters) { + return function toBeResolvedTo(util) { return { compare: function(actualPromise, expectedValue) { if (!j$.isPromiseLike(actualPromise)) { @@ -26,7 +26,7 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { return actualPromise.then( function(actualValue) { - if (util.equals(actualValue, expectedValue, customEqualityTesters)) { + if (util.equals(actualValue, expectedValue)) { return { pass: true, message: prefix(true) + '.' diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index cfc0c749..1aa496f4 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -1,63 +1,67 @@ -getJasmineRequireObj().matchersUtil = function(j$) { +getJasmineRequireObj().MatchersUtil = function(j$) { // TODO: what to do about jasmine.pp not being inject? move to JSON.stringify? gut PrettyPrinter? - return { - equals: equals, + function MatchersUtil(options) { + options = options || {}; + this.customTesters_ = options.customTesters || []; - contains: function(haystack, needle, customTesters) { - customTesters = customTesters || []; - - if (j$.isSet(haystack)) { - return haystack.has(needle); - } - - if ((Object.prototype.toString.apply(haystack) === '[object Array]') || - (!!haystack && !haystack.indexOf)) - { - for (var i = 0; i < haystack.length; i++) { - if (equals(haystack[i], needle, customTesters)) { - return true; - } - } - return false; - } - - return !!haystack && haystack.indexOf(needle) >= 0; - }, - - buildFailureMessage: function() { - var args = Array.prototype.slice.call(arguments, 0), - matcherName = args[0], - isNot = args[1], - actual = args[2], - expected = args.slice(3), - englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { return ' ' + s.toLowerCase(); }); - - var message = 'Expected ' + - j$.pp(actual) + - (isNot ? ' not ' : ' ') + - englishyPredicate; - - if (expected.length > 0) { - for (var i = 0; i < expected.length; i++) { - if (i > 0) { - message += ','; - } - message += ' ' + j$.pp(expected[i]); - } - } - - return message + '.'; + if (!j$.isArray_(this.customTesters_)) { + throw new Error("MatchersUtil requires custom equality testers"); } + } + + MatchersUtil.prototype.contains = function(haystack, needle, customTesters) { + if (j$.isSet(haystack)) { + return haystack.has(needle); + } + + if ((Object.prototype.toString.apply(haystack) === '[object Array]') || + (!!haystack && !haystack.indexOf)) + { + for (var i = 0; i < haystack.length; i++) { + if (this.equals(haystack[i], needle, customTesters)) { + return true; + } + } + return false; + } + + return !!haystack && haystack.indexOf(needle) >= 0; + }; + + MatchersUtil.prototype.buildFailureMessage = function() { + var args = Array.prototype.slice.call(arguments, 0), + matcherName = args[0], + isNot = args[1], + actual = args[2], + expected = args.slice(3), + englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { return ' ' + s.toLowerCase(); }); + + var message = 'Expected ' + + j$.pp(actual) + + (isNot ? ' not ' : ' ') + + englishyPredicate; + + if (expected.length > 0) { + for (var i = 0; i < expected.length; i++) { + if (i > 0) { + message += ','; + } + message += ' ' + j$.pp(expected[i]); + } + } + + return message + '.'; }; function isAsymmetric(obj) { return obj && j$.isA_('Function', obj.asymmetricMatch); } - function asymmetricMatch(a, b, customTesters, diffBuilder) { + MatchersUtil.prototype.asymmetricMatch_ = function(a, b, customTesters, diffBuilder) { var asymmetricA = isAsymmetric(a), asymmetricB = isAsymmetric(b), + shim = j$.asymmetricEqualityTesterArgCompatShim(this, customTesters), result; if (asymmetricA && asymmetricB) { @@ -65,7 +69,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { } if (asymmetricA) { - result = a.asymmetricMatch(b, customTesters); + result = a.asymmetricMatch(b, shim); if (!result) { diffBuilder.record(a, b); } @@ -73,27 +77,36 @@ getJasmineRequireObj().matchersUtil = function(j$) { } if (asymmetricB) { - result = b.asymmetricMatch(a, customTesters); + result = b.asymmetricMatch(a, shim); if (!result) { diffBuilder.record(a, b); } return result; } - } + }; - function equals(a, b, customTesters, diffBuilder) { - customTesters = customTesters || []; + MatchersUtil.prototype.equals = function(a, b, customTestersOrDiffBuilder, diffBuilderOrNothing) { + var customTesters, diffBuilder; + + if (isDiffBuilder(customTestersOrDiffBuilder)) { + diffBuilder = customTestersOrDiffBuilder; + } else { + customTesters = customTestersOrDiffBuilder; + diffBuilder = diffBuilderOrNothing; + } + + customTesters = customTesters || this.customTesters_; diffBuilder = diffBuilder || j$.NullDiffBuilder(); - return eq(a, b, [], [], customTesters, diffBuilder); - } + return this.eq_(a, b, [], [], customTesters, diffBuilder); + }; // Equality function lovingly adapted from isEqual in // [Underscore](http://underscorejs.org) - function eq(a, b, aStack, bStack, customTesters, diffBuilder) { - var result = true, i; + MatchersUtil.prototype.eq_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { + var result = true, self = this, i; - var asymmetricResult = asymmetricMatch(a, b, customTesters, diffBuilder); + var asymmetricResult = this.asymmetricMatch_(a, b, customTesters, diffBuilder); if (!j$.util.isUndefined(asymmetricResult)) { return asymmetricResult; } @@ -230,7 +243,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { diffBuilder.record(a[i], void 0, actualArrayIsLongerFormatter); result = false; } else { - result = eq(i < aLength ? a[i] : void 0, i < bLength ? b[i] : void 0, aStack, bStack, customTesters, diffBuilder) && result; + result = self.eq_(i < aLength ? a[i] : void 0, i < bLength ? b[i] : void 0, aStack, bStack, customTesters, diffBuilder) && result; } }); } @@ -271,12 +284,12 @@ getJasmineRequireObj().matchersUtil = function(j$) { // otherwise explicitly look up the mapKey in the other Map since we want keys with unique // obj identity (that are otherwise equal) to not match. if (isAsymmetric(mapKey) || isAsymmetric(cmpKey) && - eq(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { + this.eq_(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { mapValueB = b.get(cmpKey); } else { mapValueB = b.get(mapKey); } - result = eq(mapValueA, mapValueB, aStack, bStack, customTesters, j$.NullDiffBuilder()); + result = this.eq_(mapValueA, mapValueB, aStack, bStack, customTesters, j$.NullDiffBuilder()); } } @@ -320,7 +333,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { otherValue = otherValues[l]; prevStackSize = baseStack.length; // compare by value equality - found = eq(baseValue, otherValue, baseStack, otherStack, customTesters, j$.NullDiffBuilder()); + found = this.eq_(baseValue, otherValue, baseStack, otherStack, customTesters, j$.NullDiffBuilder()); if (!found && prevStackSize !== baseStack.length) { baseStack.splice(prevStackSize); otherStack.splice(prevStackSize); @@ -369,7 +382,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { } diffBuilder.withPath(key, function() { - if(!eq(a[key], b[key], aStack, bStack, customTesters, diffBuilder)) { + if(!self.eq_(a[key], b[key], aStack, bStack, customTesters, diffBuilder)) { result = false; } }); @@ -384,7 +397,7 @@ getJasmineRequireObj().matchersUtil = function(j$) { bStack.pop(); return result; - } + }; function keys(obj, isArray) { var allKeys = Object.keys ? Object.keys(obj) : @@ -467,4 +480,10 @@ getJasmineRequireObj().matchersUtil = function(j$) { } return formatted; } + + function isDiffBuilder(obj) { + return obj && typeof obj.record === 'function'; + } + + return MatchersUtil; }; diff --git a/src/core/matchers/toBeInstanceOf.js b/src/core/matchers/toBeInstanceOf.js index 66b658c1..cc0a0679 100644 --- a/src/core/matchers/toBeInstanceOf.js +++ b/src/core/matchers/toBeInstanceOf.js @@ -12,7 +12,7 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { * expect(3).toBeInstanceOf(Number); * expect(new Error()).toBeInstanceOf(Error); */ - function toBeInstanceOf(util, customEqualityTesters) { + function toBeInstanceOf() { return { compare: function(actual, expected) { var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : j$.pp(actual), diff --git a/src/core/matchers/toContain.js b/src/core/matchers/toContain.js index 440bb4c4..cf511604 100644 --- a/src/core/matchers/toContain.js +++ b/src/core/matchers/toContain.js @@ -9,14 +9,12 @@ getJasmineRequireObj().toContain = function() { * expect(array).toContain(anElement); * expect(string).toContain(substring); */ - function toContain(util, customEqualityTesters) { - customEqualityTesters = customEqualityTesters || []; - + function toContain(util) { return { compare: function(actual, expected) { return { - pass: util.contains(actual, expected, customEqualityTesters) + pass: util.contains(actual, expected) }; } }; diff --git a/src/core/matchers/toEqual.js b/src/core/matchers/toEqual.js index 8697ed67..d78bde4c 100644 --- a/src/core/matchers/toEqual.js +++ b/src/core/matchers/toEqual.js @@ -8,9 +8,7 @@ getJasmineRequireObj().toEqual = function(j$) { * @example * expect(bigObject).toEqual({"foo": ['bar', 'baz']}); */ - function toEqual(util, customEqualityTesters) { - customEqualityTesters = customEqualityTesters || []; - + function toEqual(util) { return { compare: function(actual, expected) { var result = { @@ -18,7 +16,7 @@ getJasmineRequireObj().toEqual = function(j$) { }, diffBuilder = j$.DiffBuilder(); - result.pass = util.equals(actual, expected, customEqualityTesters, diffBuilder); + result.pass = util.equals(actual, expected, diffBuilder); // TODO: only set error message if test fails result.message = diffBuilder.getMessage(); diff --git a/src/core/matchers/toHaveBeenCalledWith.js b/src/core/matchers/toHaveBeenCalledWith.js index 277b33f3..9edde713 100644 --- a/src/core/matchers/toHaveBeenCalledWith.js +++ b/src/core/matchers/toHaveBeenCalledWith.js @@ -11,7 +11,7 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { * @example * expect(mySpy).toHaveBeenCalledWith('foo', 'bar', 2); */ - function toHaveBeenCalledWith(util, customEqualityTesters) { + function toHaveBeenCalledWith(util) { return { compare: function() { var args = Array.prototype.slice.call(arguments, 0), @@ -32,7 +32,7 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { return result; } - if (util.contains(actual.calls.allArgs(), expectedArgs, customEqualityTesters)) { + if (util.contains(actual.calls.allArgs(), expectedArgs)) { result.pass = true; result.message = function() { return 'Expected spy ' + actual.and.identity + ' not to have been called with:\n' + @@ -47,7 +47,7 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { var diffs = actual.calls.allArgs().map(function(argsForCall, callIx) { var diffBuilder = new j$.DiffBuilder(); - util.equals(argsForCall, expectedArgs, customEqualityTesters, diffBuilder); + util.equals(argsForCall, expectedArgs, diffBuilder); return 'Call ' + callIx + ':\n' + diffBuilder.getMessage().replace(/^/mg, ' '); }); diff --git a/src/core/matchers/toHaveClass.js b/src/core/matchers/toHaveClass.js index a2fd7507..32dc2ccf 100644 --- a/src/core/matchers/toHaveClass.js +++ b/src/core/matchers/toHaveClass.js @@ -10,7 +10,7 @@ getJasmineRequireObj().toHaveClass = function(j$) { * el.className = 'foo bar baz'; * expect(el).toHaveClass('bar'); */ - function toHaveClass(util, customEqualityTesters) { + function toHaveClass() { return { compare: function(actual, expected) { if (!isElement(actual)) { diff --git a/src/core/requireCore.js b/src/core/requireCore.js index a2c5f177..0d5b76ed 100644 --- a/src/core/requireCore.js +++ b/src/core/requireCore.js @@ -51,7 +51,12 @@ var getJasmineRequireObj = (function(jasmineGlobal) { j$.buildExpectationResult = jRequire.buildExpectationResult(); j$.noopTimer = jRequire.noopTimer(); j$.JsApiReporter = jRequire.JsApiReporter(j$); - j$.matchersUtil = jRequire.matchersUtil(j$); + j$.asymmetricEqualityTesterArgCompatShim = jRequire.asymmetricEqualityTesterArgCompatShim( + j$ + ); + j$.MatchersUtil = jRequire.MatchersUtil(j$); + j$.matchersUtil = new j$.MatchersUtil({ customTesters: [] }); + j$.ObjectContaining = jRequire.ObjectContaining(j$); j$.ArrayContaining = jRequire.ArrayContaining(j$); j$.ArrayWithExactContents = jRequire.ArrayWithExactContents(j$); From 1f23f1e4d2f4f6b45b374aa7311a8673f78e9ccd Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 8 Oct 2019 22:57:07 -0700 Subject: [PATCH 119/201] Inject a per-runable pretty printer into MatchersUtil This will allow us to add support for custom object formatters, which will be a per-runable resource like custom matchers, by injecting them into the pretty-printer. --- lib/jasmine-core/jasmine.js | 240 ++++++++++-------- spec/core/AsyncExpectationSpec.js | 15 +- spec/core/EnvSpec.js | 10 +- spec/core/ExpectationSpec.js | 3 +- spec/core/PrettyPrintSpec.js | 186 +++++++------- .../async/toBeRejectedWithErrorSpec.js | 24 +- .../matchers/async/toBeRejectedWithSpec.js | 6 +- .../core/matchers/async/toBeResolvedToSpec.js | 13 +- spec/core/matchers/matchersUtilSpec.js | 41 ++- spec/core/matchers/toBeInstanceOfSpec.js | 12 +- spec/core/matchers/toBeNaNSpec.js | 4 +- .../core/matchers/toBeNegativeInfinitySpec.js | 4 +- .../core/matchers/toBePositiveInfinitySpec.js | 4 +- spec/core/matchers/toBeSpec.js | 8 +- spec/core/matchers/toEqualSpec.js | 6 +- .../matchers/toHaveBeenCalledBeforeSpec.js | 8 +- spec/core/matchers/toHaveBeenCalledSpec.js | 4 +- .../matchers/toHaveBeenCalledTimesSpec.js | 4 +- .../core/matchers/toHaveBeenCalledWithSpec.js | 15 +- spec/core/matchers/toHaveClassSpec.js | 4 +- spec/core/matchers/toThrowErrorSpec.js | 49 ++-- spec/core/matchers/toThrowMatchingSpec.js | 10 +- spec/core/matchers/toThrowSpec.js | 16 +- spec/html/PrettyPrintHtmlSpec.js | 21 +- src/core/Env.js | 22 +- src/core/Expectation.js | 2 +- src/core/Expector.js | 2 +- src/core/PrettyPrinter.js | 43 ++-- src/core/Spy.js | 5 +- src/core/matchers/async/toBeRejectedWith.js | 8 +- .../matchers/async/toBeRejectedWithError.js | 16 +- src/core/matchers/async/toBeResolvedTo.js | 8 +- src/core/matchers/matchersUtil.js | 38 ++- src/core/matchers/toBeInstanceOf.js | 6 +- src/core/matchers/toBeNaN.js | 4 +- src/core/matchers/toBeNegativeInfinity.js | 4 +- src/core/matchers/toBePositiveInfinity.js | 4 +- src/core/matchers/toHaveBeenCalled.js | 4 +- src/core/matchers/toHaveBeenCalledBefore.js | 6 +- src/core/matchers/toHaveBeenCalledTimes.js | 4 +- src/core/matchers/toHaveBeenCalledWith.js | 16 +- src/core/matchers/toHaveClass.js | 4 +- src/core/matchers/toThrow.js | 10 +- src/core/matchers/toThrowError.js | 10 +- src/core/matchers/toThrowMatching.js | 16 +- src/core/requireCore.js | 8 +- 46 files changed, 546 insertions(+), 401 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 555cb046..7c67caa3 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -76,15 +76,19 @@ var getJasmineRequireObj = (function(jasmineGlobal) { j$.asymmetricEqualityTesterArgCompatShim = jRequire.asymmetricEqualityTesterArgCompatShim( j$ ); + j$.makePrettyPrinter = jRequire.makePrettyPrinter(j$); + j$.pp = j$.makePrettyPrinter(); j$.MatchersUtil = jRequire.MatchersUtil(j$); - j$.matchersUtil = new j$.MatchersUtil({ customTesters: [] }); + j$.matchersUtil = new j$.MatchersUtil({ + customTesters: [], + pp: j$.pp + }); j$.ObjectContaining = jRequire.ObjectContaining(j$); j$.ArrayContaining = jRequire.ArrayContaining(j$); j$.ArrayWithExactContents = jRequire.ArrayWithExactContents(j$); j$.MapContaining = jRequire.MapContaining(j$); j$.SetContaining = jRequire.SetContaining(j$); - j$.pp = jRequire.pp(j$); j$.QueueRunner = jRequire.QueueRunner(j$); j$.ReportDispatcher = jRequire.ReportDispatcher(j$); j$.Spec = jRequire.Spec(j$); @@ -1226,12 +1230,25 @@ getJasmineRequireObj().Env = function(j$) { return 'suite' + nextSuiteId++; }; + var makePrettyPrinter = function() { + return j$.makePrettyPrinter(); + }; + + var makeMatchersUtil = function() { + var customEqualityTesters = + runnableResources[currentRunnable().id].customEqualityTesters; + return new j$.MatchersUtil({ + customTesters: customEqualityTesters, + pp: makePrettyPrinter() + }); + }; + var expectationFactory = function(actual, spec) { var customEqualityTesters = runnableResources[spec.id].customEqualityTesters; return j$.Expectation.factory({ - util: new j$.MatchersUtil({ customTesters: customEqualityTesters }), + util: makeMatchersUtil(), customEqualityTesters: customEqualityTesters, customMatchers: runnableResources[spec.id].customMatchers, actual: actual, @@ -1244,11 +1261,8 @@ getJasmineRequireObj().Env = function(j$) { }; var asyncExpectationFactory = function(actual, spec) { - var customEqualityTesters = - runnableResources[spec.id].customEqualityTesters; - return j$.Expectation.asyncFactory({ - util: new j$.MatchersUtil({ customTesters: customEqualityTesters }), + util: makeMatchersUtil(), customEqualityTesters: runnableResources[spec.id].customEqualityTesters, customAsyncMatchers: runnableResources[spec.id].customAsyncMatchers, actual: actual, @@ -2060,7 +2074,7 @@ getJasmineRequireObj().Env = function(j$) { message += error; } else { // pretty print all kind of objects. This includes arrays. - message += j$.pp(error); + message += makePrettyPrinter()(error); } } @@ -3543,7 +3557,7 @@ getJasmineRequireObj().Expectation = function(j$) { args = args.slice(); args.unshift(true); args.unshift(matcherName); - return util.buildFailureMessage.apply(null, args); + return util.buildFailureMessage.apply(util, args); } function negate(result) { @@ -3761,7 +3775,7 @@ getJasmineRequireObj().Expector = function(j$) { var args = self.args.slice(); args.unshift(false); args.unshift(self.matcherName); - return self.util.buildFailureMessage.apply(null, args); + return self.util.buildFailureMessage.apply(self.util, args); } else if (j$.isFunction_(result.message)) { return result.message(); } else { @@ -3941,7 +3955,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { * @example * return expectAsync(aPromise).toBeRejectedWith({prop: 'value'}); */ - return function toBeRejectedWith(util) { + return function toBeRejectedWith(matchersUtil) { return { compare: function(actualPromise, expectedValue) { if (!j$.isPromiseLike(actualPromise)) { @@ -3951,7 +3965,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { function prefix(passed) { return 'Expected a promise ' + (passed ? 'not ' : '') + - 'to be rejected with ' + j$.pp(expectedValue); + 'to be rejected with ' + matchersUtil.pp(expectedValue); } return actualPromise.then( @@ -3962,7 +3976,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { }; }, function(actualValue) { - if (util.equals(actualValue, expectedValue)) { + if (matchersUtil.equals(actualValue, expectedValue)) { return { pass: true, message: prefix(true) + '.' @@ -3970,7 +3984,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { } else { return { pass: false, - message: prefix(false) + ' but it was rejected with ' + j$.pp(actualValue) + '.' + message: prefix(false) + ' but it was rejected with ' + matchersUtil.pp(actualValue) + '.' }; } } @@ -3996,14 +4010,14 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { * await expectAsync(aPromise).toBeRejectedWithError('Error message'); * return expectAsync(aPromise).toBeRejectedWithError(/Error message/); */ - return function toBeRejectedWithError() { + return function toBeRejectedWithError(matchersUtil) { return { compare: function(actualPromise, arg1, arg2) { if (!j$.isPromiseLike(actualPromise)) { throw new Error('Expected toBeRejectedWithError to be called on a promise.'); } - var expected = getExpectedFromArgs(arg1, arg2); + var expected = getExpectedFromArgs(arg1, arg2, matchersUtil); return actualPromise.then( function() { @@ -4012,15 +4026,15 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { message: 'Expected a promise to be rejected but it was resolved.' }; }, - function(actualValue) { return matchError(actualValue, expected); } + function(actualValue) { return matchError(actualValue, expected, matchersUtil); } ); } }; }; - function matchError(actual, expected) { + function matchError(actual, expected, matchersUtil) { if (!j$.isError_(actual)) { - return fail(expected, 'rejected with ' + j$.pp(actual)); + return fail(expected, 'rejected with ' + matchersUtil.pp(actual)); } if (!(actual instanceof expected.error)) { @@ -4037,7 +4051,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return pass(expected); } - return fail(expected, 'rejected with ' + j$.pp(actual)); + return fail(expected, 'rejected with ' + matchersUtil.pp(actual)); } function pass(expected) { @@ -4055,7 +4069,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { } - function getExpectedFromArgs(arg1, arg2) { + function getExpectedFromArgs(arg1, arg2, matchersUtil) { var error, message; if (isErrorConstructor(arg1)) { @@ -4069,7 +4083,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return { error: error, message: message, - printValue: j$.fnNameFor(error) + (typeof message === 'undefined' ? '' : ': ' + j$.pp(message)) + printValue: j$.fnNameFor(error) + (typeof message === 'undefined' ? '' : ': ' + matchersUtil.pp(message)) }; } @@ -4119,7 +4133,7 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { * @example * return expectAsync(aPromise).toBeResolvedTo({prop: 'value'}); */ - return function toBeResolvedTo(util) { + return function toBeResolvedTo(matchersUtil) { return { compare: function(actualPromise, expectedValue) { if (!j$.isPromiseLike(actualPromise)) { @@ -4129,12 +4143,12 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { function prefix(passed) { return 'Expected a promise ' + (passed ? 'not ' : '') + - 'to be resolved to ' + j$.pp(expectedValue); + 'to be resolved to ' + matchersUtil.pp(expectedValue); } return actualPromise.then( function(actualValue) { - if (util.equals(actualValue, expectedValue)) { + if (matchersUtil.equals(actualValue, expectedValue)) { return { pass: true, message: prefix(true) + '.' @@ -4142,7 +4156,7 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { } else { return { pass: false, - message: prefix(false) + ' but it was resolved to ' + j$.pp(actualValue) + '.' + message: prefix(false) + ' but it was resolved to ' + matchersUtil.pp(actualValue) + '.' }; } }, @@ -4193,16 +4207,13 @@ getJasmineRequireObj().DiffBuilder = function(j$) { }; getJasmineRequireObj().MatchersUtil = function(j$) { - // TODO: what to do about jasmine.pp not being inject? move to JSON.stringify? gut PrettyPrinter? + // TODO: convert all uses of j$.pp to use the injected pp function MatchersUtil(options) { options = options || {}; this.customTesters_ = options.customTesters || []; - - if (!j$.isArray_(this.customTesters_)) { - throw new Error("MatchersUtil requires custom equality testers"); - } - } + this.pp = options.pp || function() {}; + }; MatchersUtil.prototype.contains = function(haystack, needle, customTesters) { if (j$.isSet(haystack)) { @@ -4224,6 +4235,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { }; MatchersUtil.prototype.buildFailureMessage = function() { + var self = this; var args = Array.prototype.slice.call(arguments, 0), matcherName = args[0], isNot = args[1], @@ -4232,7 +4244,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { return ' ' + s.toLowerCase(); }); var message = 'Expected ' + - j$.pp(actual) + + self.pp(actual) + (isNot ? ' not ' : ' ') + englishyPredicate; @@ -4434,7 +4446,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { for (i = 0; i < aLength || i < bLength; i++) { diffBuilder.withPath(i, function() { if (i >= bLength) { - diffBuilder.record(a[i], void 0, actualArrayIsLongerFormatter); + diffBuilder.record(a[i], void 0, actualArrayIsLongerFormatter.bind(null, self.pp)); result = false; } else { result = self.eq_(i < aLength ? a[i] : void 0, i < bLength ? b[i] : void 0, aStack, bStack, customTesters, diffBuilder) && result; @@ -4551,7 +4563,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { a instanceof aCtor && b instanceof bCtor && !(aCtor instanceof aCtor && bCtor instanceof bCtor)) { - diffBuilder.record(a, b, constructorsAreDifferentFormatter); + diffBuilder.record(a, b, constructorsAreDifferentFormatter.bind(null, this.pp)); return false; } } @@ -4562,7 +4574,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // Ensure that both objects contain the same number of properties before comparing deep equality. if (keys(b, className == '[object Array]').length !== size) { - diffBuilder.record(a, b, objectKeysAreDifferentFormatter); + diffBuilder.record(a, b, objectKeysAreDifferentFormatter.bind(null, this.pp)); return false; } @@ -4570,7 +4582,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { key = aKeys[i]; // Deep compare each member if (!j$.util.has(b, key)) { - diffBuilder.record(a, b, objectKeysAreDifferentFormatter); + diffBuilder.record(a, b, objectKeysAreDifferentFormatter.bind(null, this.pp)); result = false; continue; } @@ -4627,11 +4639,11 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return typeof obj === 'function'; } - function objectKeysAreDifferentFormatter(actual, expected, path) { + function objectKeysAreDifferentFormatter(pp, actual, expected, path) { var missingProperties = j$.util.objectDifference(expected, actual), extraProperties = j$.util.objectDifference(actual, expected), - missingPropertiesMessage = formatKeyValuePairs(missingProperties), - extraPropertiesMessage = formatKeyValuePairs(extraProperties), + missingPropertiesMessage = formatKeyValuePairs(pp, missingProperties), + extraPropertiesMessage = formatKeyValuePairs(pp, extraProperties), messages = []; if (!path.depth()) { @@ -4649,7 +4661,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return messages.join('\n'); } - function constructorsAreDifferentFormatter(actual, expected, path) { + function constructorsAreDifferentFormatter(pp, actual, expected, path) { if (!path.depth()) { path = 'object'; } @@ -4657,20 +4669,20 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return 'Expected ' + path + ' to be a kind of ' + j$.fnNameFor(expected.constructor) + - ', but was ' + j$.pp(actual) + '.'; + ', but was ' + pp(actual) + '.'; } - function actualArrayIsLongerFormatter(actual, expected, path) { + function actualArrayIsLongerFormatter(pp, actual, expected, path) { return 'Unexpected ' + path + (path.depth() ? ' = ' : '') + - j$.pp(actual) + + pp(actual) + ' in array.'; } - function formatKeyValuePairs(obj) { + function formatKeyValuePairs(pp, obj) { var formatted = ''; for (var key in obj) { - formatted += '\n ' + key + ': ' + j$.pp(obj[key]); + formatted += '\n ' + key + ': ' + pp(obj[key]); } return formatted; } @@ -4977,11 +4989,11 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { * expect(3).toBeInstanceOf(Number); * expect(new Error()).toBeInstanceOf(Error); */ - function toBeInstanceOf() { + function toBeInstanceOf(matchersUtil) { return { compare: function(actual, expected) { - var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : j$.pp(actual), - expectedType = expected ? j$.fnNameFor(expected) : j$.pp(expected), + var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : matchersUtil.pp(actual), + expectedType = expected ? j$.fnNameFor(expected) : matchersUtil.pp(expected), expectedMatcher, pass; @@ -5067,7 +5079,7 @@ getJasmineRequireObj().toBeNaN = function(j$) { * @example * expect(thing).toBeNaN(); */ - function toBeNaN() { + function toBeNaN(matchersUtil) { return { compare: function(actual) { var result = { @@ -5077,7 +5089,7 @@ getJasmineRequireObj().toBeNaN = function(j$) { if (result.pass) { result.message = 'Expected actual not to be NaN.'; } else { - result.message = function() { return 'Expected ' + j$.pp(actual) + ' to be NaN.'; }; + result.message = function() { return 'Expected ' + matchersUtil.pp(actual) + ' to be NaN.'; }; } return result; @@ -5097,7 +5109,7 @@ getJasmineRequireObj().toBeNegativeInfinity = function(j$) { * @example * expect(thing).toBeNegativeInfinity(); */ - function toBeNegativeInfinity() { + function toBeNegativeInfinity(matchersUtil) { return { compare: function(actual) { var result = { @@ -5107,7 +5119,7 @@ getJasmineRequireObj().toBeNegativeInfinity = function(j$) { if (result.pass) { result.message = 'Expected actual not to be -Infinity.'; } else { - result.message = function() { return 'Expected ' + j$.pp(actual) + ' to be -Infinity.'; }; + result.message = function() { return 'Expected ' + matchersUtil.pp(actual) + ' to be -Infinity.'; }; } return result; @@ -5149,7 +5161,7 @@ getJasmineRequireObj().toBePositiveInfinity = function(j$) { * @example * expect(thing).toBePositiveInfinity(); */ - function toBePositiveInfinity() { + function toBePositiveInfinity(matchersUtil) { return { compare: function(actual) { var result = { @@ -5159,7 +5171,7 @@ getJasmineRequireObj().toBePositiveInfinity = function(j$) { if (result.pass) { result.message = 'Expected actual not to be Infinity.'; } else { - result.message = function() { return 'Expected ' + j$.pp(actual) + ' to be Infinity.'; }; + result.message = function() { return 'Expected ' + matchersUtil.pp(actual) + ' to be Infinity.'; }; } return result; @@ -5305,13 +5317,13 @@ getJasmineRequireObj().toHaveBeenCalled = function(j$) { * expect(mySpy).toHaveBeenCalled(); * expect(mySpy).not.toHaveBeenCalled(); */ - function toHaveBeenCalled() { + function toHaveBeenCalled(matchersUtil) { return { compare: function(actual) { var result = {}; if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); + throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(actual) + '.')); } if (arguments.length > 1) { @@ -5345,14 +5357,14 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { * @example * expect(mySpy).toHaveBeenCalledBefore(otherSpy); */ - function toHaveBeenCalledBefore() { + function toHaveBeenCalledBefore(matchersUtil) { return { compare: function(firstSpy, latterSpy) { if (!j$.isSpy(firstSpy)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(firstSpy) + '.')); + throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(firstSpy) + '.')); } if (!j$.isSpy(latterSpy)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(latterSpy) + '.')); + throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(latterSpy) + '.')); } var result = { pass: false }; @@ -5407,11 +5419,11 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { * @example * expect(mySpy).toHaveBeenCalledTimes(3); */ - function toHaveBeenCalledTimes() { + function toHaveBeenCalledTimes(matchersUtil) { return { compare: function(actual, expected) { if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); + throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(actual) + '.')); } var args = Array.prototype.slice.call(arguments, 0), @@ -5449,7 +5461,7 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { * @example * expect(mySpy).toHaveBeenCalledWith('foo', 'bar', 2); */ - function toHaveBeenCalledWith(util) { + function toHaveBeenCalledWith(matchersUtil) { return { compare: function() { var args = Array.prototype.slice.call(arguments, 0), @@ -5458,40 +5470,40 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { result = { pass: false }; if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); + throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(actual) + '.')); } if (!actual.calls.any()) { result.message = function() { return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + - ' ' + j$.pp(expectedArgs) + + ' ' + matchersUtil.pp(expectedArgs) + '\nbut it was never called.'; }; return result; } - if (util.contains(actual.calls.allArgs(), expectedArgs)) { + if (matchersUtil.contains(actual.calls.allArgs(), expectedArgs)) { result.pass = true; result.message = function() { return 'Expected spy ' + actual.and.identity + ' not to have been called with:\n' + - ' ' + j$.pp(expectedArgs) + + ' ' + matchersUtil.pp(expectedArgs) + '\nbut it was.'; }; } else { result.message = function() { var prettyPrintedCalls = actual.calls.allArgs().map(function(argsForCall) { - return ' ' + j$.pp(argsForCall); + return ' ' + matchersUtil.pp(argsForCall); }); var diffs = actual.calls.allArgs().map(function(argsForCall, callIx) { var diffBuilder = new j$.DiffBuilder(); - util.equals(argsForCall, expectedArgs, diffBuilder); + matchersUtil.equals(argsForCall, expectedArgs, diffBuilder); return 'Call ' + callIx + ':\n' + diffBuilder.getMessage().replace(/^/mg, ' '); }); return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + - ' ' + j$.pp(expectedArgs) + '\n' + '' + + ' ' + matchersUtil.pp(expectedArgs) + '\n' + '' + 'but actual calls were:\n' + prettyPrintedCalls.join(',\n') + '.\n\n' + diffs.join('\n'); @@ -5518,11 +5530,11 @@ getJasmineRequireObj().toHaveClass = function(j$) { * el.className = 'foo bar baz'; * expect(el).toHaveClass('bar'); */ - function toHaveClass() { + function toHaveClass(matchersUtil) { return { compare: function(actual, expected) { if (!isElement(actual)) { - throw new Error(j$.pp(actual) + ' is not a DOM element'); + throw new Error(matchersUtil.pp(actual) + ' is not a DOM element'); } return { @@ -5588,7 +5600,7 @@ getJasmineRequireObj().toThrow = function(j$) { * expect(function() { return 'things'; }).toThrow('foo'); * expect(function() { return 'stuff'; }).toThrow(); */ - function toThrow(util) { + function toThrow(matchersUtil) { return { compare: function(actual, expected) { var result = { pass: false }, @@ -5613,16 +5625,16 @@ getJasmineRequireObj().toThrow = function(j$) { if (arguments.length == 1) { result.pass = true; - result.message = function() { return 'Expected function not to throw, but it threw ' + j$.pp(thrown) + '.'; }; + result.message = function() { return 'Expected function not to throw, but it threw ' + matchersUtil.pp(thrown) + '.'; }; return result; } - if (util.equals(thrown, expected)) { + if (matchersUtil.equals(thrown, expected)) { result.pass = true; - result.message = function() { return 'Expected function not to throw ' + j$.pp(expected) + '.'; }; + result.message = function() { return 'Expected function not to throw ' + matchersUtil.pp(expected) + '.'; }; } else { - result.message = function() { return 'Expected function to throw ' + j$.pp(expected) + ', but it threw ' + j$.pp(thrown) + '.'; }; + result.message = function() { return 'Expected function to throw ' + matchersUtil.pp(expected) + ', but it threw ' + matchersUtil.pp(thrown) + '.'; }; } return result; @@ -5651,7 +5663,7 @@ getJasmineRequireObj().toThrowError = function(j$) { * expect(function() { return 'other'; }).toThrowError(/foo/); * expect(function() { return 'other'; }).toThrowError(); */ - function toThrowError () { + function toThrowError(matchersUtil) { return { compare: function(actual) { var errorMatcher = getMatcher.apply(null, arguments), @@ -5669,7 +5681,7 @@ getJasmineRequireObj().toThrowError = function(j$) { } if (!j$.isError_(thrown)) { - return fail(function() { return 'Expected function to throw an Error, but it threw ' + j$.pp(thrown) + '.'; }); + return fail(function() { return 'Expected function to throw an Error, but it threw ' + matchersUtil.pp(thrown) + '.'; }); } return errorMatcher.match(thrown); @@ -5732,7 +5744,7 @@ getJasmineRequireObj().toThrowError = function(j$) { thrownMessage = ''; if (expected) { - thrownMessage = ' with message ' + j$.pp(thrown.message); + thrownMessage = ' with message ' + matchersUtil.pp(thrown.message); } return thrownName + thrownMessage; @@ -5742,9 +5754,9 @@ getJasmineRequireObj().toThrowError = function(j$) { if (expected === null) { return ''; } else if (expected instanceof RegExp) { - return ' with a message matching ' + j$.pp(expected); + return ' with a message matching ' + matchersUtil.pp(expected); } else { - return ' with message ' + j$.pp(expected); + return ' with message ' + matchersUtil.pp(expected); } } @@ -5813,7 +5825,7 @@ getJasmineRequireObj().toThrowMatching = function(j$) { * @example * expect(function() { throw new Error('nope'); }).toThrowMatching(function(thrown) { return thrown.message === 'nope'; }); */ - function toThrowMatching() { + function toThrowMatching(matchersUtil) { return { compare: function(actual, predicate) { var thrown; @@ -5843,14 +5855,14 @@ getJasmineRequireObj().toThrowMatching = function(j$) { } } }; - } - function thrownDescription(thrown) { - if (thrown && thrown.constructor) { - return j$.fnNameFor(thrown.constructor) + ' with message ' + - j$.pp(thrown.message); - } else { - return j$.pp(thrown); + function thrownDescription(thrown) { + if (thrown && thrown.constructor) { + return j$.fnNameFor(thrown.constructor) + ' with message ' + + matchersUtil.pp(thrown.message); + } else { + return matchersUtil.pp(thrown); + } } } @@ -5977,8 +5989,8 @@ getJasmineRequireObj().MockDate = function() { return MockDate; }; -getJasmineRequireObj().pp = function(j$) { - function PrettyPrinter() { +getJasmineRequireObj().makePrettyPrinter = function(j$) { + function SinglePrettyPrintRun() { this.ppNestLevel_ = 0; this.seen = []; this.length = 0; @@ -6000,7 +6012,7 @@ getJasmineRequireObj().pp = function(j$) { } } - PrettyPrinter.prototype.format = function(value) { + SinglePrettyPrintRun.prototype.format = function(value) { this.ppNestLevel_++; try { if (j$.util.isUndefined(value)) { @@ -6074,7 +6086,7 @@ getJasmineRequireObj().pp = function(j$) { } }; - PrettyPrinter.prototype.iterateObject = function(obj, fn) { + SinglePrettyPrintRun.prototype.iterateObject = function(obj, fn) { var objKeys = keys(obj, j$.isArray_(obj)); var isGetter = function isGetter(prop) {}; @@ -6093,15 +6105,15 @@ getJasmineRequireObj().pp = function(j$) { return objKeys.length > length; }; - PrettyPrinter.prototype.emitScalar = function(value) { + SinglePrettyPrintRun.prototype.emitScalar = function(value) { this.append(value); }; - PrettyPrinter.prototype.emitString = function(value) { + SinglePrettyPrintRun.prototype.emitString = function(value) { this.append("'" + value + "'"); }; - PrettyPrinter.prototype.emitArray = function(array) { + SinglePrettyPrintRun.prototype.emitArray = function(array) { if (this.ppNestLevel_ > j$.MAX_PRETTY_PRINT_DEPTH) { this.append('Array'); return; @@ -6137,7 +6149,7 @@ getJasmineRequireObj().pp = function(j$) { this.append(' ]'); }; - PrettyPrinter.prototype.emitSet = function(set) { + SinglePrettyPrintRun.prototype.emitSet = function(set) { if (this.ppNestLevel_ > j$.MAX_PRETTY_PRINT_DEPTH) { this.append('Set'); return; @@ -6162,7 +6174,7 @@ getJasmineRequireObj().pp = function(j$) { this.append(' )'); }; - PrettyPrinter.prototype.emitMap = function(map) { + SinglePrettyPrintRun.prototype.emitMap = function(map) { if (this.ppNestLevel_ > j$.MAX_PRETTY_PRINT_DEPTH) { this.append('Map'); return; @@ -6187,7 +6199,7 @@ getJasmineRequireObj().pp = function(j$) { this.append(' )'); }; - PrettyPrinter.prototype.emitObject = function(obj) { + SinglePrettyPrintRun.prototype.emitObject = function(obj) { var ctor = obj.constructor, constructorName; @@ -6223,7 +6235,7 @@ getJasmineRequireObj().pp = function(j$) { this.append(' })'); }; - PrettyPrinter.prototype.emitTypedArray = function(arr) { + SinglePrettyPrintRun.prototype.emitTypedArray = function(arr) { var constructorName = j$.fnNameFor(arr.constructor), limitedArray = Array.prototype.slice.call( arr, @@ -6239,7 +6251,7 @@ getJasmineRequireObj().pp = function(j$) { this.append(constructorName + ' [ ' + itemsString + ' ]'); }; - PrettyPrinter.prototype.emitDomElement = function(el) { + SinglePrettyPrintRun.prototype.emitDomElement = function(el) { var tagName = el.tagName.toLowerCase(), attrs = el.attributes, i, @@ -6265,7 +6277,11 @@ getJasmineRequireObj().pp = function(j$) { this.append(out); }; - PrettyPrinter.prototype.formatProperty = function(obj, property, isGetter) { + SinglePrettyPrintRun.prototype.formatProperty = function( + obj, + property, + isGetter + ) { this.append(property); this.append(': '); if (isGetter) { @@ -6275,7 +6291,7 @@ getJasmineRequireObj().pp = function(j$) { } }; - PrettyPrinter.prototype.append = function(value) { + SinglePrettyPrintRun.prototype.append = function(value) { // This check protects us from the rare case where an object has overriden // `toString()` with an invalid implementation (returning a non-string). if (typeof value !== 'string') { @@ -6339,10 +6355,13 @@ getJasmineRequireObj().pp = function(j$) { return extraKeys; } - return function(value) { - var prettyPrinter = new PrettyPrinter(); - prettyPrinter.format(value); - return prettyPrinter.stringParts.join(''); + + return function() { + return function(value) { + var prettyPrinter = new SinglePrettyPrintRun(); + prettyPrinter.format(value); + return prettyPrinter.stringParts.join(''); + }; }; }; @@ -7033,7 +7052,10 @@ getJasmineRequireObj().Spy = function(j$) { }; })(); - var matchersUtil = new j$.MatchersUtil(); + var matchersUtil = new j$.MatchersUtil({ + customTesters: [], + pp: j$.makePrettyPrinter() + }); /** * _Note:_ Do not construct this directly, use {@link spyOn}, {@link spyOnProperty}, {@link jasmine.createSpy}, or {@link jasmine.createSpyObj} diff --git a/spec/core/AsyncExpectationSpec.js b/spec/core/AsyncExpectationSpec.js index 23d145e1..74eb2dad 100644 --- a/spec/core/AsyncExpectationSpec.js +++ b/spec/core/AsyncExpectationSpec.js @@ -24,8 +24,9 @@ describe('AsyncExpectation', function() { var addExpectationResult = jasmine.createSpy('addExpectationResult'), actual = Promise.resolve(), + pp = jasmineUnderTest.makePrettyPrinter(), expectation = jasmineUnderTest.Expectation.asyncFactory({ - util: new jasmineUnderTest.MatchersUtil(), + util: new jasmineUnderTest.MatchersUtil({ pp: pp }), actual: actual, addExpectationResult: addExpectationResult }); @@ -47,7 +48,7 @@ describe('AsyncExpectation', function() { var addExpectationResult = jasmine.createSpy('addExpectationResult'), actual = Promise.reject(), expectation = jasmineUnderTest.Expectation.asyncFactory({ - util: new jasmineUnderTest.MatchersUtil(), + util: new jasmineUnderTest.MatchersUtil({ pp: function() {} }), actual: actual, addExpectationResult: addExpectationResult }); @@ -122,7 +123,8 @@ describe('AsyncExpectation', function() { var util = { buildFailureMessage: function() { return 'failure message'; - } + }, + pp: jasmineUnderTest.makePrettyPrinter() }, addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation = jasmineUnderTest.Expectation.asyncFactory({ @@ -180,10 +182,11 @@ describe('AsyncExpectation', function() { var addExpectationResult = jasmine.createSpy('addExpectationResult'), actual = Promise.resolve(), + pp = jasmineUnderTest.makePrettyPrinter(), expectation = jasmineUnderTest.Expectation.asyncFactory({ actual: actual, addExpectationResult: addExpectationResult, - util: new jasmineUnderTest.MatchersUtil() + util: new jasmineUnderTest.MatchersUtil({ pp: pp }) }); return expectation @@ -208,7 +211,9 @@ describe('AsyncExpectation', function() { expectation = jasmineUnderTest.Expectation.asyncFactory({ actual: actual, addExpectationResult: addExpectationResult, - util: new jasmineUnderTest.MatchersUtil() + util: new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }) }); return expectation diff --git a/spec/core/EnvSpec.js b/spec/core/EnvSpec.js index dc7233c8..80dcffbb 100644 --- a/spec/core/EnvSpec.js +++ b/spec/core/EnvSpec.js @@ -307,10 +307,12 @@ describe('Env', function() { it('creates an expectationFactory that uses the current custom equality testers', function(done) { function customEqualityTester() {} + function prettyPrinter() {} var RealSpec = jasmineUnderTest.Spec, specInstance, expectationFactory; spyOn(jasmineUnderTest, 'MatchersUtil'); + spyOn(jasmineUnderTest, 'makePrettyPrinter').and.returnValue(prettyPrinter); spyOn(jasmineUnderTest, 'Spec').and.callFake(function(options) { expectationFactory = options.expectationFactory; specInstance = new RealSpec(options); @@ -325,7 +327,8 @@ describe('Env', function() { env.addReporter({ jasmineDone: function() { expect(jasmineUnderTest.MatchersUtil).toHaveBeenCalledWith({ - customTesters: [customEqualityTester] + customTesters: [customEqualityTester], + pp: prettyPrinter }); done(); } @@ -336,10 +339,12 @@ describe('Env', function() { it('creates an asyncExpectationFactory that uses the current custom equality testers', function(done) { function customEqualityTester() {} + function prettyPrinter() {} var RealSpec = jasmineUnderTest.Spec, specInstance, asyncExpectationFactory; spyOn(jasmineUnderTest, 'MatchersUtil'); + spyOn(jasmineUnderTest, 'makePrettyPrinter').and.returnValue(prettyPrinter); spyOn(jasmineUnderTest, 'Spec').and.callFake(function(options) { asyncExpectationFactory = options.asyncExpectationFactory; specInstance = new RealSpec(options); @@ -354,7 +359,8 @@ describe('Env', function() { env.addReporter({ jasmineDone: function() { expect(jasmineUnderTest.MatchersUtil).toHaveBeenCalledWith({ - customTesters: [customEqualityTester] + customTesters: [customEqualityTester], + pp: prettyPrinter }); done(); } diff --git a/spec/core/ExpectationSpec.js b/spec/core/ExpectationSpec.js index 361224ab..5b205730 100644 --- a/spec/core/ExpectationSpec.js +++ b/spec/core/ExpectationSpec.js @@ -632,9 +632,10 @@ describe('Expectation', function() { } }, addExpectationResult = jasmine.createSpy('addExpectationResult'), + pp = jasmineUnderTest.makePrettyPrinter(), expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - util: new jasmineUnderTest.MatchersUtil(), + util: new jasmineUnderTest.MatchersUtil({ pp: pp }), actual: 'an actual', addExpectationResult: addExpectationResult }); diff --git a/spec/core/PrettyPrintSpec.js b/spec/core/PrettyPrintSpec.js index 1249d8c6..46f08d6a 100644 --- a/spec/core/PrettyPrintSpec.js +++ b/spec/core/PrettyPrintSpec.js @@ -1,17 +1,19 @@ -describe('jasmineUnderTest.pp', function() { +describe('PrettyPrinter', function() { it('should wrap strings in single quotes', function() { - expect(jasmineUnderTest.pp('some string')).toEqual("'some string'"); - expect(jasmineUnderTest.pp("som' string")).toEqual("'som' string'"); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp('some string')).toEqual("'some string'"); + expect(pp("som' string")).toEqual("'som' string'"); }); it('should stringify primitives properly', function() { - expect(jasmineUnderTest.pp(true)).toEqual('true'); - expect(jasmineUnderTest.pp(false)).toEqual('false'); - expect(jasmineUnderTest.pp(null)).toEqual('null'); - expect(jasmineUnderTest.pp(jasmine.undefined)).toEqual('undefined'); - expect(jasmineUnderTest.pp(3)).toEqual('3'); - expect(jasmineUnderTest.pp(-3.14)).toEqual('-3.14'); - expect(jasmineUnderTest.pp(-0)).toEqual('-0'); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp(true)).toEqual('true'); + expect(pp(false)).toEqual('false'); + expect(pp(null)).toEqual('null'); + expect(pp(jasmine.undefined)).toEqual('undefined'); + expect(pp(3)).toEqual('3'); + expect(pp(-3.14)).toEqual('-3.14'); + expect(pp(-0)).toEqual('-0'); }); describe('stringify sets', function() { @@ -20,7 +22,8 @@ describe('jasmineUnderTest.pp', function() { var set = new Set(); set.add(1); set.add(2); - expect(jasmineUnderTest.pp(set)).toEqual('Set( 1, 2 )'); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp(set)).toEqual('Set( 1, 2 )'); }); it('should truncate sets with more elements than jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH', function() { @@ -33,7 +36,8 @@ describe('jasmineUnderTest.pp', function() { set.add('a'); set.add('b'); set.add('c'); - expect(jasmineUnderTest.pp(set)).toEqual("Set( 'a', 'b', ... )"); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp(set)).toEqual("Set( 'a', 'b', ... )"); } finally { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = originalMaxSize; } @@ -45,7 +49,8 @@ describe('jasmineUnderTest.pp', function() { jasmine.getEnv().requireFunctioningMaps(); var map = new Map(); map.set(1, 2); - expect(jasmineUnderTest.pp(map)).toEqual('Map( [ 1, 2 ] )'); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp(map)).toEqual('Map( [ 1, 2 ] )'); }); it('should truncate maps with more elements than jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH', function() { @@ -58,9 +63,8 @@ describe('jasmineUnderTest.pp', function() { map.set('a', 1); map.set('b', 2); map.set('c', 3); - expect(jasmineUnderTest.pp(map)).toEqual( - "Map( [ 'a', 1 ], [ 'b', 2 ], ... )" - ); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp(map)).toEqual("Map( [ 'a', 1 ], [ 'b', 2 ], ... )"); } finally { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = originalMaxSize; } @@ -69,43 +73,44 @@ describe('jasmineUnderTest.pp', function() { describe('stringify arrays', function() { it('should stringify arrays properly', function() { - expect(jasmineUnderTest.pp([1, 2])).toEqual('[ 1, 2 ]'); - expect( - jasmineUnderTest.pp([1, 'foo', {}, jasmine.undefined, null]) - ).toEqual("[ 1, 'foo', Object({ }), undefined, null ]"); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp([1, 2])).toEqual('[ 1, 2 ]'); + expect(pp([1, 'foo', {}, jasmine.undefined, null])).toEqual( + "[ 1, 'foo', Object({ }), undefined, null ]" + ); }); it('should truncate arrays that are longer than jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH', function() { var originalMaxLength = jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH; var array = [1, 2, 3]; + var pp = jasmineUnderTest.makePrettyPrinter(); try { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = 2; - expect(jasmineUnderTest.pp(array)).toEqual('[ 1, 2, ... ]'); + expect(pp(array)).toEqual('[ 1, 2, ... ]'); } finally { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = originalMaxLength; } }); it('should stringify arrays with properties properly', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var arr = [1, 2]; arr.foo = 'bar'; arr.baz = {}; - expect(jasmineUnderTest.pp(arr)).toEqual( - "[ 1, 2, foo: 'bar', baz: Object({ }) ]" - ); + expect(pp(arr)).toEqual("[ 1, 2, foo: 'bar', baz: Object({ }) ]"); }); it('should stringify empty arrays with properties properly', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var empty = []; empty.foo = 'bar'; empty.baz = {}; - expect(jasmineUnderTest.pp(empty)).toEqual( - "[ foo: 'bar', baz: Object({ }) ]" - ); + expect(pp(empty)).toEqual("[ foo: 'bar', baz: Object({ }) ]"); }); it('should stringify long arrays with properties properly', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var originalMaxLength = jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH; var long = [1, 2, 3]; long.foo = 'bar'; @@ -113,7 +118,7 @@ describe('jasmineUnderTest.pp', function() { try { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = 2; - expect(jasmineUnderTest.pp(long)).toEqual( + expect(pp(long)).toEqual( "[ 1, 2, ..., foo: 'bar', baz: Object({ }) ]" ); } finally { @@ -122,26 +127,25 @@ describe('jasmineUnderTest.pp', function() { }); it('should indicate circular array references', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var array1 = [1, 2]; var array2 = [array1]; array1.push(array2); - expect(jasmineUnderTest.pp(array1)).toEqual( - '[ 1, 2, [ ] ]' - ); + expect(pp(array1)).toEqual('[ 1, 2, [ ] ]'); }); it('should not indicate circular references incorrectly', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var array = [[1]]; - expect(jasmineUnderTest.pp(array)).toEqual('[ [ 1 ] ]'); + expect(pp(array)).toEqual('[ [ 1 ] ]'); }); }); it('should stringify objects properly', function() { - expect(jasmineUnderTest.pp({ foo: 'bar' })).toEqual( - "Object({ foo: 'bar' })" - ); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp({ foo: 'bar' })).toEqual("Object({ foo: 'bar' })"); expect( - jasmineUnderTest.pp({ + pp({ foo: 'bar', baz: 3, nullValue: null, @@ -150,24 +154,24 @@ describe('jasmineUnderTest.pp', function() { ).toEqual( "Object({ foo: 'bar', baz: 3, nullValue: null, undefinedValue: undefined })" ); - expect(jasmineUnderTest.pp({ foo: function() {}, bar: [1, 2, 3] })).toEqual( + expect(pp({ foo: function() {}, bar: [1, 2, 3] })).toEqual( 'Object({ foo: Function, bar: [ 1, 2, 3 ] })' ); }); it('should stringify objects that almost look like DOM nodes', function() { - expect(jasmineUnderTest.pp({ nodeType: 1 })).toEqual( - 'Object({ nodeType: 1 })' - ); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp({ nodeType: 1 })).toEqual('Object({ nodeType: 1 })'); }); it('should truncate objects with too many keys', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var originalMaxLength = jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH; var long = { a: 1, b: 2, c: 3 }; try { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = 2; - expect(jasmineUnderTest.pp(long)).toEqual('Object({ a: 1, b: 2, ... })'); + expect(pp(long)).toEqual('Object({ a: 1, b: 2, ... })'); } finally { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = originalMaxLength; } @@ -185,12 +189,11 @@ describe('jasmineUnderTest.pp', function() { } it('should truncate outputs that are too long', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var big = [{ a: 1, b: 'a long string' }, {}]; withMaxChars(34, function() { - expect(jasmineUnderTest.pp(big)).toEqual( - "[ Object({ a: 1, b: 'a long st ..." - ); + expect(pp(big)).toEqual("[ Object({ a: 1, b: 'a long st ..."); }); }); @@ -214,59 +217,55 @@ describe('jasmineUnderTest.pp', function() { jasmineToString: jasmine .createSpy('d jasmineToString') .and.returnValue('') - }; + }, + pp = jasmineUnderTest.makePrettyPrinter(); withMaxChars(30, function() { - jasmineUnderTest.pp([{ a: a, b: b, c: c }, d]); + pp([{ a: a, b: b, c: c }, d]); expect(c.jasmineToString).not.toHaveBeenCalled(); expect(d.jasmineToString).not.toHaveBeenCalled(); }); }); it("should print 'null' as the constructor of an object with its own constructor property", function() { - expect(jasmineUnderTest.pp({ constructor: function() {} })).toContain( - 'null({' - ); - expect(jasmineUnderTest.pp({ constructor: 'foo' })).toContain('null({'); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp({ constructor: function() {} })).toContain('null({'); + expect(pp({ constructor: 'foo' })).toContain('null({'); }); it('should not include inherited properties when stringifying an object', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var SomeClass = function SomeClass() {}; SomeClass.prototype.foo = 'inherited foo'; var instance = new SomeClass(); instance.bar = 'my own bar'; - expect(jasmineUnderTest.pp(instance)).toEqual( - "SomeClass({ bar: 'my own bar' })" - ); + expect(pp(instance)).toEqual("SomeClass({ bar: 'my own bar' })"); }); it('should not recurse objects and arrays more deeply than jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var originalMaxDepth = jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH; var nestedObject = { level1: { level2: { level3: { level4: 'leaf' } } } }; var nestedArray = [1, [2, [3, [4, 'leaf']]]]; try { jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH = 2; - expect(jasmineUnderTest.pp(nestedObject)).toEqual( + expect(pp(nestedObject)).toEqual( 'Object({ level1: Object({ level2: Object }) })' ); - expect(jasmineUnderTest.pp(nestedArray)).toEqual('[ 1, [ 2, Array ] ]'); + expect(pp(nestedArray)).toEqual('[ 1, [ 2, Array ] ]'); jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH = 3; - expect(jasmineUnderTest.pp(nestedObject)).toEqual( + expect(pp(nestedObject)).toEqual( 'Object({ level1: Object({ level2: Object({ level3: Object }) }) })' ); - expect(jasmineUnderTest.pp(nestedArray)).toEqual( - '[ 1, [ 2, [ 3, Array ] ] ]' - ); + expect(pp(nestedArray)).toEqual('[ 1, [ 2, [ 3, Array ] ] ]'); jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH = 4; - expect(jasmineUnderTest.pp(nestedObject)).toEqual( + expect(pp(nestedObject)).toEqual( "Object({ level1: Object({ level2: Object({ level3: Object({ level4: 'leaf' }) }) }) })" ); - expect(jasmineUnderTest.pp(nestedArray)).toEqual( - "[ 1, [ 2, [ 3, [ 4, 'leaf' ] ] ] ]" - ); + expect(pp(nestedArray)).toEqual("[ 1, [ 2, [ 3, [ 4, 'leaf' ] ] ] ]"); } finally { jasmineUnderTest.MAX_PRETTY_PRINT_DEPTH = originalMaxDepth; } @@ -274,28 +273,32 @@ describe('jasmineUnderTest.pp', function() { it('should stringify immutable circular objects', function() { if (Object.freeze) { + var pp = jasmineUnderTest.makePrettyPrinter(); var frozenObject = { foo: { bar: 'baz' } }; frozenObject.circular = frozenObject; frozenObject = Object.freeze(frozenObject); - expect(jasmineUnderTest.pp(frozenObject)).toEqual( + expect(pp(frozenObject)).toEqual( "Object({ foo: Object({ bar: 'baz' }), circular: })" ); } }); it('should stringify RegExp objects properly', function() { - expect(jasmineUnderTest.pp(/x|y|z/)).toEqual('/x|y|z/'); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp(/x|y|z/)).toEqual('/x|y|z/'); }); it('should indicate circular object references', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var sampleValue = { foo: 'hello' }; sampleValue.nested = sampleValue; - expect(jasmineUnderTest.pp(sampleValue)).toEqual( + expect(pp(sampleValue)).toEqual( "Object({ foo: 'hello', nested: })" ); }); it('should indicate getters on objects as such', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var sampleValue = { id: 1 }; if (sampleValue.__defineGetter__) { //not supported in IE! @@ -304,34 +307,38 @@ describe('jasmineUnderTest.pp', function() { }); } if (sampleValue.__defineGetter__) { - expect(jasmineUnderTest.pp(sampleValue)).toEqual( + expect(pp(sampleValue)).toEqual( 'Object({ id: 1, calculatedValue: })' ); } else { - expect(jasmineUnderTest.pp(sampleValue)).toEqual('Object({ id: 1 })'); + expect(pp(sampleValue)).toEqual('Object({ id: 1 })'); } }); it('should not do HTML escaping of strings', function() { - expect(jasmineUnderTest.pp('some html string &', false)).toEqual( + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp('some html string &', false)).toEqual( "'some html string &'" ); }); it('should abbreviate the global (usually window) object', function() { - expect(jasmineUnderTest.pp(jasmine.getGlobal())).toEqual(''); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp(jasmine.getGlobal())).toEqual(''); }); it('should stringify Date objects properly', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var now = new Date(); - expect(jasmineUnderTest.pp(now)).toEqual('Date(' + now.toString() + ')'); + expect(pp(now)).toEqual('Date(' + now.toString() + ')'); }); it('should stringify spy objects properly', function() { var TestObject = { someFunction: function() {} }, - env = new jasmineUnderTest.Env(); + env = new jasmineUnderTest.Env(), + pp = jasmineUnderTest.makePrettyPrinter(); var spyRegistry = new jasmineUnderTest.SpyRegistry({ currentSpies: function() { @@ -343,20 +350,17 @@ describe('jasmineUnderTest.pp', function() { }); spyRegistry.spyOn(TestObject, 'someFunction'); - expect(jasmineUnderTest.pp(TestObject.someFunction)).toEqual( - 'spy on someFunction' - ); + expect(pp(TestObject.someFunction)).toEqual('spy on someFunction'); - expect(jasmineUnderTest.pp(env.createSpy('something'))).toEqual( - 'spy on something' - ); + expect(pp(env.createSpy('something'))).toEqual('spy on something'); }); it('should stringify spyOn toString properly', function() { var TestObject = { someFunction: function() {} }, - env = new jasmineUnderTest.Env(); + env = new jasmineUnderTest.Env(), + pp = jasmineUnderTest.makePrettyPrinter(); var spyRegistry = new jasmineUnderTest.SpyRegistry({ currentSpies: function() { @@ -370,29 +374,29 @@ describe('jasmineUnderTest.pp', function() { spyRegistry.spyOn(TestObject, 'toString'); var testSpyObj = env.createSpyObj('TheClassName', ['toString']); - expect(jasmineUnderTest.pp(testSpyObj)).toEqual( - 'spy on TheClassName.toString' - ); + expect(pp(testSpyObj)).toEqual('spy on TheClassName.toString'); }); it('should stringify objects that implement jasmineToString', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var obj = { jasmineToString: function() { return 'strung'; } }; - expect(jasmineUnderTest.pp(obj)).toEqual('strung'); + expect(pp(obj)).toEqual('strung'); }); it('should stringify objects that implement custom toString', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var obj = { toString: function() { return 'my toString'; } }; - expect(jasmineUnderTest.pp(obj)).toEqual('my toString'); + expect(pp(obj)).toEqual('my toString'); // Simulate object from another global context (e.g. an iframe or Web Worker) that does not actually have a custom // toString despite obj.toString !== Object.prototype.toString @@ -403,20 +407,22 @@ describe('jasmineUnderTest.pp', function() { } }; - expect(jasmineUnderTest.pp(objFromOtherContext)).toEqual( + expect(pp(objFromOtherContext)).toEqual( "Object({ foo: 'bar', toString: Function })" ); }); it("should stringify objects have have a toString that isn't a function", function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var obj = { toString: 'foo' }; - expect(jasmineUnderTest.pp(obj)).toEqual("Object({ toString: 'foo' })"); + expect(pp(obj)).toEqual("Object({ toString: 'foo' })"); }); it('should stringify objects from anonymous constructors with custom toString', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var MyAnonymousConstructor = (function() { return function() {}; })(); @@ -426,17 +432,19 @@ describe('jasmineUnderTest.pp', function() { var a = new MyAnonymousConstructor(); - expect(jasmineUnderTest.pp(a)).toEqual('({ })'); + expect(pp(a)).toEqual('({ })'); }); it('should handle objects with null prototype', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var obj = Object.create(null); obj.foo = 'bar'; - expect(jasmineUnderTest.pp(obj)).toEqual("null({ foo: 'bar' })"); + expect(pp(obj)).toEqual("null({ foo: 'bar' })"); }); it('should gracefully handle objects with invalid toString implementations', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var obj = { foo: { toString: function() { @@ -466,7 +474,7 @@ describe('jasmineUnderTest.pp', function() { } }; - expect(jasmineUnderTest.pp(obj)).toEqual( + expect(pp(obj)).toEqual( 'Object({ foo: [object Number], bar: [object Object], baz: 3, qux: Error: bar, baddy: has-invalid-toString-method })' ); }); diff --git a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js index 03a337b0..97260d59 100644 --- a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js @@ -2,7 +2,7 @@ describe('#toBeRejectedWithError', function () { it('passes when Error type matches', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new TypeError('foo')); @@ -17,7 +17,7 @@ describe('#toBeRejectedWithError', function () { it('passes when Error type and message matches', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new TypeError('foo')); @@ -32,7 +32,7 @@ describe('#toBeRejectedWithError', function () { it('passes when Error matches and is exactly Error', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error()); @@ -48,7 +48,7 @@ describe('#toBeRejectedWithError', function () { it('passes when Error message matches a string', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error('foo')); @@ -63,7 +63,7 @@ describe('#toBeRejectedWithError', function () { it('passes when Error message matches a RegExp', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error('foo')); @@ -78,7 +78,7 @@ describe('#toBeRejectedWithError', function () { it('passes when Error message is empty', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error()); @@ -93,7 +93,7 @@ describe('#toBeRejectedWithError', function () { it('passes when no arguments', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error()); @@ -108,7 +108,7 @@ describe('#toBeRejectedWithError', function () { it('fails when resolved', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.resolve(new Error('foo')); @@ -123,7 +123,7 @@ describe('#toBeRejectedWithError', function () { it('fails when rejected with non Error type', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject('foo'); @@ -138,7 +138,7 @@ describe('#toBeRejectedWithError', function () { it('fails when Error type mismatches', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error('foo')); @@ -153,7 +153,7 @@ describe('#toBeRejectedWithError', function () { it('fails when Error message mismatches', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error('foo')); @@ -166,7 +166,7 @@ describe('#toBeRejectedWithError', function () { }); it('fails if actual is not a promise', function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = 'not a promise'; diff --git a/spec/core/matchers/async/toBeRejectedWithSpec.js b/spec/core/matchers/async/toBeRejectedWithSpec.js index c1d22d0b..2c02a03a 100644 --- a/spec/core/matchers/async/toBeRejectedWithSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithSpec.js @@ -26,7 +26,7 @@ describe('#toBeRejectedWith', function () { it('should fail if the promise is rejected with a different value', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = Promise.reject('A Bad Apple'); @@ -41,7 +41,7 @@ describe('#toBeRejectedWith', function () { it('should build its error correctly when negated', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = Promise.reject(true); @@ -67,7 +67,7 @@ describe('#toBeRejectedWith', function () { }); it('fails if actual is not a promise', function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = 'not a promise'; diff --git a/spec/core/matchers/async/toBeResolvedToSpec.js b/spec/core/matchers/async/toBeResolvedToSpec.js index 426f9f12..c68eb0e0 100644 --- a/spec/core/matchers/async/toBeResolvedToSpec.js +++ b/spec/core/matchers/async/toBeResolvedToSpec.js @@ -14,7 +14,7 @@ describe('#toBeResolvedTo', function() { it('fails if the promise is rejected', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.reject('AsyncExpectationSpec error'); @@ -29,7 +29,7 @@ describe('#toBeResolvedTo', function() { it('fails if the promise is resolved to a different value', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.resolve({foo: 17}); @@ -44,7 +44,7 @@ describe('#toBeResolvedTo', function() { it('builds its message correctly when negated', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.resolve(true); @@ -60,7 +60,10 @@ describe('#toBeResolvedTo', function() { jasmine.getEnv().requirePromises(); var customEqualityTesters = [function() { return true; }], - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: customEqualityTesters}), + matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: customEqualityTesters, + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.resolve('actual'); @@ -70,7 +73,7 @@ describe('#toBeResolvedTo', function() { }); it('fails if actual is not a promise', function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil(), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = 'not a promise'; diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index 096d7c86..ff9b159d 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -1,4 +1,11 @@ describe("matchersUtil", function() { + it("exposes the injected pretty-printer as .pp", function() { + var pp = function() {}, + matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}); + + expect(matchersUtil.pp).toBe(pp); + }); + describe("equals", function() { it("passes for literals that are triple-equal", function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -76,7 +83,7 @@ describe("matchersUtil", function() { }); it("fails for Arrays that have different lengths", function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil(); + matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals([1, 2], [1, 2, 3])).toBe(false); }); @@ -392,7 +399,7 @@ describe("matchersUtil", function() { it("passes when a custom equality matcher passed to the constructor returns true", function() { var tester = function(a, b) { return true; }, - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester], pp: function() {}}); expect(matchersUtil.equals(1, 2)).toBe(true); }); @@ -416,7 +423,7 @@ describe("matchersUtil", function() { var tester = function(a, b) { return jasmine.undefined; }; it("passes for two empty Objects", function () { - var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); + var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester], pp: function() {}}); expect(matchersUtil.equals({}, {})).toBe(true); }); }); @@ -431,7 +438,7 @@ describe("matchersUtil", function() { it("fails for equivalents when a custom equality matcher passed to the constructor returns false", function() { var tester = function(a, b) { return false; }, - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester], pp: function() {}}); expect(matchersUtil.equals(1, 1)).toBe(false); }); @@ -449,7 +456,7 @@ describe("matchersUtil", function() { it("passes for an asymmetric equality tester that returns true when a custom equality tester passed to the constructor return false", function() { var asymmetricTester = { asymmetricMatch: function(other) { return true; } }, symmetricTester = function(a, b) { return false; }, - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [symmetricTester()]}); + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [symmetricTester()], pp: function() {}}); expect(matchersUtil.equals(asymmetricTester, true)).toBe(true); expect(matchersUtil.equals(true, asymmetricTester)).toBe(true); @@ -475,7 +482,7 @@ describe("matchersUtil", function() { it("is both a matchersUtil and the custom equality testers passed to the constructor", function() { var asymmetricTester = jasmine.createSpyObj('tester', ['asymmetricMatch']), symmetricTester = function() { } , - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [symmetricTester]}), + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [symmetricTester], pp: function() {}}), shim; matchersUtil.equals(true, asymmetricTester); @@ -783,7 +790,7 @@ describe("matchersUtil", function() { it("uses custom equality testers if passed to the constructor and actual is an Array", function() { var customTester = function(a, b) {return true;}, - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [customTester]}); + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [customTester], pp: function() {}}); expect(matchersUtil.contains([1, 2], 3)).toBe(true); }); @@ -838,7 +845,8 @@ describe("matchersUtil", function() { it("builds an English sentence for a failure case", function() { var actual = "foo", name = "toBar", - matchersUtil = new jasmineUnderTest.MatchersUtil(), + pp = jasmineUnderTest.makePrettyPrinter(), + matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), message = matchersUtil.buildFailureMessage(name, false, actual); expect(message).toEqual("Expected 'foo' to bar."); @@ -848,7 +856,8 @@ describe("matchersUtil", function() { var actual = "foo", name = "toBar", isNot = true, - matchersUtil = new jasmineUnderTest.MatchersUtil(), + pp = jasmineUnderTest.makePrettyPrinter(), + matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), message = message = matchersUtil.buildFailureMessage(name, isNot, actual); expect(message).toEqual("Expected 'foo' not to bar."); @@ -857,10 +866,22 @@ describe("matchersUtil", function() { it("builds an English sentence for an arbitrary array of expected arguments", function() { var actual = "foo", name = "toBar", - matchersUtil = new jasmineUnderTest.MatchersUtil(), + pp = jasmineUnderTest.makePrettyPrinter(), + matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), message = matchersUtil.buildFailureMessage(name, false, actual, "quux", "corge"); expect(message).toEqual("Expected 'foo' to bar 'quux', 'corge'."); }); + + it("uses the injected pretty-printer to format the expected", function() { + var actual = "foo", + name = "toBar", + isNot = false, + pp = function(value) { return '<' + value + '>'; }, + matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), + message = message = matchersUtil.buildFailureMessage(name, isNot, actual); + + expect(message).toEqual("Expected to bar."); + }); }); }); diff --git a/spec/core/matchers/toBeInstanceOfSpec.js b/spec/core/matchers/toBeInstanceOfSpec.js index d31845e9..d8355af7 100644 --- a/spec/core/matchers/toBeInstanceOfSpec.js +++ b/spec/core/matchers/toBeInstanceOfSpec.js @@ -10,7 +10,9 @@ describe('toBeInstanceOf', function() { }); it('passes for NaN', function() { - var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var matcher = jasmineUnderTest.matchers.toBeInstanceOf({ + pp: jasmineUnderTest.makePrettyPrinter() + }); var result = matcher.compare(NaN, Number); expect(result).toEqual({ pass: true, @@ -156,7 +158,9 @@ describe('toBeInstanceOf', function() { it('passes for objects with no constructor', function() { var object = Object.create(null); - var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var matcher = jasmineUnderTest.matchers.toBeInstanceOf({ + pp: jasmineUnderTest.makePrettyPrinter() + }); var result = matcher.compare(object, Object); expect(result).toEqual({ pass: true, @@ -219,7 +223,9 @@ describe('toBeInstanceOf', function() { }); it('raises an error if missing an expected value', function() { - var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); + var matcher = jasmineUnderTest.matchers.toBeInstanceOf({ + pp: jasmineUnderTest.makePrettyPrinter() + }); expect(function() { matcher.compare({}, undefined); }).toThrowError(' : Expected value is not a constructor function\n' + diff --git a/spec/core/matchers/toBeNaNSpec.js b/spec/core/matchers/toBeNaNSpec.js index b490d089..e859f64f 100644 --- a/spec/core/matchers/toBeNaNSpec.js +++ b/spec/core/matchers/toBeNaNSpec.js @@ -29,7 +29,9 @@ describe("toBeNaN", function() { }); it("has a custom message on failure", function() { - var matcher = jasmineUnderTest.matchers.toBeNaN(), + var matcher = jasmineUnderTest.matchers.toBeNaN({ + pp: jasmineUnderTest.makePrettyPrinter() + }), result = matcher.compare(0); expect(result.message()).toEqual("Expected 0 to be NaN."); diff --git a/spec/core/matchers/toBeNegativeInfinitySpec.js b/spec/core/matchers/toBeNegativeInfinitySpec.js index 4aca8978..876bf209 100644 --- a/spec/core/matchers/toBeNegativeInfinitySpec.js +++ b/spec/core/matchers/toBeNegativeInfinitySpec.js @@ -14,7 +14,9 @@ describe("toBeNegativeInfinity", function() { }); it("has a custom message on failure", function() { - var matcher = jasmineUnderTest.matchers.toBeNegativeInfinity(), + var matcher = jasmineUnderTest.matchers.toBeNegativeInfinity({ + pp: jasmineUnderTest.makePrettyPrinter() + }), result = matcher.compare(0); expect(result.message()).toEqual("Expected 0 to be -Infinity.") diff --git a/spec/core/matchers/toBePositiveInfinitySpec.js b/spec/core/matchers/toBePositiveInfinitySpec.js index 239833d9..6fc91b65 100644 --- a/spec/core/matchers/toBePositiveInfinitySpec.js +++ b/spec/core/matchers/toBePositiveInfinitySpec.js @@ -14,7 +14,9 @@ describe("toBePositiveInfinity", function() { }); it("has a custom message on failure", function() { - var matcher = jasmineUnderTest.matchers.toBePositiveInfinity(), + var matcher = jasmineUnderTest.matchers.toBePositiveInfinity({ + pp: jasmineUnderTest.makePrettyPrinter() + }), result = matcher.compare(0); expect(result.message()).toEqual("Expected 0 to be Infinity.") diff --git a/spec/core/matchers/toBeSpec.js b/spec/core/matchers/toBeSpec.js index 8e27b992..d95f2b49 100644 --- a/spec/core/matchers/toBeSpec.js +++ b/spec/core/matchers/toBeSpec.js @@ -9,7 +9,7 @@ describe("toBe", function() { }); it("passes with a custom message when expected is an array", function() { - var util = new jasmineUnderTest.MatchersUtil(), + var util = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.matchers.toBe(util), result, array = [1]; @@ -20,7 +20,7 @@ describe("toBe", function() { }); it("passes with a custom message when expected is an object", function() { - var util = new jasmineUnderTest.MatchersUtil(), + var util = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.matchers.toBe(util), result, obj = {foo: "bar"}; @@ -41,7 +41,7 @@ describe("toBe", function() { }); it("fails with a custom message when expected is an array", function() { - var util = new jasmineUnderTest.MatchersUtil(), + var util = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.matchers.toBe(util), result; @@ -51,7 +51,7 @@ describe("toBe", function() { }); it("fails with a custom message when expected is an object", function() { - var util = new jasmineUnderTest.MatchersUtil(), + var util = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.matchers.toBe(util), result; diff --git a/spec/core/matchers/toEqualSpec.js b/spec/core/matchers/toEqualSpec.js index 2bd2f077..5702f7bb 100644 --- a/spec/core/matchers/toEqualSpec.js +++ b/spec/core/matchers/toEqualSpec.js @@ -2,7 +2,9 @@ describe("toEqual", function() { "use strict"; function compareEquals(actual, expected) { - var util = new jasmineUnderTest.MatchersUtil(), + var util = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.matchers.toEqual(util); var result = matcher.compare(actual, expected); @@ -103,8 +105,6 @@ describe("toEqual", function() { " g: 3\n" + "Expected $.x not to have properties\n" + " f: 4"; - - expect(compareEquals(actual, expected).message).toEqual(message); }); it("reports extra and missing properties of the root-level object", function() { diff --git a/spec/core/matchers/toHaveBeenCalledBeforeSpec.js b/spec/core/matchers/toHaveBeenCalledBeforeSpec.js index f2e89c2f..b47514d5 100644 --- a/spec/core/matchers/toHaveBeenCalledBeforeSpec.js +++ b/spec/core/matchers/toHaveBeenCalledBeforeSpec.js @@ -1,6 +1,8 @@ describe("toHaveBeenCalledBefore", function() { it("throws an exception when the actual is not a spy", function() { - var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), + var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore({ + pp: jasmineUnderTest.makePrettyPrinter() + }), fn = function() {}, secondSpy = new jasmineUnderTest.Env().createSpy('second spy'); @@ -8,7 +10,9 @@ describe("toHaveBeenCalledBefore", function() { }); it("throws an exception when the expected is not a spy", function() { - var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), + var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore({ + pp: jasmineUnderTest.makePrettyPrinter() + }), firstSpy = new jasmineUnderTest.Env().createSpy('first spy'), fn = function() {}; diff --git a/spec/core/matchers/toHaveBeenCalledSpec.js b/spec/core/matchers/toHaveBeenCalledSpec.js index b14116f0..4f7e1efb 100644 --- a/spec/core/matchers/toHaveBeenCalledSpec.js +++ b/spec/core/matchers/toHaveBeenCalledSpec.js @@ -21,7 +21,9 @@ describe("toHaveBeenCalled", function() { }); it("throws an exception when the actual is not a spy", function() { - var matcher = jasmineUnderTest.matchers.toHaveBeenCalled(), + var matcher = jasmineUnderTest.matchers.toHaveBeenCalled({ + pp: jasmineUnderTest.makePrettyPrinter() + }), fn = function() {}; expect(function() { matcher.compare(fn) }).toThrowError(Error, /Expected a spy, but got Function./); diff --git a/spec/core/matchers/toHaveBeenCalledTimesSpec.js b/spec/core/matchers/toHaveBeenCalledTimesSpec.js index 62778fbd..9102b4b7 100644 --- a/spec/core/matchers/toHaveBeenCalledTimesSpec.js +++ b/spec/core/matchers/toHaveBeenCalledTimesSpec.js @@ -49,7 +49,9 @@ describe("toHaveBeenCalledTimes", function() { }); it("throws an exception when the actual is not a spy", function() { - var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), + var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes({ + pp: jasmineUnderTest.makePrettyPrinter() + }), fn = function() {}; expect(function() { diff --git a/spec/core/matchers/toHaveBeenCalledWithSpec.js b/spec/core/matchers/toHaveBeenCalledWithSpec.js index a57bc4a4..852dd837 100644 --- a/spec/core/matchers/toHaveBeenCalledWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledWithSpec.js @@ -2,7 +2,8 @@ describe("toHaveBeenCalledWith", function() { it("passes when the actual was called with matching parameters", function() { var util = { - contains: jasmine.createSpy('delegated-contains').and.returnValue(true) + contains: jasmine.createSpy('delegated-contains').and.returnValue(true), + pp: jasmineUnderTest.makePrettyPrinter() }, matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util), calledSpy = new jasmineUnderTest.Env().createSpy('called-spy'), @@ -29,7 +30,8 @@ describe("toHaveBeenCalledWith", function() { it("fails when the actual was not called", function() { var util = { - contains: jasmine.createSpy('delegated-contains').and.returnValue(false) + contains: jasmine.createSpy('delegated-contains').and.returnValue(false), + pp: jasmineUnderTest.makePrettyPrinter() }, matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util), uncalledSpy = new jasmineUnderTest.Env().createSpy('uncalled spy'), @@ -41,7 +43,7 @@ describe("toHaveBeenCalledWith", function() { }); it("fails when the actual was called with different parameters", function() { - var util = new jasmineUnderTest.MatchersUtil(), + var util = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util), calledSpy = new jasmineUnderTest.Env().createSpy('called spy'), result; @@ -71,8 +73,11 @@ describe("toHaveBeenCalledWith", function() { }); it("throws an exception when the actual is not a spy", function() { - var matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(), - fn = function() {}; + var matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + fn = function () { + }; expect(function() { matcher.compare(fn) }).toThrowError(/Expected a spy, but got Function./); }); diff --git a/spec/core/matchers/toHaveClassSpec.js b/spec/core/matchers/toHaveClassSpec.js index 109babbb..5f593abc 100644 --- a/spec/core/matchers/toHaveClassSpec.js +++ b/spec/core/matchers/toHaveClassSpec.js @@ -27,7 +27,9 @@ describe('toHaveClass', function() { }); it('throws an exception when actual is not a DOM element', function() { - var matcher = jasmineUnderTest.matchers.toHaveClass(); + var matcher = jasmineUnderTest.matchers.toHaveClass({ + pp: jasmineUnderTest.makePrettyPrinter() + }); expect(function() { matcher.compare('x', 'foo'); diff --git a/spec/core/matchers/toThrowErrorSpec.js b/spec/core/matchers/toThrowErrorSpec.js index 148997ce..8070719c 100644 --- a/spec/core/matchers/toThrowErrorSpec.js +++ b/spec/core/matchers/toThrowErrorSpec.js @@ -54,7 +54,9 @@ describe("toThrowError", function() { }); it("fails if thrown is not an instanceof Error", function() { - var matcher = jasmineUnderTest.matchers.toThrowError(), + var matcher = jasmineUnderTest.matchers.toThrowError({ + pp: jasmineUnderTest.makePrettyPrinter() + }), fn = function() { throw 4; }, @@ -103,7 +105,9 @@ describe("toThrowError", function() { }); it("fails with the correct message if thrown is a falsy value", function() { - var matcher = jasmineUnderTest.matchers.toThrowError(), + var matcher = jasmineUnderTest.matchers.toThrowError({ + pp: jasmineUnderTest.makePrettyPrinter() + }), fn = function() { throw undefined; }, @@ -128,7 +132,9 @@ describe("toThrowError", function() { }); it("passes if thrown is an Error and the expected is the same message", function() { - var matcher = jasmineUnderTest.matchers.toThrowError(), + var matcher = jasmineUnderTest.matchers.toThrowError({ + pp: jasmineUnderTest.makePrettyPrinter() + }), fn = function() { throw new Error("foo"); }, @@ -141,7 +147,9 @@ describe("toThrowError", function() { }); it("fails if thrown is an Error and the expected is not the same message", function() { - var matcher = jasmineUnderTest.matchers.toThrowError(), + var matcher = jasmineUnderTest.matchers.toThrowError({ + pp: jasmineUnderTest.makePrettyPrinter() + }), fn = function() { throw new Error("foo"); }, @@ -154,7 +162,9 @@ describe("toThrowError", function() { }); it("passes if thrown is an Error and the expected is a RegExp that matches the message", function() { - var matcher = jasmineUnderTest.matchers.toThrowError(), + var matcher = jasmineUnderTest.matchers.toThrowError({ + pp: jasmineUnderTest.makePrettyPrinter() + }), fn = function() { throw new Error("a long message"); }, @@ -167,7 +177,9 @@ describe("toThrowError", function() { }); it("fails if thrown is an Error and the expected is a RegExp that does not match the message", function() { - var matcher = jasmineUnderTest.matchers.toThrowError(), + var matcher = jasmineUnderTest.matchers.toThrowError({ + pp: jasmineUnderTest.makePrettyPrinter() + }), fn = function() { throw new Error("a long message"); }, @@ -232,9 +244,10 @@ describe("toThrowError", function() { it("passes if thrown is a type of Error and it is equal to the expected Error and message", function() { var util = { - equals: jasmine.createSpy('delegated-equal').and.returnValue(true) + equals: jasmine.createSpy('delegated-equal').and.returnValue(true), + pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrowError(), + matcher = jasmineUnderTest.matchers.toThrowError(util), fn = function() { throw new TypeError("foo"); }, @@ -248,9 +261,10 @@ describe("toThrowError", function() { it("passes if thrown is a custom error that takes arguments and it is equal to the expected custom error and message", function() { var util = { - equals: jasmine.createSpy('delegated-equal').and.returnValue(true) + equals: jasmine.createSpy('delegated-equal').and.returnValue(true), + pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrowError(), + matcher = jasmineUnderTest.matchers.toThrowError(util), CustomError = function CustomError(arg) { this.message = arg.message }, fn = function() { throw new CustomError({message: "foo"}); @@ -267,9 +281,10 @@ describe("toThrowError", function() { it("fails if thrown is a type of Error and the expected is a different Error", function() { var util = { - equals: jasmine.createSpy('delegated-equal').and.returnValue(false) + equals: jasmine.createSpy('delegated-equal').and.returnValue(false), + pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrowError(), + matcher = jasmineUnderTest.matchers.toThrowError(util), fn = function() { throw new TypeError("foo"); }, @@ -283,9 +298,10 @@ describe("toThrowError", function() { it("passes if thrown is a type of Error and has the same type as the expected Error and the message matches the expected message", function() { var util = { - equals: jasmine.createSpy('delegated-equal').and.returnValue(true) + equals: jasmine.createSpy('delegated-equal').and.returnValue(true), + pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrowError(), + matcher = jasmineUnderTest.matchers.toThrowError(util), fn = function() { throw new TypeError("foo"); }, @@ -299,9 +315,10 @@ describe("toThrowError", function() { it("fails if thrown is a type of Error and the expected is a different Error", function() { var util = { - equals: jasmine.createSpy('delegated-equal').and.returnValue(false) + equals: jasmine.createSpy('delegated-equal').and.returnValue(false), + pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrowError(), + matcher = jasmineUnderTest.matchers.toThrowError(util), fn = function() { throw new TypeError("foo"); }, diff --git a/spec/core/matchers/toThrowMatchingSpec.js b/spec/core/matchers/toThrowMatchingSpec.js index 1987b73d..507683b0 100644 --- a/spec/core/matchers/toThrowMatchingSpec.js +++ b/spec/core/matchers/toThrowMatchingSpec.js @@ -32,7 +32,9 @@ describe("toThrowMatching", function() { }); it("fails with the correct message if thrown is a falsy value", function() { - var matcher = jasmineUnderTest.matchers.toThrowMatching(), + var matcher = jasmineUnderTest.matchers.toThrowMatching({ + pp: jasmineUnderTest.makePrettyPrinter() + }), fn = function() { throw undefined; }, @@ -58,8 +60,10 @@ describe("toThrowMatching", function() { }); it("fails if the argument is a function that returns false when called with the error", function() { - var matcher = jasmineUnderTest.matchers.toThrowMatching(), - predicate = function(e) { return e.message === "oh no" }, + var matcher = jasmineUnderTest.matchers.toThrowMatching({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + predicate = function(e) { return e.message === "oh no" }, fn = function() { throw new TypeError("nope"); }, diff --git a/spec/core/matchers/toThrowSpec.js b/spec/core/matchers/toThrowSpec.js index 03e11b38..979ddc1d 100644 --- a/spec/core/matchers/toThrowSpec.js +++ b/spec/core/matchers/toThrowSpec.js @@ -24,7 +24,8 @@ describe("toThrow", function() { it("passes if it throws but there is no expected", function() { var util = { - equals: jasmine.createSpy('delegated-equal').and.returnValue(true) + equals: jasmine.createSpy('delegated-equal').and.returnValue(true), + pp: jasmineUnderTest.makePrettyPrinter() }, matcher = jasmineUnderTest.matchers.toThrow(util), fn = function() { @@ -39,7 +40,9 @@ describe("toThrow", function() { }); it("passes even if what is thrown is falsy", function() { - var matcher = jasmineUnderTest.matchers.toThrow(), + var matcher = jasmineUnderTest.matchers.toThrow({ + pp: jasmineUnderTest.makePrettyPrinter() + }), fn = function() { throw undefined; }, @@ -52,7 +55,8 @@ describe("toThrow", function() { it("passes if what is thrown is equivalent to what is expected", function() { var util = { - equals: jasmine.createSpy('delegated-equal').and.returnValue(true) + equals: jasmine.createSpy('delegated-equal').and.returnValue(true), + pp: jasmineUnderTest.makePrettyPrinter() }, matcher = jasmineUnderTest.matchers.toThrow(util), fn = function() { @@ -68,7 +72,8 @@ describe("toThrow", function() { it("fails if what is thrown is not equivalent to what is expected", function() { var util = { - equals: jasmine.createSpy('delegated-equal').and.returnValue(false) + equals: jasmine.createSpy('delegated-equal').and.returnValue(false), + pp: jasmineUnderTest.makePrettyPrinter() }, matcher = jasmineUnderTest.matchers.toThrow(util), fn = function() { @@ -84,7 +89,8 @@ describe("toThrow", function() { it("fails if what is thrown is not equivalent to undefined", function() { var util = { - equals: jasmine.createSpy('delegated-equal').and.returnValue(false) + equals: jasmine.createSpy('delegated-equal').and.returnValue(false), + pp: jasmineUnderTest.makePrettyPrinter() }, matcher = jasmineUnderTest.matchers.toThrow(util), fn = function() { diff --git a/spec/html/PrettyPrintHtmlSpec.js b/spec/html/PrettyPrintHtmlSpec.js index 77bb2bac..fd364d9e 100644 --- a/spec/html/PrettyPrintHtmlSpec.js +++ b/spec/html/PrettyPrintHtmlSpec.js @@ -1,43 +1,46 @@ -describe('jasmineUnderTest.pp (HTML Dependent)', function() { +describe('PrettyPrinter (HTML Dependent)', function() { it('should stringify non-element HTML nodes properly', function() { var sampleNode = document.createTextNode(''); - expect(jasmineUnderTest.pp(sampleNode)).toEqual('HTMLNode'); - expect(jasmineUnderTest.pp({ foo: sampleNode })).toEqual( - 'Object({ foo: HTMLNode })' - ); + var pp = jasmineUnderTest.makePrettyPrinter(); + expect(pp(sampleNode)).toEqual('HTMLNode'); + expect(pp({ foo: sampleNode })).toEqual('Object({ foo: HTMLNode })'); }); it('should stringify empty HTML elements as their opening tags', function() { var simple = document.createElement('div'); + var pp = jasmineUnderTest.makePrettyPrinter(); simple.className = 'foo'; - expect(jasmineUnderTest.pp(simple)).toEqual('
'); + expect(pp(simple)).toEqual('
'); }); it('should stringify non-empty HTML elements as tags with placeholders', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var nonEmpty = document.createElement('div'); nonEmpty.className = 'foo'; nonEmpty.innerHTML = '

Irrelevant

'; - expect(jasmineUnderTest.pp(nonEmpty)).toEqual('
...
'); + expect(pp(nonEmpty)).toEqual('
...
'); }); it("should print Firefox's wrapped native objects correctly", function() { if (jasmine.getEnv().firefoxVersion) { + var pp = jasmineUnderTest.makePrettyPrinter(); try { new CustomEvent(); } catch (e) { var err = e; } // Different versions of FF produce different error messages. - expect(jasmineUnderTest.pp(err)).toMatch( + expect(pp(err)).toMatch( /Not enough arguments|CustomEvent requires at least 1 argument, but only 0 were passed/ ); } }); it('should stringify HTML element with text and attributes', function() { + var pp = jasmineUnderTest.makePrettyPrinter(); var el = document.createElement('div'); el.setAttribute('things', 'foo'); el.innerHTML = 'foo'; - expect(jasmineUnderTest.pp(el)).toEqual('
...
'); + expect(pp(el)).toEqual('
...
'); }); }); diff --git a/src/core/Env.js b/src/core/Env.js index e3c5f5c6..42ba2756 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -309,12 +309,25 @@ getJasmineRequireObj().Env = function(j$) { return 'suite' + nextSuiteId++; }; + var makePrettyPrinter = function() { + return j$.makePrettyPrinter(); + }; + + var makeMatchersUtil = function() { + var customEqualityTesters = + runnableResources[currentRunnable().id].customEqualityTesters; + return new j$.MatchersUtil({ + customTesters: customEqualityTesters, + pp: makePrettyPrinter() + }); + }; + var expectationFactory = function(actual, spec) { var customEqualityTesters = runnableResources[spec.id].customEqualityTesters; return j$.Expectation.factory({ - util: new j$.MatchersUtil({ customTesters: customEqualityTesters }), + util: makeMatchersUtil(), customEqualityTesters: customEqualityTesters, customMatchers: runnableResources[spec.id].customMatchers, actual: actual, @@ -327,11 +340,8 @@ getJasmineRequireObj().Env = function(j$) { }; var asyncExpectationFactory = function(actual, spec) { - var customEqualityTesters = - runnableResources[spec.id].customEqualityTesters; - return j$.Expectation.asyncFactory({ - util: new j$.MatchersUtil({ customTesters: customEqualityTesters }), + util: makeMatchersUtil(), customEqualityTesters: runnableResources[spec.id].customEqualityTesters, customAsyncMatchers: runnableResources[spec.id].customAsyncMatchers, actual: actual, @@ -1143,7 +1153,7 @@ getJasmineRequireObj().Env = function(j$) { message += error; } else { // pretty print all kind of objects. This includes arrays. - message += j$.pp(error); + message += makePrettyPrinter()(error); } } diff --git a/src/core/Expectation.js b/src/core/Expectation.js index add788cb..ba079532 100644 --- a/src/core/Expectation.js +++ b/src/core/Expectation.js @@ -141,7 +141,7 @@ getJasmineRequireObj().Expectation = function(j$) { args = args.slice(); args.unshift(true); args.unshift(matcherName); - return util.buildFailureMessage.apply(null, args); + return util.buildFailureMessage.apply(util, args); } function negate(result) { diff --git a/src/core/Expector.js b/src/core/Expector.js index 78db5c1b..18e8784e 100644 --- a/src/core/Expector.js +++ b/src/core/Expector.js @@ -44,7 +44,7 @@ getJasmineRequireObj().Expector = function(j$) { var args = self.args.slice(); args.unshift(false); args.unshift(self.matcherName); - return self.util.buildFailureMessage.apply(null, args); + return self.util.buildFailureMessage.apply(self.util, args); } else if (j$.isFunction_(result.message)) { return result.message(); } else { diff --git a/src/core/PrettyPrinter.js b/src/core/PrettyPrinter.js index e01afc80..14091e5e 100644 --- a/src/core/PrettyPrinter.js +++ b/src/core/PrettyPrinter.js @@ -1,5 +1,5 @@ -getJasmineRequireObj().pp = function(j$) { - function PrettyPrinter() { +getJasmineRequireObj().makePrettyPrinter = function(j$) { + function SinglePrettyPrintRun() { this.ppNestLevel_ = 0; this.seen = []; this.length = 0; @@ -21,7 +21,7 @@ getJasmineRequireObj().pp = function(j$) { } } - PrettyPrinter.prototype.format = function(value) { + SinglePrettyPrintRun.prototype.format = function(value) { this.ppNestLevel_++; try { if (j$.util.isUndefined(value)) { @@ -95,7 +95,7 @@ getJasmineRequireObj().pp = function(j$) { } }; - PrettyPrinter.prototype.iterateObject = function(obj, fn) { + SinglePrettyPrintRun.prototype.iterateObject = function(obj, fn) { var objKeys = keys(obj, j$.isArray_(obj)); var isGetter = function isGetter(prop) {}; @@ -114,15 +114,15 @@ getJasmineRequireObj().pp = function(j$) { return objKeys.length > length; }; - PrettyPrinter.prototype.emitScalar = function(value) { + SinglePrettyPrintRun.prototype.emitScalar = function(value) { this.append(value); }; - PrettyPrinter.prototype.emitString = function(value) { + SinglePrettyPrintRun.prototype.emitString = function(value) { this.append("'" + value + "'"); }; - PrettyPrinter.prototype.emitArray = function(array) { + SinglePrettyPrintRun.prototype.emitArray = function(array) { if (this.ppNestLevel_ > j$.MAX_PRETTY_PRINT_DEPTH) { this.append('Array'); return; @@ -158,7 +158,7 @@ getJasmineRequireObj().pp = function(j$) { this.append(' ]'); }; - PrettyPrinter.prototype.emitSet = function(set) { + SinglePrettyPrintRun.prototype.emitSet = function(set) { if (this.ppNestLevel_ > j$.MAX_PRETTY_PRINT_DEPTH) { this.append('Set'); return; @@ -183,7 +183,7 @@ getJasmineRequireObj().pp = function(j$) { this.append(' )'); }; - PrettyPrinter.prototype.emitMap = function(map) { + SinglePrettyPrintRun.prototype.emitMap = function(map) { if (this.ppNestLevel_ > j$.MAX_PRETTY_PRINT_DEPTH) { this.append('Map'); return; @@ -208,7 +208,7 @@ getJasmineRequireObj().pp = function(j$) { this.append(' )'); }; - PrettyPrinter.prototype.emitObject = function(obj) { + SinglePrettyPrintRun.prototype.emitObject = function(obj) { var ctor = obj.constructor, constructorName; @@ -244,7 +244,7 @@ getJasmineRequireObj().pp = function(j$) { this.append(' })'); }; - PrettyPrinter.prototype.emitTypedArray = function(arr) { + SinglePrettyPrintRun.prototype.emitTypedArray = function(arr) { var constructorName = j$.fnNameFor(arr.constructor), limitedArray = Array.prototype.slice.call( arr, @@ -260,7 +260,7 @@ getJasmineRequireObj().pp = function(j$) { this.append(constructorName + ' [ ' + itemsString + ' ]'); }; - PrettyPrinter.prototype.emitDomElement = function(el) { + SinglePrettyPrintRun.prototype.emitDomElement = function(el) { var tagName = el.tagName.toLowerCase(), attrs = el.attributes, i, @@ -286,7 +286,11 @@ getJasmineRequireObj().pp = function(j$) { this.append(out); }; - PrettyPrinter.prototype.formatProperty = function(obj, property, isGetter) { + SinglePrettyPrintRun.prototype.formatProperty = function( + obj, + property, + isGetter + ) { this.append(property); this.append(': '); if (isGetter) { @@ -296,7 +300,7 @@ getJasmineRequireObj().pp = function(j$) { } }; - PrettyPrinter.prototype.append = function(value) { + SinglePrettyPrintRun.prototype.append = function(value) { // This check protects us from the rare case where an object has overriden // `toString()` with an invalid implementation (returning a non-string). if (typeof value !== 'string') { @@ -360,9 +364,12 @@ getJasmineRequireObj().pp = function(j$) { return extraKeys; } - return function(value) { - var prettyPrinter = new PrettyPrinter(); - prettyPrinter.format(value); - return prettyPrinter.stringParts.join(''); + + return function() { + return function(value) { + var prettyPrinter = new SinglePrettyPrintRun(); + prettyPrinter.format(value); + return prettyPrinter.stringParts.join(''); + }; }; }; diff --git a/src/core/Spy.js b/src/core/Spy.js index 3d4aca21..7160f5d5 100644 --- a/src/core/Spy.js +++ b/src/core/Spy.js @@ -7,7 +7,10 @@ getJasmineRequireObj().Spy = function(j$) { }; })(); - var matchersUtil = new j$.MatchersUtil(); + var matchersUtil = new j$.MatchersUtil({ + customTesters: [], + pp: j$.makePrettyPrinter() + }); /** * _Note:_ Do not construct this directly, use {@link spyOn}, {@link spyOnProperty}, {@link jasmine.createSpy}, or {@link jasmine.createSpyObj} diff --git a/src/core/matchers/async/toBeRejectedWith.js b/src/core/matchers/async/toBeRejectedWith.js index 621daf0b..6c0af904 100644 --- a/src/core/matchers/async/toBeRejectedWith.js +++ b/src/core/matchers/async/toBeRejectedWith.js @@ -11,7 +11,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { * @example * return expectAsync(aPromise).toBeRejectedWith({prop: 'value'}); */ - return function toBeRejectedWith(util) { + return function toBeRejectedWith(matchersUtil) { return { compare: function(actualPromise, expectedValue) { if (!j$.isPromiseLike(actualPromise)) { @@ -21,7 +21,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { function prefix(passed) { return 'Expected a promise ' + (passed ? 'not ' : '') + - 'to be rejected with ' + j$.pp(expectedValue); + 'to be rejected with ' + matchersUtil.pp(expectedValue); } return actualPromise.then( @@ -32,7 +32,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { }; }, function(actualValue) { - if (util.equals(actualValue, expectedValue)) { + if (matchersUtil.equals(actualValue, expectedValue)) { return { pass: true, message: prefix(true) + '.' @@ -40,7 +40,7 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { } else { return { pass: false, - message: prefix(false) + ' but it was rejected with ' + j$.pp(actualValue) + '.' + message: prefix(false) + ' but it was rejected with ' + matchersUtil.pp(actualValue) + '.' }; } } diff --git a/src/core/matchers/async/toBeRejectedWithError.js b/src/core/matchers/async/toBeRejectedWithError.js index 8a578a60..203cd863 100644 --- a/src/core/matchers/async/toBeRejectedWithError.js +++ b/src/core/matchers/async/toBeRejectedWithError.js @@ -14,14 +14,14 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { * await expectAsync(aPromise).toBeRejectedWithError('Error message'); * return expectAsync(aPromise).toBeRejectedWithError(/Error message/); */ - return function toBeRejectedWithError() { + return function toBeRejectedWithError(matchersUtil) { return { compare: function(actualPromise, arg1, arg2) { if (!j$.isPromiseLike(actualPromise)) { throw new Error('Expected toBeRejectedWithError to be called on a promise.'); } - var expected = getExpectedFromArgs(arg1, arg2); + var expected = getExpectedFromArgs(arg1, arg2, matchersUtil); return actualPromise.then( function() { @@ -30,15 +30,15 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { message: 'Expected a promise to be rejected but it was resolved.' }; }, - function(actualValue) { return matchError(actualValue, expected); } + function(actualValue) { return matchError(actualValue, expected, matchersUtil); } ); } }; }; - function matchError(actual, expected) { + function matchError(actual, expected, matchersUtil) { if (!j$.isError_(actual)) { - return fail(expected, 'rejected with ' + j$.pp(actual)); + return fail(expected, 'rejected with ' + matchersUtil.pp(actual)); } if (!(actual instanceof expected.error)) { @@ -55,7 +55,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return pass(expected); } - return fail(expected, 'rejected with ' + j$.pp(actual)); + return fail(expected, 'rejected with ' + matchersUtil.pp(actual)); } function pass(expected) { @@ -73,7 +73,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { } - function getExpectedFromArgs(arg1, arg2) { + function getExpectedFromArgs(arg1, arg2, matchersUtil) { var error, message; if (isErrorConstructor(arg1)) { @@ -87,7 +87,7 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return { error: error, message: message, - printValue: j$.fnNameFor(error) + (typeof message === 'undefined' ? '' : ': ' + j$.pp(message)) + printValue: j$.fnNameFor(error) + (typeof message === 'undefined' ? '' : ': ' + matchersUtil.pp(message)) }; } diff --git a/src/core/matchers/async/toBeResolvedTo.js b/src/core/matchers/async/toBeResolvedTo.js index a0295c8a..61abb9f2 100644 --- a/src/core/matchers/async/toBeResolvedTo.js +++ b/src/core/matchers/async/toBeResolvedTo.js @@ -11,7 +11,7 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { * @example * return expectAsync(aPromise).toBeResolvedTo({prop: 'value'}); */ - return function toBeResolvedTo(util) { + return function toBeResolvedTo(matchersUtil) { return { compare: function(actualPromise, expectedValue) { if (!j$.isPromiseLike(actualPromise)) { @@ -21,12 +21,12 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { function prefix(passed) { return 'Expected a promise ' + (passed ? 'not ' : '') + - 'to be resolved to ' + j$.pp(expectedValue); + 'to be resolved to ' + matchersUtil.pp(expectedValue); } return actualPromise.then( function(actualValue) { - if (util.equals(actualValue, expectedValue)) { + if (matchersUtil.equals(actualValue, expectedValue)) { return { pass: true, message: prefix(true) + '.' @@ -34,7 +34,7 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { } else { return { pass: false, - message: prefix(false) + ' but it was resolved to ' + j$.pp(actualValue) + '.' + message: prefix(false) + ' but it was resolved to ' + matchersUtil.pp(actualValue) + '.' }; } }, diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index 1aa496f4..8a0eb75c 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -1,14 +1,11 @@ getJasmineRequireObj().MatchersUtil = function(j$) { - // TODO: what to do about jasmine.pp not being inject? move to JSON.stringify? gut PrettyPrinter? + // TODO: convert all uses of j$.pp to use the injected pp function MatchersUtil(options) { options = options || {}; this.customTesters_ = options.customTesters || []; - - if (!j$.isArray_(this.customTesters_)) { - throw new Error("MatchersUtil requires custom equality testers"); - } - } + this.pp = options.pp || function() {}; + }; MatchersUtil.prototype.contains = function(haystack, needle, customTesters) { if (j$.isSet(haystack)) { @@ -30,6 +27,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { }; MatchersUtil.prototype.buildFailureMessage = function() { + var self = this; var args = Array.prototype.slice.call(arguments, 0), matcherName = args[0], isNot = args[1], @@ -38,7 +36,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { return ' ' + s.toLowerCase(); }); var message = 'Expected ' + - j$.pp(actual) + + self.pp(actual) + (isNot ? ' not ' : ' ') + englishyPredicate; @@ -240,7 +238,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { for (i = 0; i < aLength || i < bLength; i++) { diffBuilder.withPath(i, function() { if (i >= bLength) { - diffBuilder.record(a[i], void 0, actualArrayIsLongerFormatter); + diffBuilder.record(a[i], void 0, actualArrayIsLongerFormatter.bind(null, self.pp)); result = false; } else { result = self.eq_(i < aLength ? a[i] : void 0, i < bLength ? b[i] : void 0, aStack, bStack, customTesters, diffBuilder) && result; @@ -357,7 +355,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { a instanceof aCtor && b instanceof bCtor && !(aCtor instanceof aCtor && bCtor instanceof bCtor)) { - diffBuilder.record(a, b, constructorsAreDifferentFormatter); + diffBuilder.record(a, b, constructorsAreDifferentFormatter.bind(null, this.pp)); return false; } } @@ -368,7 +366,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // Ensure that both objects contain the same number of properties before comparing deep equality. if (keys(b, className == '[object Array]').length !== size) { - diffBuilder.record(a, b, objectKeysAreDifferentFormatter); + diffBuilder.record(a, b, objectKeysAreDifferentFormatter.bind(null, this.pp)); return false; } @@ -376,7 +374,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { key = aKeys[i]; // Deep compare each member if (!j$.util.has(b, key)) { - diffBuilder.record(a, b, objectKeysAreDifferentFormatter); + diffBuilder.record(a, b, objectKeysAreDifferentFormatter.bind(null, this.pp)); result = false; continue; } @@ -433,11 +431,11 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return typeof obj === 'function'; } - function objectKeysAreDifferentFormatter(actual, expected, path) { + function objectKeysAreDifferentFormatter(pp, actual, expected, path) { var missingProperties = j$.util.objectDifference(expected, actual), extraProperties = j$.util.objectDifference(actual, expected), - missingPropertiesMessage = formatKeyValuePairs(missingProperties), - extraPropertiesMessage = formatKeyValuePairs(extraProperties), + missingPropertiesMessage = formatKeyValuePairs(pp, missingProperties), + extraPropertiesMessage = formatKeyValuePairs(pp, extraProperties), messages = []; if (!path.depth()) { @@ -455,7 +453,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return messages.join('\n'); } - function constructorsAreDifferentFormatter(actual, expected, path) { + function constructorsAreDifferentFormatter(pp, actual, expected, path) { if (!path.depth()) { path = 'object'; } @@ -463,20 +461,20 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return 'Expected ' + path + ' to be a kind of ' + j$.fnNameFor(expected.constructor) + - ', but was ' + j$.pp(actual) + '.'; + ', but was ' + pp(actual) + '.'; } - function actualArrayIsLongerFormatter(actual, expected, path) { + function actualArrayIsLongerFormatter(pp, actual, expected, path) { return 'Unexpected ' + path + (path.depth() ? ' = ' : '') + - j$.pp(actual) + + pp(actual) + ' in array.'; } - function formatKeyValuePairs(obj) { + function formatKeyValuePairs(pp, obj) { var formatted = ''; for (var key in obj) { - formatted += '\n ' + key + ': ' + j$.pp(obj[key]); + formatted += '\n ' + key + ': ' + pp(obj[key]); } return formatted; } diff --git a/src/core/matchers/toBeInstanceOf.js b/src/core/matchers/toBeInstanceOf.js index cc0a0679..609b9301 100644 --- a/src/core/matchers/toBeInstanceOf.js +++ b/src/core/matchers/toBeInstanceOf.js @@ -12,11 +12,11 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { * expect(3).toBeInstanceOf(Number); * expect(new Error()).toBeInstanceOf(Error); */ - function toBeInstanceOf() { + function toBeInstanceOf(matchersUtil) { return { compare: function(actual, expected) { - var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : j$.pp(actual), - expectedType = expected ? j$.fnNameFor(expected) : j$.pp(expected), + var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : matchersUtil.pp(actual), + expectedType = expected ? j$.fnNameFor(expected) : matchersUtil.pp(expected), expectedMatcher, pass; diff --git a/src/core/matchers/toBeNaN.js b/src/core/matchers/toBeNaN.js index dcff00a1..7adf5b34 100644 --- a/src/core/matchers/toBeNaN.js +++ b/src/core/matchers/toBeNaN.js @@ -7,7 +7,7 @@ getJasmineRequireObj().toBeNaN = function(j$) { * @example * expect(thing).toBeNaN(); */ - function toBeNaN() { + function toBeNaN(matchersUtil) { return { compare: function(actual) { var result = { @@ -17,7 +17,7 @@ getJasmineRequireObj().toBeNaN = function(j$) { if (result.pass) { result.message = 'Expected actual not to be NaN.'; } else { - result.message = function() { return 'Expected ' + j$.pp(actual) + ' to be NaN.'; }; + result.message = function() { return 'Expected ' + matchersUtil.pp(actual) + ' to be NaN.'; }; } return result; diff --git a/src/core/matchers/toBeNegativeInfinity.js b/src/core/matchers/toBeNegativeInfinity.js index ce60a62d..fe2de803 100644 --- a/src/core/matchers/toBeNegativeInfinity.js +++ b/src/core/matchers/toBeNegativeInfinity.js @@ -7,7 +7,7 @@ getJasmineRequireObj().toBeNegativeInfinity = function(j$) { * @example * expect(thing).toBeNegativeInfinity(); */ - function toBeNegativeInfinity() { + function toBeNegativeInfinity(matchersUtil) { return { compare: function(actual) { var result = { @@ -17,7 +17,7 @@ getJasmineRequireObj().toBeNegativeInfinity = function(j$) { if (result.pass) { result.message = 'Expected actual not to be -Infinity.'; } else { - result.message = function() { return 'Expected ' + j$.pp(actual) + ' to be -Infinity.'; }; + result.message = function() { return 'Expected ' + matchersUtil.pp(actual) + ' to be -Infinity.'; }; } return result; diff --git a/src/core/matchers/toBePositiveInfinity.js b/src/core/matchers/toBePositiveInfinity.js index c1c41f8e..39cb5e34 100644 --- a/src/core/matchers/toBePositiveInfinity.js +++ b/src/core/matchers/toBePositiveInfinity.js @@ -7,7 +7,7 @@ getJasmineRequireObj().toBePositiveInfinity = function(j$) { * @example * expect(thing).toBePositiveInfinity(); */ - function toBePositiveInfinity() { + function toBePositiveInfinity(matchersUtil) { return { compare: function(actual) { var result = { @@ -17,7 +17,7 @@ getJasmineRequireObj().toBePositiveInfinity = function(j$) { if (result.pass) { result.message = 'Expected actual not to be Infinity.'; } else { - result.message = function() { return 'Expected ' + j$.pp(actual) + ' to be Infinity.'; }; + result.message = function() { return 'Expected ' + matchersUtil.pp(actual) + ' to be Infinity.'; }; } return result; diff --git a/src/core/matchers/toHaveBeenCalled.js b/src/core/matchers/toHaveBeenCalled.js index bf1df2ed..3e6d2601 100644 --- a/src/core/matchers/toHaveBeenCalled.js +++ b/src/core/matchers/toHaveBeenCalled.js @@ -11,13 +11,13 @@ getJasmineRequireObj().toHaveBeenCalled = function(j$) { * expect(mySpy).toHaveBeenCalled(); * expect(mySpy).not.toHaveBeenCalled(); */ - function toHaveBeenCalled() { + function toHaveBeenCalled(matchersUtil) { return { compare: function(actual) { var result = {}; if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); + throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(actual) + '.')); } if (arguments.length > 1) { diff --git a/src/core/matchers/toHaveBeenCalledBefore.js b/src/core/matchers/toHaveBeenCalledBefore.js index 5c9b7063..293e73ff 100644 --- a/src/core/matchers/toHaveBeenCalledBefore.js +++ b/src/core/matchers/toHaveBeenCalledBefore.js @@ -11,14 +11,14 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { * @example * expect(mySpy).toHaveBeenCalledBefore(otherSpy); */ - function toHaveBeenCalledBefore() { + function toHaveBeenCalledBefore(matchersUtil) { return { compare: function(firstSpy, latterSpy) { if (!j$.isSpy(firstSpy)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(firstSpy) + '.')); + throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(firstSpy) + '.')); } if (!j$.isSpy(latterSpy)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(latterSpy) + '.')); + throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(latterSpy) + '.')); } var result = { pass: false }; diff --git a/src/core/matchers/toHaveBeenCalledTimes.js b/src/core/matchers/toHaveBeenCalledTimes.js index 282f8776..fa3eef3d 100644 --- a/src/core/matchers/toHaveBeenCalledTimes.js +++ b/src/core/matchers/toHaveBeenCalledTimes.js @@ -11,11 +11,11 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { * @example * expect(mySpy).toHaveBeenCalledTimes(3); */ - function toHaveBeenCalledTimes() { + function toHaveBeenCalledTimes(matchersUtil) { return { compare: function(actual, expected) { if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); + throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(actual) + '.')); } var args = Array.prototype.slice.call(arguments, 0), diff --git a/src/core/matchers/toHaveBeenCalledWith.js b/src/core/matchers/toHaveBeenCalledWith.js index 9edde713..76628b55 100644 --- a/src/core/matchers/toHaveBeenCalledWith.js +++ b/src/core/matchers/toHaveBeenCalledWith.js @@ -11,7 +11,7 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { * @example * expect(mySpy).toHaveBeenCalledWith('foo', 'bar', 2); */ - function toHaveBeenCalledWith(util) { + function toHaveBeenCalledWith(matchersUtil) { return { compare: function() { var args = Array.prototype.slice.call(arguments, 0), @@ -20,40 +20,40 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { result = { pass: false }; if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); + throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(actual) + '.')); } if (!actual.calls.any()) { result.message = function() { return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + - ' ' + j$.pp(expectedArgs) + + ' ' + matchersUtil.pp(expectedArgs) + '\nbut it was never called.'; }; return result; } - if (util.contains(actual.calls.allArgs(), expectedArgs)) { + if (matchersUtil.contains(actual.calls.allArgs(), expectedArgs)) { result.pass = true; result.message = function() { return 'Expected spy ' + actual.and.identity + ' not to have been called with:\n' + - ' ' + j$.pp(expectedArgs) + + ' ' + matchersUtil.pp(expectedArgs) + '\nbut it was.'; }; } else { result.message = function() { var prettyPrintedCalls = actual.calls.allArgs().map(function(argsForCall) { - return ' ' + j$.pp(argsForCall); + return ' ' + matchersUtil.pp(argsForCall); }); var diffs = actual.calls.allArgs().map(function(argsForCall, callIx) { var diffBuilder = new j$.DiffBuilder(); - util.equals(argsForCall, expectedArgs, diffBuilder); + matchersUtil.equals(argsForCall, expectedArgs, diffBuilder); return 'Call ' + callIx + ':\n' + diffBuilder.getMessage().replace(/^/mg, ' '); }); return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + - ' ' + j$.pp(expectedArgs) + '\n' + '' + + ' ' + matchersUtil.pp(expectedArgs) + '\n' + '' + 'but actual calls were:\n' + prettyPrintedCalls.join(',\n') + '.\n\n' + diffs.join('\n'); diff --git a/src/core/matchers/toHaveClass.js b/src/core/matchers/toHaveClass.js index 32dc2ccf..efe17f10 100644 --- a/src/core/matchers/toHaveClass.js +++ b/src/core/matchers/toHaveClass.js @@ -10,11 +10,11 @@ getJasmineRequireObj().toHaveClass = function(j$) { * el.className = 'foo bar baz'; * expect(el).toHaveClass('bar'); */ - function toHaveClass() { + function toHaveClass(matchersUtil) { return { compare: function(actual, expected) { if (!isElement(actual)) { - throw new Error(j$.pp(actual) + ' is not a DOM element'); + throw new Error(matchersUtil.pp(actual) + ' is not a DOM element'); } return { diff --git a/src/core/matchers/toThrow.js b/src/core/matchers/toThrow.js index a7e089d6..a471a5d9 100644 --- a/src/core/matchers/toThrow.js +++ b/src/core/matchers/toThrow.js @@ -12,7 +12,7 @@ getJasmineRequireObj().toThrow = function(j$) { * expect(function() { return 'things'; }).toThrow('foo'); * expect(function() { return 'stuff'; }).toThrow(); */ - function toThrow(util) { + function toThrow(matchersUtil) { return { compare: function(actual, expected) { var result = { pass: false }, @@ -37,16 +37,16 @@ getJasmineRequireObj().toThrow = function(j$) { if (arguments.length == 1) { result.pass = true; - result.message = function() { return 'Expected function not to throw, but it threw ' + j$.pp(thrown) + '.'; }; + result.message = function() { return 'Expected function not to throw, but it threw ' + matchersUtil.pp(thrown) + '.'; }; return result; } - if (util.equals(thrown, expected)) { + if (matchersUtil.equals(thrown, expected)) { result.pass = true; - result.message = function() { return 'Expected function not to throw ' + j$.pp(expected) + '.'; }; + result.message = function() { return 'Expected function not to throw ' + matchersUtil.pp(expected) + '.'; }; } else { - result.message = function() { return 'Expected function to throw ' + j$.pp(expected) + ', but it threw ' + j$.pp(thrown) + '.'; }; + result.message = function() { return 'Expected function to throw ' + matchersUtil.pp(expected) + ', but it threw ' + matchersUtil.pp(thrown) + '.'; }; } return result; diff --git a/src/core/matchers/toThrowError.js b/src/core/matchers/toThrowError.js index 11c6d746..00f3e69a 100644 --- a/src/core/matchers/toThrowError.js +++ b/src/core/matchers/toThrowError.js @@ -16,7 +16,7 @@ getJasmineRequireObj().toThrowError = function(j$) { * expect(function() { return 'other'; }).toThrowError(/foo/); * expect(function() { return 'other'; }).toThrowError(); */ - function toThrowError () { + function toThrowError(matchersUtil) { return { compare: function(actual) { var errorMatcher = getMatcher.apply(null, arguments), @@ -34,7 +34,7 @@ getJasmineRequireObj().toThrowError = function(j$) { } if (!j$.isError_(thrown)) { - return fail(function() { return 'Expected function to throw an Error, but it threw ' + j$.pp(thrown) + '.'; }); + return fail(function() { return 'Expected function to throw an Error, but it threw ' + matchersUtil.pp(thrown) + '.'; }); } return errorMatcher.match(thrown); @@ -97,7 +97,7 @@ getJasmineRequireObj().toThrowError = function(j$) { thrownMessage = ''; if (expected) { - thrownMessage = ' with message ' + j$.pp(thrown.message); + thrownMessage = ' with message ' + matchersUtil.pp(thrown.message); } return thrownName + thrownMessage; @@ -107,9 +107,9 @@ getJasmineRequireObj().toThrowError = function(j$) { if (expected === null) { return ''; } else if (expected instanceof RegExp) { - return ' with a message matching ' + j$.pp(expected); + return ' with a message matching ' + matchersUtil.pp(expected); } else { - return ' with message ' + j$.pp(expected); + return ' with message ' + matchersUtil.pp(expected); } } diff --git a/src/core/matchers/toThrowMatching.js b/src/core/matchers/toThrowMatching.js index bf9be39e..45e3fc85 100644 --- a/src/core/matchers/toThrowMatching.js +++ b/src/core/matchers/toThrowMatching.js @@ -10,7 +10,7 @@ getJasmineRequireObj().toThrowMatching = function(j$) { * @example * expect(function() { throw new Error('nope'); }).toThrowMatching(function(thrown) { return thrown.message === 'nope'; }); */ - function toThrowMatching() { + function toThrowMatching(matchersUtil) { return { compare: function(actual, predicate) { var thrown; @@ -40,14 +40,14 @@ getJasmineRequireObj().toThrowMatching = function(j$) { } } }; - } - function thrownDescription(thrown) { - if (thrown && thrown.constructor) { - return j$.fnNameFor(thrown.constructor) + ' with message ' + - j$.pp(thrown.message); - } else { - return j$.pp(thrown); + function thrownDescription(thrown) { + if (thrown && thrown.constructor) { + return j$.fnNameFor(thrown.constructor) + ' with message ' + + matchersUtil.pp(thrown.message); + } else { + return matchersUtil.pp(thrown); + } } } diff --git a/src/core/requireCore.js b/src/core/requireCore.js index 0d5b76ed..a21044ff 100644 --- a/src/core/requireCore.js +++ b/src/core/requireCore.js @@ -54,15 +54,19 @@ var getJasmineRequireObj = (function(jasmineGlobal) { j$.asymmetricEqualityTesterArgCompatShim = jRequire.asymmetricEqualityTesterArgCompatShim( j$ ); + j$.makePrettyPrinter = jRequire.makePrettyPrinter(j$); + j$.pp = j$.makePrettyPrinter(); j$.MatchersUtil = jRequire.MatchersUtil(j$); - j$.matchersUtil = new j$.MatchersUtil({ customTesters: [] }); + j$.matchersUtil = new j$.MatchersUtil({ + customTesters: [], + pp: j$.pp + }); j$.ObjectContaining = jRequire.ObjectContaining(j$); j$.ArrayContaining = jRequire.ArrayContaining(j$); j$.ArrayWithExactContents = jRequire.ArrayWithExactContents(j$); j$.MapContaining = jRequire.MapContaining(j$); j$.SetContaining = jRequire.SetContaining(j$); - j$.pp = jRequire.pp(j$); j$.QueueRunner = jRequire.QueueRunner(j$); j$.ReportDispatcher = jRequire.ReportDispatcher(j$); j$.Spec = jRequire.Spec(j$); From 25816a6e7749bd64d1bb6382579e81099f3490fd Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 11 Jan 2020 14:51:12 -0800 Subject: [PATCH 120/201] Added support for custom object formatters Custom object formatters allow users to customize how an object is stringified in matcher failure messages. This can already be done by adding a `jasmineToString` method to the objects in question. But it's not always desirable or possible to do that, particularly when objects of a given "type" do not inherit from a specific prototype. For instance, suppose a web service returns a list of foos that are deserialized from JSON, e.g.: { fooId: 42, /* more properties */ } The only way to define `jasmineToString` on those is by writing code to add it to each instance at runtime. But a custom object formatter can recognize that the object it's looking at is a foo and format it accordingly: jasmine.addCustomObjectFormatter(function(obj) { if (typeof obj.fooId !== 'number') { return undefined; } return '[Foo with ID ' + obj.fooId + ']'; }); Unlike `jasmineToString`, custom object formatters are scoped to a particular spec or suite and don't require any changes to the code under test. --- lib/jasmine-core/jasmine.js | 105 ++++++++--- spec/core/EnvSpec.js | 14 +- spec/core/PrettyPrintSpec.js | 42 +++++ .../ArrayContainingSpec.js | 9 +- .../ArrayWithExactContentsSpec.js | 9 +- .../asymmetric_equality/MapContainingSpec.js | 9 +- .../ObjectContainingSpec.js | 10 +- .../asymmetric_equality/SetContainingSpec.js | 9 +- .../integration/CustomObjectFormatterSpec.js | 67 +++++++ spec/core/integration/MatchersSpec.js | 178 ++++++++++++++++++ spec/core/matchers/DiffBuilderSpec.js | 26 +++ spec/core/matchers/matchersUtilSpec.js | 10 +- spec/core/matchers/toBeSpec.js | 12 ++ spec/core/matchers/toEqualSpec.js | 59 +++++- src/core/Env.js | 19 +- src/core/PrettyPrinter.js | 35 +++- .../asymmetric_equality/ArrayContaining.js | 4 +- .../ArrayWithExactContents.js | 4 +- src/core/asymmetric_equality/MapContaining.js | 4 +- .../asymmetric_equality/ObjectContaining.js | 4 +- src/core/asymmetric_equality/SetContaining.js | 4 +- src/core/matchers/DiffBuilder.js | 13 +- src/core/matchers/matchersUtil.js | 2 +- src/core/matchers/toEqual.js | 2 +- src/core/requireInterface.js | 14 ++ 25 files changed, 591 insertions(+), 73 deletions(-) create mode 100644 spec/core/integration/CustomObjectFormatterSpec.js diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 7c67caa3..9f7e3106 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1217,6 +1217,18 @@ getJasmineRequireObj().Env = function(j$) { } }; + this.addCustomObjectFormatter = function(formatter) { + if (!currentRunnable()) { + throw new Error( + 'Custom object formatters must be added in a before function or a spec' + ); + } + + runnableResources[currentRunnable().id].customObjectFormatters.push( + formatter + ); + }; + j$.Expectation.addCoreMatchers(j$.matchers); j$.Expectation.addAsyncCoreMatchers(j$.asyncMatchers); @@ -1231,7 +1243,9 @@ getJasmineRequireObj().Env = function(j$) { }; var makePrettyPrinter = function() { - return j$.makePrettyPrinter(); + var customObjectFormatters = + runnableResources[currentRunnable().id].customObjectFormatters; + return j$.makePrettyPrinter(customObjectFormatters); }; var makeMatchersUtil = function() { @@ -1281,7 +1295,8 @@ getJasmineRequireObj().Env = function(j$) { customMatchers: {}, customAsyncMatchers: {}, customSpyStrategies: {}, - defaultStrategyFn: undefined + defaultStrategyFn: undefined, + customObjectFormatters: [] }; if (runnableResources[parentRunnableId]) { @@ -2318,8 +2333,8 @@ getJasmineRequireObj().ArrayContaining = function(j$) { return true; }; - ArrayContaining.prototype.jasmineToString = function () { - return ''; + ArrayContaining.prototype.jasmineToString = function (pp) { + return ''; }; return ArrayContaining; @@ -2350,8 +2365,8 @@ getJasmineRequireObj().ArrayWithExactContents = function(j$) { return true; }; - ArrayWithExactContents.prototype.jasmineToString = function() { - return ''; + ArrayWithExactContents.prototype.jasmineToString = function(pp) { + return ''; }; return ArrayWithExactContents; @@ -2433,8 +2448,8 @@ getJasmineRequireObj().MapContaining = function(j$) { return hasAllMatches; }; - MapContaining.prototype.jasmineToString = function() { - return ''; + MapContaining.prototype.jasmineToString = function(pp) { + return ''; }; return MapContaining; @@ -2510,8 +2525,8 @@ getJasmineRequireObj().ObjectContaining = function(j$) { return true; }; - ObjectContaining.prototype.jasmineToString = function() { - return ''; + ObjectContaining.prototype.jasmineToString = function(pp) { + return ''; }; return ObjectContaining; @@ -2550,8 +2565,8 @@ getJasmineRequireObj().SetContaining = function(j$) { return hasAllMatches; }; - SetContaining.prototype.jasmineToString = function() { - return ''; + SetContaining.prototype.jasmineToString = function(pp) { + return ''; }; return SetContaining; @@ -4173,14 +4188,15 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { }; getJasmineRequireObj().DiffBuilder = function(j$) { - return function DiffBuilder() { + return function DiffBuilder(config) { var path = new j$.ObjectPath(), - mismatches = []; + mismatches = [], + prettyPrinter = (config || {}).prettyPrinter || j$.makePrettyPrinter(); return { record: function (actual, expected, formatter) { formatter = formatter || defaultFormatter; - mismatches.push(formatter(actual, expected, path)); + mismatches.push(formatter(actual, expected, path, prettyPrinter)); }, getMessage: function () { @@ -4195,12 +4211,12 @@ getJasmineRequireObj().DiffBuilder = function(j$) { } }; - function defaultFormatter (actual, expected, path) { + function defaultFormatter (actual, expected, path, prettyPrinter) { return 'Expected ' + path + (path.depth() ? ' = ' : '') + - j$.pp(actual) + + prettyPrinter(actual) + ' to equal ' + - j$.pp(expected) + + prettyPrinter(expected) + '.'; } }; @@ -4253,7 +4269,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (i > 0) { message += ','; } - message += ' ' + j$.pp(expected[i]); + message += ' ' + self.pp(expected[i]); } } @@ -5289,7 +5305,7 @@ getJasmineRequireObj().toEqual = function(j$) { var result = { pass: false }, - diffBuilder = j$.DiffBuilder(); + diffBuilder = j$.DiffBuilder({prettyPrinter: util.pp}); result.pass = util.equals(actual, expected, diffBuilder); @@ -5990,11 +6006,13 @@ getJasmineRequireObj().MockDate = function() { }; getJasmineRequireObj().makePrettyPrinter = function(j$) { - function SinglePrettyPrintRun() { + function SinglePrettyPrintRun(customObjectFormatters, pp) { + this.customObjectFormatters_ = customObjectFormatters; this.ppNestLevel_ = 0; this.seen = []; this.length = 0; this.stringParts = []; + this.pp_ = pp; } function hasCustomToString(value) { @@ -6015,7 +6033,11 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { SinglePrettyPrintRun.prototype.format = function(value) { this.ppNestLevel_++; try { - if (j$.util.isUndefined(value)) { + var customFormatResult = this.applyCustomFormatters_(value); + + if (customFormatResult) { + this.emitScalar(customFormatResult); + } else if (j$.util.isUndefined(value)) { this.emitScalar('undefined'); } else if (value === null) { this.emitScalar('null'); @@ -6024,7 +6046,7 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { } else if (value === j$.getGlobal()) { this.emitScalar(''); } else if (value.jasmineToString) { - this.emitScalar(value.jasmineToString()); + this.emitScalar(value.jasmineToString(this.pp_)); } else if (typeof value === 'string') { this.emitString(value); } else if (j$.isSpy(value)) { @@ -6086,6 +6108,18 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { } }; + SinglePrettyPrintRun.prototype.applyCustomFormatters_ = function(value) { + var i, result; + + for (i = 0; i < this.customObjectFormatters_.length; i++) { + result = this.customObjectFormatters_[i](value); + + if (result !== undefined) { + return result; + } + } + }; + SinglePrettyPrintRun.prototype.iterateObject = function(obj, fn) { var objKeys = keys(obj, j$.isArray_(obj)); var isGetter = function isGetter(prop) {}; @@ -6356,12 +6390,17 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { return extraKeys; } - return function() { - return function(value) { - var prettyPrinter = new SinglePrettyPrintRun(); + return function(customObjectFormatters) { + var pp = function(value) { + var prettyPrinter = new SinglePrettyPrintRun( + customObjectFormatters || [], + pp + ); prettyPrinter.format(value); return prettyPrinter.stringParts.join(''); }; + + return pp; }; }; @@ -6972,6 +7011,20 @@ getJasmineRequireObj().interface = function(jasmine, env) { return env.addAsyncMatchers(matchers); }; + /** + * Add a custom object formatter for the current scope of specs. + * + * _Note:_ This is only callable from within a {@link beforeEach}, {@link it}, or {@link beforeAll}. + * @name jasmine.addCustomObjectFormatter + * @since 3.6.0 + * @function + * @param {Function} formatter - A function which takes a value to format and returns a string if it knows how to format it, and `undefined` otherwise. + * @see custom_object_formatter + */ + jasmine.addCustomObjectFormatter = function(formatter) { + return env.addCustomObjectFormatter(formatter); + }; + /** * Get the currently booted mock {Clock} for this Jasmine environment. * @name jasmine.clock diff --git a/spec/core/EnvSpec.js b/spec/core/EnvSpec.js index 80dcffbb..9349a78d 100644 --- a/spec/core/EnvSpec.js +++ b/spec/core/EnvSpec.js @@ -305,8 +305,9 @@ describe('Env', function() { }); }); - it('creates an expectationFactory that uses the current custom equality testers', function(done) { + it('creates an expectationFactory that uses the current custom equality testers and object formatters', function(done) { function customEqualityTester() {} + function customObjectFormatter() {} function prettyPrinter() {} var RealSpec = jasmineUnderTest.Spec, specInstance, @@ -321,11 +322,15 @@ describe('Env', function() { env.it('spec', function() { env.addCustomEqualityTester(customEqualityTester); + env.addCustomObjectFormatter(customObjectFormatter); expectationFactory('actual', specInstance); }); env.addReporter({ jasmineDone: function() { + expect(jasmineUnderTest.makePrettyPrinter).toHaveBeenCalledWith([ + customObjectFormatter + ]); expect(jasmineUnderTest.MatchersUtil).toHaveBeenCalledWith({ customTesters: [customEqualityTester], pp: prettyPrinter @@ -337,8 +342,9 @@ describe('Env', function() { env.execute(); }); - it('creates an asyncExpectationFactory that uses the current custom equality testers', function(done) { + it('creates an asyncExpectationFactory that uses the current custom equality testers and object formatters', function(done) { function customEqualityTester() {} + function customObjectFormatter() {} function prettyPrinter() {} var RealSpec = jasmineUnderTest.Spec, specInstance, @@ -353,11 +359,15 @@ describe('Env', function() { env.it('spec', function() { env.addCustomEqualityTester(customEqualityTester); + env.addCustomObjectFormatter(customObjectFormatter); asyncExpectationFactory('actual', specInstance); }); env.addReporter({ jasmineDone: function() { + expect(jasmineUnderTest.makePrettyPrinter).toHaveBeenCalledWith([ + customObjectFormatter + ]); expect(jasmineUnderTest.MatchersUtil).toHaveBeenCalledWith({ customTesters: [customEqualityTester], pp: prettyPrinter diff --git a/spec/core/PrettyPrintSpec.js b/spec/core/PrettyPrintSpec.js index 46f08d6a..4aafefcd 100644 --- a/spec/core/PrettyPrintSpec.js +++ b/spec/core/PrettyPrintSpec.js @@ -388,6 +388,16 @@ describe('PrettyPrinter', function() { expect(pp(obj)).toEqual('strung'); }); + it('should pass itself to jasmineToString', function() { + var pp = jasmineUnderTest.makePrettyPrinter([]); + var obj = { + jasmineToString: jasmine.createSpy('jasmineToString').and.returnValue('') + }; + + pp(obj); + expect(obj.jasmineToString).toHaveBeenCalledWith(pp); + }); + it('should stringify objects that implement custom toString', function() { var pp = jasmineUnderTest.makePrettyPrinter(); var obj = { @@ -478,4 +488,36 @@ describe('PrettyPrinter', function() { 'Object({ foo: [object Number], bar: [object Object], baz: 3, qux: Error: bar, baddy: has-invalid-toString-method })' ); }); + + describe('Custom object formatters', function() { + it('should use the first custom object formatter that does not return undefined', function() { + var customObjectFormatters = [ + function(obj) { + return undefined; + }, + function(obj) { + return '2nd: ' + obj.foo; + }, + function(obj) { + return '3rd: ' + obj.foo; + } + ], + pp = jasmineUnderTest.makePrettyPrinter(customObjectFormatters), + obj = { foo: 'bar' }; + + expect(pp(obj, customObjectFormatters)).toEqual('2nd: bar'); + }); + + it('should fall back to built in logic if all custom object formatters return undefined', function() { + var customObjectFormatters = [ + function(obj) { + return undefined; + } + ], + pp = jasmineUnderTest.makePrettyPrinter(customObjectFormatters), + obj = { foo: 'bar' }; + + expect(pp(obj, customObjectFormatters)).toEqual("Object({ foo: 'bar' })"); + }); + }); }); diff --git a/spec/core/asymmetric_equality/ArrayContainingSpec.js b/spec/core/asymmetric_equality/ArrayContainingSpec.js index 4cbfa66d..33e411e6 100644 --- a/spec/core/asymmetric_equality/ArrayContainingSpec.js +++ b/spec/core/asymmetric_equality/ArrayContainingSpec.js @@ -42,9 +42,14 @@ describe("ArrayContaining", function() { }); it("jasmineToStrings itself", function() { - var containing = new jasmineUnderTest.ArrayContaining([]); + var sample = [], + matcher = new jasmineUnderTest.ArrayContaining(sample), + pp = jasmine.createSpy('pp').and.returnValue('sample'); - expect(containing.jasmineToString()).toMatch("' + ); + expect(pp).toHaveBeenCalledWith(sample); }); it("uses custom equality testers", function() { diff --git a/spec/core/asymmetric_equality/ArrayWithExactContentsSpec.js b/spec/core/asymmetric_equality/ArrayWithExactContentsSpec.js index 5f8795d6..fd0bb30c 100644 --- a/spec/core/asymmetric_equality/ArrayWithExactContentsSpec.js +++ b/spec/core/asymmetric_equality/ArrayWithExactContentsSpec.js @@ -30,9 +30,14 @@ describe("ArrayWithExactContents", function() { }); it("jasmineToStrings itself", function() { - var matcher = new jasmineUnderTest.ArrayWithExactContents([]); + var sample = [], + matcher = new jasmineUnderTest.ArrayWithExactContents(sample), + pp = jasmine.createSpy('pp').and.returnValue('sample'); - expect(matcher.jasmineToString()).toMatch("' + ); + expect(pp).toHaveBeenCalledWith(sample); }); it("uses custom equality testers", function() { diff --git a/spec/core/asymmetric_equality/MapContainingSpec.js b/spec/core/asymmetric_equality/MapContainingSpec.js index f264e693..c9ea83a6 100644 --- a/spec/core/asymmetric_equality/MapContainingSpec.js +++ b/spec/core/asymmetric_equality/MapContainingSpec.js @@ -184,8 +184,13 @@ describe('MapContaining', function() { }); it('defines a `jasmineToString` method', function() { - var containing = new jasmineUnderTest.MapContaining(new Map()); + var sample = new Map(), + containing = new jasmineUnderTest.MapContaining(sample), + pp = jasmine.createSpy('pp').and.returnValue('sample'); - expect(containing.jasmineToString()).toMatch(/^' + ); + expect(pp).toHaveBeenCalledWith(sample); }); }); diff --git a/spec/core/asymmetric_equality/ObjectContainingSpec.js b/spec/core/asymmetric_equality/ObjectContainingSpec.js index 13fa0a90..4fc16d6b 100644 --- a/spec/core/asymmetric_equality/ObjectContainingSpec.js +++ b/spec/core/asymmetric_equality/ObjectContainingSpec.js @@ -37,9 +37,15 @@ describe("ObjectContaining", function() { }); it("jasmineToString's itself", function() { - var containing = new jasmineUnderTest.ObjectContaining({}); + var sample = {}, + matcher = new jasmineUnderTest.ObjectContaining(sample), + pp = jasmine.createSpy('pp').and.returnValue('sample'); + + expect(matcher.jasmineToString(pp)).toEqual( + '' + ); + expect(pp).toHaveBeenCalledWith(sample); - expect(containing.jasmineToString()).toMatch("' + ); + expect(pp).toHaveBeenCalledWith(sample); }); }); diff --git a/spec/core/integration/CustomObjectFormatterSpec.js b/spec/core/integration/CustomObjectFormatterSpec.js new file mode 100644 index 00000000..10ed4d71 --- /dev/null +++ b/spec/core/integration/CustomObjectFormatterSpec.js @@ -0,0 +1,67 @@ +describe("Custom object formatters", function() { + var env; + + beforeEach(function() { + env = new jasmineUnderTest.Env(); + env.configure({random: false}); + }); + + it("scopes custom object formatters to a spec", function(done) { + env.it('a spec with custom pretty-printer', function() { + env.addCustomObjectFormatter(function(obj) { return 'custom(' + obj + ')'; }); + env.expect(42).toBeUndefined(); + }); + + env.it('a spec without custom pretty-printer', function() { + env.expect(42).toBeUndefined(); + }); + + var specResults = []; + var specDone = function(result) { + specResults.push(result); + }; + var expectations = function() { + expect(specResults[0].failedExpectations[0].message).toEqual("Expected custom(42) to be undefined."); + expect(specResults[1].failedExpectations[0].message).toEqual("Expected 42 to be undefined."); + done(); + }; + env.addReporter({ specDone:specDone, jasmineDone: expectations}); + + env.execute(); + }); + + it("scopes custom object formatters to a suite", function(done) { + env.it('a spec without custom pretty-printer', function() { + env.expect(42).toBeUndefined(); + }); + + env.describe('with custom pretty-printer', function() { + env.beforeEach(function() { + env.addCustomObjectFormatter(function(obj) { return 'custom(' + obj + ')'; }); + }); + + env.it('a spec', function() { + env.expect(42).toBeUndefined(); + }); + }); + + var specResults = []; + var specDone = function(result) { + specResults.push(result); + }; + var expectations = function() { + expect(specResults[0].failedExpectations[0].message).toEqual("Expected 42 to be undefined."); + expect(specResults[1].failedExpectations[0].message).toEqual("Expected custom(42) to be undefined."); + done(); + }; + env.addReporter({ specDone:specDone, jasmineDone: expectations}); + + env.execute(); + }); + + it("throws an exception if you try to add a custom object formatter outside a runable", function() { + expect(function() { + env.addCustomObjectFormatter(function() {}); + }).toThrowError('Custom object formatters must be added in a before function or a spec') + }); +}); diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js index b21208d5..337f9eb2 100644 --- a/spec/core/integration/MatchersSpec.js +++ b/spec/core/integration/MatchersSpec.js @@ -48,6 +48,28 @@ describe('Matchers (Integration)', function() { }); } + function verifyFailsWithCustomObjectFormatters(config) { + it('uses custom object formatters', function(done) { + var env = new jasmineUnderTest.Env(); + env.it('a spec', function () { + env.addCustomObjectFormatter(config.formatter); + config.expectations(env); + }); + + var specExpectations = function (result) { + expect(result.status).toEqual('failed'); + expect(result.failedExpectations.length) + .withContext('Number of failed expectations') + .toEqual(1); + expect(result.failedExpectations[0].message) + .toEqual(config.expectedMessage); + }; + + env.addReporter({specDone: specExpectations, jasmineDone: done}); + env.execute(); + }); + } + function verifyPassesAsync(expectations) { it('passes', function(done) { jasmine.getEnv().requirePromises(); @@ -101,6 +123,30 @@ describe('Matchers (Integration)', function() { }); } + function verifyFailsWithCustomObjectFormattersAsync(config) { + it('uses custom object formatters', function(done) { + var env = new jasmineUnderTest.Env(); + jasmine.getEnv().requirePromises(); + env.it('a spec', function () { + env.addCustomObjectFormatter(config.formatter); + return config.expectations(env); + }); + + var specExpectations = function (result) { + expect(result.status).toEqual('failed'); + expect(result.failedExpectations.length) + .withContext('Number of failed expectations') + .toEqual(1); + expect(result.failedExpectations[0].message) + .toEqual(config.expectedMessage); + }; + + env.addReporter({specDone: specExpectations, jasmineDone: done}); + env.execute(); + }); + } + + describe('nothing', function() { verifyPasses(function(env) { env.expect().nothing(); @@ -217,6 +263,16 @@ describe('Matchers (Integration)', function() { verifyFails(function(env) { env.expect(2).toBeNaN(); }); + + verifyFailsWithCustomObjectFormatters({ + formatter: function(val) { + return '|' + val + '|'; + }, + expectations: function(env) { + env.expect(1).toBeNaN(); + }, + expectedMessage: 'Expected |1| to be NaN.' + }); }); describe('toBeNegativeInfinity', function() { @@ -227,6 +283,16 @@ describe('Matchers (Integration)', function() { verifyFails(function(env) { env.expect(2).toBeNegativeInfinity(); }); + + verifyFailsWithCustomObjectFormatters({ + formatter: function(val) { + return '|' + val + '|'; + }, + expectations: function(env) { + env.expect(1).toBeNegativeInfinity(); + }, + expectedMessage: 'Expected |1| to be -Infinity.' + }); }); describe('toBeNull', function() { @@ -247,6 +313,16 @@ describe('Matchers (Integration)', function() { verifyFails(function(env) { env.expect(2).toBePositiveInfinity(); }); + + verifyFailsWithCustomObjectFormatters({ + formatter: function(val) { + return '|' + val + '|'; + }, + expectations: function(env) { + env.expect(1).toBePositiveInfinity(); + }, + expectedMessage: 'Expected |1| to be Infinity.' + }) }); describe('toBeResolved', function() { @@ -270,6 +346,17 @@ describe('Matchers (Integration)', function() { verifyFailsAsync(function(env) { return env.expectAsync(Promise.resolve('foo')).toBeResolvedTo('bar'); }); + + verifyFailsWithCustomObjectFormattersAsync({ + formatter: function(val) { + return '|' + val + '|'; + }, + expectations: function(env) { + return env.expectAsync(Promise.resolve('x')).toBeResolvedTo('y'); + }, + expectedMessage: 'Expected a promise to be resolved to |y| ' + + 'but it was resolved to |x|.' + }); }); describe('toBeRejected', function() { @@ -293,6 +380,17 @@ describe('Matchers (Integration)', function() { verifyFailsAsync(function(env) { return env.expectAsync(Promise.resolve()).toBeRejectedWith('nope'); }); + + verifyFailsWithCustomObjectFormattersAsync({ + formatter: function(val) { + return '|' + val + '|'; + }, + expectations: function(env) { + return env.expectAsync(Promise.reject('x')).toBeRejectedWith('y'); + }, + expectedMessage: 'Expected a promise to be rejected with |y| ' + + 'but it was rejected with |x|.' + }); }); describe('toBeRejectedWithError', function() { @@ -303,6 +401,17 @@ describe('Matchers (Integration)', function() { verifyFailsAsync(function(env) { return env.expectAsync(Promise.resolve()).toBeRejectedWithError(Error); }); + + verifyFailsWithCustomObjectFormattersAsync({ + formatter: function(val) { + return '|' + val + '|'; + }, + expectations: function(env) { + return env.expectAsync(Promise.reject('foo')).toBeRejectedWithError('foo'); + }, + expectedMessage: 'Expected a promise to be rejected with Error: |foo| ' + + 'but it was rejected with |foo|.' + }); }); describe('toBeTrue', function() { @@ -359,6 +468,20 @@ describe('Matchers (Integration)', function() { verifyFails(function(env) { env.expect('a').toEqual('b'); }); + + verifyFailsWithCustomObjectFormatters({ + formatter: function(val) { + if (val === 5) { + return "five" + } else if (val === 4) { + return "four" + } + }, + expectations: function(env) { + env.expect([{foo: 4}]).toEqual([{foo: 5}]); + }, + expectedMessage: 'Expected $[0].foo = four to equal five.' + }); }); describe('toHaveBeenCalled', function() { @@ -417,6 +540,19 @@ describe('Matchers (Integration)', function() { var spy = env.createSpy(); env.expect(spy).toHaveBeenCalledWith('foo'); }); + + verifyFailsWithCustomObjectFormatters({ + formatter: function(val) { + return '|' + val + '|'; + }, + expectations: function(env) { + var spy = env.createSpy('foo'); + env.expect(spy).toHaveBeenCalledWith('x'); + }, + expectedMessage: 'Expected spy foo to have been called with:\n' + + ' |x|\n' + + 'but it was never called.' + }); }); describe('toHaveClass', function() { @@ -458,6 +594,19 @@ describe('Matchers (Integration)', function() { verifyFails(function(env) { env.expect(function() {}).toThrow(); }); + + verifyFailsWithCustomObjectFormatters({ + formatter: function(val) { + return '|' + val + '|'; + }, + expectations: function(env) { + var spy = env.createSpy('foo'); + env.expect(function() { + throw 'x' + }).not.toThrow(); + }, + expectedMessage: 'Expected function not to throw, but it threw |x|.' + }); }); describe('toThrowError', function() { @@ -468,6 +617,19 @@ describe('Matchers (Integration)', function() { verifyFails(function(env) { env.expect(function() { }).toThrowError(); }); + + verifyFailsWithCustomObjectFormatters({ + formatter: function(val) { + return '|' + val + '|'; + }, + expectations: function(env) { + var spy = env.createSpy('foo'); + env.expect(function() { + throw 'x' + }).toThrowError(); + }, + expectedMessage: 'Expected function to throw an Error, but it threw |x|.' + }); }); describe('toThrowMatching', function() { @@ -482,5 +644,21 @@ describe('Matchers (Integration)', function() { verifyFails(function(env) { env.expect(throws).toThrowMatching(function() { return false; }); }); + + verifyFailsWithCustomObjectFormatters({ + formatter: function(val) { + return '|' + val + '|'; + }, + expectations: function(env) { + var spy = env.createSpy('foo'); + env.expect(function() { + throw new Error('nope') + }).toThrowMatching(function() { + return false; + }); + }, + expectedMessage: 'Expected function to throw an exception matching ' + + 'a predicate, but it threw Error with message |nope|.' + }); }); }); diff --git a/spec/core/matchers/DiffBuilderSpec.js b/spec/core/matchers/DiffBuilderSpec.js index 2fe8f1bf..3b68207d 100644 --- a/spec/core/matchers/DiffBuilderSpec.js +++ b/spec/core/matchers/DiffBuilderSpec.js @@ -44,4 +44,30 @@ describe("DiffBuilder", function() { expect(diffBuilder.getMessage()).toEqual("I find your lack of foo disturbing. (was bar, at $.x)"); }); + + it("uses the injected pretty-printer", function() { + var prettyPrinter = function(val) { + return '|' + val + '|'; + }, + diffBuilder = jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}); + + diffBuilder.withPath('foo', function() { + diffBuilder.record('actual', 'expected'); + }); + + expect(diffBuilder.getMessage()).toEqual("Expected $.foo = |actual| to equal |expected|."); + }); + + + it("passes the injected pretty-printer to the diff formatter", function() { + var diffFormatter = jasmine.createSpy('diffFormatter'), + prettyPrinter = function() {}, + diffBuilder = jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}); + + diffBuilder.withPath('x', function() { + diffBuilder.record('bar', 'foo', diffFormatter); + }); + + expect(diffFormatter).toHaveBeenCalledWith('bar', 'foo', jasmine.anything(), prettyPrinter); + }); }); diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index ff9b159d..1c0903ba 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -840,7 +840,7 @@ describe("matchersUtil", function() { }); }); - describe("buildMessage", function() { + describe("buildFailureMessage", function() { it("builds an English sentence for a failure case", function() { var actual = "foo", @@ -873,15 +873,17 @@ describe("matchersUtil", function() { expect(message).toEqual("Expected 'foo' to bar 'quux', 'corge'."); }); - it("uses the injected pretty-printer to format the expected", function() { + it("uses the injected pretty-printer to format the expecteds and actual", function() { var actual = "foo", + expected1 = "qux", + expected2 = "grault", name = "toBar", isNot = false, pp = function(value) { return '<' + value + '>'; }, matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), - message = message = matchersUtil.buildFailureMessage(name, isNot, actual); + message = message = matchersUtil.buildFailureMessage(name, isNot, actual, expected1, expected2); - expect(message).toEqual("Expected to bar."); + expect(message).toEqual("Expected to bar , ."); }); }); }); diff --git a/spec/core/matchers/toBeSpec.js b/spec/core/matchers/toBeSpec.js index d95f2b49..49484f5f 100644 --- a/spec/core/matchers/toBeSpec.js +++ b/spec/core/matchers/toBeSpec.js @@ -59,4 +59,16 @@ describe("toBe", function() { expect(result.pass).toBe(false); expect(result.message).toBe("Expected Object({ foo: 'bar' }) to be Object({ foo: 'bar' }). Tip: To check for deep equality, use .toEqual() instead of .toBe().") }); + + it("works with custom object formatters when expected is an object", function() { + var formatter = function(x) { return '<' + x.foo + '>'; }, + prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]), + util = new jasmineUnderTest.MatchersUtil({pp: prettyPrinter}), + matcher = jasmineUnderTest.matchers.toBe(util), + result; + + result = matcher.compare({foo: "bar"}, {foo: "bar"}); + expect(result.pass).toBe(false); + expect(result.message).toBe("Expected to be . Tip: To check for deep equality, use .toEqual() instead of .toBe().") + }); }); diff --git a/spec/core/matchers/toEqualSpec.js b/spec/core/matchers/toEqualSpec.js index 5702f7bb..5bfc7715 100644 --- a/spec/core/matchers/toEqualSpec.js +++ b/spec/core/matchers/toEqualSpec.js @@ -97,14 +97,34 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports extra and missing properties together", function() { + it("uses custom object formatters to pretty-print properties", function() { + function formatter(x) { return '|' + x + '|'; } + var actual = {x: {y: 1, z: 2, f: 4}}, expected = {x: {y: 1, z: 2, g: 3}}, + pp = jasmineUnderTest.makePrettyPrinter([formatter]), + util = new jasmineUnderTest.MatchersUtil({pp: pp}), + matcher = jasmineUnderTest.matchers.toEqual(util), message = "Expected $.x to have properties\n" + - " g: 3\n" + + " g: |3|\n" + "Expected $.x not to have properties\n" + - " f: 4"; + " f: |4|"; + + expect(matcher.compare(actual, expected).message).toEqual(message); + }); + + it("uses custom object formatters to build diffs", function() { + function formatter(x) { return '|' + x + '|'; } + + var actual = [{foo: 4}], + expected = [{foo: 5}], + prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]), + util = new jasmineUnderTest.MatchersUtil({pp: prettyPrinter}), + matcher = jasmineUnderTest.matchers.toEqual(util), + message = "Expected $[0].foo = |4| to equal |5|."; + + expect(matcher.compare(actual, expected).message).toEqual(message); }); it("reports extra and missing properties of the root-level object", function() { @@ -277,12 +297,27 @@ describe("toEqual", function() { function Bar() {} var actual = {x: new Foo()}, - expected = {x: new Bar()}, - message = "Expected $.x to be a kind of Bar, but was Foo({ })."; + expected = {x: new Bar()}, + message = "Expected $.x to be a kind of Bar, but was Foo({ })."; expect(compareEquals(actual, expected).message).toEqual(message); }); + it("uses custom object formatters to report objects with different constructors", function () { + function Foo() {} + function Bar() {} + function formatter(x) { return '|' + x + '|'; } + + var actual = {x: new Foo()}, + expected = {x: new Bar()}, + message = "Expected $.x to be a kind of Bar, but was |[object Object]|.", + pp = jasmineUnderTest.makePrettyPrinter([formatter]), + util = new jasmineUnderTest.MatchersUtil({pp: pp}), + matcher = jasmineUnderTest.matchers.toEqual(util); + + expect(matcher.compare(actual, expected).message).toEqual(message); + }); + it("reports type mismatches at the root level", function () { function Foo() {} function Bar() {} @@ -803,6 +838,20 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); + it("uses custom object formatters when the actual array is longer", function() { + function formatter(x) { return '|' + x + '|'; } + + var actual = [1, 1, 2, 3, 5], + expected = [1, 1, 2, 3], + pp = jasmineUnderTest.makePrettyPrinter([formatter]), + util = new jasmineUnderTest.MatchersUtil({pp: pp}), + matcher = jasmineUnderTest.matchers.toEqual(util), + message = 'Expected $.length = |5| to equal |4|.\n' + + 'Unexpected $[4] = |5| in array.'; + + expect(matcher.compare(actual, expected).message).toEqual(message); + }); + it("expected array is longer", function() { var actual = [1, 1, 2, 3], expected = [1, 1, 2, 3, 5], diff --git a/src/core/Env.js b/src/core/Env.js index 42ba2756..62510708 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -296,6 +296,18 @@ getJasmineRequireObj().Env = function(j$) { } }; + this.addCustomObjectFormatter = function(formatter) { + if (!currentRunnable()) { + throw new Error( + 'Custom object formatters must be added in a before function or a spec' + ); + } + + runnableResources[currentRunnable().id].customObjectFormatters.push( + formatter + ); + }; + j$.Expectation.addCoreMatchers(j$.matchers); j$.Expectation.addAsyncCoreMatchers(j$.asyncMatchers); @@ -310,7 +322,9 @@ getJasmineRequireObj().Env = function(j$) { }; var makePrettyPrinter = function() { - return j$.makePrettyPrinter(); + var customObjectFormatters = + runnableResources[currentRunnable().id].customObjectFormatters; + return j$.makePrettyPrinter(customObjectFormatters); }; var makeMatchersUtil = function() { @@ -360,7 +374,8 @@ getJasmineRequireObj().Env = function(j$) { customMatchers: {}, customAsyncMatchers: {}, customSpyStrategies: {}, - defaultStrategyFn: undefined + defaultStrategyFn: undefined, + customObjectFormatters: [] }; if (runnableResources[parentRunnableId]) { diff --git a/src/core/PrettyPrinter.js b/src/core/PrettyPrinter.js index 14091e5e..a15177ce 100644 --- a/src/core/PrettyPrinter.js +++ b/src/core/PrettyPrinter.js @@ -1,9 +1,11 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { - function SinglePrettyPrintRun() { + function SinglePrettyPrintRun(customObjectFormatters, pp) { + this.customObjectFormatters_ = customObjectFormatters; this.ppNestLevel_ = 0; this.seen = []; this.length = 0; this.stringParts = []; + this.pp_ = pp; } function hasCustomToString(value) { @@ -24,7 +26,11 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { SinglePrettyPrintRun.prototype.format = function(value) { this.ppNestLevel_++; try { - if (j$.util.isUndefined(value)) { + var customFormatResult = this.applyCustomFormatters_(value); + + if (customFormatResult) { + this.emitScalar(customFormatResult); + } else if (j$.util.isUndefined(value)) { this.emitScalar('undefined'); } else if (value === null) { this.emitScalar('null'); @@ -33,7 +39,7 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { } else if (value === j$.getGlobal()) { this.emitScalar(''); } else if (value.jasmineToString) { - this.emitScalar(value.jasmineToString()); + this.emitScalar(value.jasmineToString(this.pp_)); } else if (typeof value === 'string') { this.emitString(value); } else if (j$.isSpy(value)) { @@ -95,6 +101,18 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { } }; + SinglePrettyPrintRun.prototype.applyCustomFormatters_ = function(value) { + var i, result; + + for (i = 0; i < this.customObjectFormatters_.length; i++) { + result = this.customObjectFormatters_[i](value); + + if (result !== undefined) { + return result; + } + } + }; + SinglePrettyPrintRun.prototype.iterateObject = function(obj, fn) { var objKeys = keys(obj, j$.isArray_(obj)); var isGetter = function isGetter(prop) {}; @@ -365,11 +383,16 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { return extraKeys; } - return function() { - return function(value) { - var prettyPrinter = new SinglePrettyPrintRun(); + return function(customObjectFormatters) { + var pp = function(value) { + var prettyPrinter = new SinglePrettyPrintRun( + customObjectFormatters || [], + pp + ); prettyPrinter.format(value); return prettyPrinter.stringParts.join(''); }; + + return pp; }; }; diff --git a/src/core/asymmetric_equality/ArrayContaining.js b/src/core/asymmetric_equality/ArrayContaining.js index 95c9f3f1..7faea8b4 100644 --- a/src/core/asymmetric_equality/ArrayContaining.js +++ b/src/core/asymmetric_equality/ArrayContaining.js @@ -25,8 +25,8 @@ getJasmineRequireObj().ArrayContaining = function(j$) { return true; }; - ArrayContaining.prototype.jasmineToString = function () { - return ''; + ArrayContaining.prototype.jasmineToString = function (pp) { + return ''; }; return ArrayContaining; diff --git a/src/core/asymmetric_equality/ArrayWithExactContents.js b/src/core/asymmetric_equality/ArrayWithExactContents.js index 9bdba8d4..d2049047 100644 --- a/src/core/asymmetric_equality/ArrayWithExactContents.js +++ b/src/core/asymmetric_equality/ArrayWithExactContents.js @@ -23,8 +23,8 @@ getJasmineRequireObj().ArrayWithExactContents = function(j$) { return true; }; - ArrayWithExactContents.prototype.jasmineToString = function() { - return ''; + ArrayWithExactContents.prototype.jasmineToString = function(pp) { + return ''; }; return ArrayWithExactContents; diff --git a/src/core/asymmetric_equality/MapContaining.js b/src/core/asymmetric_equality/MapContaining.js index 7c8e3c5b..ba6b0ce9 100644 --- a/src/core/asymmetric_equality/MapContaining.js +++ b/src/core/asymmetric_equality/MapContaining.js @@ -33,8 +33,8 @@ getJasmineRequireObj().MapContaining = function(j$) { return hasAllMatches; }; - MapContaining.prototype.jasmineToString = function() { - return ''; + MapContaining.prototype.jasmineToString = function(pp) { + return ''; }; return MapContaining; diff --git a/src/core/asymmetric_equality/ObjectContaining.js b/src/core/asymmetric_equality/ObjectContaining.js index 93069b25..7d9f4cf6 100644 --- a/src/core/asymmetric_equality/ObjectContaining.js +++ b/src/core/asymmetric_equality/ObjectContaining.js @@ -41,8 +41,8 @@ getJasmineRequireObj().ObjectContaining = function(j$) { return true; }; - ObjectContaining.prototype.jasmineToString = function() { - return ''; + ObjectContaining.prototype.jasmineToString = function(pp) { + return ''; }; return ObjectContaining; diff --git a/src/core/asymmetric_equality/SetContaining.js b/src/core/asymmetric_equality/SetContaining.js index 00627935..f3ad3527 100644 --- a/src/core/asymmetric_equality/SetContaining.js +++ b/src/core/asymmetric_equality/SetContaining.js @@ -31,8 +31,8 @@ getJasmineRequireObj().SetContaining = function(j$) { return hasAllMatches; }; - SetContaining.prototype.jasmineToString = function() { - return ''; + SetContaining.prototype.jasmineToString = function(pp) { + return ''; }; return SetContaining; diff --git a/src/core/matchers/DiffBuilder.js b/src/core/matchers/DiffBuilder.js index 131b5b92..f5517e17 100644 --- a/src/core/matchers/DiffBuilder.js +++ b/src/core/matchers/DiffBuilder.js @@ -1,12 +1,13 @@ getJasmineRequireObj().DiffBuilder = function(j$) { - return function DiffBuilder() { + return function DiffBuilder(config) { var path = new j$.ObjectPath(), - mismatches = []; + mismatches = [], + prettyPrinter = (config || {}).prettyPrinter || j$.makePrettyPrinter(); return { record: function (actual, expected, formatter) { formatter = formatter || defaultFormatter; - mismatches.push(formatter(actual, expected, path)); + mismatches.push(formatter(actual, expected, path, prettyPrinter)); }, getMessage: function () { @@ -21,12 +22,12 @@ getJasmineRequireObj().DiffBuilder = function(j$) { } }; - function defaultFormatter (actual, expected, path) { + function defaultFormatter (actual, expected, path, prettyPrinter) { return 'Expected ' + path + (path.depth() ? ' = ' : '') + - j$.pp(actual) + + prettyPrinter(actual) + ' to equal ' + - j$.pp(expected) + + prettyPrinter(expected) + '.'; } }; diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index 8a0eb75c..f38b9185 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -45,7 +45,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (i > 0) { message += ','; } - message += ' ' + j$.pp(expected[i]); + message += ' ' + self.pp(expected[i]); } } diff --git a/src/core/matchers/toEqual.js b/src/core/matchers/toEqual.js index d78bde4c..54aea12f 100644 --- a/src/core/matchers/toEqual.js +++ b/src/core/matchers/toEqual.js @@ -14,7 +14,7 @@ getJasmineRequireObj().toEqual = function(j$) { var result = { pass: false }, - diffBuilder = j$.DiffBuilder(); + diffBuilder = j$.DiffBuilder({prettyPrinter: util.pp}); result.pass = util.equals(actual, expected, diffBuilder); diff --git a/src/core/requireInterface.js b/src/core/requireInterface.js index f8f15ac6..52569888 100644 --- a/src/core/requireInterface.js +++ b/src/core/requireInterface.js @@ -316,6 +316,20 @@ getJasmineRequireObj().interface = function(jasmine, env) { return env.addAsyncMatchers(matchers); }; + /** + * Add a custom object formatter for the current scope of specs. + * + * _Note:_ This is only callable from within a {@link beforeEach}, {@link it}, or {@link beforeAll}. + * @name jasmine.addCustomObjectFormatter + * @since 3.6.0 + * @function + * @param {Function} formatter - A function which takes a value to format and returns a string if it knows how to format it, and `undefined` otherwise. + * @see custom_object_formatter + */ + jasmine.addCustomObjectFormatter = function(formatter) { + return env.addCustomObjectFormatter(formatter); + }; + /** * Get the currently booted mock {Clock} for this Jasmine environment. * @name jasmine.clock From 873d1c294552e90bbcb96b5589324a3bdf5ff597 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 1 Feb 2020 18:49:06 -0800 Subject: [PATCH 121/201] Use custom object formatters for any part of a diff, not just leaf nodes --- lib/jasmine-core/jasmine.js | 223 +++++++++++++++++----- spec/core/PrettyPrintSpec.js | 36 +++- spec/core/matchers/DiffBuilderSpec.js | 109 ++++++++--- spec/core/matchers/MismatchTreeSpec.js | 136 +++++++++++++ spec/core/matchers/NullDiffBuilderSpec.js | 9 +- spec/core/matchers/ObjectPathSpec.js | 10 +- spec/core/matchers/matchersUtilSpec.js | 8 +- spec/core/matchers/toEqualSpec.js | 59 +++++- src/core/PrettyPrinter.js | 33 ++-- src/core/matchers/DiffBuilder.js | 60 ++++-- src/core/matchers/MismatchTree.js | 62 ++++++ src/core/matchers/NullDiffBuilder.js | 3 +- src/core/matchers/ObjectPath.js | 14 ++ src/core/matchers/matchersUtil.js | 47 ++--- src/core/requireCore.js | 1 + 15 files changed, 669 insertions(+), 141 deletions(-) create mode 100644 spec/core/matchers/MismatchTreeSpec.js create mode 100644 src/core/matchers/MismatchTree.js diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 9f7e3106..2616482f 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1,5 +1,5 @@ /* -Copyright (c) 2008-2019 Pivotal Labs +Copyright (c) 2008-2020 Pivotal Labs Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the @@ -106,6 +106,7 @@ var getJasmineRequireObj = (function(jasmineGlobal) { j$.DiffBuilder = jRequire.DiffBuilder(j$); j$.NullDiffBuilder = jRequire.NullDiffBuilder(j$); j$.ObjectPath = jRequire.ObjectPath(j$); + j$.MismatchTree = jRequire.MismatchTree(j$); j$.GlobalErrors = jRequire.GlobalErrors(j$); j$.Truthy = jRequire.Truthy(j$); @@ -4187,20 +4188,54 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { }; }; -getJasmineRequireObj().DiffBuilder = function(j$) { +getJasmineRequireObj().DiffBuilder = function (j$) { return function DiffBuilder(config) { - var path = new j$.ObjectPath(), - mismatches = [], - prettyPrinter = (config || {}).prettyPrinter || j$.makePrettyPrinter(); + var prettyPrinter = (config || {}).prettyPrinter || j$.makePrettyPrinter(), + mismatches = new j$.MismatchTree(), + path = new j$.ObjectPath(), + actualRoot = undefined, + expectedRoot = undefined; return { - record: function (actual, expected, formatter) { - formatter = formatter || defaultFormatter; - mismatches.push(formatter(actual, expected, path, prettyPrinter)); + setRoots: function (actual, expected) { + actualRoot = actual; + expectedRoot = expected; + }, + + recordMismatch: function (formatter) { + mismatches.add(path, formatter); }, getMessage: function () { - return mismatches.join('\n'); + var messages = []; + + mismatches.traverse(function (path, isLeaf, formatter) { + var actualCustom, expectedCustom, useCustom, + actual = path.dereference(actualRoot), + expected = path.dereference(expectedRoot); + + if (formatter) { + messages.push(formatter(actual, expected, path, prettyPrinter)); + return true; + } + + actualCustom = prettyPrinter.customFormat_(actual); + expectedCustom = prettyPrinter.customFormat_(expected); + useCustom = !(j$.util.isUndefined(actualCustom) && j$.util.isUndefined(expectedCustom)); + + if (useCustom) { + messages.push(wrapPrettyPrinted(actualCustom, expectedCustom, path)); + return false; // don't recurse further + } + + if (isLeaf) { + messages.push(defaultFormatter(actual, expected, path, prettyPrinter)); + } + + return true; + }); + + return messages.join('\n'); }, withPath: function (pathComponent, block) { @@ -4211,12 +4246,16 @@ getJasmineRequireObj().DiffBuilder = function(j$) { } }; - function defaultFormatter (actual, expected, path, prettyPrinter) { + function defaultFormatter(actual, expected, path, prettyPrinter) { + return wrapPrettyPrinted(prettyPrinter(actual), prettyPrinter(expected), path); + } + + function wrapPrettyPrinted(actual, expected, path) { return 'Expected ' + path + (path.depth() ? ' = ' : '') + - prettyPrinter(actual) + + actual + ' to equal ' + - prettyPrinter(expected) + + expected + '.'; } }; @@ -4293,7 +4332,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (asymmetricA) { result = a.asymmetricMatch(b, shim); if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; } @@ -4301,7 +4340,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (asymmetricB) { result = b.asymmetricMatch(a, shim); if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; } @@ -4319,6 +4358,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { customTesters = customTesters || this.customTesters_; diffBuilder = diffBuilder || j$.NullDiffBuilder(); + diffBuilder.setRoots(a, b); return this.eq_(a, b, [], [], customTesters, diffBuilder); }; @@ -4337,7 +4377,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { var customTesterResult = customTesters[i](a, b); if (!j$.util.isUndefined(customTesterResult)) { if (!customTesterResult) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return customTesterResult; } @@ -4346,7 +4386,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (a instanceof Error && b instanceof Error) { result = a.message == b.message; if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; } @@ -4356,7 +4396,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (a === b) { result = a !== 0 || 1 / a == 1 / b; if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; } @@ -4364,13 +4404,13 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (a === null || b === null) { result = a === b; if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; } var className = Object.prototype.toString.call(a); if (className != Object.prototype.toString.call(b)) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } switch (className) { @@ -4380,7 +4420,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // equivalent to `new String("5")`. result = a == String(b); if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; case '[object Number]': @@ -4388,7 +4428,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // other numeric values. result = a != +a ? b != +b : (a === 0 ? 1 / a == 1 / b : a == +b); if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; case '[object Date]': @@ -4398,7 +4438,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // of `NaN` are not equivalent. result = +a == +b; if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; // RegExps are compared by their source patterns and flags. @@ -4409,7 +4449,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { a.ignoreCase == b.ignoreCase; } if (typeof a != 'object' || typeof b != 'object') { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } @@ -4419,12 +4459,12 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // At first try to use DOM3 method isEqualNode result = a.isEqualNode(b); if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; } if (aIsDomNode || bIsDomNode) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } @@ -4454,7 +4494,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { diffBuilder.withPath('length', function() { if (aLength !== bLength) { - diffBuilder.record(aLength, bLength); + diffBuilder.recordMismatch(); result = false; } }); @@ -4462,7 +4502,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { for (i = 0; i < aLength || i < bLength; i++) { diffBuilder.withPath(i, function() { if (i >= bLength) { - diffBuilder.record(a[i], void 0, actualArrayIsLongerFormatter.bind(null, self.pp)); + diffBuilder.recordMismatch(actualArrayIsLongerFormatter.bind(null, self.pp)); result = false; } else { result = self.eq_(i < aLength ? a[i] : void 0, i < bLength ? b[i] : void 0, aStack, bStack, customTesters, diffBuilder) && result; @@ -4474,7 +4514,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } } else if (j$.isMap(a) && j$.isMap(b)) { if (a.size != b.size) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } @@ -4516,12 +4556,12 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } } else if (j$.isSet(a) && j$.isSet(b)) { if (a.size != b.size) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } @@ -4566,7 +4606,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } } else { @@ -4579,7 +4619,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { a instanceof aCtor && b instanceof bCtor && !(aCtor instanceof aCtor && bCtor instanceof bCtor)) { - diffBuilder.record(a, b, constructorsAreDifferentFormatter.bind(null, this.pp)); + diffBuilder.recordMismatch(constructorsAreDifferentFormatter.bind(null, this.pp)); return false; } } @@ -4590,7 +4630,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // Ensure that both objects contain the same number of properties before comparing deep equality. if (keys(b, className == '[object Array]').length !== size) { - diffBuilder.record(a, b, objectKeysAreDifferentFormatter.bind(null, this.pp)); + diffBuilder.recordMismatch(objectKeysAreDifferentFormatter.bind(null, this.pp)); return false; } @@ -4598,7 +4638,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { key = aKeys[i]; // Deep compare each member if (!j$.util.has(b, key)) { - diffBuilder.record(a, b, objectKeysAreDifferentFormatter.bind(null, this.pp)); + diffBuilder.recordMismatch(objectKeysAreDifferentFormatter.bind(null, this.pp)); result = false; continue; } @@ -4704,12 +4744,75 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } function isDiffBuilder(obj) { - return obj && typeof obj.record === 'function'; + return obj && typeof obj.recordMismatch === 'function'; } return MatchersUtil; }; +getJasmineRequireObj().MismatchTree = function (j$) { + + /* + To be able to apply custom object formatters at all possible levels of an + object graph, DiffBuilder needs to be able to know not just where the + mismatch occurred but also all ancestors of the mismatched value in both + the expected and actual object graphs. MismatchTree maintains that context + and provides it via the traverse method. + */ + function MismatchTree(path) { + this.path = path || new j$.ObjectPath([]); + this.formatter = undefined; + this.children = []; + this.isMismatch = false; + } + + MismatchTree.prototype.add = function (path, formatter) { + var key, child; + + if (path.depth() === 0) { + this.formatter = formatter; + this.isMismatch = true; + } else { + key = path.components[0]; + path = path.shift(); + child = this.child(key); + + if (!child) { + child = new MismatchTree(this.path.add(key)); + this.children.push(child); + } + + child.add(path, formatter); + } + }; + + MismatchTree.prototype.traverse = function (visit) { + var i, hasChildren = this.children.length > 0; + + if (this.isMismatch || hasChildren) { + if (visit(this.path, !hasChildren, this.formatter)) { + for (i = 0; i < this.children.length; i++) { + this.children[i].traverse(visit); + } + } + } + }; + + MismatchTree.prototype.child = function(key) { + var i, pathEls; + + for (i = 0; i < this.children.length; i++) { + pathEls = this.children[i].path.components; + if (pathEls[pathEls.length - 1] === key) { + return this.children[i]; + } + } + }; + + return MismatchTree; +}; + + getJasmineRequireObj().nothing = function() { /** * {@link expect} nothing explicitly. @@ -4738,7 +4841,8 @@ getJasmineRequireObj().NullDiffBuilder = function(j$) { withPath: function(_, block) { block(); }, - record: function() {} + setRoots: function() {}, + recordMismatch: function() {} }; }; }; @@ -4756,10 +4860,24 @@ getJasmineRequireObj().ObjectPath = function(j$) { } }; + ObjectPath.prototype.dereference = function(obj) { + var i; + + for (i = 0; i < this.components.length; i++) { + obj = obj[this.components[i]]; + } + + return obj; + }; + ObjectPath.prototype.add = function(component) { return new ObjectPath(this.components.concat([component])); }; + ObjectPath.prototype.shift = function() { + return new ObjectPath(this.components.slice(1)); + }; + ObjectPath.prototype.depth = function() { return this.components.length; }; @@ -6109,15 +6227,7 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { }; SinglePrettyPrintRun.prototype.applyCustomFormatters_ = function(value) { - var i, result; - - for (i = 0; i < this.customObjectFormatters_.length; i++) { - result = this.customObjectFormatters_[i](value); - - if (result !== undefined) { - return result; - } - } + return customFormat(value, this.customObjectFormatters_); }; SinglePrettyPrintRun.prototype.iterateObject = function(obj, fn) { @@ -6390,16 +6500,31 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { return extraKeys; } + function customFormat(value, customObjectFormatters) { + var i, result; + + for (i = 0; i < customObjectFormatters.length; i++) { + result = customObjectFormatters[i](value); + + if (result !== undefined) { + return result; + } + } + } + return function(customObjectFormatters) { + customObjectFormatters = customObjectFormatters || []; + var pp = function(value) { - var prettyPrinter = new SinglePrettyPrintRun( - customObjectFormatters || [], - pp - ); + var prettyPrinter = new SinglePrettyPrintRun(customObjectFormatters, pp); prettyPrinter.format(value); return prettyPrinter.stringParts.join(''); }; + pp.customFormat_ = function(value) { + return customFormat(value, customObjectFormatters); + }; + return pp; }; }; diff --git a/spec/core/PrettyPrintSpec.js b/spec/core/PrettyPrintSpec.js index 4aafefcd..f12469b7 100644 --- a/spec/core/PrettyPrintSpec.js +++ b/spec/core/PrettyPrintSpec.js @@ -505,7 +505,7 @@ describe('PrettyPrinter', function() { pp = jasmineUnderTest.makePrettyPrinter(customObjectFormatters), obj = { foo: 'bar' }; - expect(pp(obj, customObjectFormatters)).toEqual('2nd: bar'); + expect(pp(obj)).toEqual('2nd: bar'); }); it('should fall back to built in logic if all custom object formatters return undefined', function() { @@ -517,7 +517,39 @@ describe('PrettyPrinter', function() { pp = jasmineUnderTest.makePrettyPrinter(customObjectFormatters), obj = { foo: 'bar' }; - expect(pp(obj, customObjectFormatters)).toEqual("Object({ foo: 'bar' })"); + expect(pp(obj)).toEqual("Object({ foo: 'bar' })"); + }); + }); + + describe('#customFormat_', function() { + it('should use the first custom object formatter that does not return undefined', function() { + var customObjectFormatters = [ + function(obj) { + return undefined; + }, + function(obj) { + return '2nd: ' + obj.foo; + }, + function(obj) { + return '3rd: ' + obj.foo; + } + ], + pp = jasmineUnderTest.makePrettyPrinter(customObjectFormatters), + obj = { foo: 'bar' }; + + expect(pp.customFormat_(obj)).toEqual('2nd: bar'); + }); + + it('should return undefined if all custom object formatters return undefined', function() { + var customObjectFormatters = [ + function(obj) { + return undefined; + } + ], + pp = jasmineUnderTest.makePrettyPrinter(customObjectFormatters), + obj = { foo: 'bar' }; + + expect(pp.customFormat_(obj)).toBeUndefined(); }); }); }); diff --git a/spec/core/matchers/DiffBuilderSpec.js b/spec/core/matchers/DiffBuilderSpec.js index 3b68207d..6d82c3f8 100644 --- a/spec/core/matchers/DiffBuilderSpec.js +++ b/spec/core/matchers/DiffBuilderSpec.js @@ -1,73 +1,136 @@ -describe("DiffBuilder", function() { - it("records the actual and expected objects", function() { +describe("DiffBuilder", function () { + it("records the actual and expected objects", function () { var diffBuilder = jasmineUnderTest.DiffBuilder(); - diffBuilder.record({x: 'actual'}, {x: 'expected'}); + diffBuilder.setRoots({x: 'actual'}, {x: 'expected'}); + diffBuilder.recordMismatch(); expect(diffBuilder.getMessage()).toEqual("Expected Object({ x: 'actual' }) to equal Object({ x: 'expected' })."); }); - it("prints the path at which the difference was found", function() { + it("prints the path at which the difference was found", function () { var diffBuilder = jasmineUnderTest.DiffBuilder(); + diffBuilder.setRoots({foo: {x: 'actual'}}, {foo: {x: 'expected'}}); - diffBuilder.withPath('foo', function() { - diffBuilder.record({x: 'actual'}, {x: 'expected'}); + diffBuilder.withPath('foo', function () { + diffBuilder.recordMismatch(); }); expect(diffBuilder.getMessage()).toEqual("Expected $.foo = Object({ x: 'actual' }) to equal Object({ x: 'expected' })."); }); - it("prints multiple messages, separated by newlines", function() { + it("prints multiple messages, separated by newlines", function () { var diffBuilder = jasmineUnderTest.DiffBuilder(); + diffBuilder.setRoots({foo: 1, bar: 3}, {foo: 2, bar: 4}); - diffBuilder.withPath('foo', function() { - diffBuilder.record(1, 2); + diffBuilder.withPath('foo', function () { + diffBuilder.recordMismatch(); + }); + diffBuilder.withPath('bar', function () { + diffBuilder.recordMismatch(); }); var message = "Expected $.foo = 1 to equal 2.\n" + - "Expected 3 to equal 4."; + "Expected $.bar = 3 to equal 4."; - diffBuilder.record(3, 4); expect(diffBuilder.getMessage()).toEqual(message); }); - it("allows customization of the message", function() { + it("allows customization of the message", function () { var diffBuilder = jasmineUnderTest.DiffBuilder(); + diffBuilder.setRoots({x: 'bar'}, {x: 'foo'}); function darthVaderFormatter(actual, expected, path) { return "I find your lack of " + expected + " disturbing. (was " + actual + ", at " + path + ")" } - diffBuilder.withPath('x', function() { - diffBuilder.record('bar', 'foo', darthVaderFormatter); + diffBuilder.withPath('x', function () { + diffBuilder.recordMismatch(darthVaderFormatter); }); expect(diffBuilder.getMessage()).toEqual("I find your lack of foo disturbing. (was bar, at $.x)"); }); - it("uses the injected pretty-printer", function() { - var prettyPrinter = function(val) { + it("uses the injected pretty-printer", function () { + var prettyPrinter = function (val) { return '|' + val + '|'; }, diffBuilder = jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}); + prettyPrinter.customFormat_ = function () { + }; - diffBuilder.withPath('foo', function() { - diffBuilder.record('actual', 'expected'); + diffBuilder.setRoots({foo: 'actual'}, {foo: 'expected'}); + diffBuilder.withPath('foo', function () { + diffBuilder.recordMismatch(); }); expect(diffBuilder.getMessage()).toEqual("Expected $.foo = |actual| to equal |expected|."); }); - - it("passes the injected pretty-printer to the diff formatter", function() { + it("passes the injected pretty-printer to the diff formatter", function () { var diffFormatter = jasmine.createSpy('diffFormatter'), - prettyPrinter = function() {}, + prettyPrinter = function () { + }, diffBuilder = jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}); + prettyPrinter.customFormat_ = function () { + }; - diffBuilder.withPath('x', function() { - diffBuilder.record('bar', 'foo', diffFormatter); + diffBuilder.setRoots({x: 'bar'}, {x: 'foo'}); + diffBuilder.withPath('x', function () { + diffBuilder.recordMismatch(diffFormatter); }); + diffBuilder.getMessage(); + expect(diffFormatter).toHaveBeenCalledWith('bar', 'foo', jasmine.anything(), prettyPrinter); }); + + it("uses custom object formatters on leaf nodes", function() { + var formatter = function(x) { + if (typeof x === 'number') { + return '[number:' + x + ']'; + } + }; + prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]); + var diffBuilder = new jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}); + + diffBuilder.setRoots(5, 4); + diffBuilder.recordMismatch(); + + expect(diffBuilder.getMessage()).toEqual('Expected [number:5] to equal [number:4].'); + }); + + + it("uses custom object formatters on non leaf nodes", function () { + var formatter = function (x) { + if (x.hasOwnProperty('a')) { + return '[thing with a=' + x.a + ', b=' + JSON.stringify(x.b) + ']'; + } + }; + prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]); + var diffBuilder = new jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}); + var expectedMsg = 'Expected $[0].foo = [thing with a=1, b={"x":42}] to equal [thing with a=1, b={"x":43}].\n' + + "Expected $[0].bar = 'yes' to equal 'no'."; + + diffBuilder.setRoots( + [{foo: {a: 1, b: {x: 42}}, bar: 'yes'}], + [{foo: {a: 1, b: {x: 43}}, bar: 'no'}] + ); + + diffBuilder.withPath(0, function () { + diffBuilder.withPath('foo', function () { + diffBuilder.withPath('b', function () { + diffBuilder.withPath('x', function () { + diffBuilder.recordMismatch(); + }); + }); + }); + + diffBuilder.withPath('bar', function () { + diffBuilder.recordMismatch(); + }); + }); + + expect(diffBuilder.getMessage()).toEqual(expectedMsg); + }); }); diff --git a/spec/core/matchers/MismatchTreeSpec.js b/spec/core/matchers/MismatchTreeSpec.js new file mode 100644 index 00000000..ea053eb7 --- /dev/null +++ b/spec/core/matchers/MismatchTreeSpec.js @@ -0,0 +1,136 @@ +describe('MismatchTree', function () { + describe('#add', function () { + describe('When the path is empty', function () { + it('flags the root node as mismatched', function () { + var tree = new jasmineUnderTest.MismatchTree(); + tree.add(new jasmineUnderTest.ObjectPath([])); + expect(tree.isMismatch).toBe(true); + }); + }); + + describe('When the path is not empty', function () { + it('flags the node as mismatched', function () { + var tree = new jasmineUnderTest.MismatchTree(); + + tree.add(new jasmineUnderTest.ObjectPath(['a', 'b'])); + + expect(tree.child('a').child('b').isMismatch).toBe(true); + }); + + it('does not flag ancestors as mismatched', function () { + var tree = new jasmineUnderTest.MismatchTree(); + + tree.add(new jasmineUnderTest.ObjectPath(['a', 'b'])); + + expect(tree.isMismatch).toBe(false); + expect(tree.child('a').isMismatch).toBe(false); + }); + }); + + it('stores the formatter on only the target node', function () { + var tree = new jasmineUnderTest.MismatchTree(); + + tree.add(new jasmineUnderTest.ObjectPath(['a', 'b']), formatter); + + expect(tree.formatter).toBeFalsy(); + expect(tree.child('a').formatter).toBeFalsy(); + expect(tree.child('a').child('b').formatter).toBe(formatter); + }); + + it('stores the path to the node', function () { + var tree = new jasmineUnderTest.MismatchTree(); + + tree.add(new jasmineUnderTest.ObjectPath(['a', 'b']), formatter); + + expect(tree.child('a').child('b').path.components).toEqual(['a', 'b']); + }); + }); + + describe('#traverse', function () { + it('calls the callback for all nodes that are or contain mismatches', function () { + var tree = new jasmineUnderTest.MismatchTree(); + tree.add(new jasmineUnderTest.ObjectPath(['a', 'b']), formatter); + tree.add(new jasmineUnderTest.ObjectPath(['c'])); + var visit = jasmine.createSpy('visit').and.returnValue(true); + + tree.traverse(visit); + + expect(visit).toHaveBeenCalledWith( + new jasmineUnderTest.ObjectPath([]), false, undefined + ); + expect(visit).toHaveBeenCalledWith( + new jasmineUnderTest.ObjectPath(['a']), false, undefined + ); + expect(visit).toHaveBeenCalledWith( + new jasmineUnderTest.ObjectPath(['a', 'b']), true, formatter + ); + expect(visit).toHaveBeenCalledWith( + new jasmineUnderTest.ObjectPath(['c']), true, undefined + ); + }); + + it('does not call the callback if there are no mismatches', function () { + var tree = new jasmineUnderTest.MismatchTree(); + var visit = jasmine.createSpy('visit'); + + tree.traverse(visit); + + expect(visit).not.toHaveBeenCalled(); + }); + + it('visits parents before children', function () { + var tree = new jasmineUnderTest.MismatchTree(); + tree.add(new jasmineUnderTest.ObjectPath(['a', 'b'])); + var visited = []; + + tree.traverse(function (path) { + visited.push(path); + return true; + }); + + expect(visited).toEqual([ + new jasmineUnderTest.ObjectPath([]), + new jasmineUnderTest.ObjectPath(['a']), + new jasmineUnderTest.ObjectPath(['a', 'b']) + ]); + }); + + it('visits children in the order they were recorded', function() { + var tree = new jasmineUnderTest.MismatchTree(); + tree.add(new jasmineUnderTest.ObjectPath(['length'])); + tree.add(new jasmineUnderTest.ObjectPath([1])); + var visited = []; + + tree.traverse(function (path) { + visited.push(path); + return true; + }); + + expect(visited).toEqual([ + new jasmineUnderTest.ObjectPath([]), + new jasmineUnderTest.ObjectPath(['length']), + new jasmineUnderTest.ObjectPath([1]) + ]); + }); + + it('does not visit children if the callback returns falsy', function() { + var tree = new jasmineUnderTest.MismatchTree(); + tree.add(new jasmineUnderTest.ObjectPath(['a', 'b'])); + var visited = []; + + tree.traverse(function (path) { + visited.push(path); + return path.depth() === 0; + }); + + expect(visited).toEqual([ + new jasmineUnderTest.ObjectPath([]), + new jasmineUnderTest.ObjectPath(['a']) + ]); + }); + }); + + function formatter() { + } + +}); diff --git a/spec/core/matchers/NullDiffBuilderSpec.js b/spec/core/matchers/NullDiffBuilderSpec.js index a9aac3db..3333776b 100644 --- a/spec/core/matchers/NullDiffBuilderSpec.js +++ b/spec/core/matchers/NullDiffBuilderSpec.js @@ -1,13 +1,8 @@ -describe('NullDiffBuilder', function() { - it('responds to withPath() by calling the passed function', function() { +describe('NullDiffBuilder', function () { + it('responds to withPath() by calling the passed function', function () { var spy = jasmine.createSpy('callback'); jasmineUnderTest.NullDiffBuilder().withPath('does not matter', spy); expect(spy).toHaveBeenCalled(); }); - it('responds to record()', function() { - expect(function() { - jasmineUnderTest.NullDiffBuilder().record('does not matter'); - }).not.toThrow(); - }) }); diff --git a/spec/core/matchers/ObjectPathSpec.js b/spec/core/matchers/ObjectPathSpec.js index 88b023d1..9750272e 100644 --- a/spec/core/matchers/ObjectPathSpec.js +++ b/spec/core/matchers/ObjectPathSpec.js @@ -39,5 +39,13 @@ describe('ObjectPath', function() { expect(path.toString()).toEqual('$.foo'); expect(root.toString()).toEqual(''); - }) + }); + + describe('#dereference', function() { + it('returns the value corresponding to the path', function () { + var path = new ObjectPath().add('foo').add(1).add('bar'); + var obj = {foo: ['', {bar: 42}]}; + expect(path.dereference(obj)).toEqual(42); + }); + }); }); diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index 1c0903ba..48f4781a 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -730,26 +730,26 @@ describe("matchersUtil", function() { var diffBuilder = new jasmineUnderTest.DiffBuilder(), matchersUtil = new jasmineUnderTest.MatchersUtil(); - spyOn(diffBuilder, 'record'); + spyOn(diffBuilder, 'recordMismatch'); spyOn(diffBuilder, 'withPath').and.callThrough(); matchersUtil.equals([1], [2], [], diffBuilder); expect(diffBuilder.withPath).toHaveBeenCalledWith('length', jasmine.any(Function)); expect(diffBuilder.withPath).toHaveBeenCalledWith(0, jasmine.any(Function)); - expect(diffBuilder.record).toHaveBeenCalledWith(1, 2); + expect(diffBuilder.recordMismatch).toHaveBeenCalledWith(); }); it('uses a diffBuilder if one is provided as the third argument', function() { var diffBuilder = new jasmineUnderTest.DiffBuilder(), matchersUtil = new jasmineUnderTest.MatchersUtil(); - spyOn(diffBuilder, 'record'); + spyOn(diffBuilder, 'recordMismatch'); spyOn(diffBuilder, 'withPath').and.callThrough(); matchersUtil.equals([1], [2], diffBuilder); expect(diffBuilder.withPath).toHaveBeenCalledWith('length', jasmine.any(Function)); expect(diffBuilder.withPath).toHaveBeenCalledWith(0, jasmine.any(Function)); - expect(diffBuilder.record).toHaveBeenCalledWith(1, 2); + expect(diffBuilder.recordMismatch).toHaveBeenCalled(); }); }); diff --git a/spec/core/matchers/toEqualSpec.js b/spec/core/matchers/toEqualSpec.js index 5bfc7715..78b40ef0 100644 --- a/spec/core/matchers/toEqualSpec.js +++ b/spec/core/matchers/toEqualSpec.js @@ -97,8 +97,12 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("uses custom object formatters to pretty-print properties", function() { - function formatter(x) { return '|' + x + '|'; } + it("uses custom object formatters to pretty-print simple properties", function() { + function formatter(x) { + if (typeof x === 'number') { + return '|' + x + '|'; + } + } var actual = {x: {y: 1, z: 2, f: 4}}, expected = {x: {y: 1, z: 2, g: 3}}, @@ -114,8 +118,12 @@ describe("toEqual", function() { expect(matcher.compare(actual, expected).message).toEqual(message); }); - it("uses custom object formatters to build diffs", function() { - function formatter(x) { return '|' + x + '|'; } + it("uses custom object formatters to show simple values in diffs", function() { + function formatter(x) { + if (typeof x === 'number') { + return '|' + x + '|'; + } + } var actual = [{foo: 4}], expected = [{foo: 5}], @@ -127,6 +135,30 @@ describe("toEqual", function() { expect(matcher.compare(actual, expected).message).toEqual(message); }); + it("uses custom object formatters to show more complex objects diffs", function() { + function formatter(x) { + if (x.hasOwnProperty('a')) { + return '[thing with a=' + x.a + ', b=' + x.b + ']'; + } + } + + var actual = [{ + foo: {a: 1, b: 2}, + bar: 'should not be pretty printed' + }], + expected = [{ + foo: {a: 5, b: 2}, + bar: "shouldn't be pretty printed" + }], + prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]), + util = new jasmineUnderTest.MatchersUtil({pp: prettyPrinter}), + matcher = jasmineUnderTest.matchers.toEqual(util), + message = "Expected $[0].foo = [thing with a=1, b=2] to equal [thing with a=5, b=2].\n" + + "Expected $[0].bar = 'should not be pretty printed' to equal 'shouldn't be pretty printed'."; + + expect(matcher.compare(actual, expected).message).toEqual(message); + }); + it("reports extra and missing properties of the root-level object", function() { var actual = {x: 1}, expected = {a: 1}, @@ -303,10 +335,14 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("uses custom object formatters to report objects with different constructors", function () { + it("uses custom object formatters for the value but not the type when reporting objects with different constructors", function () { function Foo() {} function Bar() {} - function formatter(x) { return '|' + x + '|'; } + function formatter(x) { + if (x instanceof Foo || x instanceof Bar) { + return '|' + x + '|'; + } + } var actual = {x: new Foo()}, expected = {x: new Bar()}, @@ -329,6 +365,11 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); + it("reports value mismatches at the root level", function() { + expect(compareEquals(1, 2).message).toEqual("Expected 1 to equal 2."); + }); + + it("reports mismatches between objects with their own constructor property", function () { function Foo() {} function Bar() {} @@ -839,7 +880,11 @@ describe("toEqual", function() { }); it("uses custom object formatters when the actual array is longer", function() { - function formatter(x) { return '|' + x + '|'; } + function formatter(x) { + if (typeof x === 'number') { + return '|' + x + '|'; + } + } var actual = [1, 1, 2, 3, 5], expected = [1, 1, 2, 3], diff --git a/src/core/PrettyPrinter.js b/src/core/PrettyPrinter.js index a15177ce..5faa3bbf 100644 --- a/src/core/PrettyPrinter.js +++ b/src/core/PrettyPrinter.js @@ -102,15 +102,7 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { }; SinglePrettyPrintRun.prototype.applyCustomFormatters_ = function(value) { - var i, result; - - for (i = 0; i < this.customObjectFormatters_.length; i++) { - result = this.customObjectFormatters_[i](value); - - if (result !== undefined) { - return result; - } - } + return customFormat(value, this.customObjectFormatters_); }; SinglePrettyPrintRun.prototype.iterateObject = function(obj, fn) { @@ -383,16 +375,31 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { return extraKeys; } + function customFormat(value, customObjectFormatters) { + var i, result; + + for (i = 0; i < customObjectFormatters.length; i++) { + result = customObjectFormatters[i](value); + + if (result !== undefined) { + return result; + } + } + } + return function(customObjectFormatters) { + customObjectFormatters = customObjectFormatters || []; + var pp = function(value) { - var prettyPrinter = new SinglePrettyPrintRun( - customObjectFormatters || [], - pp - ); + var prettyPrinter = new SinglePrettyPrintRun(customObjectFormatters, pp); prettyPrinter.format(value); return prettyPrinter.stringParts.join(''); }; + pp.customFormat_ = function(value) { + return customFormat(value, customObjectFormatters); + }; + return pp; }; }; diff --git a/src/core/matchers/DiffBuilder.js b/src/core/matchers/DiffBuilder.js index f5517e17..197e4c71 100644 --- a/src/core/matchers/DiffBuilder.js +++ b/src/core/matchers/DiffBuilder.js @@ -1,17 +1,51 @@ -getJasmineRequireObj().DiffBuilder = function(j$) { +getJasmineRequireObj().DiffBuilder = function (j$) { return function DiffBuilder(config) { - var path = new j$.ObjectPath(), - mismatches = [], - prettyPrinter = (config || {}).prettyPrinter || j$.makePrettyPrinter(); + var prettyPrinter = (config || {}).prettyPrinter || j$.makePrettyPrinter(), + mismatches = new j$.MismatchTree(), + path = new j$.ObjectPath(), + actualRoot = undefined, + expectedRoot = undefined; return { - record: function (actual, expected, formatter) { - formatter = formatter || defaultFormatter; - mismatches.push(formatter(actual, expected, path, prettyPrinter)); + setRoots: function (actual, expected) { + actualRoot = actual; + expectedRoot = expected; + }, + + recordMismatch: function (formatter) { + mismatches.add(path, formatter); }, getMessage: function () { - return mismatches.join('\n'); + var messages = []; + + mismatches.traverse(function (path, isLeaf, formatter) { + var actualCustom, expectedCustom, useCustom, + actual = path.dereference(actualRoot), + expected = path.dereference(expectedRoot); + + if (formatter) { + messages.push(formatter(actual, expected, path, prettyPrinter)); + return true; + } + + actualCustom = prettyPrinter.customFormat_(actual); + expectedCustom = prettyPrinter.customFormat_(expected); + useCustom = !(j$.util.isUndefined(actualCustom) && j$.util.isUndefined(expectedCustom)); + + if (useCustom) { + messages.push(wrapPrettyPrinted(actualCustom, expectedCustom, path)); + return false; // don't recurse further + } + + if (isLeaf) { + messages.push(defaultFormatter(actual, expected, path, prettyPrinter)); + } + + return true; + }); + + return messages.join('\n'); }, withPath: function (pathComponent, block) { @@ -22,12 +56,16 @@ getJasmineRequireObj().DiffBuilder = function(j$) { } }; - function defaultFormatter (actual, expected, path, prettyPrinter) { + function defaultFormatter(actual, expected, path, prettyPrinter) { + return wrapPrettyPrinted(prettyPrinter(actual), prettyPrinter(expected), path); + } + + function wrapPrettyPrinted(actual, expected, path) { return 'Expected ' + path + (path.depth() ? ' = ' : '') + - prettyPrinter(actual) + + actual + ' to equal ' + - prettyPrinter(expected) + + expected + '.'; } }; diff --git a/src/core/matchers/MismatchTree.js b/src/core/matchers/MismatchTree.js new file mode 100644 index 00000000..1ce356de --- /dev/null +++ b/src/core/matchers/MismatchTree.js @@ -0,0 +1,62 @@ +getJasmineRequireObj().MismatchTree = function (j$) { + + /* + To be able to apply custom object formatters at all possible levels of an + object graph, DiffBuilder needs to be able to know not just where the + mismatch occurred but also all ancestors of the mismatched value in both + the expected and actual object graphs. MismatchTree maintains that context + and provides it via the traverse method. + */ + function MismatchTree(path) { + this.path = path || new j$.ObjectPath([]); + this.formatter = undefined; + this.children = []; + this.isMismatch = false; + } + + MismatchTree.prototype.add = function (path, formatter) { + var key, child; + + if (path.depth() === 0) { + this.formatter = formatter; + this.isMismatch = true; + } else { + key = path.components[0]; + path = path.shift(); + child = this.child(key); + + if (!child) { + child = new MismatchTree(this.path.add(key)); + this.children.push(child); + } + + child.add(path, formatter); + } + }; + + MismatchTree.prototype.traverse = function (visit) { + var i, hasChildren = this.children.length > 0; + + if (this.isMismatch || hasChildren) { + if (visit(this.path, !hasChildren, this.formatter)) { + for (i = 0; i < this.children.length; i++) { + this.children[i].traverse(visit); + } + } + } + }; + + MismatchTree.prototype.child = function(key) { + var i, pathEls; + + for (i = 0; i < this.children.length; i++) { + pathEls = this.children[i].path.components; + if (pathEls[pathEls.length - 1] === key) { + return this.children[i]; + } + } + }; + + return MismatchTree; +}; + diff --git a/src/core/matchers/NullDiffBuilder.js b/src/core/matchers/NullDiffBuilder.js index de7d3464..cb6672e4 100644 --- a/src/core/matchers/NullDiffBuilder.js +++ b/src/core/matchers/NullDiffBuilder.js @@ -4,7 +4,8 @@ getJasmineRequireObj().NullDiffBuilder = function(j$) { withPath: function(_, block) { block(); }, - record: function() {} + setRoots: function() {}, + recordMismatch: function() {} }; }; }; diff --git a/src/core/matchers/ObjectPath.js b/src/core/matchers/ObjectPath.js index cd1629e2..266e8e62 100644 --- a/src/core/matchers/ObjectPath.js +++ b/src/core/matchers/ObjectPath.js @@ -11,10 +11,24 @@ getJasmineRequireObj().ObjectPath = function(j$) { } }; + ObjectPath.prototype.dereference = function(obj) { + var i; + + for (i = 0; i < this.components.length; i++) { + obj = obj[this.components[i]]; + } + + return obj; + }; + ObjectPath.prototype.add = function(component) { return new ObjectPath(this.components.concat([component])); }; + ObjectPath.prototype.shift = function() { + return new ObjectPath(this.components.slice(1)); + }; + ObjectPath.prototype.depth = function() { return this.components.length; }; diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index f38b9185..bd7664a0 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -69,7 +69,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (asymmetricA) { result = a.asymmetricMatch(b, shim); if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; } @@ -77,7 +77,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (asymmetricB) { result = b.asymmetricMatch(a, shim); if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; } @@ -95,6 +95,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { customTesters = customTesters || this.customTesters_; diffBuilder = diffBuilder || j$.NullDiffBuilder(); + diffBuilder.setRoots(a, b); return this.eq_(a, b, [], [], customTesters, diffBuilder); }; @@ -113,7 +114,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { var customTesterResult = customTesters[i](a, b); if (!j$.util.isUndefined(customTesterResult)) { if (!customTesterResult) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return customTesterResult; } @@ -122,7 +123,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (a instanceof Error && b instanceof Error) { result = a.message == b.message; if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; } @@ -132,7 +133,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (a === b) { result = a !== 0 || 1 / a == 1 / b; if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; } @@ -140,13 +141,13 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (a === null || b === null) { result = a === b; if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; } var className = Object.prototype.toString.call(a); if (className != Object.prototype.toString.call(b)) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } switch (className) { @@ -156,7 +157,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // equivalent to `new String("5")`. result = a == String(b); if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; case '[object Number]': @@ -164,7 +165,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // other numeric values. result = a != +a ? b != +b : (a === 0 ? 1 / a == 1 / b : a == +b); if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; case '[object Date]': @@ -174,7 +175,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // of `NaN` are not equivalent. result = +a == +b; if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; // RegExps are compared by their source patterns and flags. @@ -185,7 +186,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { a.ignoreCase == b.ignoreCase; } if (typeof a != 'object' || typeof b != 'object') { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } @@ -195,12 +196,12 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // At first try to use DOM3 method isEqualNode result = a.isEqualNode(b); if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); } return result; } if (aIsDomNode || bIsDomNode) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } @@ -230,7 +231,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { diffBuilder.withPath('length', function() { if (aLength !== bLength) { - diffBuilder.record(aLength, bLength); + diffBuilder.recordMismatch(); result = false; } }); @@ -238,7 +239,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { for (i = 0; i < aLength || i < bLength; i++) { diffBuilder.withPath(i, function() { if (i >= bLength) { - diffBuilder.record(a[i], void 0, actualArrayIsLongerFormatter.bind(null, self.pp)); + diffBuilder.recordMismatch(actualArrayIsLongerFormatter.bind(null, self.pp)); result = false; } else { result = self.eq_(i < aLength ? a[i] : void 0, i < bLength ? b[i] : void 0, aStack, bStack, customTesters, diffBuilder) && result; @@ -250,7 +251,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } } else if (j$.isMap(a) && j$.isMap(b)) { if (a.size != b.size) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } @@ -292,12 +293,12 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } } else if (j$.isSet(a) && j$.isSet(b)) { if (a.size != b.size) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } @@ -342,7 +343,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } if (!result) { - diffBuilder.record(a, b); + diffBuilder.recordMismatch(); return false; } } else { @@ -355,7 +356,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { a instanceof aCtor && b instanceof bCtor && !(aCtor instanceof aCtor && bCtor instanceof bCtor)) { - diffBuilder.record(a, b, constructorsAreDifferentFormatter.bind(null, this.pp)); + diffBuilder.recordMismatch(constructorsAreDifferentFormatter.bind(null, this.pp)); return false; } } @@ -366,7 +367,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // Ensure that both objects contain the same number of properties before comparing deep equality. if (keys(b, className == '[object Array]').length !== size) { - diffBuilder.record(a, b, objectKeysAreDifferentFormatter.bind(null, this.pp)); + diffBuilder.recordMismatch(objectKeysAreDifferentFormatter.bind(null, this.pp)); return false; } @@ -374,7 +375,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { key = aKeys[i]; // Deep compare each member if (!j$.util.has(b, key)) { - diffBuilder.record(a, b, objectKeysAreDifferentFormatter.bind(null, this.pp)); + diffBuilder.recordMismatch(objectKeysAreDifferentFormatter.bind(null, this.pp)); result = false; continue; } @@ -480,7 +481,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } function isDiffBuilder(obj) { - return obj && typeof obj.record === 'function'; + return obj && typeof obj.recordMismatch === 'function'; } return MatchersUtil; diff --git a/src/core/requireCore.js b/src/core/requireCore.js index a21044ff..0a30f424 100644 --- a/src/core/requireCore.js +++ b/src/core/requireCore.js @@ -84,6 +84,7 @@ var getJasmineRequireObj = (function(jasmineGlobal) { j$.DiffBuilder = jRequire.DiffBuilder(j$); j$.NullDiffBuilder = jRequire.NullDiffBuilder(j$); j$.ObjectPath = jRequire.ObjectPath(j$); + j$.MismatchTree = jRequire.MismatchTree(j$); j$.GlobalErrors = jRequire.GlobalErrors(j$); j$.Truthy = jRequire.Truthy(j$); From d41139fea285f6f7906a82059f803f60f7400c22 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Fri, 7 Feb 2020 13:03:35 -0800 Subject: [PATCH 122/201] Added jsdocs for MatchersUtil --- lib/jasmine-core/jasmine.js | 35 +++++++++++++++++++++++++++++++ src/core/matchers/matchersUtil.js | 35 +++++++++++++++++++++++++++++++ 2 files changed, 70 insertions(+) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 2616482f..15627639 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -4264,12 +4264,38 @@ getJasmineRequireObj().DiffBuilder = function (j$) { getJasmineRequireObj().MatchersUtil = function(j$) { // TODO: convert all uses of j$.pp to use the injected pp + /** + * _Note:_ Do not construct this directly. Jasmine will construct one and + * pass it to matchers and asymmetric equality testers. + * @name MatchersUtil + * @since 2.0.0 + * @classdesc Utilities for use in implementing matchers + * @constructor + */ function MatchersUtil(options) { options = options || {}; this.customTesters_ = options.customTesters || []; + /** + * Formats a value for use in matcher failure messages and similar contexts, + * taking into account the current set of custom value formatters. + * @function + * @name MatchersUtil#pp + * @param {*} value The value to pretty-print + * @return {string} The pretty-printed value + */ this.pp = options.pp || function() {}; }; + /** + * Determines whether `haystack` contains `needle`, using the same comparison + * logic as {@link MatchersUtil#equals}. + * @function + * @name MatchersUtil#contains + * @param {*} haystack The collection to search + * @param {*} needle The value to search for + * @param [customTesters] An array of custom equality testers + * @returns {boolean} True if `needle` was found in `haystack` + */ MatchersUtil.prototype.contains = function(haystack, needle, customTesters) { if (j$.isSet(haystack)) { return haystack.has(needle); @@ -4346,6 +4372,15 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } }; + /** + * Determines whether two values are deeply equal to each other. + * @function + * @name MatchersUtil#equals + * @param {*} a The first value to compare + * @param {*} b The second value to compare + * @param [customTesters] An array of custom equality testers + * @returns {boolean} True if the values are equal + */ MatchersUtil.prototype.equals = function(a, b, customTestersOrDiffBuilder, diffBuilderOrNothing) { var customTesters, diffBuilder; diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index bd7664a0..bd3d46cd 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -1,12 +1,38 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // TODO: convert all uses of j$.pp to use the injected pp + /** + * _Note:_ Do not construct this directly. Jasmine will construct one and + * pass it to matchers and asymmetric equality testers. + * @name MatchersUtil + * @since 2.0.0 + * @classdesc Utilities for use in implementing matchers + * @constructor + */ function MatchersUtil(options) { options = options || {}; this.customTesters_ = options.customTesters || []; + /** + * Formats a value for use in matcher failure messages and similar contexts, + * taking into account the current set of custom value formatters. + * @function + * @name MatchersUtil#pp + * @param {*} value The value to pretty-print + * @return {string} The pretty-printed value + */ this.pp = options.pp || function() {}; }; + /** + * Determines whether `haystack` contains `needle`, using the same comparison + * logic as {@link MatchersUtil#equals}. + * @function + * @name MatchersUtil#contains + * @param {*} haystack The collection to search + * @param {*} needle The value to search for + * @param [customTesters] An array of custom equality testers + * @returns {boolean} True if `needle` was found in `haystack` + */ MatchersUtil.prototype.contains = function(haystack, needle, customTesters) { if (j$.isSet(haystack)) { return haystack.has(needle); @@ -83,6 +109,15 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } }; + /** + * Determines whether two values are deeply equal to each other. + * @function + * @name MatchersUtil#equals + * @param {*} a The first value to compare + * @param {*} b The second value to compare + * @param [customTesters] An array of custom equality testers + * @returns {boolean} True if the values are equal + */ MatchersUtil.prototype.equals = function(a, b, customTestersOrDiffBuilder, diffBuilderOrNothing) { var customTesters, diffBuilder; From ea3dd9dffc66942cd1bdf5367cce1cdcf34b7f59 Mon Sep 17 00:00:00 2001 From: Pivotal Date: Mon, 10 Feb 2020 14:12:56 -0800 Subject: [PATCH 123/201] Refer to MatchersUtil instances as matchersUtil, not util --- lib/jasmine-core/jasmine.js | 41 +++++++++-------- spec/core/AsyncExpectationSpec.js | 44 ++++++++++--------- spec/core/ExpectationFilterChainSpec.js | 6 +-- spec/core/ExpectationSpec.js | 31 +++++++------ spec/core/matchers/toBeSpec.js | 28 ++++++------ spec/core/matchers/toContainSpec.js | 6 +-- spec/core/matchers/toEqualSpec.js | 36 +++++++-------- .../core/matchers/toHaveBeenCalledWithSpec.js | 12 ++--- spec/core/matchers/toThrowErrorSpec.js | 37 ++++++---------- spec/core/matchers/toThrowSpec.js | 16 +++---- spec/helpers/integrationMatchers.js | 2 +- spec/npmPackage/npmPackageSpec.js | 2 +- src/core/Env.js | 4 +- src/core/Expectation.js | 4 +- src/core/ExpectationFilterChain.js | 2 +- src/core/Expector.js | 13 ++++-- src/core/matchers/async/toBeRejected.js | 2 +- src/core/matchers/async/toBeResolved.js | 2 +- src/core/matchers/toBe.js | 4 +- src/core/matchers/toContain.js | 4 +- src/core/matchers/toEqual.js | 6 +-- 21 files changed, 154 insertions(+), 148 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 15627639..cce34724 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1263,7 +1263,7 @@ getJasmineRequireObj().Env = function(j$) { runnableResources[spec.id].customEqualityTesters; return j$.Expectation.factory({ - util: makeMatchersUtil(), + matchersUtil: makeMatchersUtil(), customEqualityTesters: customEqualityTesters, customMatchers: runnableResources[spec.id].customMatchers, actual: actual, @@ -1277,7 +1277,7 @@ getJasmineRequireObj().Env = function(j$) { var asyncExpectationFactory = function(actual, spec) { return j$.Expectation.asyncFactory({ - util: makeMatchersUtil(), + matchersUtil: makeMatchersUtil(), customEqualityTesters: runnableResources[spec.id].customEqualityTesters, customAsyncMatchers: runnableResources[spec.id].customAsyncMatchers, actual: actual, @@ -3561,7 +3561,7 @@ getJasmineRequireObj().Expectation = function(j$) { return result; } - function negatedFailureMessage(result, matcherName, args, util) { + function negatedFailureMessage(result, matcherName, args, matchersUtil) { if (result.message) { if (j$.isFunction_(result.message)) { return result.message(); @@ -3573,7 +3573,7 @@ getJasmineRequireObj().Expectation = function(j$) { args = args.slice(); args.unshift(true); args.unshift(matcherName); - return util.buildFailureMessage.apply(util, args); + return matchersUtil.buildFailureMessage.apply(matchersUtil, args); } function negate(result) { @@ -3645,7 +3645,7 @@ getJasmineRequireObj().ExpectationFilterChain = function() { result, matcherName, args, - util + matchersUtil ) { return this.callFirst_('buildFailureMessage', arguments).result; }; @@ -3747,7 +3747,9 @@ getJasmineRequireObj().buildExpectationResult = function() { getJasmineRequireObj().Expector = function(j$) { function Expector(options) { - this.util = options.util || { buildFailureMessage: function() {} }; + this.matchersUtil = options.matchersUtil || { + buildFailureMessage: function() {} + }; this.customEqualityTesters = options.customEqualityTesters || []; this.actual = options.actual; this.addExpectationResult = options.addExpectationResult || function() {}; @@ -3765,7 +3767,7 @@ getJasmineRequireObj().Expector = function(j$) { this.args.unshift(this.actual); - var matcher = matcherFactory(this.util, this.customEqualityTesters); + var matcher = matcherFactory(this.matchersUtil, this.customEqualityTesters); var comparisonFunc = this.filters.selectComparisonFunc(matcher); return comparisonFunc || matcher.compare; }; @@ -3781,7 +3783,7 @@ getJasmineRequireObj().Expector = function(j$) { result, this.matcherName, this.args, - this.util, + this.matchersUtil, defaultMessage ); return this.filters.modifyFailureMessage(msg || defaultMessage()); @@ -3791,7 +3793,10 @@ getJasmineRequireObj().Expector = function(j$) { var args = self.args.slice(); args.unshift(false); args.unshift(self.matcherName); - return self.util.buildFailureMessage.apply(self.util, args); + return self.matchersUtil.buildFailureMessage.apply( + self.matchersUtil, + args + ); } else if (j$.isFunction_(result.message)) { return result.message(); } else { @@ -3943,7 +3948,7 @@ getJasmineRequireObj().toBeRejected = function(j$) { * @example * return expectAsync(aPromise).toBeRejected(); */ - return function toBeRejected(util) { + return function toBeRejected() { return { compare: function(actual) { if (!j$.isPromiseLike(actual)) { @@ -4120,7 +4125,7 @@ getJasmineRequireObj().toBeResolved = function(j$) { * @example * return expectAsync(aPromise).toBeResolved(); */ - return function toBeResolved(util) { + return function toBeResolved() { return { compare: function(actual) { if (!j$.isPromiseLike(actual)) { @@ -4972,7 +4977,7 @@ getJasmineRequireObj().toBe = function(j$) { * @example * expect(thing).toBe(realThing); */ - function toBe(util) { + function toBe(matchersUtil) { var tip = ' Tip: To check for deep equality, use .toEqual() instead of .toBe().'; return { @@ -4982,7 +4987,7 @@ getJasmineRequireObj().toBe = function(j$) { }; if (typeof expected === 'object') { - result.message = util.buildFailureMessage('toBe', result.pass, actual, expected) + tip; + result.message = matchersUtil.buildFailureMessage('toBe', result.pass, actual, expected) + tip; } return result; @@ -5428,12 +5433,12 @@ getJasmineRequireObj().toContain = function() { * expect(array).toContain(anElement); * expect(string).toContain(substring); */ - function toContain(util) { + function toContain(matchersUtil) { return { compare: function(actual, expected) { return { - pass: util.contains(actual, expected) + pass: matchersUtil.contains(actual, expected) }; } }; @@ -5452,15 +5457,15 @@ getJasmineRequireObj().toEqual = function(j$) { * @example * expect(bigObject).toEqual({"foo": ['bar', 'baz']}); */ - function toEqual(util) { + function toEqual(matchersUtil) { return { compare: function(actual, expected) { var result = { pass: false }, - diffBuilder = j$.DiffBuilder({prettyPrinter: util.pp}); + diffBuilder = j$.DiffBuilder({prettyPrinter: matchersUtil.pp}); - result.pass = util.equals(actual, expected, diffBuilder); + result.pass = matchersUtil.equals(actual, expected, diffBuilder); // TODO: only set error message if test fails result.message = diffBuilder.getMessage(); diff --git a/spec/core/AsyncExpectationSpec.js b/spec/core/AsyncExpectationSpec.js index 74eb2dad..40f63731 100644 --- a/spec/core/AsyncExpectationSpec.js +++ b/spec/core/AsyncExpectationSpec.js @@ -26,7 +26,7 @@ describe('AsyncExpectation', function() { actual = Promise.resolve(), pp = jasmineUnderTest.makePrettyPrinter(), expectation = jasmineUnderTest.Expectation.asyncFactory({ - util: new jasmineUnderTest.MatchersUtil({ pp: pp }), + matchersUtil: new jasmineUnderTest.MatchersUtil({ pp: pp }), actual: actual, addExpectationResult: addExpectationResult }); @@ -48,7 +48,9 @@ describe('AsyncExpectation', function() { var addExpectationResult = jasmine.createSpy('addExpectationResult'), actual = Promise.reject(), expectation = jasmineUnderTest.Expectation.asyncFactory({ - util: new jasmineUnderTest.MatchersUtil({ pp: function() {} }), + matchersUtil: new jasmineUnderTest.MatchersUtil({ + pp: function() {} + }), actual: actual, addExpectationResult: addExpectationResult }); @@ -92,7 +94,7 @@ describe('AsyncExpectation', function() { it('prepends the context to the generated failure message', function() { jasmine.getEnv().requirePromises(); - var util = { + var matchersUtil = { buildFailureMessage: function() { return 'failure message'; } @@ -101,7 +103,7 @@ describe('AsyncExpectation', function() { expectation = jasmineUnderTest.Expectation.asyncFactory({ actual: Promise.reject('rejected'), addExpectationResult: addExpectationResult, - util: util + matchersUtil: matchersUtil }); return expectation @@ -120,7 +122,7 @@ describe('AsyncExpectation', function() { it('prepends the context to a custom failure message', function() { jasmine.getEnv().requirePromises(); - var util = { + var matchersUtil = { buildFailureMessage: function() { return 'failure message'; }, @@ -130,7 +132,7 @@ describe('AsyncExpectation', function() { expectation = jasmineUnderTest.Expectation.asyncFactory({ actual: Promise.reject('b'), addExpectationResult: addExpectationResult, - util: util + matchersUtil: matchersUtil }); return expectation @@ -151,7 +153,7 @@ describe('AsyncExpectation', function() { pending('should actually work, but no custom matchers for async yet'); jasmine.getEnv().requirePromises(); - var util = { + var matchersUtil = { buildFailureMessage: function() { return 'failure message'; } @@ -161,7 +163,7 @@ describe('AsyncExpectation', function() { expectation = jasmineUnderTest.Expectation.asyncFactory({ actual: actual, addExpectationResult: addExpectationResult, - util: util + matchersUtil: matchersUtil }); return expectation @@ -186,7 +188,7 @@ describe('AsyncExpectation', function() { expectation = jasmineUnderTest.Expectation.asyncFactory({ actual: actual, addExpectationResult: addExpectationResult, - util: new jasmineUnderTest.MatchersUtil({ pp: pp }) + matchersUtil: new jasmineUnderTest.MatchersUtil({ pp: pp }) }); return expectation @@ -211,7 +213,7 @@ describe('AsyncExpectation', function() { expectation = jasmineUnderTest.Expectation.asyncFactory({ actual: actual, addExpectationResult: addExpectationResult, - util: new jasmineUnderTest.MatchersUtil({ + matchersUtil: new jasmineUnderTest.MatchersUtil({ pp: jasmineUnderTest.makePrettyPrinter() }) }); @@ -261,7 +263,7 @@ describe('AsyncExpectation', function() { matchers = { toFoo: matcherFactory }, - util = { + matchersUtil = { buildFailureMessage: jasmine.createSpy('buildFailureMessage') }, customEqualityTesters = ['a'], @@ -269,7 +271,7 @@ describe('AsyncExpectation', function() { expectation; expectation = jasmineUnderTest.Expectation.asyncFactory({ - util: util, + matchersUtil: matchersUtil, customAsyncMatchers: matchers, customEqualityTesters: customEqualityTesters, actual: 'an actual', @@ -278,7 +280,7 @@ describe('AsyncExpectation', function() { return expectation.toFoo('hello').then(function() { expect(matcherFactory).toHaveBeenCalledWith( - util, + matchersUtil, customEqualityTesters ); }); @@ -297,14 +299,14 @@ describe('AsyncExpectation', function() { }; } }, - util = { + matchersUtil = { buildFailureMessage: jasmine.createSpy('buildFailureMessage') }, addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation; expectation = jasmineUnderTest.Expectation.asyncFactory({ - util: util, + matchersUtil: matchersUtil, customAsyncMatchers: matchers, actual: 'an actual', addExpectationResult: addExpectationResult @@ -327,7 +329,7 @@ describe('AsyncExpectation', function() { }; } }, - util = { + matchersUtil = { buildFailureMessage: jasmine.createSpy('buildFailureMessage') }, addExpectationResult = jasmine.createSpy('addExpectationResult'), @@ -340,7 +342,7 @@ describe('AsyncExpectation', function() { expectation = jasmineUnderTest.Expectation.asyncFactory({ customAsyncMatchers: matchers, - util: util, + matchersUtil: matchersUtil, actual: 'an actual', addExpectationResult: addExpectationResult }); @@ -370,7 +372,7 @@ describe('AsyncExpectation', function() { }; } }, - util = { + matchersUtil = { buildFailureMessage: function() { return ''; } @@ -385,7 +387,7 @@ describe('AsyncExpectation', function() { expectation = jasmineUnderTest.Expectation.asyncFactory({ customAsyncMatchers: matchers, - util: util, + matchersUtil: matchersUtil, actual: 'an actual', addExpectationResult: addExpectationResult }); @@ -541,7 +543,7 @@ describe('AsyncExpectation', function() { }; } }, - util = { + matchersUtil = { buildFailureMessage: function() { return 'default message'; } @@ -558,7 +560,7 @@ describe('AsyncExpectation', function() { expectation = jasmineUnderTest.Expectation.asyncFactory({ customAsyncMatchers: matchers, actual: 'an actual', - util: util, + matchersUtil: matchersUtil, addExpectationResult: addExpectationResult }).not; diff --git a/spec/core/ExpectationFilterChainSpec.js b/spec/core/ExpectationFilterChainSpec.js index 911f6b30..009a5ba3 100644 --- a/spec/core/ExpectationFilterChainSpec.js +++ b/spec/core/ExpectationFilterChainSpec.js @@ -72,21 +72,21 @@ describe('ExpectationFilterChain', function() { matcherResult = { pass: false }, matcherName = 'foo', args = [], - util = {}, + matchersUtil = {}, result; result = chain.buildFailureMessage( matcherResult, matcherName, args, - util + matchersUtil ); expect(first).toHaveBeenCalledWith( matcherResult, matcherName, args, - util + matchersUtil ); expect(second).not.toHaveBeenCalled(); expect(result).toEqual('first'); diff --git a/spec/core/ExpectationSpec.js b/spec/core/ExpectationSpec.js index 5b205730..0ad411b9 100644 --- a/spec/core/ExpectationSpec.js +++ b/spec/core/ExpectationSpec.js @@ -37,7 +37,7 @@ describe('Expectation', function() { matchers = { toFoo: matcherFactory }, - util = { + matchersUtil = { buildFailureMessage: jasmine.createSpy('buildFailureMessage') }, customEqualityTesters = ['a'], @@ -45,7 +45,7 @@ describe('Expectation', function() { expectation; expectation = jasmineUnderTest.Expectation.factory({ - util: util, + matchersUtil: matchersUtil, customMatchers: matchers, customEqualityTesters: customEqualityTesters, actual: 'an actual', @@ -54,7 +54,10 @@ describe('Expectation', function() { expectation.toFoo('hello'); - expect(matcherFactory).toHaveBeenCalledWith(util, customEqualityTesters); + expect(matcherFactory).toHaveBeenCalledWith( + matchersUtil, + customEqualityTesters + ); }); it("wraps matchers's compare functions, passing the actual and expected", function() { @@ -68,14 +71,14 @@ describe('Expectation', function() { }; } }, - util = { + matchersUtil = { buildFailureMessage: jasmine.createSpy('buildFailureMessage') }, addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation; expectation = jasmineUnderTest.Expectation.factory({ - util: util, + matchersUtil: matchersUtil, customMatchers: matchers, actual: 'an actual', addExpectationResult: addExpectationResult @@ -96,7 +99,7 @@ describe('Expectation', function() { }; } }, - util = { + matchersUtil = { buildFailureMessage: jasmine.createSpy('buildFailureMessage') }, addExpectationResult = jasmine.createSpy('addExpectationResult'), @@ -104,7 +107,7 @@ describe('Expectation', function() { expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - util: util, + matchersUtil: matchersUtil, actual: 'an actual', addExpectationResult: addExpectationResult }); @@ -132,7 +135,7 @@ describe('Expectation', function() { }; } }, - util = { + matchersUtil = { buildFailureMessage: function() { return ''; } @@ -142,7 +145,7 @@ describe('Expectation', function() { expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - util: util, + matchersUtil: matchersUtil, actual: 'an actual', addExpectationResult: addExpectationResult }); @@ -275,7 +278,7 @@ describe('Expectation', function() { }; } }, - util = { + matchersUtil = { buildFailureMessage: function() { return 'default message'; } @@ -287,7 +290,7 @@ describe('Expectation', function() { expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, actual: 'an actual', - util: util, + matchersUtil: matchersUtil, addExpectationResult: addExpectationResult }).not; @@ -539,7 +542,7 @@ describe('Expectation', function() { }; } }, - util = { + matchersUtil = { buildFailureMessage: function() { return 'failure message'; } @@ -547,7 +550,7 @@ describe('Expectation', function() { addExpectationResult = jasmine.createSpy('addExpectationResult'), expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - util: util, + matchersUtil: matchersUtil, actual: 'an actual', addExpectationResult: addExpectationResult }); @@ -635,7 +638,7 @@ describe('Expectation', function() { pp = jasmineUnderTest.makePrettyPrinter(), expectation = jasmineUnderTest.Expectation.factory({ customMatchers: matchers, - util: new jasmineUnderTest.MatchersUtil({ pp: pp }), + matchersUtil: new jasmineUnderTest.MatchersUtil({ pp: pp }), actual: 'an actual', addExpectationResult: addExpectationResult }); diff --git a/spec/core/matchers/toBeSpec.js b/spec/core/matchers/toBeSpec.js index 49484f5f..4d74a6de 100644 --- a/spec/core/matchers/toBeSpec.js +++ b/spec/core/matchers/toBeSpec.js @@ -1,7 +1,7 @@ describe("toBe", function() { it("passes with no message when actual === expected", function() { - var util = new jasmineUnderTest.MatchersUtil(), - matcher = jasmineUnderTest.matchers.toBe(util), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result; result = matcher.compare(1, 1); @@ -9,8 +9,8 @@ describe("toBe", function() { }); it("passes with a custom message when expected is an array", function() { - var util = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.matchers.toBe(util), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result, array = [1]; @@ -20,8 +20,8 @@ describe("toBe", function() { }); it("passes with a custom message when expected is an object", function() { - var util = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.matchers.toBe(util), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result, obj = {foo: "bar"}; @@ -31,8 +31,8 @@ describe("toBe", function() { }); it("fails with no message when actual !== expected", function() { - var util = new jasmineUnderTest.MatchersUtil(), - matcher = jasmineUnderTest.matchers.toBe(util), + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result; result = matcher.compare(1, 2); @@ -41,8 +41,8 @@ describe("toBe", function() { }); it("fails with a custom message when expected is an array", function() { - var util = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.matchers.toBe(util), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result; result = matcher.compare([1], [1]); @@ -51,8 +51,8 @@ describe("toBe", function() { }); it("fails with a custom message when expected is an object", function() { - var util = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.matchers.toBe(util), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result; result = matcher.compare({foo: "bar"}, {foo: "bar"}); @@ -63,8 +63,8 @@ describe("toBe", function() { it("works with custom object formatters when expected is an object", function() { var formatter = function(x) { return '<' + x.foo + '>'; }, prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]), - util = new jasmineUnderTest.MatchersUtil({pp: prettyPrinter}), - matcher = jasmineUnderTest.matchers.toBe(util), + matchersUtil = new jasmineUnderTest.MatchersUtil({pp: prettyPrinter}), + matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result; result = matcher.compare({foo: "bar"}, {foo: "bar"}); diff --git a/spec/core/matchers/toContainSpec.js b/spec/core/matchers/toContainSpec.js index effe5862..5fd1c8f8 100644 --- a/spec/core/matchers/toContainSpec.js +++ b/spec/core/matchers/toContainSpec.js @@ -1,13 +1,13 @@ describe("toContain", function() { it("delegates to jasmineUnderTest.matchersUtil.contains", function() { - var util = { + var matchersUtil = { contains: jasmine.createSpy('delegated-contains').and.returnValue(true) }, - matcher = jasmineUnderTest.matchers.toContain(util), + matcher = jasmineUnderTest.matchers.toContain(matchersUtil), result; result = matcher.compare("ABC", "B"); - expect(util.contains).toHaveBeenCalledWith("ABC", "B"); + expect(matchersUtil.contains).toHaveBeenCalledWith("ABC", "B"); expect(result.pass).toBe(true); }); diff --git a/spec/core/matchers/toEqualSpec.js b/spec/core/matchers/toEqualSpec.js index 78b40ef0..be8e9f6d 100644 --- a/spec/core/matchers/toEqualSpec.js +++ b/spec/core/matchers/toEqualSpec.js @@ -2,10 +2,10 @@ describe("toEqual", function() { "use strict"; function compareEquals(actual, expected) { - var util = new jasmineUnderTest.MatchersUtil({ + var matchersUtil = new jasmineUnderTest.MatchersUtil({ pp: jasmineUnderTest.makePrettyPrinter() }), - matcher = jasmineUnderTest.matchers.toEqual(util); + matcher = jasmineUnderTest.matchers.toEqual(matchersUtil); var result = matcher.compare(actual, expected); @@ -13,19 +13,19 @@ describe("toEqual", function() { } it("delegates to equals function", function() { - var util = { + var matchersUtil = { equals: jasmine.createSpy('delegated-equals').and.returnValue(true), buildFailureMessage: function() { - return 'does not matter' + return 'does not matter'; }, DiffBuilder: new jasmineUnderTest.DiffBuilder() }, - matcher = jasmineUnderTest.matchers.toEqual(util), + matcher = jasmineUnderTest.matchers.toEqual(matchersUtil), result; result = matcher.compare(1, 1); - expect(util.equals).toHaveBeenCalledWith(1, 1, jasmine.anything()); + expect(matchersUtil.equals).toHaveBeenCalledWith(1, 1, jasmine.anything()); expect(result.pass).toBe(true); }); @@ -33,8 +33,8 @@ describe("toEqual", function() { var tester = function (a, b) { return a.toString() === b.toString(); }, - util = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}), - matcher = jasmineUnderTest.matchers.toEqual(util), + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}), + matcher = jasmineUnderTest.matchers.toEqual(matchersUtil), result; result = matcher.compare(1, '1'); @@ -107,8 +107,8 @@ describe("toEqual", function() { var actual = {x: {y: 1, z: 2, f: 4}}, expected = {x: {y: 1, z: 2, g: 3}}, pp = jasmineUnderTest.makePrettyPrinter([formatter]), - util = new jasmineUnderTest.MatchersUtil({pp: pp}), - matcher = jasmineUnderTest.matchers.toEqual(util), + matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), + matcher = jasmineUnderTest.matchers.toEqual(matchersUtil), message = "Expected $.x to have properties\n" + " g: |3|\n" + @@ -128,8 +128,8 @@ describe("toEqual", function() { var actual = [{foo: 4}], expected = [{foo: 5}], prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]), - util = new jasmineUnderTest.MatchersUtil({pp: prettyPrinter}), - matcher = jasmineUnderTest.matchers.toEqual(util), + matchersUtil = new jasmineUnderTest.MatchersUtil({pp: prettyPrinter}), + matcher = jasmineUnderTest.matchers.toEqual(matchersUtil), message = "Expected $[0].foo = |4| to equal |5|."; expect(matcher.compare(actual, expected).message).toEqual(message); @@ -151,8 +151,8 @@ describe("toEqual", function() { bar: "shouldn't be pretty printed" }], prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]), - util = new jasmineUnderTest.MatchersUtil({pp: prettyPrinter}), - matcher = jasmineUnderTest.matchers.toEqual(util), + matchersUtil = new jasmineUnderTest.MatchersUtil({pp: prettyPrinter}), + matcher = jasmineUnderTest.matchers.toEqual(matchersUtil), message = "Expected $[0].foo = [thing with a=1, b=2] to equal [thing with a=5, b=2].\n" + "Expected $[0].bar = 'should not be pretty printed' to equal 'shouldn't be pretty printed'."; @@ -348,8 +348,8 @@ describe("toEqual", function() { expected = {x: new Bar()}, message = "Expected $.x to be a kind of Bar, but was |[object Object]|.", pp = jasmineUnderTest.makePrettyPrinter([formatter]), - util = new jasmineUnderTest.MatchersUtil({pp: pp}), - matcher = jasmineUnderTest.matchers.toEqual(util); + matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), + matcher = jasmineUnderTest.matchers.toEqual(matchersUtil); expect(matcher.compare(actual, expected).message).toEqual(message); }); @@ -889,8 +889,8 @@ describe("toEqual", function() { var actual = [1, 1, 2, 3, 5], expected = [1, 1, 2, 3], pp = jasmineUnderTest.makePrettyPrinter([formatter]), - util = new jasmineUnderTest.MatchersUtil({pp: pp}), - matcher = jasmineUnderTest.matchers.toEqual(util), + matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), + matcher = jasmineUnderTest.matchers.toEqual(matchersUtil), message = 'Expected $.length = |5| to equal |4|.\n' + 'Unexpected $[4] = |5| in array.'; diff --git a/spec/core/matchers/toHaveBeenCalledWithSpec.js b/spec/core/matchers/toHaveBeenCalledWithSpec.js index 852dd837..5a320f68 100644 --- a/spec/core/matchers/toHaveBeenCalledWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledWithSpec.js @@ -1,11 +1,11 @@ describe("toHaveBeenCalledWith", function() { it("passes when the actual was called with matching parameters", function() { - var util = { + var matchersUtil = { contains: jasmine.createSpy('delegated-contains').and.returnValue(true), pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util), + matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(matchersUtil), calledSpy = new jasmineUnderTest.Env().createSpy('called-spy'), result; @@ -29,11 +29,11 @@ describe("toHaveBeenCalledWith", function() { }); it("fails when the actual was not called", function() { - var util = { + var matchersUtil = { contains: jasmine.createSpy('delegated-contains').and.returnValue(false), pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util), + matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(matchersUtil), uncalledSpy = new jasmineUnderTest.Env().createSpy('uncalled spy'), result; @@ -43,8 +43,8 @@ describe("toHaveBeenCalledWith", function() { }); it("fails when the actual was called with different parameters", function() { - var util = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(util), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(matchersUtil), calledSpy = new jasmineUnderTest.Env().createSpy('called spy'), result; diff --git a/spec/core/matchers/toThrowErrorSpec.js b/spec/core/matchers/toThrowErrorSpec.js index 8070719c..68fdf8be 100644 --- a/spec/core/matchers/toThrowErrorSpec.js +++ b/spec/core/matchers/toThrowErrorSpec.js @@ -192,10 +192,7 @@ describe("toThrowError", function() { }); it("passes if thrown is an Error and the expected the same Error", function() { - var util = { - equals: jasmine.createSpy('delegated-equal').and.returnValue(true) - }, - matcher = jasmineUnderTest.matchers.toThrowError(), + var matcher = jasmineUnderTest.matchers.toThrowError(), fn = function() { throw new Error(); }, @@ -208,10 +205,7 @@ describe("toThrowError", function() { }); it("passes if thrown is a custom error that takes arguments and the expected is the same error", function() { - var util = { - equals: jasmine.createSpy('delegated-equal').and.returnValue(true) - }, - matcher = jasmineUnderTest.matchers.toThrowError(), + var matcher = jasmineUnderTest.matchers.toThrowError(), CustomError = function CustomError(arg) { arg.x }, fn = function() { throw new CustomError({ x: 1 }); @@ -227,10 +221,7 @@ describe("toThrowError", function() { }); it("fails if thrown is an Error and the expected is a different Error", function() { - var util = { - equals: jasmine.createSpy('delegated-equal').and.returnValue(false) - }, - matcher = jasmineUnderTest.matchers.toThrowError(), + var matcher = jasmineUnderTest.matchers.toThrowError(), fn = function() { throw new Error(); }, @@ -243,11 +234,11 @@ describe("toThrowError", function() { }); it("passes if thrown is a type of Error and it is equal to the expected Error and message", function() { - var util = { + var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(true), pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrowError(util), + matcher = jasmineUnderTest.matchers.toThrowError(matchersUtil), fn = function() { throw new TypeError("foo"); }, @@ -260,12 +251,12 @@ describe("toThrowError", function() { }); it("passes if thrown is a custom error that takes arguments and it is equal to the expected custom error and message", function() { - var util = { + var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(true), pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrowError(util), - CustomError = function CustomError(arg) { this.message = arg.message }, + matcher = jasmineUnderTest.matchers.toThrowError(matchersUtil), + CustomError = function CustomError(arg) { this.message = arg.message; }, fn = function() { throw new CustomError({message: "foo"}); }, @@ -280,11 +271,11 @@ describe("toThrowError", function() { }); it("fails if thrown is a type of Error and the expected is a different Error", function() { - var util = { + var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(false), pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrowError(util), + matcher = jasmineUnderTest.matchers.toThrowError(matchersUtil), fn = function() { throw new TypeError("foo"); }, @@ -297,11 +288,11 @@ describe("toThrowError", function() { }); it("passes if thrown is a type of Error and has the same type as the expected Error and the message matches the expected message", function() { - var util = { + var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(true), pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrowError(util), + matcher = jasmineUnderTest.matchers.toThrowError(matchersUtil), fn = function() { throw new TypeError("foo"); }, @@ -314,11 +305,11 @@ describe("toThrowError", function() { }); it("fails if thrown is a type of Error and the expected is a different Error", function() { - var util = { + var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(false), pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrowError(util), + matcher = jasmineUnderTest.matchers.toThrowError(matchersUtil), fn = function() { throw new TypeError("foo"); }, diff --git a/spec/core/matchers/toThrowSpec.js b/spec/core/matchers/toThrowSpec.js index 979ddc1d..7144b2b3 100644 --- a/spec/core/matchers/toThrowSpec.js +++ b/spec/core/matchers/toThrowSpec.js @@ -23,11 +23,11 @@ describe("toThrow", function() { }); it("passes if it throws but there is no expected", function() { - var util = { + var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(true), pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrow(util), + matcher = jasmineUnderTest.matchers.toThrow(matchersUtil), fn = function() { throw 5; }, @@ -54,11 +54,11 @@ describe("toThrow", function() { }); it("passes if what is thrown is equivalent to what is expected", function() { - var util = { + var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(true), pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrow(util), + matcher = jasmineUnderTest.matchers.toThrow(matchersUtil), fn = function() { throw 5; }, @@ -71,11 +71,11 @@ describe("toThrow", function() { }); it("fails if what is thrown is not equivalent to what is expected", function() { - var util = { + var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(false), pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrow(util), + matcher = jasmineUnderTest.matchers.toThrow(matchersUtil), fn = function() { throw 5; }, @@ -88,11 +88,11 @@ describe("toThrow", function() { }); it("fails if what is thrown is not equivalent to undefined", function() { - var util = { + var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(false), pp: jasmineUnderTest.makePrettyPrinter() }, - matcher = jasmineUnderTest.matchers.toThrow(util), + matcher = jasmineUnderTest.matchers.toThrow(matchersUtil), fn = function() { throw 5; }, diff --git a/spec/helpers/integrationMatchers.js b/spec/helpers/integrationMatchers.js index f473385c..75bec185 100644 --- a/spec/helpers/integrationMatchers.js +++ b/spec/helpers/integrationMatchers.js @@ -1,7 +1,7 @@ (function(env) { env.registerIntegrationMatchers = function() { jasmine.addMatchers({ - toHaveFailedExpectationsForRunnable: function(util) { + toHaveFailedExpectationsForRunnable: function() { return { compare: function(actual, fullName, expectedFailures) { var foundRunnable = false, diff --git a/spec/npmPackage/npmPackageSpec.js b/spec/npmPackage/npmPackageSpec.js index 908b1c06..ea292bc2 100644 --- a/spec/npmPackage/npmPackageSpec.js +++ b/spec/npmPackage/npmPackageSpec.js @@ -23,7 +23,7 @@ describe('npm package', function() { beforeEach(function() { jasmine.addMatchers({ - toExistInPath: function(util) { + toExistInPath: function() { return { compare: function(actual, expected) { var fullPath = path.resolve(expected, actual); diff --git a/src/core/Env.js b/src/core/Env.js index 62510708..9ead1348 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -341,7 +341,7 @@ getJasmineRequireObj().Env = function(j$) { runnableResources[spec.id].customEqualityTesters; return j$.Expectation.factory({ - util: makeMatchersUtil(), + matchersUtil: makeMatchersUtil(), customEqualityTesters: customEqualityTesters, customMatchers: runnableResources[spec.id].customMatchers, actual: actual, @@ -355,7 +355,7 @@ getJasmineRequireObj().Env = function(j$) { var asyncExpectationFactory = function(actual, spec) { return j$.Expectation.asyncFactory({ - util: makeMatchersUtil(), + matchersUtil: makeMatchersUtil(), customEqualityTesters: runnableResources[spec.id].customEqualityTesters, customAsyncMatchers: runnableResources[spec.id].customAsyncMatchers, actual: actual, diff --git a/src/core/Expectation.js b/src/core/Expectation.js index ba079532..90580211 100644 --- a/src/core/Expectation.js +++ b/src/core/Expectation.js @@ -129,7 +129,7 @@ getJasmineRequireObj().Expectation = function(j$) { return result; } - function negatedFailureMessage(result, matcherName, args, util) { + function negatedFailureMessage(result, matcherName, args, matchersUtil) { if (result.message) { if (j$.isFunction_(result.message)) { return result.message(); @@ -141,7 +141,7 @@ getJasmineRequireObj().Expectation = function(j$) { args = args.slice(); args.unshift(true); args.unshift(matcherName); - return util.buildFailureMessage.apply(util, args); + return matchersUtil.buildFailureMessage.apply(matchersUtil, args); } function negate(result) { diff --git a/src/core/ExpectationFilterChain.js b/src/core/ExpectationFilterChain.js index 6ecbd17c..d7f020b8 100644 --- a/src/core/ExpectationFilterChain.js +++ b/src/core/ExpectationFilterChain.js @@ -16,7 +16,7 @@ getJasmineRequireObj().ExpectationFilterChain = function() { result, matcherName, args, - util + matchersUtil ) { return this.callFirst_('buildFailureMessage', arguments).result; }; diff --git a/src/core/Expector.js b/src/core/Expector.js index 18e8784e..e0f7ae9c 100644 --- a/src/core/Expector.js +++ b/src/core/Expector.js @@ -1,6 +1,8 @@ getJasmineRequireObj().Expector = function(j$) { function Expector(options) { - this.util = options.util || { buildFailureMessage: function() {} }; + this.matchersUtil = options.matchersUtil || { + buildFailureMessage: function() {} + }; this.customEqualityTesters = options.customEqualityTesters || []; this.actual = options.actual; this.addExpectationResult = options.addExpectationResult || function() {}; @@ -18,7 +20,7 @@ getJasmineRequireObj().Expector = function(j$) { this.args.unshift(this.actual); - var matcher = matcherFactory(this.util, this.customEqualityTesters); + var matcher = matcherFactory(this.matchersUtil, this.customEqualityTesters); var comparisonFunc = this.filters.selectComparisonFunc(matcher); return comparisonFunc || matcher.compare; }; @@ -34,7 +36,7 @@ getJasmineRequireObj().Expector = function(j$) { result, this.matcherName, this.args, - this.util, + this.matchersUtil, defaultMessage ); return this.filters.modifyFailureMessage(msg || defaultMessage()); @@ -44,7 +46,10 @@ getJasmineRequireObj().Expector = function(j$) { var args = self.args.slice(); args.unshift(false); args.unshift(self.matcherName); - return self.util.buildFailureMessage.apply(self.util, args); + return self.matchersUtil.buildFailureMessage.apply( + self.matchersUtil, + args + ); } else if (j$.isFunction_(result.message)) { return result.message(); } else { diff --git a/src/core/matchers/async/toBeRejected.js b/src/core/matchers/async/toBeRejected.js index 62f1a3e9..3ec95bf3 100644 --- a/src/core/matchers/async/toBeRejected.js +++ b/src/core/matchers/async/toBeRejected.js @@ -10,7 +10,7 @@ getJasmineRequireObj().toBeRejected = function(j$) { * @example * return expectAsync(aPromise).toBeRejected(); */ - return function toBeRejected(util) { + return function toBeRejected() { return { compare: function(actual) { if (!j$.isPromiseLike(actual)) { diff --git a/src/core/matchers/async/toBeResolved.js b/src/core/matchers/async/toBeResolved.js index efe367e9..997ddeea 100644 --- a/src/core/matchers/async/toBeResolved.js +++ b/src/core/matchers/async/toBeResolved.js @@ -10,7 +10,7 @@ getJasmineRequireObj().toBeResolved = function(j$) { * @example * return expectAsync(aPromise).toBeResolved(); */ - return function toBeResolved(util) { + return function toBeResolved() { return { compare: function(actual) { if (!j$.isPromiseLike(actual)) { diff --git a/src/core/matchers/toBe.js b/src/core/matchers/toBe.js index 3aab9416..8115adc0 100644 --- a/src/core/matchers/toBe.js +++ b/src/core/matchers/toBe.js @@ -8,7 +8,7 @@ getJasmineRequireObj().toBe = function(j$) { * @example * expect(thing).toBe(realThing); */ - function toBe(util) { + function toBe(matchersUtil) { var tip = ' Tip: To check for deep equality, use .toEqual() instead of .toBe().'; return { @@ -18,7 +18,7 @@ getJasmineRequireObj().toBe = function(j$) { }; if (typeof expected === 'object') { - result.message = util.buildFailureMessage('toBe', result.pass, actual, expected) + tip; + result.message = matchersUtil.buildFailureMessage('toBe', result.pass, actual, expected) + tip; } return result; diff --git a/src/core/matchers/toContain.js b/src/core/matchers/toContain.js index cf511604..5732447e 100644 --- a/src/core/matchers/toContain.js +++ b/src/core/matchers/toContain.js @@ -9,12 +9,12 @@ getJasmineRequireObj().toContain = function() { * expect(array).toContain(anElement); * expect(string).toContain(substring); */ - function toContain(util) { + function toContain(matchersUtil) { return { compare: function(actual, expected) { return { - pass: util.contains(actual, expected) + pass: matchersUtil.contains(actual, expected) }; } }; diff --git a/src/core/matchers/toEqual.js b/src/core/matchers/toEqual.js index 54aea12f..3a7add38 100644 --- a/src/core/matchers/toEqual.js +++ b/src/core/matchers/toEqual.js @@ -8,15 +8,15 @@ getJasmineRequireObj().toEqual = function(j$) { * @example * expect(bigObject).toEqual({"foo": ['bar', 'baz']}); */ - function toEqual(util) { + function toEqual(matchersUtil) { return { compare: function(actual, expected) { var result = { pass: false }, - diffBuilder = j$.DiffBuilder({prettyPrinter: util.pp}); + diffBuilder = j$.DiffBuilder({prettyPrinter: matchersUtil.pp}); - result.pass = util.equals(actual, expected, diffBuilder); + result.pass = matchersUtil.equals(actual, expected, diffBuilder); // TODO: only set error message if test fails result.message = diffBuilder.getMessage(); From 3be797c8d8b86cf37f116573bc55b487cf9fcb82 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 11 Feb 2020 16:25:53 -0800 Subject: [PATCH 124/201] Fixed diffs involving jasmine.objectContaining --- lib/jasmine-core/jasmine.js | 51 +++++++++++-------- .../ObjectContainingSpec.js | 3 +- spec/core/matchers/ObjectPathSpec.js | 8 --- spec/core/matchers/toEqualSpec.js | 4 +- src/core/base.js | 4 ++ src/core/matchers/DiffBuilder.js | 23 ++++++++- src/core/matchers/ObjectPath.js | 10 ---- src/core/matchers/matchersUtil.js | 14 ++--- 8 files changed, 62 insertions(+), 55 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index fc466dbe..65146cf8 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -278,6 +278,10 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return false; }; + j$.isAsymmetricEqualityTester_ = function(obj) { + return obj && j$.isA_('Function', obj.asymmetricMatch); + }; + j$.getType_ = function(value) { return Object.prototype.toString.apply(value); }; @@ -4329,8 +4333,9 @@ getJasmineRequireObj().DiffBuilder = function (j$) { mismatches.traverse(function (path, isLeaf, formatter) { var actualCustom, expectedCustom, useCustom, - actual = path.dereference(actualRoot), - expected = path.dereference(expectedRoot); + derefResult = dereferencePath(path, actualRoot, expectedRoot, prettyPrinter), + actual = derefResult.actual, + expected = derefResult.expected; if (formatter) { messages.push(formatter(actual, expected, path, prettyPrinter)); @@ -4377,6 +4382,24 @@ getJasmineRequireObj().DiffBuilder = function (j$) { '.'; } }; + + function dereferencePath(objectPath, actual, expected, pp) { + var i, asymmetricResult + + for (i = 0; i < objectPath.components.length; i++) { + actual = actual[objectPath.components[i]]; + expected = expected[objectPath.components[i]]; + + if (j$.isAsymmetricEqualityTester_(expected) && j$.isFunction_(expected.valuesForDiff_)) { + var asymmetricResult = expected.valuesForDiff_(actual, pp); + expected = asymmetricResult.self; + actual = asymmetricResult.other; + } + } + + return {actual: actual, expected: expected}; + } + }; getJasmineRequireObj().MatchersUtil = function(j$) { @@ -4459,13 +4482,9 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return message + '.'; }; - function isAsymmetric(obj) { - return obj && j$.isA_('Function', obj.asymmetricMatch); - } - MatchersUtil.prototype.asymmetricDiff_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { if (j$.isFunction_(b.valuesForDiff_)) { - var values = b.valuesForDiff_(a); + var values = b.valuesForDiff_(a, this.pp); this.eq_(values.other, values.self, aStack, bStack, customTesters, diffBuilder); } else { diffBuilder.recordMismatch(); @@ -4473,8 +4492,8 @@ getJasmineRequireObj().MatchersUtil = function(j$) { }; MatchersUtil.prototype.asymmetricMatch_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { - var asymmetricA = isAsymmetric(a), - asymmetricB = isAsymmetric(b), + var asymmetricA = j$.isAsymmetricEqualityTester_(a), + asymmetricB = j$.isAsymmetricEqualityTester_(b), shim = j$.asymmetricEqualityTesterArgCompatShim(this, customTesters), result; @@ -4485,8 +4504,6 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (asymmetricA) { result = a.asymmetricMatch(b, shim); if (!result) { - // TODO: Do we want to build an asymmetric diff when the actual was an - // asymmeteric equality tester? Might be confusing. diffBuilder.recordMismatch(); } return result; @@ -4709,7 +4726,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // Only use the cmpKey when one of the keys is asymmetric and the corresponding key matches, // otherwise explicitly look up the mapKey in the other Map since we want keys with unique // obj identity (that are otherwise equal) to not match. - if (isAsymmetric(mapKey) || isAsymmetric(cmpKey) && + if (j$.isAsymmetricEqualityTester_(mapKey) || j$.isAsymmetricEqualityTester_(cmpKey) && this.eq_(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { mapValueB = b.get(cmpKey); } else { @@ -5024,16 +5041,6 @@ getJasmineRequireObj().ObjectPath = function(j$) { } }; - ObjectPath.prototype.dereference = function(obj) { - var i; - - for (i = 0; i < this.components.length; i++) { - obj = obj[this.components[i]]; - } - - return obj; - }; - ObjectPath.prototype.add = function(component) { return new ObjectPath(this.components.concat([component])); }; diff --git a/spec/core/asymmetric_equality/ObjectContainingSpec.js b/spec/core/asymmetric_equality/ObjectContainingSpec.js index bec44fe2..8cad948d 100644 --- a/spec/core/asymmetric_equality/ObjectContainingSpec.js +++ b/spec/core/asymmetric_equality/ObjectContainingSpec.js @@ -125,7 +125,8 @@ describe("ObjectContaining", function() { describe("when other is not an object", function() { it("sets self to jasmineToString()", function () { var containing = new jasmineUnderTest.ObjectContaining({}), - result = containing.valuesForDiff_('a'); + pp = jasmineUnderTest.makePrettyPrinter(), + result = containing.valuesForDiff_('a', pp); expect(result).toEqual({ self: '', diff --git a/spec/core/matchers/ObjectPathSpec.js b/spec/core/matchers/ObjectPathSpec.js index 9750272e..4e0d99fa 100644 --- a/spec/core/matchers/ObjectPathSpec.js +++ b/spec/core/matchers/ObjectPathSpec.js @@ -40,12 +40,4 @@ describe('ObjectPath', function() { expect(path.toString()).toEqual('$.foo'); expect(root.toString()).toEqual(''); }); - - describe('#dereference', function() { - it('returns the value corresponding to the path', function () { - var path = new ObjectPath().add('foo').add(1).add('bar'); - var obj = {foo: ['', {bar: 42}]}; - expect(path.dereference(obj)).toEqual(42); - }); - }); }); diff --git a/spec/core/matchers/toEqualSpec.js b/spec/core/matchers/toEqualSpec.js index 3a1ce985..3a249364 100644 --- a/spec/core/matchers/toEqualSpec.js +++ b/spec/core/matchers/toEqualSpec.js @@ -429,10 +429,10 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches involving objectContaining", function() { + it("reports mismatches involving objectContaining and an object", function() { var actual = {x: {a: 1, b: 4, c: 3, extra: 'ignored'}}; var expected = {x: jasmineUnderTest.objectContaining({a: 1, b: 2, c: 3})}; - expect(compareEquals(actual, expected).message).toEqual('Expected $.x.b = 4 to equal 2.') + expect(compareEquals(actual, expected).message).toEqual('Expected $.x.b = 4 to equal 2.'); }); it("reports mismatches between a non-object and objectContaining", function() { diff --git a/src/core/base.js b/src/core/base.js index 3a2a097d..37aa692e 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -111,6 +111,10 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return false; }; + j$.isAsymmetricEqualityTester_ = function(obj) { + return obj && j$.isA_('Function', obj.asymmetricMatch); + }; + j$.getType_ = function(value) { return Object.prototype.toString.apply(value); }; diff --git a/src/core/matchers/DiffBuilder.js b/src/core/matchers/DiffBuilder.js index 197e4c71..4e43aeaa 100644 --- a/src/core/matchers/DiffBuilder.js +++ b/src/core/matchers/DiffBuilder.js @@ -21,8 +21,9 @@ getJasmineRequireObj().DiffBuilder = function (j$) { mismatches.traverse(function (path, isLeaf, formatter) { var actualCustom, expectedCustom, useCustom, - actual = path.dereference(actualRoot), - expected = path.dereference(expectedRoot); + derefResult = dereferencePath(path, actualRoot, expectedRoot, prettyPrinter), + actual = derefResult.actual, + expected = derefResult.expected; if (formatter) { messages.push(formatter(actual, expected, path, prettyPrinter)); @@ -69,4 +70,22 @@ getJasmineRequireObj().DiffBuilder = function (j$) { '.'; } }; + + function dereferencePath(objectPath, actual, expected, pp) { + var i, asymmetricResult + + for (i = 0; i < objectPath.components.length; i++) { + actual = actual[objectPath.components[i]]; + expected = expected[objectPath.components[i]]; + + if (j$.isAsymmetricEqualityTester_(expected) && j$.isFunction_(expected.valuesForDiff_)) { + var asymmetricResult = expected.valuesForDiff_(actual, pp); + expected = asymmetricResult.self; + actual = asymmetricResult.other; + } + } + + return {actual: actual, expected: expected}; + } + }; diff --git a/src/core/matchers/ObjectPath.js b/src/core/matchers/ObjectPath.js index 266e8e62..a9acfdb2 100644 --- a/src/core/matchers/ObjectPath.js +++ b/src/core/matchers/ObjectPath.js @@ -11,16 +11,6 @@ getJasmineRequireObj().ObjectPath = function(j$) { } }; - ObjectPath.prototype.dereference = function(obj) { - var i; - - for (i = 0; i < this.components.length; i++) { - obj = obj[this.components[i]]; - } - - return obj; - }; - ObjectPath.prototype.add = function(component) { return new ObjectPath(this.components.concat([component])); }; diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index e79dd075..6fa812bf 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -78,13 +78,9 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return message + '.'; }; - function isAsymmetric(obj) { - return obj && j$.isA_('Function', obj.asymmetricMatch); - } - MatchersUtil.prototype.asymmetricDiff_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { if (j$.isFunction_(b.valuesForDiff_)) { - var values = b.valuesForDiff_(a); + var values = b.valuesForDiff_(a, this.pp); this.eq_(values.other, values.self, aStack, bStack, customTesters, diffBuilder); } else { diffBuilder.recordMismatch(); @@ -92,8 +88,8 @@ getJasmineRequireObj().MatchersUtil = function(j$) { }; MatchersUtil.prototype.asymmetricMatch_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { - var asymmetricA = isAsymmetric(a), - asymmetricB = isAsymmetric(b), + var asymmetricA = j$.isAsymmetricEqualityTester_(a), + asymmetricB = j$.isAsymmetricEqualityTester_(b), shim = j$.asymmetricEqualityTesterArgCompatShim(this, customTesters), result; @@ -104,8 +100,6 @@ getJasmineRequireObj().MatchersUtil = function(j$) { if (asymmetricA) { result = a.asymmetricMatch(b, shim); if (!result) { - // TODO: Do we want to build an asymmetric diff when the actual was an - // asymmeteric equality tester? Might be confusing. diffBuilder.recordMismatch(); } return result; @@ -328,7 +322,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // Only use the cmpKey when one of the keys is asymmetric and the corresponding key matches, // otherwise explicitly look up the mapKey in the other Map since we want keys with unique // obj identity (that are otherwise equal) to not match. - if (isAsymmetric(mapKey) || isAsymmetric(cmpKey) && + if (j$.isAsymmetricEqualityTester_(mapKey) || j$.isAsymmetricEqualityTester_(cmpKey) && this.eq_(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { mapValueB = b.get(cmpKey); } else { From 5096d9af4e9d02553f1f0a5947f81f9a0319001f Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 12 Feb 2020 13:52:58 -0800 Subject: [PATCH 125/201] Don't construct unnecessarily asymmetricEqualityTesterArgCompatShims This speeds up MatchersUtil#equals by about 6-7x. --- lib/jasmine-core/jasmine.js | 8 +++++--- spec/core/baseSpec.js | 21 +++++++++++++++++++++ src/core/base.js | 2 +- src/core/matchers/matchersUtil.js | 6 ++++-- 4 files changed, 31 insertions(+), 6 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 65146cf8..cf4191b5 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -279,7 +279,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { }; j$.isAsymmetricEqualityTester_ = function(obj) { - return obj && j$.isA_('Function', obj.asymmetricMatch); + return obj ? j$.isA_('Function', obj.asymmetricMatch) : false; }; j$.getType_ = function(value) { @@ -4494,13 +4494,15 @@ getJasmineRequireObj().MatchersUtil = function(j$) { MatchersUtil.prototype.asymmetricMatch_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { var asymmetricA = j$.isAsymmetricEqualityTester_(a), asymmetricB = j$.isAsymmetricEqualityTester_(b), - shim = j$.asymmetricEqualityTesterArgCompatShim(this, customTesters), + shim, result; - if (asymmetricA && asymmetricB) { + if (asymmetricA === asymmetricB) { return undefined; } + shim = j$.asymmetricEqualityTesterArgCompatShim(this, customTesters); + if (asymmetricA) { result = a.asymmetricMatch(b, shim); if (!result) { diff --git a/spec/core/baseSpec.js b/spec/core/baseSpec.js index 07f94e19..4fce2254 100644 --- a/spec/core/baseSpec.js +++ b/spec/core/baseSpec.js @@ -30,4 +30,25 @@ describe('base helpers', function() { }, 100); }); }); + + describe('isAsymmetricEqualityTester_', function() { + it('returns false when the argument is falsy', function() { + expect(jasmineUnderTest.isAsymmetricEqualityTester_(null)).toBe(false); + }); + + it('returns false when the argument does not have a asymmetricMatch property', function() { + var obj = {}; + expect(jasmineUnderTest.isAsymmetricEqualityTester_(obj)).toBe(false); + }); + + it("returns false when the argument's asymmetricMatch is not a function", function() { + var obj = { asymmetricMatch: 'yes' }; + expect(jasmineUnderTest.isAsymmetricEqualityTester_(obj)).toBe(false); + }); + + it("returns true when the argument's asymmetricMatch is a function", function() { + var obj = { asymmetricMatch: function() {} }; + expect(jasmineUnderTest.isAsymmetricEqualityTester_(obj)).toBe(true); + }); + }); }); diff --git a/src/core/base.js b/src/core/base.js index 37aa692e..e86a12c8 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -112,7 +112,7 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { }; j$.isAsymmetricEqualityTester_ = function(obj) { - return obj && j$.isA_('Function', obj.asymmetricMatch); + return obj ? j$.isA_('Function', obj.asymmetricMatch) : false; }; j$.getType_ = function(value) { diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index 6fa812bf..8ee6368e 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -90,13 +90,15 @@ getJasmineRequireObj().MatchersUtil = function(j$) { MatchersUtil.prototype.asymmetricMatch_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { var asymmetricA = j$.isAsymmetricEqualityTester_(a), asymmetricB = j$.isAsymmetricEqualityTester_(b), - shim = j$.asymmetricEqualityTesterArgCompatShim(this, customTesters), + shim, result; - if (asymmetricA && asymmetricB) { + if (asymmetricA === asymmetricB) { return undefined; } + shim = j$.asymmetricEqualityTesterArgCompatShim(this, customTesters); + if (asymmetricA) { result = a.asymmetricMatch(b, shim); if (!result) { From 6c68715554463446ee0feeb849c8fbc7f5162e4d Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 13 Feb 2020 09:26:33 -0800 Subject: [PATCH 126/201] Removed unnecessary uses of new --- .../async/toBeRejectedWithErrorSpec.js | 24 +++++++++---------- .../core/matchers/async/toBeResolvedToSpec.js | 6 ++--- 2 files changed, 15 insertions(+), 15 deletions(-) diff --git a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js index 97260d59..71c53d55 100644 --- a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js @@ -2,7 +2,7 @@ describe('#toBeRejectedWithError', function () { it('passes when Error type matches', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new TypeError('foo')); @@ -17,7 +17,7 @@ describe('#toBeRejectedWithError', function () { it('passes when Error type and message matches', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new TypeError('foo')); @@ -32,7 +32,7 @@ describe('#toBeRejectedWithError', function () { it('passes when Error matches and is exactly Error', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error()); @@ -48,7 +48,7 @@ describe('#toBeRejectedWithError', function () { it('passes when Error message matches a string', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error('foo')); @@ -63,7 +63,7 @@ describe('#toBeRejectedWithError', function () { it('passes when Error message matches a RegExp', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error('foo')); @@ -78,7 +78,7 @@ describe('#toBeRejectedWithError', function () { it('passes when Error message is empty', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error()); @@ -93,7 +93,7 @@ describe('#toBeRejectedWithError', function () { it('passes when no arguments', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error()); @@ -108,7 +108,7 @@ describe('#toBeRejectedWithError', function () { it('fails when resolved', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.resolve(new Error('foo')); @@ -123,7 +123,7 @@ describe('#toBeRejectedWithError', function () { it('fails when rejected with non Error type', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject('foo'); @@ -138,7 +138,7 @@ describe('#toBeRejectedWithError', function () { it('fails when Error type mismatches', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error('foo')); @@ -153,7 +153,7 @@ describe('#toBeRejectedWithError', function () { it('fails when Error message mismatches', function () { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = Promise.reject(new Error('foo')); @@ -166,7 +166,7 @@ describe('#toBeRejectedWithError', function () { }); it('fails if actual is not a promise', function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), actual = 'not a promise'; diff --git a/spec/core/matchers/async/toBeResolvedToSpec.js b/spec/core/matchers/async/toBeResolvedToSpec.js index c68eb0e0..b721c89e 100644 --- a/spec/core/matchers/async/toBeResolvedToSpec.js +++ b/spec/core/matchers/async/toBeResolvedToSpec.js @@ -14,7 +14,7 @@ describe('#toBeResolvedTo', function() { it('fails if the promise is rejected', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.reject('AsyncExpectationSpec error'); @@ -29,7 +29,7 @@ describe('#toBeResolvedTo', function() { it('fails if the promise is resolved to a different value', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.resolve({foo: 17}); @@ -44,7 +44,7 @@ describe('#toBeResolvedTo', function() { it('builds its message correctly when negated', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: new jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.resolve(true); From a6a9550d1eacfc303d668d8c1901185b1e66bcf6 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 13 Feb 2020 10:52:54 -0800 Subject: [PATCH 127/201] Fixed 'since' versions for MatchersUtil --- lib/jasmine-core/jasmine.js | 4 +++- src/core/matchers/matchersUtil.js | 4 +++- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index c91846b4..79e8100b 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -4409,7 +4409,6 @@ getJasmineRequireObj().MatchersUtil = function(j$) { * _Note:_ Do not construct this directly. Jasmine will construct one and * pass it to matchers and asymmetric equality testers. * @name MatchersUtil - * @since 2.0.0 * @classdesc Utilities for use in implementing matchers * @constructor */ @@ -4421,6 +4420,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { * taking into account the current set of custom value formatters. * @function * @name MatchersUtil#pp + * @since 3.6.0 * @param {*} value The value to pretty-print * @return {string} The pretty-printed value */ @@ -4432,6 +4432,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { * logic as {@link MatchersUtil#equals}. * @function * @name MatchersUtil#contains + * @since 2.0.0 * @param {*} haystack The collection to search * @param {*} needle The value to search for * @param [customTesters] An array of custom equality testers @@ -4524,6 +4525,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { * Determines whether two values are deeply equal to each other. * @function * @name MatchersUtil#equals + * @since 2.0.0 * @param {*} a The first value to compare * @param {*} b The second value to compare * @param [customTesters] An array of custom equality testers diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index 8ee6368e..d473976d 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -5,7 +5,6 @@ getJasmineRequireObj().MatchersUtil = function(j$) { * _Note:_ Do not construct this directly. Jasmine will construct one and * pass it to matchers and asymmetric equality testers. * @name MatchersUtil - * @since 2.0.0 * @classdesc Utilities for use in implementing matchers * @constructor */ @@ -17,6 +16,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { * taking into account the current set of custom value formatters. * @function * @name MatchersUtil#pp + * @since 3.6.0 * @param {*} value The value to pretty-print * @return {string} The pretty-printed value */ @@ -28,6 +28,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { * logic as {@link MatchersUtil#equals}. * @function * @name MatchersUtil#contains + * @since 2.0.0 * @param {*} haystack The collection to search * @param {*} needle The value to search for * @param [customTesters] An array of custom equality testers @@ -120,6 +121,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { * Determines whether two values are deeply equal to each other. * @function * @name MatchersUtil#equals + * @since 2.0.0 * @param {*} a The first value to compare * @param {*} b The second value to compare * @param [customTesters] An array of custom equality testers From 93ad31e0af4c01e4e80539899ecd4cecb1279bc9 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 22 Feb 2020 13:54:24 -0800 Subject: [PATCH 128/201] Correctly report spec and suite duration Previously, suite duration was always reported as 0 and spec duration was always reported as null. Suites always used a no-op timer, and specs set their result.duration after the result had already been sent to reporters. Fixes #1676. --- lib/jasmine-core/jasmine.js | 19 +++--------- spec/core/SpecSpec.js | 27 +++++++++++------ spec/core/integration/EnvSpec.js | 52 ++++++++++++++++++++++++++++++++ src/core/Env.js | 1 + src/core/JsApiReporter.js | 2 +- src/core/Spec.js | 4 +-- src/core/Suite.js | 2 +- src/core/Timer.js | 9 ------ src/core/requireCore.js | 1 - 9 files changed, 80 insertions(+), 37 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 79e8100b..0e6c91d4 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -71,7 +71,6 @@ var getJasmineRequireObj = (function(jasmineGlobal) { j$.Expector = jRequire.Expector(j$); j$.Expectation = jRequire.Expectation(j$); j$.buildExpectationResult = jRequire.buildExpectationResult(j$); - j$.noopTimer = jRequire.noopTimer(); j$.JsApiReporter = jRequire.JsApiReporter(j$); j$.asymmetricEqualityTesterArgCompatShim = jRequire.asymmetricEqualityTesterArgCompatShim( j$ @@ -681,7 +680,7 @@ getJasmineRequireObj().Spec = function(j$) { return true; }; this.throwOnExpectationFailure = !!attrs.throwOnExpectationFailure; - this.timer = attrs.timer || j$.noopTimer; + this.timer = attrs.timer || new j$.Timer(); if (!this.queueableFn.fn) { this.pend(); @@ -746,6 +745,7 @@ getJasmineRequireObj().Spec = function(j$) { fn: function(done) { self.queueableFn.fn = null; self.result.status = self.status(excluded, failSpecWithNoExp); + self.result.duration = self.timer.elapsed(); self.resultCallback(self.result, done); } }; @@ -761,7 +761,6 @@ getJasmineRequireObj().Spec = function(j$) { self.onException.apply(self, arguments); }, onComplete: function() { - self.result.duration = self.timer.elapsed(); onComplete( self.result.status === 'failed' && new j$.StopExecutionError('spec failed') @@ -1878,6 +1877,7 @@ getJasmineRequireObj().Env = function(j$) { id: getNextSuiteId(), description: description, parentSuite: currentDeclarationSuite, + timer: new j$.Timer(), expectationFactory: expectationFactory, asyncExpectationFactory: suiteAsyncExpectationFactory, expectationResultFactory: expectationResultFactory, @@ -2166,7 +2166,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { * @hideconstructor */ function JsApiReporter(options) { - var timer = options.timer || j$.noopTimer, + var timer = options.timer || new j$.Timer(), status = 'loaded'; this.started = false; @@ -8246,7 +8246,7 @@ getJasmineRequireObj().Suite = function(j$) { this.beforeAllFns = []; this.afterAllFns = []; - this.timer = attrs.timer || j$.noopTimer; + this.timer = attrs.timer || new j$.Timer(); this.children = []; @@ -8449,15 +8449,6 @@ getJasmineRequireObj().Timer = function() { return Timer; }; -getJasmineRequireObj().noopTimer = function() { - return { - start: function() {}, - elapsed: function() { - return 0; - } - }; -}; - getJasmineRequireObj().TreeProcessor = function() { function TreeProcessor(attrs) { var tree = attrs.tree, diff --git a/spec/core/SpecSpec.js b/spec/core/SpecSpec.js index 8219a1cd..38a8e780 100644 --- a/spec/core/SpecSpec.js +++ b/spec/core/SpecSpec.js @@ -227,7 +227,7 @@ describe('Spec', function() { passedExpectations: [], deprecationWarnings: [], pendingReason: '', - duration: null + duration: jasmine.any(Number) }, 'things' ); @@ -273,21 +273,30 @@ describe('Spec', function() { }); it('should report the duration of the test', function() { - var done = jasmine.createSpy('done callback'), - timer = jasmine.createSpyObj('timer', { start: null, elapsed: 77000 }), + var timer = jasmine.createSpyObj('timer', { start: null, elapsed: 77000 }), spec = new jasmineUnderTest.Spec({ queueableFn: { fn: jasmine.createSpy('spec body') }, catchExceptions: function() { return false; }, - resultCallback: function() {}, - queueRunnerFactory: function(attrs) { - attrs.onComplete(); + resultCallback: function(result) { + duration = result.duration; + }, + queueRunnerFactory: function(config) { + config.queueableFns.forEach(function(qf) { + qf.fn(); + }); + config.cleanupFns.forEach(function(qf) { + qf.fn(); + }); + config.onComplete(); }, timer: timer - }); - spec.execute(done); - expect(spec.result.duration).toBe(77000); + }), + duration = undefined; + + spec.execute(function() {}); + expect(duration).toBe(77000); }); it('#status returns passing by default', function() { diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index bd35817c..8c5c1941 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -616,6 +616,58 @@ describe("Env integration", function() { env.execute(); }); + + it('reports the duration of the suite', function(done) { + var duration; + + env.addReporter({ + suiteDone: function(result) { + expect(duration).toBeUndefined(); + duration = result.duration; + }, + jasmineDone: function() { + expect(duration).toBeGreaterThanOrEqual(10); + done(); + } + }); + + env.describe('my suite', function() { + env.it('takes time', function(done) { + // We can't just use the mock clock here because the timer is designed + // to record real time even when the mock clock is installed. + setTimeout(done, 10); + }) + }); + + env.execute(); + }); + }); + + describe('specDone reporting', function() { + it('reports the duration of the spec', function(done) { + var duration; + + env.addReporter({ + specDone: function(result) { + expect(duration).toBeUndefined(); + duration = result.duration; + }, + jasmineDone: function() { + expect(duration).toBeGreaterThanOrEqual(10); + done(); + } + }); + + env.describe('my suite', function() { + env.it('takes time', function(done) { + // We can't just use the mock clock here because the timer is designed + // to record real time even when the mock clock is installed. + setTimeout(done, 10); + }) + }); + + env.execute(); + }); }); it('reports expectation failures in global beforeAll', function(done) { diff --git a/src/core/Env.js b/src/core/Env.js index 2cb9c2cc..47915c0a 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -952,6 +952,7 @@ getJasmineRequireObj().Env = function(j$) { id: getNextSuiteId(), description: description, parentSuite: currentDeclarationSuite, + timer: new j$.Timer(), expectationFactory: expectationFactory, asyncExpectationFactory: suiteAsyncExpectationFactory, expectationResultFactory: expectationResultFactory, diff --git a/src/core/JsApiReporter.js b/src/core/JsApiReporter.js index 8875a45e..a498f388 100644 --- a/src/core/JsApiReporter.js +++ b/src/core/JsApiReporter.js @@ -6,7 +6,7 @@ getJasmineRequireObj().JsApiReporter = function(j$) { * @hideconstructor */ function JsApiReporter(options) { - var timer = options.timer || j$.noopTimer, + var timer = options.timer || new j$.Timer(), status = 'loaded'; this.started = false; diff --git a/src/core/Spec.js b/src/core/Spec.js index b8791890..db35de64 100644 --- a/src/core/Spec.js +++ b/src/core/Spec.js @@ -31,7 +31,7 @@ getJasmineRequireObj().Spec = function(j$) { return true; }; this.throwOnExpectationFailure = !!attrs.throwOnExpectationFailure; - this.timer = attrs.timer || j$.noopTimer; + this.timer = attrs.timer || new j$.Timer(); if (!this.queueableFn.fn) { this.pend(); @@ -96,6 +96,7 @@ getJasmineRequireObj().Spec = function(j$) { fn: function(done) { self.queueableFn.fn = null; self.result.status = self.status(excluded, failSpecWithNoExp); + self.result.duration = self.timer.elapsed(); self.resultCallback(self.result, done); } }; @@ -111,7 +112,6 @@ getJasmineRequireObj().Spec = function(j$) { self.onException.apply(self, arguments); }, onComplete: function() { - self.result.duration = self.timer.elapsed(); onComplete( self.result.status === 'failed' && new j$.StopExecutionError('spec failed') diff --git a/src/core/Suite.js b/src/core/Suite.js index 75104068..4d33ceaa 100644 --- a/src/core/Suite.js +++ b/src/core/Suite.js @@ -14,7 +14,7 @@ getJasmineRequireObj().Suite = function(j$) { this.beforeAllFns = []; this.afterAllFns = []; - this.timer = attrs.timer || j$.noopTimer; + this.timer = attrs.timer || new j$.Timer(); this.children = []; diff --git a/src/core/Timer.js b/src/core/Timer.js index 35ef9f32..ebe6983d 100644 --- a/src/core/Timer.js +++ b/src/core/Timer.js @@ -22,12 +22,3 @@ getJasmineRequireObj().Timer = function() { return Timer; }; - -getJasmineRequireObj().noopTimer = function() { - return { - start: function() {}, - elapsed: function() { - return 0; - } - }; -}; diff --git a/src/core/requireCore.js b/src/core/requireCore.js index e2d7ef87..df7f2571 100644 --- a/src/core/requireCore.js +++ b/src/core/requireCore.js @@ -49,7 +49,6 @@ var getJasmineRequireObj = (function(jasmineGlobal) { j$.Expector = jRequire.Expector(j$); j$.Expectation = jRequire.Expectation(j$); j$.buildExpectationResult = jRequire.buildExpectationResult(j$); - j$.noopTimer = jRequire.noopTimer(); j$.JsApiReporter = jRequire.JsApiReporter(j$); j$.asymmetricEqualityTesterArgCompatShim = jRequire.asymmetricEqualityTesterArgCompatShim( j$ From 6440ca434d0bf41b687bd49145c9fb480f17eb6d Mon Sep 17 00:00:00 2001 From: Chives Date: Sat, 29 Feb 2020 04:30:03 -0500 Subject: [PATCH 129/201] Add trailing newlines to example code --- lib/jasmine-core/example/src/Player.js | 2 +- lib/jasmine-core/example/src/Song.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/jasmine-core/example/src/Player.js b/lib/jasmine-core/example/src/Player.js index fcce8268..11851966 100644 --- a/lib/jasmine-core/example/src/Player.js +++ b/lib/jasmine-core/example/src/Player.js @@ -19,4 +19,4 @@ Player.prototype.resume = function() { Player.prototype.makeFavorite = function() { this.currentlyPlayingSong.persistFavoriteStatus(true); -}; \ No newline at end of file +}; diff --git a/lib/jasmine-core/example/src/Song.js b/lib/jasmine-core/example/src/Song.js index a8a3f2dd..02527cb1 100644 --- a/lib/jasmine-core/example/src/Song.js +++ b/lib/jasmine-core/example/src/Song.js @@ -4,4 +4,4 @@ function Song() { Song.prototype.persistFavoriteStatus = function(value) { // something complicated throw new Error("not yet implemented"); -}; \ No newline at end of file +}; From e13fd13529099e2f8b65d030c415435098258778 Mon Sep 17 00:00:00 2001 From: Maksym Kobieliev Date: Fri, 13 Mar 2020 20:41:24 +0200 Subject: [PATCH 130/201] Add a toHaveBeenCalledOnceWith matcher --- spec/core/integration/MatchersSpec.js | 16 ++++ .../matchers/toHaveBeenCalledOnceWithSpec.js | 89 +++++++++++++++++++ src/core/matchers/requireMatchers.js | 1 + src/core/matchers/toHaveBeenCalledOnceWith.js | 56 ++++++++++++ 4 files changed, 162 insertions(+) create mode 100644 spec/core/matchers/toHaveBeenCalledOnceWithSpec.js create mode 100644 src/core/matchers/toHaveBeenCalledOnceWith.js diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js index 25af3217..b0cf91f0 100644 --- a/spec/core/integration/MatchersSpec.js +++ b/spec/core/integration/MatchersSpec.js @@ -425,6 +425,22 @@ describe('Matchers (Integration)', function() { }); }); + describe('toHaveBeenCalledOnceWith', function() { + verifyPasses(function(env) { + var spy = env.createSpy(); + spy('5', 3); + env.addCustomEqualityTester(function(a, b) { + return a.toString() === b.toString(); + }); + env.expect(spy).toHaveBeenCalledOnceWith(5, 3); + }); + + verifyFails(function(env) { + var spy = env.createSpy(); + env.expect(spy).toHaveBeenCalledOnceWith(5, 3); + }); + }); + describe('toHaveClass', function() { beforeEach(function() { this.domHelpers = jasmine.getEnv().domHelpers(); diff --git a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js new file mode 100644 index 00000000..b3678bfb --- /dev/null +++ b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js @@ -0,0 +1,89 @@ +describe("toHaveBeenCalledOnceWith", function () { + + it("passes when the actual was called only once and with matching parameters", function () { + var util = jasmineUnderTest.matchersUtil, + matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), + calledSpy = new jasmineUnderTest.Spy('called-spy'), + result; + + calledSpy('a', 'b'); + result = matcher.compare(calledSpy, 'a', 'b'); + + expect(result.pass).toBe(true); + expect(result.message).toEqual("Expected spy called-spy to have been called 0 times, multiple times, or once, but with arguments different from:\n [ 'a', 'b' ]\nBut the actual call was:\n [ 'a', 'b' ].\n\n"); + }); + + it("passes through the custom equality testers", function () { + var util = { + contains: jasmine.createSpy('delegated-contains').and.returnValue(false) + }, + customEqualityTesters = [function () { return true; }], + matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util, customEqualityTesters), + calledSpy = new jasmineUnderTest.Spy('called-spy'); + + calledSpy('a', 'b'); + matcher.compare(calledSpy, 'a', 'b'); + + expect(util.contains).toHaveBeenCalledWith([['a', 'b']], ['a', 'b'], customEqualityTesters); + }); + + it("fails when the actual was never called", function () { + var util = jasmineUnderTest.matchersUtil, + matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), + calledSpy = new jasmineUnderTest.Spy('called-spy'), + result; + + result = matcher.compare(calledSpy, 'a', 'b'); + + expect(result.pass).toBe(false); + expect(result.message).toEqual("Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut it was never called.\n\n"); + }); + + it("fails when the actual was called once with different parameters", function () { + var util = jasmineUnderTest.matchersUtil, + matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), + calledSpy = new jasmineUnderTest.Spy('called-spy'), + result; + + calledSpy('a', 'c'); + result = matcher.compare(calledSpy, 'a', 'b'); + + expect(result.pass).toBe(false); + expect(result.message).toEqual("Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut the actual calls were:\n [ 'a', 'c' ].\n\n"); + }); + + it("fails when the actual was called multiple times with expected parameters", function () { + var util = jasmineUnderTest.matchersUtil, + matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), + calledSpy = new jasmineUnderTest.Spy('called-spy'), + result; + + calledSpy('a', 'b'); + calledSpy('a', 'b'); + result = matcher.compare(calledSpy, 'a', 'b'); + + expect(result.pass).toBe(false); + expect(result.message).toEqual("Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut the actual calls were:\n [ 'a', 'b' ],\n [ 'a', 'b' ].\n\n"); + }); + + it("fails when the actual was called multiple times (one of them - with expected parameters)", function () { + var util = jasmineUnderTest.matchersUtil, + matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), + calledSpy = new jasmineUnderTest.Spy('called-spy'), + result; + + calledSpy('a', 'b'); + calledSpy('a', 'c'); + result = matcher.compare(calledSpy, 'a', 'b'); + + expect(result.pass).toBe(false); + expect(result.message).toEqual("Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut the actual calls were:\n [ 'a', 'b' ],\n [ 'a', 'c' ].\n\n"); + }); + + it("throws an exception when the actual is not a spy", function () { + var matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(), + fn = function () { }; + + expect(function () { matcher.compare(fn) }).toThrowError(/Expected a spy, but got Function./); + }); +}); diff --git a/src/core/matchers/requireMatchers.js b/src/core/matchers/requireMatchers.js index e8b1fd58..4ff1f841 100644 --- a/src/core/matchers/requireMatchers.js +++ b/src/core/matchers/requireMatchers.js @@ -22,6 +22,7 @@ getJasmineRequireObj().requireMatchers = function(jRequire, j$) { 'toEqual', 'toHaveBeenCalled', 'toHaveBeenCalledBefore', + 'toHaveBeenCalledOnceWith', 'toHaveBeenCalledTimes', 'toHaveBeenCalledWith', 'toHaveClass', diff --git a/src/core/matchers/toHaveBeenCalledOnceWith.js b/src/core/matchers/toHaveBeenCalledOnceWith.js new file mode 100644 index 00000000..ccd707c7 --- /dev/null +++ b/src/core/matchers/toHaveBeenCalledOnceWith.js @@ -0,0 +1,56 @@ +getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { + + var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledOnceWith(...arguments)'); + + /** + * {@link expect} the actual (a {@link Spy}) to have been called exactly once, and exactly with the particular arguments. + * @function + * @name matchers#toHaveBeenCalledOnceWith + * @since 3.6.0 + * @param {...Object} - The arguments to look for + * @example + * expect(mySpy).toHaveBeenCalledOnceWith('foo', 'bar', 2); + */ + function toHaveBeenCalledOnceWith(util, customEqualityTesters) { + return { + compare: function () { + var args = Array.prototype.slice.call(arguments, 0), + actual = args[0], + expectedArgs = args.slice(1); + + if (!j$.isSpy(actual)) { + throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); + } + + var prettyPrintedCalls = actual.calls.allArgs().map(function (argsForCall) { + return ' ' + j$.pp(argsForCall); + }); + + if (actual.calls.count() === 1 && util.contains(actual.calls.allArgs(), expectedArgs, customEqualityTesters)) { + return { + pass: true, + message: 'Expected spy ' + actual.and.identity + ' to have been called 0 times, multiple times, or once, but with arguments different from:\n' + + ' ' + j$.pp(expectedArgs) + '\n' + + 'But the actual call was:\n' + + prettyPrintedCalls.join(',\n') + '.\n\n' + }; + } + + function butString() { + return actual.calls.count() !== 0 + ? 'But the actual calls were:\n' + prettyPrintedCalls.join(',\n') + '.\n\n' + : 'But it was never called.\n\n'; + } + + return { + pass: false, + message: 'Expected spy ' + actual.and.identity + ' to have been called only once, and with given args:\n' + + ' ' + j$.pp(expectedArgs) + '\n' + + butString() + }; + } + }; + } + + return toHaveBeenCalledOnceWith; +}; From 66fe69a149e89456700ae2c1a71623b1fd24a1ad Mon Sep 17 00:00:00 2001 From: Chives Date: Mon, 16 Mar 2020 03:15:58 -0400 Subject: [PATCH 131/201] Add test for resolveTo/rejectWith with empty parameters --- spec/core/SpyStrategySpec.js | 45 ++++++++++++++++++++++++++++++++++++ 1 file changed, 45 insertions(+) diff --git a/spec/core/SpyStrategySpec.js b/spec/core/SpyStrategySpec.js index e861dc8b..5e454b64 100644 --- a/spec/core/SpyStrategySpec.js +++ b/spec/core/SpyStrategySpec.js @@ -140,6 +140,28 @@ describe('SpyStrategy', function() { .catch(done.fail); }); + it('allows an empty resolved promise to be returned', function(done) { + jasmine.getEnv().requirePromises(); + + var originalFn = jasmine.createSpy('original'), + getPromise = function() { + return Promise; + }, + spyStrategy = new jasmineUnderTest.SpyStrategy({ + fn: originalFn, + getPromise: getPromise + }); + + spyStrategy.resolveTo(); + spyStrategy + .exec() + .then(function(returnValue) { + expect(returnValue).toBe(); + done(); + }) + .catch(done.fail); + }); + it('fails if promises are not available', function() { var originalFn = jasmine.createSpy('original'), spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }); @@ -176,6 +198,29 @@ describe('SpyStrategy', function() { .catch(done.fail); }); + it('allows an empty rejected promise to be returned', function(done) { + jasmine.getEnv().requirePromises(); + + var originalFn = jasmine.createSpy('original'), + getPromise = function() { + return Promise; + }, + spyStrategy = new jasmineUnderTest.SpyStrategy({ + fn: originalFn, + getPromise: getPromise + }); + + spyStrategy.rejectWith(); + spyStrategy + .exec() + .then(done.fail) + .catch(function(error) { + expect(error).toBe(); + done(); + }) + .catch(done.fail); + }); + it('allows a non-Error to be rejected', function(done) { jasmine.getEnv().requirePromises(); From c521b4d47c1931f53051f38285a2e8c614e455ab Mon Sep 17 00:00:00 2001 From: Francois Wauquier Date: Fri, 28 Feb 2020 18:18:14 +0100 Subject: [PATCH 132/201] toHaveSize --- lib/jasmine-core/jasmine.js | 154 +++++++++++++------------- package.json | 2 +- spec/core/integration/MatchersSpec.js | 73 +++++++++++- spec/core/matchers/toHaveSizeSpec.js | 21 ++++ src/core/matchers/requireMatchers.js | 1 + src/core/matchers/toHaveSize.js | 79 +++++++++++++ 6 files changed, 250 insertions(+), 80 deletions(-) create mode 100644 spec/core/matchers/toHaveSizeSpec.js create mode 100644 src/core/matchers/toHaveSize.js diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 0e6c91d4..4c17bf3c 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -290,9 +290,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return typeof jasmineGlobal.Node !== 'undefined' ? obj instanceof jasmineGlobal.Node : obj !== null && - typeof obj === 'object' && - typeof obj.nodeType === 'number' && - typeof obj.nodeName === 'string'; + typeof obj === 'object' && + typeof obj.nodeType === 'number' && + typeof obj.nodeName === 'string'; // return obj.nodeType > 0; }; @@ -763,7 +763,7 @@ getJasmineRequireObj().Spec = function(j$) { onComplete: function() { onComplete( self.result.status === 'failed' && - new j$.StopExecutionError('spec failed') + new j$.StopExecutionError('spec failed') ); }, userContext: this.userContext() @@ -828,8 +828,8 @@ getJasmineRequireObj().Spec = function(j$) { this.result.failedExpectations.length > 0 || (failSpecWithNoExpectations && this.result.failedExpectations.length + - this.result.passedExpectations.length === - 0) + this.result.passedExpectations.length === + 0) ) { return 'failed'; } @@ -1170,7 +1170,7 @@ getJasmineRequireObj().Env = function(j$) { } runnableResources[ currentRunnable().id - ].defaultStrategyFn = defaultStrategyFn; + ].defaultStrategyFn = defaultStrategyFn; }; this.addSpyStrategy = function(name, fn) { @@ -2565,7 +2565,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { for (var property in this.sample) { if (!hasProperty(other, property) || - !matchersUtil.equals(this.sample[property], other[property])) { + !matchersUtil.equals(this.sample[property], other[property])) { return false; } } @@ -3373,7 +3373,7 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { // scheduled in a funcToRun from forcing an extra iteration currentTime !== endTime && scheduledLookup[0] <= endTime - ); + ); // ran out of functions to call, but still time left on the clock if (currentTime !== endTime) { @@ -4108,24 +4108,24 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { return actualPromise.then( function() { - return { - pass: false, - message: prefix(false) + ' but it was resolved.' - }; - }, - function(actualValue) { - if (matchersUtil.equals(actualValue, expectedValue)) { - return { - pass: true, - message: prefix(true) + '.' - }; - } else { return { pass: false, - message: prefix(false) + ' but it was rejected with ' + matchersUtil.pp(actualValue) + '.' + message: prefix(false) + ' but it was resolved.' }; + }, + function(actualValue) { + if (matchersUtil.equals(actualValue, expectedValue)) { + return { + pass: true, + message: prefix(true) + '.' + }; + } else { + return { + pass: false, + message: prefix(false) + ' but it was rejected with ' + matchersUtil.pp(actualValue) + '.' + }; + } } - } ); } }; @@ -4494,9 +4494,9 @@ getJasmineRequireObj().MatchersUtil = function(j$) { MatchersUtil.prototype.asymmetricMatch_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { var asymmetricA = j$.isAsymmetricEqualityTester_(a), - asymmetricB = j$.isAsymmetricEqualityTester_(b), - shim, - result; + asymmetricB = j$.isAsymmetricEqualityTester_(b), + shim, + result; if (asymmetricA === asymmetricB) { return undefined; @@ -4731,7 +4731,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // otherwise explicitly look up the mapKey in the other Map since we want keys with unique // obj identity (that are otherwise equal) to not match. if (j$.isAsymmetricEqualityTester_(mapKey) || j$.isAsymmetricEqualityTester_(cmpKey) && - this.eq_(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { + this.eq_(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { mapValueB = b.get(cmpKey); } else { mapValueB = b.get(mapKey); @@ -4800,9 +4800,9 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // or `Array`s from different frames are. var aCtor = a.constructor, bCtor = b.constructor; if (aCtor !== bCtor && - isFunction(aCtor) && isFunction(bCtor) && - a instanceof aCtor && b instanceof bCtor && - !(aCtor instanceof aCtor && bCtor instanceof bCtor)) { + isFunction(aCtor) && isFunction(bCtor) && + a instanceof aCtor && b instanceof bCtor && + !(aCtor instanceof aCtor && bCtor instanceof bCtor)) { diffBuilder.recordMismatch(constructorsAreDifferentFormatter.bind(null, this.pp)); return false; @@ -4849,13 +4849,13 @@ getJasmineRequireObj().MatchersUtil = function(j$) { function keys(obj, isArray) { var allKeys = Object.keys ? Object.keys(obj) : (function(o) { - var keys = []; - for (var key in o) { - if (j$.util.has(o, key)) { - keys.push(key); - } + var keys = []; + for (var key in o) { + if (j$.util.has(o, key)) { + keys.push(key); } - return keys; + } + return keys; })(obj); if (!isArray) { @@ -4863,7 +4863,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } if (allKeys.length === 0) { - return allKeys; + return allKeys; } var extraKeys = []; @@ -4882,10 +4882,10 @@ getJasmineRequireObj().MatchersUtil = function(j$) { function objectKeysAreDifferentFormatter(pp, actual, expected, path) { var missingProperties = j$.util.objectDifference(expected, actual), - extraProperties = j$.util.objectDifference(actual, expected), - missingPropertiesMessage = formatKeyValuePairs(pp, missingProperties), - extraPropertiesMessage = formatKeyValuePairs(pp, extraProperties), - messages = []; + extraProperties = j$.util.objectDifference(actual, expected), + missingPropertiesMessage = formatKeyValuePairs(pp, missingProperties), + extraPropertiesMessage = formatKeyValuePairs(pp, extraProperties), + messages = []; if (!path.depth()) { path = 'object'; @@ -5302,15 +5302,15 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { return { compare: function(actual, expected) { var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : matchersUtil.pp(actual), - expectedType = expected ? j$.fnNameFor(expected) : matchersUtil.pp(expected), - expectedMatcher, - pass; + expectedType = expected ? j$.fnNameFor(expected) : matchersUtil.pp(expected), + expectedMatcher, + pass; try { - expectedMatcher = new j$.Any(expected); - pass = expectedMatcher.asymmetricMatch(actual); + expectedMatcher = new j$.Any(expected); + pass = expectedMatcher.asymmetricMatch(actual); } catch (error) { - throw new Error(usageError('Expected value is not a constructor function')); + throw new Error(usageError('Expected value is not a constructor function')); } if (pass) { @@ -5805,7 +5805,7 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { }); var diffs = actual.calls.allArgs().map(function(argsForCall, callIx) { - var diffBuilder = new j$.DiffBuilder(); + var diffBuilder = new j$.DiffBuilder(); matchersUtil.equals(argsForCall, expectedArgs, diffBuilder); return 'Call ' + callIx + ':\n' + diffBuilder.getMessage().replace(/^/mg, ' '); @@ -6050,7 +6050,7 @@ getJasmineRequireObj().toThrowError = function(j$) { function thrownDescription(thrown) { var thrownName = errorType ? j$.fnNameFor(thrown.constructor) : 'an exception', - thrownMessage = ''; + thrownMessage = ''; if (expected) { thrownMessage = ' with message ' + matchersUtil.pp(thrown.message); @@ -6157,10 +6157,10 @@ getJasmineRequireObj().toThrowMatching = function(j$) { if (predicate(thrown)) { return pass('Expected function not to throw an exception matching a predicate.'); } else { - return fail(function() { - return 'Expected function to throw an exception matching a predicate, ' + - 'but it threw ' + thrownDescription(thrown) + '.'; - }); + return fail(function() { + return 'Expected function to throw an exception matching a predicate, ' + + 'but it threw ' + thrownDescription(thrown) + '.'; + }); } } }; @@ -6378,8 +6378,8 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { } else if (j$.util.arrayContains(this.seen, value)) { this.emitScalar( '' + (j$.isArray_(value) ? 'Array' : 'Object') + + '>' ); } else if (j$.isArray_(value) || j$.isA_('Object', value)) { this.seen.push(value); @@ -6648,14 +6648,14 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { var allKeys = Object.keys ? Object.keys(obj) : (function(o) { - var keys = []; - for (var key in o) { - if (j$.util.has(o, key)) { - keys.push(key); - } + var keys = []; + for (var key in o) { + if (j$.util.has(o, key)) { + keys.push(key); } - return keys; - })(obj); + } + return keys; + })(obj); if (!isArray) { return allKeys; @@ -6841,11 +6841,11 @@ getJasmineRequireObj().QueueRunner = function(j$) { timeoutId = self.setTimeout(function() { var error = new Error( 'Timeout - Async function did not complete within ' + - timeoutInterval + - 'ms ' + - (queueableFn.timeout - ? '(custom timeout)' - : '(set by jasmine.DEFAULT_TIMEOUT_INTERVAL)') + timeoutInterval + + 'ms ' + + (queueableFn.timeout + ? '(custom timeout)' + : '(set by jasmine.DEFAULT_TIMEOUT_INTERVAL)') ); onException(error); next(); @@ -7563,10 +7563,10 @@ getJasmineRequireObj().Spy = function(j$) { if (argsStrategies.any() && !baseStrategy.isConfigured()) { throw new Error( "Spy '" + - strategyArgs.name + - "' received a call with arguments " + - j$.pp(Array.prototype.slice.call(args)) + - ' but all configured strategies specify other arguments.' + strategyArgs.name + + "' received a call with arguments " + + j$.pp(Array.prototype.slice.call(args)) + + ' but all configured strategies specify other arguments.' ); } else { strategy = baseStrategy; @@ -7789,8 +7789,8 @@ getJasmineRequireObj().SpyRegistry = function(j$) { throw new Error( getErrorMsg( 'spyOn could not find an object to spy upon for ' + - propertyName + - '' + propertyName + + '' ) ); } @@ -7815,9 +7815,9 @@ getJasmineRequireObj().SpyRegistry = function(j$) { throw new Error( getErrorMsg( 'Property ' + - propertyName + - ' does not have access type ' + - accessType + propertyName + + ' does not have access type ' + + accessType ) ); } @@ -7948,7 +7948,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { if (!Promise) { throw new Error( name + - ' requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`' + ' requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`' ); } diff --git a/package.json b/package.json index bc602f6f..8db8eace 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "jasmine-core", "license": "MIT", - "version": "3.5.0", + "version": "3.5.1", "repository": { "type": "git", "url": "https://github.com/jasmine/jasmine.git" diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js index 7f19a95c..ec3404ff 100644 --- a/spec/core/integration/MatchersSpec.js +++ b/spec/core/integration/MatchersSpec.js @@ -47,6 +47,9 @@ describe('Matchers (Integration)', function() { expect(result.failedExpectations[0].message) .withContext('Failed with a thrown error rather than a matcher failure') .not.toMatch(/^Error: /); + expect(result.failedExpectations[0].message) + .withContext('Failed with a thrown type error rather than a matcher failure') + .not.toMatch(/^TypeError: /); expect(result.failedExpectations[0].matcherName).withContext('Matcher name') .not.toEqual(''); }; @@ -477,9 +480,9 @@ describe('Matchers (Integration)', function() { verifyFailsWithCustomObjectFormatters({ formatter: function(val) { if (val === 5) { - return "five" + return 'five'; } else if (val === 4) { - return "four" + return 'four'; } }, expectations: function(env) { @@ -489,6 +492,72 @@ describe('Matchers (Integration)', function() { }); }); + describe('toHaveSize', function() { + verifyPasses(function(env) { + env.expect(['a','b']).toHaveSize(2); + }); + verifyFails(function(env) { + env.expect(['a','b']).toHaveSize(1); + }); + + verifyPasses(function(env) { + env.expect({a: 1, b: 2}).toHaveSize(2); + }); + verifyFails(function(env) { + env.expect({a: 1, b: 2}).toHaveSize(1); + }); + + verifyPasses(function(env) { + env.expect({a: 1, b: 2, length: 5}).toHaveSize(5); + }); + verifyFails(function(env) { + env.expect({a: 1, b: 2, length: 5}).toHaveSize(1); + }); + + verifyPasses(function(env) { + env.expect('ab').toHaveSize(2); + }); + verifyFails(function(env) { + env.expect('ab').toHaveSize(1); + }); + + verifyPasses(function(env) { + var map = new Map(); + map.set('a',1); + map.set('b',2); + env.expect(map).toHaveSize(2); + }); + verifyFails(function(env) { + var map = new Map(); + map.set('a',1); + map.set('b',2); + env.expect(map).toHaveSize(1); + }); + + verifyPasses(function(env) { + var set = new Set(); + set.add('a'); + set.add('b'); + env.expect(set).toHaveSize(2); + }); + verifyFails(function(env) { + var set = new Set(); + set.add('a'); + set.add('b'); + env.expect(set).toHaveSize(1); + }); + + verifyFails(function(env) { + env.expect(new WeakSet()).toHaveSize(1); + }); + verifyFails(function(env) { + env.expect(new WeakMap()).toHaveSize(1); + }); + verifyFails(function(env) { + env.expect(new DataView(new ArrayBuffer(128))).toHaveSize(1); + }); + }); + describe('toHaveBeenCalled', function() { verifyPasses(function(env) { var spy = env.createSpy('spy'); diff --git a/spec/core/matchers/toHaveSizeSpec.js b/spec/core/matchers/toHaveSizeSpec.js new file mode 100644 index 00000000..08045432 --- /dev/null +++ b/spec/core/matchers/toHaveSizeSpec.js @@ -0,0 +1,21 @@ +describe('toHaveSize', function() { + 'use strict'; + + it('delegates to equals function', function() { + var matchersUtil = { + equals: jasmine.createSpy('delegated-equals').and.returnValue(true), + buildFailureMessage: function() { + return 'does not matter'; + }, + DiffBuilder: new jasmineUnderTest.DiffBuilder() + }, + matcher = jasmineUnderTest.matchers.toHaveSize(matchersUtil), + result; + + result = matcher.compare([1], 1); + + expect(matchersUtil.equals).toHaveBeenCalledWith(1, 1, jasmine.anything(), jasmine.anything()); + expect(result.pass).toBe(true); + }); + +}); diff --git a/src/core/matchers/requireMatchers.js b/src/core/matchers/requireMatchers.js index e8b1fd58..e0b256e5 100644 --- a/src/core/matchers/requireMatchers.js +++ b/src/core/matchers/requireMatchers.js @@ -20,6 +20,7 @@ getJasmineRequireObj().requireMatchers = function(jRequire, j$) { 'toBeUndefined', 'toContain', 'toEqual', + 'toHaveSize', 'toHaveBeenCalled', 'toHaveBeenCalledBefore', 'toHaveBeenCalledTimes', diff --git a/src/core/matchers/toHaveSize.js b/src/core/matchers/toHaveSize.js new file mode 100644 index 00000000..b4ea9c55 --- /dev/null +++ b/src/core/matchers/toHaveSize.js @@ -0,0 +1,79 @@ +getJasmineRequireObj().toHaveSize = function(j$) { + /** + * {@link expect} the actual size to be equal to the expected, using array-like length or object keys size. + * @function + * @name matchers#toHaveSize + * @since 3.5.1 + * @param {Object} expected - Expected size + * @example + * array = [1,2]; + * expect(array).toHaveSize(2); + */ + function toHaveSize(matchersUtil) { + return { + compare: function(actual, expected) { + var result = { + pass: false + }, + simpleEqualityTesters = [function(a, b) { + return a === b; + }], + diffBuilder = j$.DiffBuilder(); + + // Avoid misleading collections size matching + if (actual instanceof WeakSet + || actual instanceof WeakMap + || actual instanceof DataView) { + result.message = 'Cannot get size of ' + actual + '.'; + return result; + } + + // Ref https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects + if (Array.isArray(actual) || isArrayLike(actual)) + result.pass = matchersUtil.equals(actual.length, expected, simpleEqualityTesters, diffBuilder); + else if ( actual instanceof String || typeof actual === 'string') + result.pass = matchersUtil.equals(actual.length, expected, simpleEqualityTesters, diffBuilder); + else if (actual instanceof Set || actual instanceof Map) + result.pass = matchersUtil.equals(actual.size, expected, simpleEqualityTesters, diffBuilder); + // instanceof Object + else + result.pass = matchersUtil.equals(Object.keys(actual).length, expected, simpleEqualityTesters, diffBuilder); + + if(!result.pass) + result.message = diffBuilder.getMessage() ; + return result; + } + }; + } + + /** + * Checks if `value` is array-like. A value is considered array-like if it's + * not a function and has a `value.length` that's an integer greater than or + * equal to `0` and less than or equal to `Number.MAX_SAFE_INTEGER`. + * From lodash + * @param {*} value The value to check. + * @returns {boolean} Returns `true` if `value` is array-like, else `false`. + * @example + * _.isArrayLike([1, 2, 3]); + * // => true + * _.isArrayLike(document.body.children); + * // => true + * _.isArrayLike('abc'); + * // => true + * _.isArrayLike(_.noop); + * // => false + */ + function isArrayLike(value) { + return value != null && isLength(value.length) && !isFunction(value); + } + var MAX_SAFE_INTEGER = 9007199254740991; + function isLength(value) { + return (typeof value == 'number') && value > -1 && value % 1 == 0 && value <= MAX_SAFE_INTEGER; + } + var functionTags = ['[object Function]','[object GeneratorFunction]','[object AsyncFunction]','[object Proxy]']; + function isFunction(functionToCheck) { + return functionToCheck && functionTags.indexOf( Object.prototype.toString.call(functionToCheck) ) != -1; + } + + return toHaveSize; +}; From ec3ebcb7bb2c8612e2b18662a0582859439ac56d Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Wed, 18 Mar 2020 08:12:40 -0700 Subject: [PATCH 133/201] Clean up toHaveSize --- lib/jasmine-core/jasmine.js | 200 ++++++++++++++++---------- spec/core/integration/MatchersSpec.js | 58 +------- spec/core/matchers/toHaveSizeSpec.js | 140 ++++++++++++++++-- src/core/matchers/toHaveSize.js | 63 ++------ 4 files changed, 263 insertions(+), 198 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 4c17bf3c..824036b1 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -144,6 +144,7 @@ getJasmineRequireObj().requireMatchers = function(jRequire, j$) { 'toBeUndefined', 'toContain', 'toEqual', + 'toHaveSize', 'toHaveBeenCalled', 'toHaveBeenCalledBefore', 'toHaveBeenCalledTimes', @@ -290,9 +291,9 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return typeof jasmineGlobal.Node !== 'undefined' ? obj instanceof jasmineGlobal.Node : obj !== null && - typeof obj === 'object' && - typeof obj.nodeType === 'number' && - typeof obj.nodeName === 'string'; + typeof obj === 'object' && + typeof obj.nodeType === 'number' && + typeof obj.nodeName === 'string'; // return obj.nodeType > 0; }; @@ -763,7 +764,7 @@ getJasmineRequireObj().Spec = function(j$) { onComplete: function() { onComplete( self.result.status === 'failed' && - new j$.StopExecutionError('spec failed') + new j$.StopExecutionError('spec failed') ); }, userContext: this.userContext() @@ -828,8 +829,8 @@ getJasmineRequireObj().Spec = function(j$) { this.result.failedExpectations.length > 0 || (failSpecWithNoExpectations && this.result.failedExpectations.length + - this.result.passedExpectations.length === - 0) + this.result.passedExpectations.length === + 0) ) { return 'failed'; } @@ -1170,7 +1171,7 @@ getJasmineRequireObj().Env = function(j$) { } runnableResources[ currentRunnable().id - ].defaultStrategyFn = defaultStrategyFn; + ].defaultStrategyFn = defaultStrategyFn; }; this.addSpyStrategy = function(name, fn) { @@ -2565,7 +2566,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { for (var property in this.sample) { if (!hasProperty(other, property) || - !matchersUtil.equals(this.sample[property], other[property])) { + !matchersUtil.equals(this.sample[property], other[property])) { return false; } } @@ -3373,7 +3374,7 @@ getJasmineRequireObj().DelayedFunctionScheduler = function(j$) { // scheduled in a funcToRun from forcing an extra iteration currentTime !== endTime && scheduledLookup[0] <= endTime - ); + ); // ran out of functions to call, but still time left on the clock if (currentTime !== endTime) { @@ -4108,24 +4109,24 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { return actualPromise.then( function() { + return { + pass: false, + message: prefix(false) + ' but it was resolved.' + }; + }, + function(actualValue) { + if (matchersUtil.equals(actualValue, expectedValue)) { + return { + pass: true, + message: prefix(true) + '.' + }; + } else { return { pass: false, - message: prefix(false) + ' but it was resolved.' + message: prefix(false) + ' but it was rejected with ' + matchersUtil.pp(actualValue) + '.' }; - }, - function(actualValue) { - if (matchersUtil.equals(actualValue, expectedValue)) { - return { - pass: true, - message: prefix(true) + '.' - }; - } else { - return { - pass: false, - message: prefix(false) + ' but it was rejected with ' + matchersUtil.pp(actualValue) + '.' - }; - } } + } ); } }; @@ -4494,9 +4495,9 @@ getJasmineRequireObj().MatchersUtil = function(j$) { MatchersUtil.prototype.asymmetricMatch_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { var asymmetricA = j$.isAsymmetricEqualityTester_(a), - asymmetricB = j$.isAsymmetricEqualityTester_(b), - shim, - result; + asymmetricB = j$.isAsymmetricEqualityTester_(b), + shim, + result; if (asymmetricA === asymmetricB) { return undefined; @@ -4731,7 +4732,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // otherwise explicitly look up the mapKey in the other Map since we want keys with unique // obj identity (that are otherwise equal) to not match. if (j$.isAsymmetricEqualityTester_(mapKey) || j$.isAsymmetricEqualityTester_(cmpKey) && - this.eq_(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { + this.eq_(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { mapValueB = b.get(cmpKey); } else { mapValueB = b.get(mapKey); @@ -4800,9 +4801,9 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // or `Array`s from different frames are. var aCtor = a.constructor, bCtor = b.constructor; if (aCtor !== bCtor && - isFunction(aCtor) && isFunction(bCtor) && - a instanceof aCtor && b instanceof bCtor && - !(aCtor instanceof aCtor && bCtor instanceof bCtor)) { + isFunction(aCtor) && isFunction(bCtor) && + a instanceof aCtor && b instanceof bCtor && + !(aCtor instanceof aCtor && bCtor instanceof bCtor)) { diffBuilder.recordMismatch(constructorsAreDifferentFormatter.bind(null, this.pp)); return false; @@ -4849,13 +4850,13 @@ getJasmineRequireObj().MatchersUtil = function(j$) { function keys(obj, isArray) { var allKeys = Object.keys ? Object.keys(obj) : (function(o) { - var keys = []; - for (var key in o) { - if (j$.util.has(o, key)) { - keys.push(key); + var keys = []; + for (var key in o) { + if (j$.util.has(o, key)) { + keys.push(key); + } } - } - return keys; + return keys; })(obj); if (!isArray) { @@ -4863,7 +4864,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } if (allKeys.length === 0) { - return allKeys; + return allKeys; } var extraKeys = []; @@ -4882,10 +4883,10 @@ getJasmineRequireObj().MatchersUtil = function(j$) { function objectKeysAreDifferentFormatter(pp, actual, expected, path) { var missingProperties = j$.util.objectDifference(expected, actual), - extraProperties = j$.util.objectDifference(actual, expected), - missingPropertiesMessage = formatKeyValuePairs(pp, missingProperties), - extraPropertiesMessage = formatKeyValuePairs(pp, extraProperties), - messages = []; + extraProperties = j$.util.objectDifference(actual, expected), + missingPropertiesMessage = formatKeyValuePairs(pp, missingProperties), + extraPropertiesMessage = formatKeyValuePairs(pp, extraProperties), + messages = []; if (!path.depth()) { path = 'object'; @@ -5302,15 +5303,15 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { return { compare: function(actual, expected) { var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : matchersUtil.pp(actual), - expectedType = expected ? j$.fnNameFor(expected) : matchersUtil.pp(expected), - expectedMatcher, - pass; + expectedType = expected ? j$.fnNameFor(expected) : matchersUtil.pp(expected), + expectedMatcher, + pass; try { - expectedMatcher = new j$.Any(expected); - pass = expectedMatcher.asymmetricMatch(actual); + expectedMatcher = new j$.Any(expected); + pass = expectedMatcher.asymmetricMatch(actual); } catch (error) { - throw new Error(usageError('Expected value is not a constructor function')); + throw new Error(usageError('Expected value is not a constructor function')); } if (pass) { @@ -5805,7 +5806,7 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { }); var diffs = actual.calls.allArgs().map(function(argsForCall, callIx) { - var diffBuilder = new j$.DiffBuilder(); + var diffBuilder = new j$.DiffBuilder(); matchersUtil.equals(argsForCall, expectedArgs, diffBuilder); return 'Call ' + callIx + ':\n' + diffBuilder.getMessage().replace(/^/mg, ' '); @@ -5862,6 +5863,49 @@ getJasmineRequireObj().toHaveClass = function(j$) { return toHaveClass; }; +getJasmineRequireObj().toHaveSize = function(j$) { + /** + * {@link expect} the actual size to be equal to the expected, using array-like length or object keys size. + * @function + * @name matchers#toHaveSize + * @since 3.5.1 + * @param {Object} expected - Expected size + * @example + * array = [1,2]; + * expect(array).toHaveSize(2); + */ + function toHaveSize() { + return { + compare: function(actual, expected) { + var result = { + pass: false + }; + + if (actual instanceof WeakSet || actual instanceof WeakMap || actual instanceof DataView) { + throw new Error('Cannot get size of ' + actual + '.'); + } + + if (actual instanceof Set || actual instanceof Map) { + result.pass = actual.size === expected; + } else if (isLength(actual.length)) { + result.pass = actual.length === expected; + } else { + result.pass = Object.keys(actual).length === expected; + } + + return result; + } + }; + } + + var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || 9007199254740991; + function isLength(value) { + return (typeof value == 'number') && value > -1 && value % 1 === 0 && value <= MAX_SAFE_INTEGER; + } + + return toHaveSize; +}; + getJasmineRequireObj().toMatch = function(j$) { var getErrorMsg = j$.formatErrorMsg('', 'expect().toMatch( || )'); @@ -6050,7 +6094,7 @@ getJasmineRequireObj().toThrowError = function(j$) { function thrownDescription(thrown) { var thrownName = errorType ? j$.fnNameFor(thrown.constructor) : 'an exception', - thrownMessage = ''; + thrownMessage = ''; if (expected) { thrownMessage = ' with message ' + matchersUtil.pp(thrown.message); @@ -6157,10 +6201,10 @@ getJasmineRequireObj().toThrowMatching = function(j$) { if (predicate(thrown)) { return pass('Expected function not to throw an exception matching a predicate.'); } else { - return fail(function() { - return 'Expected function to throw an exception matching a predicate, ' + - 'but it threw ' + thrownDescription(thrown) + '.'; - }); + return fail(function() { + return 'Expected function to throw an exception matching a predicate, ' + + 'but it threw ' + thrownDescription(thrown) + '.'; + }); } } }; @@ -6378,8 +6422,8 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { } else if (j$.util.arrayContains(this.seen, value)) { this.emitScalar( '' + (j$.isArray_(value) ? 'Array' : 'Object') + + '>' ); } else if (j$.isArray_(value) || j$.isA_('Object', value)) { this.seen.push(value); @@ -6648,14 +6692,14 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { var allKeys = Object.keys ? Object.keys(obj) : (function(o) { - var keys = []; - for (var key in o) { - if (j$.util.has(o, key)) { - keys.push(key); + var keys = []; + for (var key in o) { + if (j$.util.has(o, key)) { + keys.push(key); + } } - } - return keys; - })(obj); + return keys; + })(obj); if (!isArray) { return allKeys; @@ -6841,11 +6885,11 @@ getJasmineRequireObj().QueueRunner = function(j$) { timeoutId = self.setTimeout(function() { var error = new Error( 'Timeout - Async function did not complete within ' + - timeoutInterval + - 'ms ' + - (queueableFn.timeout - ? '(custom timeout)' - : '(set by jasmine.DEFAULT_TIMEOUT_INTERVAL)') + timeoutInterval + + 'ms ' + + (queueableFn.timeout + ? '(custom timeout)' + : '(set by jasmine.DEFAULT_TIMEOUT_INTERVAL)') ); onException(error); next(); @@ -7563,10 +7607,10 @@ getJasmineRequireObj().Spy = function(j$) { if (argsStrategies.any() && !baseStrategy.isConfigured()) { throw new Error( "Spy '" + - strategyArgs.name + - "' received a call with arguments " + - j$.pp(Array.prototype.slice.call(args)) + - ' but all configured strategies specify other arguments.' + strategyArgs.name + + "' received a call with arguments " + + j$.pp(Array.prototype.slice.call(args)) + + ' but all configured strategies specify other arguments.' ); } else { strategy = baseStrategy; @@ -7789,8 +7833,8 @@ getJasmineRequireObj().SpyRegistry = function(j$) { throw new Error( getErrorMsg( 'spyOn could not find an object to spy upon for ' + - propertyName + - '' + propertyName + + '' ) ); } @@ -7815,9 +7859,9 @@ getJasmineRequireObj().SpyRegistry = function(j$) { throw new Error( getErrorMsg( 'Property ' + - propertyName + - ' does not have access type ' + - accessType + propertyName + + ' does not have access type ' + + accessType ) ); } @@ -7948,7 +7992,7 @@ getJasmineRequireObj().SpyStrategy = function(j$) { if (!Promise) { throw new Error( name + - ' requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`' + ' requires global Promise, or `Promise` configured with `jasmine.getEnv().configure()`' ); } @@ -8724,5 +8768,5 @@ getJasmineRequireObj().UserContext = function(j$) { }; getJasmineRequireObj().version = function() { - return '3.5.0'; + return '3.5.1'; }; diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js index ec3404ff..c1d2dd09 100644 --- a/spec/core/integration/MatchersSpec.js +++ b/spec/core/integration/MatchersSpec.js @@ -496,66 +496,10 @@ describe('Matchers (Integration)', function() { verifyPasses(function(env) { env.expect(['a','b']).toHaveSize(2); }); + verifyFails(function(env) { env.expect(['a','b']).toHaveSize(1); }); - - verifyPasses(function(env) { - env.expect({a: 1, b: 2}).toHaveSize(2); - }); - verifyFails(function(env) { - env.expect({a: 1, b: 2}).toHaveSize(1); - }); - - verifyPasses(function(env) { - env.expect({a: 1, b: 2, length: 5}).toHaveSize(5); - }); - verifyFails(function(env) { - env.expect({a: 1, b: 2, length: 5}).toHaveSize(1); - }); - - verifyPasses(function(env) { - env.expect('ab').toHaveSize(2); - }); - verifyFails(function(env) { - env.expect('ab').toHaveSize(1); - }); - - verifyPasses(function(env) { - var map = new Map(); - map.set('a',1); - map.set('b',2); - env.expect(map).toHaveSize(2); - }); - verifyFails(function(env) { - var map = new Map(); - map.set('a',1); - map.set('b',2); - env.expect(map).toHaveSize(1); - }); - - verifyPasses(function(env) { - var set = new Set(); - set.add('a'); - set.add('b'); - env.expect(set).toHaveSize(2); - }); - verifyFails(function(env) { - var set = new Set(); - set.add('a'); - set.add('b'); - env.expect(set).toHaveSize(1); - }); - - verifyFails(function(env) { - env.expect(new WeakSet()).toHaveSize(1); - }); - verifyFails(function(env) { - env.expect(new WeakMap()).toHaveSize(1); - }); - verifyFails(function(env) { - env.expect(new DataView(new ArrayBuffer(128))).toHaveSize(1); - }); }); describe('toHaveBeenCalled', function() { diff --git a/spec/core/matchers/toHaveSizeSpec.js b/spec/core/matchers/toHaveSizeSpec.js index 08045432..a1b4cccb 100644 --- a/spec/core/matchers/toHaveSizeSpec.js +++ b/spec/core/matchers/toHaveSizeSpec.js @@ -1,21 +1,135 @@ describe('toHaveSize', function() { 'use strict'; - it('delegates to equals function', function() { - var matchersUtil = { - equals: jasmine.createSpy('delegated-equals').and.returnValue(true), - buildFailureMessage: function() { - return 'does not matter'; - }, - DiffBuilder: new jasmineUnderTest.DiffBuilder() - }, - matcher = jasmineUnderTest.matchers.toHaveSize(matchersUtil), - result; + it('passes for an array whose length matches', function() { + var matcher = jasmineUnderTest.matchers.toHaveSize(), + result = matcher.compare([1, 2], 2); - result = matcher.compare([1], 1); - - expect(matchersUtil.equals).toHaveBeenCalledWith(1, 1, jasmine.anything(), jasmine.anything()); expect(result.pass).toBe(true); }); + it('fails for an array whose length does not match', function() { + var matcher = jasmineUnderTest.matchers.toHaveSize(), + result = matcher.compare([1, 2, 3], 2); + + expect(result.pass).toBe(false); + }); + + it('passes for an object with the proper number of keys', function() { + var matcher = jasmineUnderTest.matchers.toHaveSize(), + result = matcher.compare({a: 1, b: 2}, 2); + + expect(result.pass).toBe(true); + }); + + it('fails for an object with a different number of keys', function() { + var matcher = jasmineUnderTest.matchers.toHaveSize(), + result = matcher.compare({a: 1, b: 2}, 1); + + expect(result.pass).toBe(false); + }); + + it('passes for an object with an explicit `length` property that matches', function() { + var matcher = jasmineUnderTest.matchers.toHaveSize(), + result = matcher.compare({a: 1, b: 2, length: 5}, 5); + + expect(result.pass).toBe(true); + }); + + it('fails for an object with an explicit `length` property that does not match', function() { + var matcher = jasmineUnderTest.matchers.toHaveSize(), + result = matcher.compare({a: 1, b: 2, length: 5}, 1); + + expect(result.pass).toBe(false); + }); + + it('passes for a string whose length matches', function() { + var matcher = jasmineUnderTest.matchers.toHaveSize(), + result = matcher.compare('ab', 2); + + expect(result.pass).toBe(true); + }); + + it('fails for a string whose length does not match', function() { + var matcher = jasmineUnderTest.matchers.toHaveSize(), + result = matcher.compare('abc', 2); + + expect(result.pass).toBe(false); + }); + + it('passes for a Map whose length matches', function() { + jasmine.getEnv().requireFunctioningMaps(); + + var map = new Map(); + map.set('a',1); + map.set('b',2); + + var matcher = jasmineUnderTest.matchers.toHaveSize(), + result = matcher.compare(map, 2); + + expect(result.pass).toBe(true); + }); + + it('fails for a Map whose length does not match', function() { + jasmine.getEnv().requireFunctioningMaps(); + + var map = new Map(); + map.set('a',1); + map.set('b',2); + + var matcher = jasmineUnderTest.matchers.toHaveSize(), + result = matcher.compare(map, 1); + + expect(result.pass).toBe(false); + }); + + it('passes for a Set whose length matches', function() { + jasmine.getEnv().requireFunctioningSets(); + + var set = new Set(); + set.add('a'); + set.add('b'); + + var matcher = jasmineUnderTest.matchers.toHaveSize(), + result = matcher.compare(set, 2); + + expect(result.pass).toBe(true); + }); + + it('fails for a Set whose length does not match', function() { + jasmine.getEnv().requireFunctioningSets(); + + var set = new Set(); + set.add('a'); + set.add('b'); + + var matcher = jasmineUnderTest.matchers.toHaveSize(), + result = matcher.compare(set, 1); + + expect(result.pass).toBe(false); + }); + + it('throws an error for WeakSet', function() { + var matcher = jasmineUnderTest.matchers.toHaveSize(); + + expect(function() { + matcher.compare(new WeakSet(), 2); + }).toThrowError('Cannot get size of [object WeakSet].'); + }); + + it('throws an error for WeakMap', function() { + var matcher = jasmineUnderTest.matchers.toHaveSize(); + + expect(function() { + matcher.compare(new WeakMap(), 2); + }).toThrowError('Cannot get size of [object WeakMap].'); + }); + + it('throws an error for DataView', function() { + var matcher = jasmineUnderTest.matchers.toHaveSize(); + + expect(function() { + matcher.compare(new DataView(new ArrayBuffer(128)), 2); + }).toThrowError('Cannot get size of [object DataView].'); + }); }); diff --git a/src/core/matchers/toHaveSize.js b/src/core/matchers/toHaveSize.js index b4ea9c55..ae344ca9 100644 --- a/src/core/matchers/toHaveSize.js +++ b/src/core/matchers/toHaveSize.js @@ -9,70 +9,33 @@ getJasmineRequireObj().toHaveSize = function(j$) { * array = [1,2]; * expect(array).toHaveSize(2); */ - function toHaveSize(matchersUtil) { + function toHaveSize() { return { compare: function(actual, expected) { var result = { pass: false - }, - simpleEqualityTesters = [function(a, b) { - return a === b; - }], - diffBuilder = j$.DiffBuilder(); + }; - // Avoid misleading collections size matching - if (actual instanceof WeakSet - || actual instanceof WeakMap - || actual instanceof DataView) { - result.message = 'Cannot get size of ' + actual + '.'; - return result; + if (actual instanceof WeakSet || actual instanceof WeakMap || actual instanceof DataView) { + throw new Error('Cannot get size of ' + actual + '.'); } - // Ref https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects - if (Array.isArray(actual) || isArrayLike(actual)) - result.pass = matchersUtil.equals(actual.length, expected, simpleEqualityTesters, diffBuilder); - else if ( actual instanceof String || typeof actual === 'string') - result.pass = matchersUtil.equals(actual.length, expected, simpleEqualityTesters, diffBuilder); - else if (actual instanceof Set || actual instanceof Map) - result.pass = matchersUtil.equals(actual.size, expected, simpleEqualityTesters, diffBuilder); - // instanceof Object - else - result.pass = matchersUtil.equals(Object.keys(actual).length, expected, simpleEqualityTesters, diffBuilder); + if (actual instanceof Set || actual instanceof Map) { + result.pass = actual.size === expected; + } else if (isLength(actual.length)) { + result.pass = actual.length === expected; + } else { + result.pass = Object.keys(actual).length === expected; + } - if(!result.pass) - result.message = diffBuilder.getMessage() ; return result; } }; } - /** - * Checks if `value` is array-like. A value is considered array-like if it's - * not a function and has a `value.length` that's an integer greater than or - * equal to `0` and less than or equal to `Number.MAX_SAFE_INTEGER`. - * From lodash - * @param {*} value The value to check. - * @returns {boolean} Returns `true` if `value` is array-like, else `false`. - * @example - * _.isArrayLike([1, 2, 3]); - * // => true - * _.isArrayLike(document.body.children); - * // => true - * _.isArrayLike('abc'); - * // => true - * _.isArrayLike(_.noop); - * // => false - */ - function isArrayLike(value) { - return value != null && isLength(value.length) && !isFunction(value); - } - var MAX_SAFE_INTEGER = 9007199254740991; + var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || 9007199254740991; function isLength(value) { - return (typeof value == 'number') && value > -1 && value % 1 == 0 && value <= MAX_SAFE_INTEGER; - } - var functionTags = ['[object Function]','[object GeneratorFunction]','[object AsyncFunction]','[object Proxy]']; - function isFunction(functionToCheck) { - return functionToCheck && functionTags.indexOf( Object.prototype.toString.call(functionToCheck) ) != -1; + return (typeof value == 'number') && value > -1 && value % 1 === 0 && value <= MAX_SAFE_INTEGER; } return toHaveSize; From 79d55216fcf17f17a6e05e32a5564a03508705bf Mon Sep 17 00:00:00 2001 From: Gregg Van Hove Date: Wed, 18 Mar 2020 08:57:44 -0700 Subject: [PATCH 134/201] Use internal type checks instead of `instanceof` to support browsers that don't include the types --- lib/jasmine-core/jasmine.js | 2 +- src/core/matchers/toHaveSize.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 824036b1..5f9e531e 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -5881,7 +5881,7 @@ getJasmineRequireObj().toHaveSize = function(j$) { pass: false }; - if (actual instanceof WeakSet || actual instanceof WeakMap || actual instanceof DataView) { + if (j$.isA_('WeakSet', actual) || j$.isA_('WeakMap', actual) || j$.isA_('DataView', actual)) { throw new Error('Cannot get size of ' + actual + '.'); } diff --git a/src/core/matchers/toHaveSize.js b/src/core/matchers/toHaveSize.js index ae344ca9..c0e84cb3 100644 --- a/src/core/matchers/toHaveSize.js +++ b/src/core/matchers/toHaveSize.js @@ -16,7 +16,7 @@ getJasmineRequireObj().toHaveSize = function(j$) { pass: false }; - if (actual instanceof WeakSet || actual instanceof WeakMap || actual instanceof DataView) { + if (j$.isA_('WeakSet', actual) || j$.isA_('WeakMap', actual) || j$.isA_('DataView', actual)) { throw new Error('Cannot get size of ' + actual + '.'); } From bcc28d7063971cd04cad89a1bcee2c96726abe97 Mon Sep 17 00:00:00 2001 From: Maksym Kobieliev Date: Thu, 2 Apr 2020 21:31:17 +0300 Subject: [PATCH 135/201] Output a diff if there was only one call, but with wrong parameters --- .../matchers/toHaveBeenCalledOnceWithSpec.js | 2 +- src/core/matchers/toHaveBeenCalledOnceWith.js | 19 ++++++++++++++++--- 2 files changed, 17 insertions(+), 4 deletions(-) diff --git a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js index b3678bfb..97fdaf9c 100644 --- a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js @@ -49,7 +49,7 @@ describe("toHaveBeenCalledOnceWith", function () { result = matcher.compare(calledSpy, 'a', 'b'); expect(result.pass).toBe(false); - expect(result.message).toEqual("Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut the actual calls were:\n [ 'a', 'c' ].\n\n"); + expect(result.message).toEqual("Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut the actual call was:\n [ 'a', 'c' ].\nExpected $[1] = 'c' to equal 'b'.\n\n"); }); it("fails when the actual was called multiple times with expected parameters", function () { diff --git a/src/core/matchers/toHaveBeenCalledOnceWith.js b/src/core/matchers/toHaveBeenCalledOnceWith.js index ccd707c7..035848b0 100644 --- a/src/core/matchers/toHaveBeenCalledOnceWith.js +++ b/src/core/matchers/toHaveBeenCalledOnceWith.js @@ -36,10 +36,23 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { }; } + function getDiffs() { + return actual.calls.allArgs().map(function (argsForCall, callIx) { + var diffBuilder = new j$.DiffBuilder(); + util.equals(argsForCall, expectedArgs, customEqualityTesters, diffBuilder); + return diffBuilder.getMessage(); + }); + } + function butString() { - return actual.calls.count() !== 0 - ? 'But the actual calls were:\n' + prettyPrintedCalls.join(',\n') + '.\n\n' - : 'But it was never called.\n\n'; + switch (actual.calls.count()) { + case 0: + return 'But it was never called.\n\n'; + case 1: + return 'But the actual call was:\n' + prettyPrintedCalls.join(',\n') + '.\n' + getDiffs().join('\n') + '\n\n'; + default: + return 'But the actual calls were:\n' + prettyPrintedCalls.join(',\n') + '.\n\n'; + } } return { From ec9904bf52e7e4c45045742c54595b6af5341aad Mon Sep 17 00:00:00 2001 From: Maksym Kobieliev Date: Thu, 2 Apr 2020 21:38:54 +0300 Subject: [PATCH 136/201] Fix test --- spec/core/matchers/toHaveBeenCalledOnceWithSpec.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js index 97fdaf9c..722a05f1 100644 --- a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js @@ -15,7 +15,8 @@ describe("toHaveBeenCalledOnceWith", function () { it("passes through the custom equality testers", function () { var util = { - contains: jasmine.createSpy('delegated-contains').and.returnValue(false) + contains: jasmine.createSpy('delegated-contains').and.returnValue(false), + equals: jasmineUnderTest.matchersUtil.equals }, customEqualityTesters = [function () { return true; }], matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util, customEqualityTesters), From 9a7dfb15d2a52a80930445091e6ecba49a894f82 Mon Sep 17 00:00:00 2001 From: Alex Parloti Date: Thu, 2 Apr 2020 21:01:56 +0200 Subject: [PATCH 137/201] fix #26 fix #26 Returning false will cause 'zone.js' to invoke e.preventDefault(), preventing the page from reloading. --- src/html/HtmlReporter.js | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/html/HtmlReporter.js b/src/html/HtmlReporter.js index 1c6478cf..24d3a404 100644 --- a/src/html/HtmlReporter.js +++ b/src/html/HtmlReporter.js @@ -321,9 +321,11 @@ jasmineRequire.HtmlReporter = function(j$) { find('.jasmine-failures-menu').onclick = function() { setMenuModeTo('jasmine-failure-list'); + return false; }; find('.jasmine-spec-list-menu').onclick = function() { setMenuModeTo('jasmine-spec-list'); + return false; }; setMenuModeTo('jasmine-failure-list'); From 6b213a958d0edb187e255286dead7828b7752d05 Mon Sep 17 00:00:00 2001 From: DCtheTall Date: Thu, 9 Apr 2020 15:13:33 -0400 Subject: [PATCH 138/201] Add expectAsync().toBePending() --- spec/core/matchers/async/toBePendingSpec.js | 51 +++++++++++++++++++++ src/core/matchers/async/toBePending.js | 25 ++++++++++ src/core/matchers/requireAsyncMatchers.js | 1 + 3 files changed, 77 insertions(+) create mode 100644 spec/core/matchers/async/toBePendingSpec.js create mode 100644 src/core/matchers/async/toBePending.js diff --git a/spec/core/matchers/async/toBePendingSpec.js b/spec/core/matchers/async/toBePendingSpec.js new file mode 100644 index 00000000..5aa4f428 --- /dev/null +++ b/spec/core/matchers/async/toBePendingSpec.js @@ -0,0 +1,51 @@ +describe('toBePending', function() { + it('passes if the actual promise is pending', function() { + jasmine.getEnv().requirePromises(); + + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBePending(matchersUtil), + actual = new Promise(function() {}); + + return matcher.compare(actual).then(function(result) { + expect(result).toEqual(jasmine.objectContaining({pass: true})); + }); + }); + + it('fails if the actual promise is resolved', function() { + jasmine.getEnv().requirePromises(); + + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBePending(matchersUtil), + actual = Promise.resolve(); + + return matcher.compare(actual).then(function(result) { + expect(result).toEqual(jasmine.objectContaining({pass: false})); + }); + }); + + it('fails if the actual promise is rejected', function() { + jasmine.getEnv().requirePromises(); + + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBePending(matchersUtil), + actual = Promise.reject(new Error('promise was rejected')); + + return matcher.compare(actual).then(function(result) { + expect(result).toEqual(jasmine.objectContaining({pass: false})); + }); + }); + + it('fails if actual is not a promise', function() { + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + matcher = jasmineUnderTest.asyncMatchers.toBePending(matchersUtil), + actual = 'not a promise'; + + function f() { + return matcher.compare(actual); + } + + expect(f).toThrowError( + 'Expected toBePending to be called on a promise.' + ); + }); +}); \ No newline at end of file diff --git a/src/core/matchers/async/toBePending.js b/src/core/matchers/async/toBePending.js new file mode 100644 index 00000000..31059084 --- /dev/null +++ b/src/core/matchers/async/toBePending.js @@ -0,0 +1,25 @@ +getJasmineRequireObj().toBePending = function(j$) { + /** + * Expect a promise to be pending, ie. the promise is neither resolved nor rejected. + * @function + * @async + * @name async-matchers#toBePending + * @since 3.5.1 (should this be the next version or the version when it was added?) + * @example + * await expectAsync(aPromise).toBePending(); + */ + return function toBePending() { + return { + compare: function(actual) { + if (!j$.isPromiseLike(actual)) { + throw new Error('Expected toBePending to be called on a promise.'); + } + var want = {}; + return Promise.race([actual, Promise.resolve(want)]).then( + function(got) { return {pass: want === got}; }, + function() { return {pass: false}; } + ); + } + }; + }; +}; \ No newline at end of file diff --git a/src/core/matchers/requireAsyncMatchers.js b/src/core/matchers/requireAsyncMatchers.js index faa91c02..abe9b8ef 100644 --- a/src/core/matchers/requireAsyncMatchers.js +++ b/src/core/matchers/requireAsyncMatchers.js @@ -1,5 +1,6 @@ getJasmineRequireObj().requireAsyncMatchers = function(jRequire, j$) { var availableMatchers = [ + 'toBePending', 'toBeResolved', 'toBeRejected', 'toBeResolvedTo', From 76a99aef86ff1bf029851b56194cd16cb7facc2c Mon Sep 17 00:00:00 2001 From: DCtheTall Date: Thu, 9 Apr 2020 15:19:47 -0400 Subject: [PATCH 139/201] add missing trailing newline --- src/core/matchers/async/toBePending.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/core/matchers/async/toBePending.js b/src/core/matchers/async/toBePending.js index 31059084..7ea12df9 100644 --- a/src/core/matchers/async/toBePending.js +++ b/src/core/matchers/async/toBePending.js @@ -22,4 +22,4 @@ getJasmineRequireObj().toBePending = function(j$) { } }; }; -}; \ No newline at end of file +}; From 08779f2657cbd088b8b37e3c17e9363ac8406c46 Mon Sep 17 00:00:00 2001 From: DCtheTall Date: Thu, 9 Apr 2020 15:20:23 -0400 Subject: [PATCH 140/201] add missing trailing newline --- spec/core/matchers/async/toBePendingSpec.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/core/matchers/async/toBePendingSpec.js b/spec/core/matchers/async/toBePendingSpec.js index 5aa4f428..318e22b7 100644 --- a/spec/core/matchers/async/toBePendingSpec.js +++ b/spec/core/matchers/async/toBePendingSpec.js @@ -48,4 +48,4 @@ describe('toBePending', function() { 'Expected toBePending to be called on a promise.' ); }); -}); \ No newline at end of file +}); From 78c3a007ad8cb29834b1ed957599804272a6b578 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 11 Apr 2020 12:08:49 -0700 Subject: [PATCH 141/201] Fixed test failure in Firefox 74 --- spec/html/PrettyPrintHtmlSpec.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/html/PrettyPrintHtmlSpec.js b/spec/html/PrettyPrintHtmlSpec.js index fd364d9e..738753ba 100644 --- a/spec/html/PrettyPrintHtmlSpec.js +++ b/spec/html/PrettyPrintHtmlSpec.js @@ -31,7 +31,7 @@ describe('PrettyPrinter (HTML Dependent)', function() { } // Different versions of FF produce different error messages. expect(pp(err)).toMatch( - /Not enough arguments|CustomEvent requires at least 1 argument, but only 0 were passed/ + /Not enough arguments|CustomEvent.*only 0.*passed/ ); } }); From 8991b1bba39b5b7e89fc5eeb07ae271a684cb1a4 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sun, 12 Apr 2020 13:43:44 -0700 Subject: [PATCH 142/201] Fixed toHaveSize matcher on IE 10 & 11 --- lib/jasmine-core/jasmine.js | 22 ++++++++++++++++++++-- spec/core/baseSpec.js | 11 +++++++++++ spec/core/matchers/toHaveSizeSpec.js | 6 ++++-- spec/helpers/checkForMap.js | 6 ++++++ spec/helpers/checkForSet.js | 6 ++++++ src/core/base.js | 18 ++++++++++++++++++ src/core/matchers/toHaveSize.js | 4 ++-- 7 files changed, 67 insertions(+), 6 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 9f4413c3..1701fd73 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -314,6 +314,24 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { obj.constructor === jasmineGlobal.Set ); }; + + j$.isWeakMap = function(obj) { + return ( + obj !== null && + typeof obj !== 'undefined' && + typeof jasmineGlobal.WeakMap !== 'undefined' && + obj.constructor === jasmineGlobal.WeakMap + ); + }; + + j$.isDataView = function(obj) { + return ( + obj !== null && + typeof obj !== 'undefined' && + typeof jasmineGlobal.DataView !== 'undefined' && + obj.constructor === jasmineGlobal.DataView + ); + }; j$.isPromise = function(obj) { return ( @@ -5908,11 +5926,11 @@ getJasmineRequireObj().toHaveSize = function(j$) { pass: false }; - if (j$.isA_('WeakSet', actual) || j$.isA_('WeakMap', actual) || j$.isA_('DataView', actual)) { + if (j$.isA_('WeakSet', actual) || j$.isWeakMap(actual) || j$.isDataView(actual)) { throw new Error('Cannot get size of ' + actual + '.'); } - if (actual instanceof Set || actual instanceof Map) { + if (j$.isSet(actual) || j$.isMap(actual)) { result.pass = actual.size === expected; } else if (isLength(actual.length)) { result.pass = actual.length === expected; diff --git a/spec/core/baseSpec.js b/spec/core/baseSpec.js index 4fce2254..b85721b9 100644 --- a/spec/core/baseSpec.js +++ b/spec/core/baseSpec.js @@ -51,4 +51,15 @@ describe('base helpers', function() { expect(jasmineUnderTest.isAsymmetricEqualityTester_(obj)).toBe(true); }); }); + + describe('isSet', function() { + it('returns true when the object is a Set', function() { + jasmine.getEnv().requireFunctioningSets(); + expect(jasmineUnderTest.isSet(new Set())).toBe(true); + }); + + it('returns false when the object is not a Set', function() { + expect(jasmineUnderTest.isSet({})).toBe(false); + }); + }); }); diff --git a/spec/core/matchers/toHaveSizeSpec.js b/spec/core/matchers/toHaveSizeSpec.js index a1b4cccb..a14a24e5 100644 --- a/spec/core/matchers/toHaveSizeSpec.js +++ b/spec/core/matchers/toHaveSizeSpec.js @@ -110,6 +110,7 @@ describe('toHaveSize', function() { }); it('throws an error for WeakSet', function() { + jasmine.getEnv().requireWeakSets(); var matcher = jasmineUnderTest.matchers.toHaveSize(); expect(function() { @@ -118,11 +119,12 @@ describe('toHaveSize', function() { }); it('throws an error for WeakMap', function() { + jasmine.getEnv().requireWeakMaps(); var matcher = jasmineUnderTest.matchers.toHaveSize(); expect(function() { matcher.compare(new WeakMap(), 2); - }).toThrowError('Cannot get size of [object WeakMap].'); + }).toThrowError(/Cannot get size of \[object (WeakMap|Object)\]\./); }); it('throws an error for DataView', function() { @@ -130,6 +132,6 @@ describe('toHaveSize', function() { expect(function() { matcher.compare(new DataView(new ArrayBuffer(128)), 2); - }).toThrowError('Cannot get size of [object DataView].'); + }).toThrowError(/Cannot get size of \[object (DataView|Object)\]\./); }); }); diff --git a/spec/helpers/checkForMap.js b/spec/helpers/checkForMap.js index 46e346a8..77fa1233 100644 --- a/spec/helpers/checkForMap.js +++ b/spec/helpers/checkForMap.js @@ -43,4 +43,10 @@ env.pending('Browser has incomplete or missing support for Maps'); } }; + + env.requireWeakMaps = function() { + if (typeof WeakMap === 'undefined') { + env.pending('Browser does not have support for WeakMap'); + } + }; })(jasmine.getEnv()); diff --git a/spec/helpers/checkForSet.js b/spec/helpers/checkForSet.js index dacb06aa..8656342d 100644 --- a/spec/helpers/checkForSet.js +++ b/spec/helpers/checkForSet.js @@ -47,4 +47,10 @@ env.pending('Browser has incomplete or missing support for Sets'); } }; + + env.requireWeakSets = function() { + if (typeof WeakSet === 'undefined') { + env.pending('Browser does not have support for WeakSet'); + } + }; })(jasmine.getEnv()); diff --git a/src/core/base.js b/src/core/base.js index e86a12c8..121ff614 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -148,6 +148,24 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { ); }; + j$.isWeakMap = function(obj) { + return ( + obj !== null && + typeof obj !== 'undefined' && + typeof jasmineGlobal.WeakMap !== 'undefined' && + obj.constructor === jasmineGlobal.WeakMap + ); + }; + + j$.isDataView = function(obj) { + return ( + obj !== null && + typeof obj !== 'undefined' && + typeof jasmineGlobal.DataView !== 'undefined' && + obj.constructor === jasmineGlobal.DataView + ); + }; + j$.isPromise = function(obj) { return ( typeof jasmineGlobal.Promise !== 'undefined' && diff --git a/src/core/matchers/toHaveSize.js b/src/core/matchers/toHaveSize.js index c0e84cb3..4f6ace0c 100644 --- a/src/core/matchers/toHaveSize.js +++ b/src/core/matchers/toHaveSize.js @@ -16,11 +16,11 @@ getJasmineRequireObj().toHaveSize = function(j$) { pass: false }; - if (j$.isA_('WeakSet', actual) || j$.isA_('WeakMap', actual) || j$.isA_('DataView', actual)) { + if (j$.isA_('WeakSet', actual) || j$.isWeakMap(actual) || j$.isDataView(actual)) { throw new Error('Cannot get size of ' + actual + '.'); } - if (actual instanceof Set || actual instanceof Map) { + if (j$.isSet(actual) || j$.isMap(actual)) { result.pass = actual.size === expected; } else if (isLength(actual.length)) { result.pass = actual.length === expected; From f90d9943fec94bd71b28509761f53d4ed537039d Mon Sep 17 00:00:00 2001 From: johnjbarton Date: Tue, 29 Oct 2019 17:17:27 -0700 Subject: [PATCH 143/201] feat(env): setSpecProperty/setSuiteProperty(key, value) to attach data to tests Use setSpecProperty to attach key/value pairs to spec results that can be picked up in specialized jasmine reporters. Example use-cases include: * Tagging specs with URLs or string-tokens referencing test-plan docs. * Recording performance information for blocks of JS. Similarly setSuiteProperty attaches key/value pairs to suite results --- spec/core/SpecSpec.js | 20 ++++++++- spec/core/integration/EnvSpec.js | 71 ++++++++++++++++++++++++++++++++ src/core/Env.js | 18 ++++++++ src/core/Spec.js | 9 +++- src/core/Suite.js | 9 +++- 5 files changed, 124 insertions(+), 3 deletions(-) diff --git a/spec/core/SpecSpec.js b/spec/core/SpecSpec.js index 38a8e780..fa530049 100644 --- a/spec/core/SpecSpec.js +++ b/spec/core/SpecSpec.js @@ -227,7 +227,8 @@ describe('Spec', function() { passedExpectations: [], deprecationWarnings: [], pendingReason: '', - duration: jasmine.any(Number) + duration: jasmine.any(Number), + properties: null }, 'things' ); @@ -299,6 +300,23 @@ describe('Spec', function() { expect(duration).toBe(77000); }); + it('should report properties set during the test', function() { + var done = jasmine.createSpy('done callback'), + spec = new jasmineUnderTest.Spec({ + queueableFn: { fn: jasmine.createSpy('spec body') }, + catchExceptions: function() { + return false; + }, + resultCallback: function() {}, + queueRunnerFactory: function(attrs) { + attrs.onComplete(); + } + }); + spec.setSpecProperty('a', 4); + spec.execute(done); + expect(spec.result.properties).toEqual({ a: 4 }); + }); + it('#status returns passing by default', function() { var spec = new jasmineUnderTest.Spec({ queueableFn: { fn: jasmine.createSpy('spec body') } diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index 8c5c1941..247744d3 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -1971,6 +1971,77 @@ describe("Env integration", function() { env.execute(); }); + it('reports test properties on specs', function(done) { + var env = new jasmineUnderTest.Env(), + reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + + reporter.specDone.and.callFake(function(e) { + expect(e.properties).toEqual({a: 'Bee'}); + done(); + }); + + env.addReporter(reporter); + env.it('calls setSpecProperty', function() { + env.setSpecProperty('a', 'Bee') + }); + env.execute(); + }); + + it('throws an exception if you try to setSpecProperty outside of a spec', function (done) { + var env = new jasmineUnderTest.Env(), + exception; + + env.describe("a suite", function () { + try { + env.setSpecProperty('a prop', 'val'); + } catch(e) { + exception = e; + } + }); + + var assertions = function() { + expect(exception.message).toBe(`'setSpecProperty' was used when there was no current spec`); + done(); + }; + + env.addReporter({jasmineDone: assertions}); + + env.execute(); + }); + + it('reports test properties on suites', function(done) { + var env = new jasmineUnderTest.Env(), + reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + + reporter.suiteDone.and.callFake(function(e) { + expect(e.properties).toEqual({b: 'Sweet'}); + done(); + }); + + env.addReporter(reporter); + env.describe('calls setSuiteProperty', function() { + env.beforeEach(() => { + env.setSuiteProperty('b', 'Sweet'); + }); + env.it('a passing spec', () => { + expect.nothing(); + }); + }); + + env.execute(); + }); + + it('throws an exception if you try to setSuiteProperty outside of a suite', function (done) { + var env = new jasmineUnderTest.Env(); + + try { + env.setSuiteProperty('a', 'Bee'); + } catch(e) { + expect(e.message).toBe(`'setSuiteProperty' was used when there was no current suite`); + done(); + } + }); + it("should associate errors thrown from async code with the correct runnable", function(done) { var reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone','specDone']); diff --git a/src/core/Env.js b/src/core/Env.js index 47915c0a..1135aee7 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -1124,6 +1124,24 @@ getJasmineRequireObj().Env = function(j$) { return spec; }; + this.setSpecProperty = function(key, value) { + if (!currentRunnable() || currentRunnable() == currentSuite()) { + throw new Error( + "'setSpecProperty' was used when there was no current spec" + ); + } + currentRunnable().setSpecProperty(key, value); + }; + + this.setSuiteProperty = function(key, value) { + if (!currentSuite()) { + throw new Error( + "'setSuiteProperty' was used when there was no current suite" + ); + } + currentSuite().setSuiteProperty(key, value); + }; + this.expect = function(actual) { if (!currentRunnable()) { throw new Error( diff --git a/src/core/Spec.js b/src/core/Spec.js index db35de64..f369ac7a 100644 --- a/src/core/Spec.js +++ b/src/core/Spec.js @@ -48,6 +48,7 @@ getJasmineRequireObj().Spec = function(j$) { * @property {String} pendingReason - If the spec is {@link pending}, this will be the reason. * @property {String} status - Once the spec has completed, this string represents the pass/fail status of this spec. * @property {number} duration - The time in ms used by the spec execution, including any before/afterEach. + * @property {Object} properties - user-supplied key-value pairs. */ this.result = { id: this.id, @@ -57,7 +58,8 @@ getJasmineRequireObj().Spec = function(j$) { passedExpectations: [], deprecationWarnings: [], pendingReason: '', - duration: null + duration: null, + properties: null }; } @@ -74,6 +76,11 @@ getJasmineRequireObj().Spec = function(j$) { } }; + Spec.prototype.setSpecProperty = function(key, value) { + this.result.properties = this.result.properties || {}; + this.result.properties[key] = value; + }; + Spec.prototype.expect = function(actual) { return this.expectationFactory(actual, this); }; diff --git a/src/core/Suite.js b/src/core/Suite.js index 4d33ceaa..5cbb9555 100644 --- a/src/core/Suite.js +++ b/src/core/Suite.js @@ -27,6 +27,7 @@ getJasmineRequireObj().Suite = function(j$) { * @property {Expectation[]} deprecationWarnings - The list of deprecation warnings that occurred on this suite. * @property {String} status - Once the suite has completed, this string represents the pass/fail status of this suite. * @property {number} duration - The time in ms for Suite execution, including any before/afterAll, before/afterEach. + * @property {Object} properties - user-supplied key-value pairs. */ this.result = { id: this.id, @@ -34,10 +35,16 @@ getJasmineRequireObj().Suite = function(j$) { fullName: this.getFullName(), failedExpectations: [], deprecationWarnings: [], - duration: null + duration: null, + properties: null }; } + Suite.prototype.setSuiteProperty = function(key, value) { + this.result.properties = this.result.properties || {}; + this.result.properties[key] = value; + }; + Suite.prototype.expect = function(actual) { return this.expectationFactory(actual, this); }; From e94e6c5b7525ea705cf369def76985f279567f01 Mon Sep 17 00:00:00 2001 From: Maksym Kobieliev Date: Tue, 14 Apr 2020 22:01:56 +0300 Subject: [PATCH 144/201] Fix failing unit test --- spec/core/matchers/toHaveBeenCalledOnceWithSpec.js | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js index 722a05f1..d5bdab43 100644 --- a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js @@ -14,11 +14,10 @@ describe("toHaveBeenCalledOnceWith", function () { }); it("passes through the custom equality testers", function () { - var util = { - contains: jasmine.createSpy('delegated-contains').and.returnValue(false), - equals: jasmineUnderTest.matchersUtil.equals - }, - customEqualityTesters = [function () { return true; }], + var util = jasmineUnderTest.matchersUtil; + spyOn(util, 'contains').and.returnValue(false); + + var customEqualityTesters = [function () { return true; }], matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util, customEqualityTesters), calledSpy = new jasmineUnderTest.Spy('called-spy'); From 8a731e17a7e4d97c73ba8428911c4f6d3a004c23 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 5 May 2020 17:58:16 -0700 Subject: [PATCH 145/201] Improved jsdocs for user-specified spec/suite properties --- lib/jasmine-core/jasmine.js | 20 ++++++++++++++++++-- src/core/Env.js | 16 ++++++++++++++++ src/core/Spec.js | 2 +- src/core/Suite.js | 2 +- 4 files changed, 36 insertions(+), 4 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 63fa4b59..ace5df87 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -716,7 +716,7 @@ getJasmineRequireObj().Spec = function(j$) { * @property {String} pendingReason - If the spec is {@link pending}, this will be the reason. * @property {String} status - Once the spec has completed, this string represents the pass/fail status of this spec. * @property {number} duration - The time in ms used by the spec execution, including any before/afterEach. - * @property {Object} properties - user-supplied key-value pairs. + * @property {Object} properties - User-supplied properties, if any, that were set using {@link Env#setSpecProperty} */ this.result = { id: this.id, @@ -2075,6 +2075,14 @@ getJasmineRequireObj().Env = function(j$) { return spec; }; + /** + * Sets a user-defined property that will be provided to reporters as part of {@link SpecResult#properties} + * @name Env#setSpecProperty + * @since 3.6.0 + * @function + * @param {String} key The name of the property + * @param {*} value The value of the property + */ this.setSpecProperty = function(key, value) { if (!currentRunnable() || currentRunnable() == currentSuite()) { throw new Error( @@ -2084,6 +2092,14 @@ getJasmineRequireObj().Env = function(j$) { currentRunnable().setSpecProperty(key, value); }; + /** + * Sets a user-defined property that will be provided to reporters as part of {@link SuiteResult#properties} + * @name Env#setSuiteProperty + * @since 3.6.0 + * @function + * @param {String} key The name of the property + * @param {*} value The value of the property + */ this.setSuiteProperty = function(key, value) { if (!currentSuite()) { throw new Error( @@ -8373,7 +8389,7 @@ getJasmineRequireObj().Suite = function(j$) { * @property {Expectation[]} deprecationWarnings - The list of deprecation warnings that occurred on this suite. * @property {String} status - Once the suite has completed, this string represents the pass/fail status of this suite. * @property {number} duration - The time in ms for Suite execution, including any before/afterAll, before/afterEach. - * @property {Object} properties - user-supplied key-value pairs. + * @property {Object} properties - User-supplied properties, if any, that were set using {@link Env#setSuiteProperty} */ this.result = { id: this.id, diff --git a/src/core/Env.js b/src/core/Env.js index 1135aee7..60025850 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -1124,6 +1124,14 @@ getJasmineRequireObj().Env = function(j$) { return spec; }; + /** + * Sets a user-defined property that will be provided to reporters as part of {@link SpecResult#properties} + * @name Env#setSpecProperty + * @since 3.6.0 + * @function + * @param {String} key The name of the property + * @param {*} value The value of the property + */ this.setSpecProperty = function(key, value) { if (!currentRunnable() || currentRunnable() == currentSuite()) { throw new Error( @@ -1133,6 +1141,14 @@ getJasmineRequireObj().Env = function(j$) { currentRunnable().setSpecProperty(key, value); }; + /** + * Sets a user-defined property that will be provided to reporters as part of {@link SuiteResult#properties} + * @name Env#setSuiteProperty + * @since 3.6.0 + * @function + * @param {String} key The name of the property + * @param {*} value The value of the property + */ this.setSuiteProperty = function(key, value) { if (!currentSuite()) { throw new Error( diff --git a/src/core/Spec.js b/src/core/Spec.js index f369ac7a..83d389d4 100644 --- a/src/core/Spec.js +++ b/src/core/Spec.js @@ -48,7 +48,7 @@ getJasmineRequireObj().Spec = function(j$) { * @property {String} pendingReason - If the spec is {@link pending}, this will be the reason. * @property {String} status - Once the spec has completed, this string represents the pass/fail status of this spec. * @property {number} duration - The time in ms used by the spec execution, including any before/afterEach. - * @property {Object} properties - user-supplied key-value pairs. + * @property {Object} properties - User-supplied properties, if any, that were set using {@link Env#setSpecProperty} */ this.result = { id: this.id, diff --git a/src/core/Suite.js b/src/core/Suite.js index 5cbb9555..e660d1f1 100644 --- a/src/core/Suite.js +++ b/src/core/Suite.js @@ -27,7 +27,7 @@ getJasmineRequireObj().Suite = function(j$) { * @property {Expectation[]} deprecationWarnings - The list of deprecation warnings that occurred on this suite. * @property {String} status - Once the suite has completed, this string represents the pass/fail status of this suite. * @property {number} duration - The time in ms for Suite execution, including any before/afterAll, before/afterEach. - * @property {Object} properties - user-supplied key-value pairs. + * @property {Object} properties - User-supplied properties, if any, that were set using {@link Env#setSuiteProperty} */ this.result = { id: this.id, From 0cb304131f4e7f3816ecb1bfca98fbd571d4cb54 Mon Sep 17 00:00:00 2001 From: johnjbarton Date: Tue, 26 May 2020 14:50:01 -0700 Subject: [PATCH 146/201] fix(env): expose setSpec/SuiteProperty on interface --- src/core/requireInterface.js | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/src/core/requireInterface.js b/src/core/requireInterface.js index 15a13cd1..adc503f8 100644 --- a/src/core/requireInterface.js +++ b/src/core/requireInterface.js @@ -168,6 +168,30 @@ getJasmineRequireObj().interface = function(jasmine, env) { return env.afterAll.apply(env, arguments); }, + /** + * Sets a user-defined property that will be provided to reporters as part of {@link SpecResult#properties} + * @name Env#setSpecProperty + * @since 3.6.0 + * @function + * @param {String} key The name of the property + * @param {*} value The value of the property + */ + setSpecProperty: function(key, value) { + return env.setSpecProperty(key, value); + }, + + /** + * Sets a user-defined property that will be provided to reporters as part of {@link SuiteResult#properties} + * @name Env#setSuiteProperty + * @since 3.6.0 + * @function + * @param {String} key The name of the property + * @param {*} value The value of the property + */ + setSuiteProperty: function(key, value) { + return env.setSuiteProperty(key, value); + }, + /** * Create an expectation for a spec. * @name expect From 45ad7fd13cb110aa59e027abde1914f6b04eeee4 Mon Sep 17 00:00:00 2001 From: Dirk Puge <67125647+dirkpuge@users.noreply.github.com> Date: Sun, 21 Jun 2020 11:48:05 -0400 Subject: [PATCH 147/201] Added missing periods --- README.md | 32 ++++++++++++++++---------------- 1 file changed, 16 insertions(+), 16 deletions(-) diff --git a/README.md b/README.md index c6a5ff36..caa0533f 100644 --- a/README.md +++ b/README.md @@ -9,35 +9,35 @@ Jasmine is a Behavior Driven Development testing framework for JavaScript. It does not rely on browsers, DOM, or any JavaScript framework. Thus it's suited for websites, [Node.js](http://nodejs.org) projects, or anywhere that JavaScript can run. Documentation & guides live here: [http://jasmine.github.io](http://jasmine.github.io/) -For a quick start guide of Jasmine, see the beginning of [http://jasmine.github.io/edge/introduction.html](http://jasmine.github.io/edge/introduction.html) +For a quick start guide of Jasmine, see the beginning of [http://jasmine.github.io/edge/introduction.html](http://jasmine.github.io/edge/introduction.html). Upgrading from Jasmine 2.x? Check out the [3.0 release notes](https://github.com/jasmine/jasmine/blob/v3.0.0/release_notes/3.0.md) for a list of what's new (including breaking changes). ## Contributing -Please read the [contributors' guide](https://github.com/jasmine/jasmine/blob/master/.github/CONTRIBUTING.md) +Please read the [contributors' guide](https://github.com/jasmine/jasmine/blob/master/.github/CONTRIBUTING.md). ## Installation For the Jasmine NPM module:
-[https://github.com/jasmine/jasmine-npm](https://github.com/jasmine/jasmine-npm) +[https://github.com/jasmine/jasmine-npm](https://github.com/jasmine/jasmine-npm). For the Jasmine Ruby Gem:
-[https://github.com/jasmine/jasmine-gem](https://github.com/jasmine/jasmine-gem) +[https://github.com/jasmine/jasmine-gem](https://github.com/jasmine/jasmine-gem). For the Jasmine Python Egg:
-[https://github.com/jasmine/jasmine-py](https://github.com/jasmine/jasmine-py) +[https://github.com/jasmine/jasmine-py](https://github.com/jasmine/jasmine-py). For the Jasmine headless browser gulp plugin:
-[https://github.com/jasmine/gulp-jasmine-browser](https://github.com/jasmine/gulp-jasmine-browser) +[https://github.com/jasmine/gulp-jasmine-browser](https://github.com/jasmine/gulp-jasmine-browser). To install Jasmine standalone on your local box (where **_{#.#.#}_** below is substituted by the release number downloaded): -* Download the standalone distribution for your desired release from the [releases page](https://github.com/jasmine/jasmine/releases) -* Create a Jasmine directory in your project - `mkdir my-project/jasmine` -* Move the dist to your project directory - `mv jasmine/dist/jasmine-standalone-{#.#.#}.zip my-project/jasmine` -* Change directory - `cd my-project/jasmine` -* Unzip the dist - `unzip jasmine-standalone-{#.#.#}.zip` +* Download the standalone distribution for your desired release from the [releases page](https://github.com/jasmine/jasmine/releases). +* Create a Jasmine directory in your project. - `mkdir my-project/jasmine` +* Move the dist to your project directory. - `mv jasmine/dist/jasmine-standalone-{#.#.#}.zip my-project/jasmine` +* Change directory. - `cd my-project/jasmine` +* Unzip the dist. - `unzip jasmine-standalone-{#.#.#}.zip` Add the following to your HTML file: @@ -52,16 +52,16 @@ Add the following to your HTML file: ## Supported environments -Jasmine tests itself across many browsers (Safari, Chrome, Firefox, Microsoft Edge, and new Internet Explorer) as well as nodejs. To see the exact version tests are run against look at our [.travis.yml](https://github.com/jasmine/jasmine/blob/master/.travis.yml) +Jasmine tests itself across many browsers (Safari, Chrome, Firefox, Microsoft Edge, and new Internet Explorer) as well as nodejs. To see the exact version tests are run against look at our [.travis.yml](https://github.com/jasmine/jasmine/blob/master/.travis.yml). [![Sauce Test Status](https://saucelabs.com/browser-matrix/jasmine-js.svg)](https://saucelabs.com/u/jasmine-js) ## Support -* Search past discussions: [http://groups.google.com/group/jasmine-js](http://groups.google.com/group/jasmine-js) -* Send an email to the list: [jasmine-js@googlegroups.com](mailto:jasmine-js@googlegroups.com) -* View the project backlog at Pivotal Tracker: [http://www.pivotaltracker.com/projects/10606](http://www.pivotaltracker.com/projects/10606) -* Follow us on Twitter: [@JasmineBDD](http://twitter.com/JasmineBDD) +* Search past discussions: [http://groups.google.com/group/jasmine-js](http://groups.google.com/group/jasmine-js). +* Send an email to the list: [jasmine-js@googlegroups.com](mailto:jasmine-js@googlegroups.com). +* View the project backlog at Pivotal Tracker: [http://www.pivotaltracker.com/projects/10606](http://www.pivotaltracker.com/projects/10606). +* Follow us on Twitter: [@JasmineBDD](http://twitter.com/JasmineBDD). ## Maintainers From 17eda7a2de269cdc400aa517ca159ae6291c182b Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 24 Jun 2020 17:49:11 -0700 Subject: [PATCH 148/201] Depend on head of jasmine-browser This should fix CI, and can be reverted once a new version of jasmine-browser that contains 33bd0fcb0ba990102dcd846e673d07b11041dd44 has been published. --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 8db8eace..3632bcbe 100644 --- a/package.json +++ b/package.json @@ -39,7 +39,7 @@ "grunt-css-url-embed": "^1.11.1", "grunt-sass": "^3.0.2", "jasmine": "^3.4.0", - "jasmine-browser-runner": "0.3.0", + "jasmine-browser-runner": "github:jasmine/jasmine-browser", "jsdom": "^15.0.0", "load-grunt-tasks": "^4.0.0", "node-sass": "^4.11.0", From ce2161ca32f829cd7c403fe28a98ad774bc7f5b8 Mon Sep 17 00:00:00 2001 From: Tobias Schweizer Date: Thu, 25 Jun 2020 09:41:39 +0200 Subject: [PATCH 149/201] Add additional test for equals matcher --- spec/core/matchers/matchersUtilSpec.js | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index 4894fefa..81874302 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -109,6 +109,11 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(123, 456)).toBe(false); }); + it("fails for a Number and a String that have equivalent values", function() { + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + expect(matchersUtil.equals(123, "123")).toBe(false); + }); + it("passes for Dates that are equivalent", function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(new Date("Jan 1, 1970"), new Date("Jan 1, 1970"))).toBe(true); From f4753ac0a44bdc578626db63b56c84bda0058d77 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 25 Jun 2020 07:36:06 -0700 Subject: [PATCH 150/201] Fixed syntax errors in IE 10 --- spec/core/integration/EnvSpec.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index 247744d3..c811c9bf 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -2000,7 +2000,7 @@ describe("Env integration", function() { }); var assertions = function() { - expect(exception.message).toBe(`'setSpecProperty' was used when there was no current spec`); + expect(exception.message).toBe("'setSpecProperty' was used when there was no current spec"); done(); }; @@ -2020,10 +2020,10 @@ describe("Env integration", function() { env.addReporter(reporter); env.describe('calls setSuiteProperty', function() { - env.beforeEach(() => { + env.beforeEach(function() { env.setSuiteProperty('b', 'Sweet'); }); - env.it('a passing spec', () => { + env.it('a passing spec', function() { expect.nothing(); }); }); @@ -2037,7 +2037,7 @@ describe("Env integration", function() { try { env.setSuiteProperty('a', 'Bee'); } catch(e) { - expect(e.message).toBe(`'setSuiteProperty' was used when there was no current suite`); + expect(e.message).toBe("'setSuiteProperty' was used when there was no current suite"); done(); } }); From 3943cc2ddbba17b50b706a79d7406340b4641b53 Mon Sep 17 00:00:00 2001 From: "Terence D. Honles" Date: Tue, 2 Jun 2020 10:35:27 -0700 Subject: [PATCH 151/201] allow spy throwError to throw an Object When using the following code to simulate a node error: spyOn(process, 'kill').and.throwError({code: 'ESRCH'}) The object passed in will be converted to a string by the Error constructor and result in '[object Object]' which is not very useful. This PR changes the ``throwError`` spy strategy to only convert strings into an Error object, but any other objects which are passed in will be thrown as is. This means the spy strategy can never emulate throwing a bare string ``throw 'error'``, but this would be a backward incompatible change. --- spec/core/SpyStrategySpec.js | 14 +++++++++++++- src/core/SpyStrategy.js | 4 ++-- 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/spec/core/SpyStrategySpec.js b/spec/core/SpyStrategySpec.js index 5e454b64..76a3a1e2 100644 --- a/spec/core/SpyStrategySpec.js +++ b/spec/core/SpyStrategySpec.js @@ -70,7 +70,7 @@ describe('SpyStrategy', function() { expect(originalFn).not.toHaveBeenCalled(); }); - it('allows a non-Error to be thrown, wrapping it into an exception when executed', function() { + it('allows a string to be thrown, wrapping it into an exception when executed', function() { var originalFn = jasmine.createSpy('original'), spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }); @@ -82,6 +82,18 @@ describe('SpyStrategy', function() { expect(originalFn).not.toHaveBeenCalled(); }); + it('allows a non-Error to be thrown when executed', function() { + var originalFn = jasmine.createSpy('original'), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: originalFn }); + + spyStrategy.throwError({ code: 'ESRCH' }); + + expect(function() { + spyStrategy.exec(); + }).toThrow({ code: 'ESRCH' }); + expect(originalFn).not.toHaveBeenCalled(); + }); + it('allows a fake function to be called instead', function() { var originalFn = jasmine.createSpy('original'), fakeFn = jasmine.createSpy('fake').and.returnValue(67), diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index 7e86abd6..41aa9258 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -150,10 +150,10 @@ getJasmineRequireObj().SpyStrategy = function(j$) { * @name SpyStrategy#throwError * @since 2.0.0 * @function - * @param {Error|String} something Thing to throw + * @param {Error|Object|String} something Thing to throw */ SpyStrategy.prototype.throwError = function(something) { - var error = something instanceof Error ? something : new Error(something); + var error = j$.isString_(something) ? new Error(something) : something; this.plan = function() { throw error; }; From b3ab9fad9d62ef72fa4851b690b56c06d86025c2 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Fri, 26 Jun 2020 15:14:02 -0700 Subject: [PATCH 152/201] Updated toHaveBeenCalledOnceWith for new matcher interface --- lib/jasmine-core/jasmine.js | 6 +++--- .../matchers/toHaveBeenCalledOnceWithSpec.js | 17 ++++++++--------- src/core/matchers/toHaveBeenCalledOnceWith.js | 6 +++--- 3 files changed, 14 insertions(+), 15 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 1f079a35..f618cced 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -5816,7 +5816,7 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { * @example * expect(mySpy).toHaveBeenCalledOnceWith('foo', 'bar', 2); */ - function toHaveBeenCalledOnceWith(util, customEqualityTesters) { + function toHaveBeenCalledOnceWith(util) { return { compare: function () { var args = Array.prototype.slice.call(arguments, 0), @@ -5831,7 +5831,7 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { return ' ' + j$.pp(argsForCall); }); - if (actual.calls.count() === 1 && util.contains(actual.calls.allArgs(), expectedArgs, customEqualityTesters)) { + if (actual.calls.count() === 1 && util.contains(actual.calls.allArgs(), expectedArgs)) { return { pass: true, message: 'Expected spy ' + actual.and.identity + ' to have been called 0 times, multiple times, or once, but with arguments different from:\n' @@ -5844,7 +5844,7 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { function getDiffs() { return actual.calls.allArgs().map(function (argsForCall, callIx) { var diffBuilder = new j$.DiffBuilder(); - util.equals(argsForCall, expectedArgs, customEqualityTesters, diffBuilder); + util.equals(argsForCall, expectedArgs, diffBuilder); return diffBuilder.getMessage(); }); } diff --git a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js index d5bdab43..be0e95bc 100644 --- a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js @@ -13,18 +13,17 @@ describe("toHaveBeenCalledOnceWith", function () { expect(result.message).toEqual("Expected spy called-spy to have been called 0 times, multiple times, or once, but with arguments different from:\n [ 'a', 'b' ]\nBut the actual call was:\n [ 'a', 'b' ].\n\n"); }); - it("passes through the custom equality testers", function () { - var util = jasmineUnderTest.matchersUtil; - spyOn(util, 'contains').and.returnValue(false); - - var customEqualityTesters = [function () { return true; }], - matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util, customEqualityTesters), - calledSpy = new jasmineUnderTest.Spy('called-spy'); + it("supports custom equality testers", function () { + var customEqualityTesters = [function() { return true; }], + matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: customEqualityTesters}), + matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(matchersUtil), + calledSpy = new jasmineUnderTest.Spy('called-spy'), + result; calledSpy('a', 'b'); - matcher.compare(calledSpy, 'a', 'b'); + result = matcher.compare(calledSpy, 'a', 'a'); - expect(util.contains).toHaveBeenCalledWith([['a', 'b']], ['a', 'b'], customEqualityTesters); + expect(result.pass).toBe(true); }); it("fails when the actual was never called", function () { diff --git a/src/core/matchers/toHaveBeenCalledOnceWith.js b/src/core/matchers/toHaveBeenCalledOnceWith.js index 035848b0..d7be3782 100644 --- a/src/core/matchers/toHaveBeenCalledOnceWith.js +++ b/src/core/matchers/toHaveBeenCalledOnceWith.js @@ -11,7 +11,7 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { * @example * expect(mySpy).toHaveBeenCalledOnceWith('foo', 'bar', 2); */ - function toHaveBeenCalledOnceWith(util, customEqualityTesters) { + function toHaveBeenCalledOnceWith(util) { return { compare: function () { var args = Array.prototype.slice.call(arguments, 0), @@ -26,7 +26,7 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { return ' ' + j$.pp(argsForCall); }); - if (actual.calls.count() === 1 && util.contains(actual.calls.allArgs(), expectedArgs, customEqualityTesters)) { + if (actual.calls.count() === 1 && util.contains(actual.calls.allArgs(), expectedArgs)) { return { pass: true, message: 'Expected spy ' + actual.and.identity + ' to have been called 0 times, multiple times, or once, but with arguments different from:\n' @@ -39,7 +39,7 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { function getDiffs() { return actual.calls.allArgs().map(function (argsForCall, callIx) { var diffBuilder = new j$.DiffBuilder(); - util.equals(argsForCall, expectedArgs, customEqualityTesters, diffBuilder); + util.equals(argsForCall, expectedArgs, diffBuilder); return diffBuilder.getMessage(); }); } From 11b63e4e3ed4cdd21dd091b8133ce2bbc61eb0a0 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Mon, 29 Jun 2020 14:36:00 -0700 Subject: [PATCH 153/201] Fixed references to master in docs --- .github/CONTRIBUTING.md | 4 ++-- README.md | 8 ++++---- RELEASE.md | 2 +- 3 files changed, 7 insertions(+), 7 deletions(-) diff --git a/.github/CONTRIBUTING.md b/.github/CONTRIBUTING.md index 686c71de..3a23f9a5 100644 --- a/.github/CONTRIBUTING.md +++ b/.github/CONTRIBUTING.md @@ -17,7 +17,7 @@ git clone git@github.com:yourUserName/jasmine.git # Clone your fork cd jasmine # Change directory git remote add upstream https://github.com/jasmine/jasmine.git # Assign original repository to a remote named 'upstream' git fetch upstream # Fetch changes not present in your local repository -git merge upstream/master # Sync local master with upstream repository +git merge upstream/main # Sync local main with upstream repository git checkout -b my-new-feature # Create your feature branch git commit -am 'Add some feature' # Commit your changes git push origin my-new-feature # Push to the branch @@ -121,7 +121,7 @@ The easiest way to run the tests in **Internet Explorer** is to run a VM that ha 1. Build `jasmine.js` with `npm run build` and run all specs again - this ensures that your changes self-test well 1. Revert your changes to `jasmine.js` and `jasmine-html.js` * We do this because `jasmine.js` and `jasmine-html.js` are auto-generated (as you've seen in the previous steps) and accepting multiple pull requests when this auto-generated file changes causes lots of headaches - * When we accept your pull request, we will generate these files as a separate commit and merge the entire branch into master + * When we accept your pull request, we will generate these files as a separate commit and merge the entire branch into main Note that we use Travis for Continuous Integration. We only accept green pull requests. diff --git a/README.md b/README.md index caa0533f..062885f5 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ -[](http://jasmine.github.io) +[](http://jasmine.github.io) -[![Build Status](https://travis-ci.org/jasmine/jasmine.svg?branch=master)](https://travis-ci.org/jasmine/jasmine) +[![Build Status](https://travis-ci.org/jasmine/jasmine.svg?branch=main)](https://travis-ci.org/jasmine/jasmine) [![Open Source Helpers](https://www.codetriage.com/jasmine/jasmine/badges/users.svg)](https://www.codetriage.com/jasmine/jasmine) [![FOSSA Status](https://app.fossa.io/api/projects/git%2Bgithub.com%2Fjasmine%2Fjasmine.svg?type=shield)](https://app.fossa.io/projects/git%2Bgithub.com%2Fjasmine%2Fjasmine?ref=badge_shield) @@ -15,7 +15,7 @@ Upgrading from Jasmine 2.x? Check out the [3.0 release notes](https://github.com ## Contributing -Please read the [contributors' guide](https://github.com/jasmine/jasmine/blob/master/.github/CONTRIBUTING.md). +Please read the [contributors' guide](https://github.com/jasmine/jasmine/blob/main/.github/CONTRIBUTING.md). ## Installation @@ -52,7 +52,7 @@ Add the following to your HTML file: ## Supported environments -Jasmine tests itself across many browsers (Safari, Chrome, Firefox, Microsoft Edge, and new Internet Explorer) as well as nodejs. To see the exact version tests are run against look at our [.travis.yml](https://github.com/jasmine/jasmine/blob/master/.travis.yml). +Jasmine tests itself across many browsers (Safari, Chrome, Firefox, Microsoft Edge, and new Internet Explorer) as well as nodejs. To see the exact version tests are run against look at our [.travis.yml](https://github.com/jasmine/jasmine/blob/main/.travis.yml). [![Sauce Test Status](https://saucelabs.com/browser-matrix/jasmine-js.svg)](https://saucelabs.com/u/jasmine-js) diff --git a/RELEASE.md b/RELEASE.md index 20790a52..61ffbadc 100644 --- a/RELEASE.md +++ b/RELEASE.md @@ -7,7 +7,7 @@ Follow the instructions in `CONTRIBUTING.md` during development. ### Git Rules -Please attempt to keep commits to `master` small, but cohesive. If a feature is contained in a bunch of small commits (e.g., it has several wip commits or small work), please squash them when pushing to `master`. +Please attempt to keep commits to `main` small, but cohesive. If a feature is contained in a bunch of small commits (e.g., it has several wip commits or small work), please squash them when pushing to `main`. ### Version From 8cd4873e4859e0f0177c1cbd9910e923bac60092 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Mon, 29 Jun 2020 14:37:08 -0700 Subject: [PATCH 154/201] Removed broken Sauce status image --- README.md | 2 -- 1 file changed, 2 deletions(-) diff --git a/README.md b/README.md index 062885f5..94ee7162 100644 --- a/README.md +++ b/README.md @@ -54,8 +54,6 @@ Add the following to your HTML file: Jasmine tests itself across many browsers (Safari, Chrome, Firefox, Microsoft Edge, and new Internet Explorer) as well as nodejs. To see the exact version tests are run against look at our [.travis.yml](https://github.com/jasmine/jasmine/blob/main/.travis.yml). -[![Sauce Test Status](https://saucelabs.com/browser-matrix/jasmine-js.svg)](https://saucelabs.com/u/jasmine-js) - ## Support * Search past discussions: [http://groups.google.com/group/jasmine-js](http://groups.google.com/group/jasmine-js). From fb2327736771833b089e1d00b8a96592714f3d22 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 1 Jul 2020 12:30:24 -0700 Subject: [PATCH 155/201] Removed IE from Travis build matrix We still support IE 10 and 11, but the Node selenium-webdriver has serious problems with it. Until that's fixed or worked around, IE builds won't pass. This gets us otherwise green so we can easily see if anything else is broken. --- .travis.yml | 8 -------- README.md | 15 ++++++++++++++- 2 files changed, 14 insertions(+), 9 deletions(-) diff --git a/.travis.yml b/.travis.yml index 3a2cb0db..bfeccecd 100644 --- a/.travis.yml +++ b/.travis.yml @@ -19,14 +19,6 @@ env: matrix: include: - - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=11 SAUCE_OS="Windows 8.1" - if: type != pull_request - addons: - sauce_connect: true - - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=10 SAUCE_OS="Windows 8" - if: type != pull_request - addons: - sauce_connect: true - env: JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='' SAUCE_OS="Windows 10" if: type != pull_request addons: diff --git a/README.md b/README.md index 94ee7162..e8b7fd53 100644 --- a/README.md +++ b/README.md @@ -52,7 +52,20 @@ Add the following to your HTML file: ## Supported environments -Jasmine tests itself across many browsers (Safari, Chrome, Firefox, Microsoft Edge, and new Internet Explorer) as well as nodejs. To see the exact version tests are run against look at our [.travis.yml](https://github.com/jasmine/jasmine/blob/main/.travis.yml). +Jasmine tests itself across many browsers (Safari, Chrome, Firefox, Microsoft Edge, and Internet Explorer) as well as nodejs. + +| Environment | Supported versions | +|-------------------|--------------------| +| Node | 8, 10, 12 | +| Safari | 8-13 | +| Chrome | Evergreen | +| Firefox | Evergreen, 68 | +| Edge | Evergreen | +| Internet Explorer | 10, 11 | + +For evergreen browsers, each version of Jasmine is tested against the version of the browser that is available to us +at the time of release. Other browsers, as well as older & newer versions of some supported browsers, are likely to work. +However, Jasmine isn't tested against them and they aren't actively supported. ## Support From ba2aae63bed536ed632fed8ed82cc0f31bd24104 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 1 Jul 2020 16:05:02 -0700 Subject: [PATCH 156/201] Run eslint against all files --- package.json | 8 ++------ spec/.eslintrc.js | 13 +++++++++++++ spec/core/matchers/matchersUtilSpec.js | 4 ++-- src/core/matchers/DiffBuilder.js | 2 +- 4 files changed, 18 insertions(+), 9 deletions(-) create mode 100644 spec/.eslintrc.js diff --git a/package.json b/package.json index 3632bcbe..fb1d215d 100644 --- a/package.json +++ b/package.json @@ -13,7 +13,7 @@ "bdd" ], "scripts": { - "posttest": "eslint src/**/*.js spec/**/*.js && prettier --check src/**/*.js spec/**/*.js", + "posttest": "eslint \"src/**/*.js\" \"spec/**/*.js\" && prettier --check src/**/*.js spec/**/*.js", "test": "grunt --stack execSpecsInNode", "cleanup": "prettier --write src/**/*.js spec/**/*.js", "build": "grunt buildDistribution", @@ -28,7 +28,7 @@ "devDependencies": { "acorn": "^6.0.0", "ejs": "^2.5.5", - "eslint": "^5.16.0", + "eslint": "7.3.1", "express": "^4.16.4", "fast-check": "^1.21.0", "fast-glob": "^2.2.6", @@ -67,10 +67,6 @@ } ], "block-spacing": "error", - "comma-dangle": [ - "error", - "never" - ], "func-call-spacing": [ "error", "never" diff --git a/spec/.eslintrc.js b/spec/.eslintrc.js new file mode 100644 index 00000000..969a4efd --- /dev/null +++ b/spec/.eslintrc.js @@ -0,0 +1,13 @@ +module.exports = { + rules: { + // Relax rules for now to allow for the quirks of the test suite + // TODO: We should probably remove these & fix the resulting errors + "quotes": "off", + "semi": "off", + "key-spacing": "off", + "space-before-blocks": "off", + "no-unused-vars": "off", + "no-trailing-spaces": "off", + "block-spacing": "off", + } +} diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index 81874302..10bd0ec0 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -821,7 +821,7 @@ describe("matchersUtil", function() { expect(diffBuilder.setRoots).toHaveBeenCalledWith(actual, expected); expect(diffBuilder.withPath).toHaveBeenCalledWith('x', jasmine.any(Function)); - expect(diffBuilder.recordMismatch). toHaveBeenCalledWith(); + expect(diffBuilder.recordMismatch).toHaveBeenCalledWith(); }); it("records both objects when the tester does not implement valuesForDiff", function() { @@ -836,7 +836,7 @@ describe("matchersUtil", function() { expect(diffBuilder.setRoots).toHaveBeenCalledWith(actual, expected); expect(diffBuilder.withPath).toHaveBeenCalledWith('x', jasmine.any(Function)); - expect(diffBuilder.recordMismatch). toHaveBeenCalledWith(); + expect(diffBuilder.recordMismatch).toHaveBeenCalledWith(); }); }); diff --git a/src/core/matchers/DiffBuilder.js b/src/core/matchers/DiffBuilder.js index 4e43aeaa..83333d8a 100644 --- a/src/core/matchers/DiffBuilder.js +++ b/src/core/matchers/DiffBuilder.js @@ -72,7 +72,7 @@ getJasmineRequireObj().DiffBuilder = function (j$) { }; function dereferencePath(objectPath, actual, expected, pp) { - var i, asymmetricResult + var i, asymmetricResult; for (i = 0; i < objectPath.components.length; i++) { actual = actual[objectPath.components[i]]; From 4e2f703615eacecf5054dd2b1f20a9da69f14f38 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 1 Jul 2020 17:28:45 -0700 Subject: [PATCH 157/201] Check for syntax and standard library objects that don't work in IE --- package.json | 17 +++- spec/.eslintrc.js | 4 + spec/core/AsyncExpectationSpec.js | 1 + spec/core/PrettyPrintSpec.js | 8 +- spec/core/UtilSpec.js | 2 +- spec/core/asymmetric_equality/AnySpec.js | 12 +-- spec/core/asymmetric_equality/AnythingSpec.js | 8 +- spec/core/asymmetric_equality/EmptySpec.js | 12 +-- .../asymmetric_equality/MapContainingSpec.js | 1 + spec/core/asymmetric_equality/NotEmptySpec.js | 12 +-- .../asymmetric_equality/SetContainingSpec.js | 1 + spec/core/baseSpec.js | 2 +- .../integration/CustomAsyncMatchersSpec.js | 1 + spec/core/integration/EnvSpec.js | 10 +-- spec/core/integration/MatchersSpec.js | 26 +++--- spec/core/matchers/async/toBePendingSpec.js | 1 + spec/core/matchers/async/toBeRejectedSpec.js | 1 + .../async/toBeRejectedWithErrorSpec.js | 1 + .../matchers/async/toBeRejectedWithSpec.js | 1 + spec/core/matchers/async/toBeResolvedSpec.js | 1 + .../core/matchers/async/toBeResolvedToSpec.js | 1 + spec/core/matchers/matchersUtilSpec.js | 69 ++++++++-------- spec/core/matchers/toEqualSpec.js | 80 +++++++++---------- spec/core/matchers/toHaveSizeSpec.js | 1 + spec/helpers/checkForMap.js | 1 + spec/helpers/checkForSet.js | 1 + spec/helpers/checkForSymbol.js | 1 + spec/helpers/checkForTypedArrays.js | 1 + .../asymmetricEqualityTesterArgCompatShim.js | 2 +- src/core/matchers/async/toBePending.js | 3 +- src/core/matchers/toHaveSize.js | 2 +- 31 files changed, 159 insertions(+), 125 deletions(-) diff --git a/package.json b/package.json index fb1d215d..a7d89f70 100644 --- a/package.json +++ b/package.json @@ -29,6 +29,7 @@ "acorn": "^6.0.0", "ejs": "^2.5.5", "eslint": "7.3.1", + "eslint-plugin-compat": "^3.8.0", "express": "^4.16.4", "fast-check": "^1.21.0", "fast-glob": "^2.2.6", @@ -52,6 +53,12 @@ "singleQuote": true }, "eslintConfig": { + "extends": [ + "plugin:compat/recommended" + ], + "parserOptions": { + "ecmaVersion": 5 + }, "rules": { "quotes": [ "error", @@ -81,5 +88,13 @@ ], "space-before-blocks": "error" } - } + }, + "browserslist": [ + "Safari >= 8", + "last 2 Chrome versions", + "last 2 Firefox versions", + "Firefox 68", + "last 2 Edge versions", + "IE >= 10" + ] } diff --git a/spec/.eslintrc.js b/spec/.eslintrc.js index 969a4efd..bfbec213 100644 --- a/spec/.eslintrc.js +++ b/spec/.eslintrc.js @@ -1,4 +1,8 @@ module.exports = { + "ignorePatterns": [ + "support/ci.js", + "support/jasmine-browser.js" + ], rules: { // Relax rules for now to allow for the quirks of the test suite // TODO: We should probably remove these & fix the resulting errors diff --git a/spec/core/AsyncExpectationSpec.js b/spec/core/AsyncExpectationSpec.js index 40f63731..94e2438c 100644 --- a/spec/core/AsyncExpectationSpec.js +++ b/spec/core/AsyncExpectationSpec.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ describe('AsyncExpectation', function() { beforeEach(function() { jasmineUnderTest.Expectation.addAsyncCoreMatchers( diff --git a/spec/core/PrettyPrintSpec.js b/spec/core/PrettyPrintSpec.js index 6c43cbd4..de6a11d6 100644 --- a/spec/core/PrettyPrintSpec.js +++ b/spec/core/PrettyPrintSpec.js @@ -19,7 +19,7 @@ describe('PrettyPrinter', function() { describe('stringify sets', function() { it('should stringify sets properly', function() { jasmine.getEnv().requireFunctioningSets(); - var set = new Set(); + var set = new Set(); // eslint-disable-line compat/compat set.add(1); set.add(2); var pp = jasmineUnderTest.makePrettyPrinter(); @@ -32,7 +32,7 @@ describe('PrettyPrinter', function() { try { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = 2; - var set = new Set(); + var set = new Set(); // eslint-disable-line compat/compat set.add('a'); set.add('b'); set.add('c'); @@ -47,7 +47,7 @@ describe('PrettyPrinter', function() { describe('stringify maps', function() { it('should stringify maps properly', function() { jasmine.getEnv().requireFunctioningMaps(); - var map = new Map(); + var map = new Map(); // eslint-disable-line compat/compat map.set(1, 2); var pp = jasmineUnderTest.makePrettyPrinter(); expect(pp(map)).toEqual('Map( [ 1, 2 ] )'); @@ -59,7 +59,7 @@ describe('PrettyPrinter', function() { try { jasmineUnderTest.MAX_PRETTY_PRINT_ARRAY_LENGTH = 2; - var map = new Map(); + var map = new Map(); // eslint-disable-line compat/compat map.set('a', 1); map.set('b', 2); map.set('c', 3); diff --git a/spec/core/UtilSpec.js b/spec/core/UtilSpec.js index 759ef8ce..8e05c6ab 100644 --- a/spec/core/UtilSpec.js +++ b/spec/core/UtilSpec.js @@ -40,7 +40,7 @@ describe('jasmineUnderTest.util', function() { beforeEach(function() { jasmine.getEnv().requirePromises(); - mockNativePromise = new Promise(function(res, rej) {}); + mockNativePromise = new Promise(function(res, rej) {}); // eslint-disable-line compat/compat mockPromiseLikeObject = new mockPromiseLike(); }); diff --git a/spec/core/asymmetric_equality/AnySpec.js b/spec/core/asymmetric_equality/AnySpec.js index 1739ae6f..8e28c306 100644 --- a/spec/core/asymmetric_equality/AnySpec.js +++ b/spec/core/asymmetric_equality/AnySpec.js @@ -34,7 +34,7 @@ describe("Any", function() { var any = new jasmineUnderTest.Any(Map); - expect(any.asymmetricMatch(new Map())).toBe(true); + expect(any.asymmetricMatch(new Map())).toBe(true); // eslint-disable-line compat/compat }); it("matches a Set", function() { @@ -42,23 +42,23 @@ describe("Any", function() { var any = new jasmineUnderTest.Any(Set); - expect(any.asymmetricMatch(new Set())).toBe(true); + expect(any.asymmetricMatch(new Set())).toBe(true); // eslint-disable-line compat/compat }); it("matches a TypedArray", function() { jasmine.getEnv().requireFunctioningTypedArrays(); - var any = new jasmineUnderTest.Any(Uint32Array); + var any = new jasmineUnderTest.Any(Uint32Array); // eslint-disable-line compat/compat - expect(any.asymmetricMatch(new Uint32Array([]))).toBe(true); + expect(any.asymmetricMatch(new Uint32Array([]))).toBe(true); // eslint-disable-line compat/compat }); it("matches a Symbol", function() { jasmine.getEnv().requireFunctioningSymbols(); - var any = new jasmineUnderTest.Any(Symbol); + var any = new jasmineUnderTest.Any(Symbol); // eslint-disable-line compat/compat - expect(any.asymmetricMatch(Symbol())).toBe(true); + expect(any.asymmetricMatch(Symbol())).toBe(true); // eslint-disable-line compat/compat }); it("matches another constructed object", function() { diff --git a/spec/core/asymmetric_equality/AnythingSpec.js b/spec/core/asymmetric_equality/AnythingSpec.js index 216757eb..4e251b91 100644 --- a/spec/core/asymmetric_equality/AnythingSpec.js +++ b/spec/core/asymmetric_equality/AnythingSpec.js @@ -28,7 +28,7 @@ describe("Anything", function() { var anything = new jasmineUnderTest.Anything(); - expect(anything.asymmetricMatch(new Map())).toBe(true); + expect(anything.asymmetricMatch(new Map())).toBe(true); // eslint-disable-line compat/compat }); it("matches a Set", function() { @@ -36,7 +36,7 @@ describe("Anything", function() { var anything = new jasmineUnderTest.Anything(); - expect(anything.asymmetricMatch(new Set())).toBe(true); + expect(anything.asymmetricMatch(new Set())).toBe(true); // eslint-disable-line compat/compat }); it("matches a TypedArray", function() { @@ -44,7 +44,7 @@ describe("Anything", function() { var anything = new jasmineUnderTest.Anything(); - expect(anything.asymmetricMatch(new Uint32Array([]))).toBe(true); + expect(anything.asymmetricMatch(new Uint32Array([]))).toBe(true); // eslint-disable-line compat/compat }); it("matches a Symbol", function() { @@ -52,7 +52,7 @@ describe("Anything", function() { var anything = new jasmineUnderTest.Anything(); - expect(anything.asymmetricMatch(Symbol())).toBe(true); + expect(anything.asymmetricMatch(Symbol())).toBe(true); // eslint-disable-line compat/compat }); it("doesn't match undefined", function() { diff --git a/spec/core/asymmetric_equality/EmptySpec.js b/spec/core/asymmetric_equality/EmptySpec.js index 902b5001..48271ce5 100644 --- a/spec/core/asymmetric_equality/EmptySpec.js +++ b/spec/core/asymmetric_equality/EmptySpec.js @@ -24,20 +24,20 @@ describe("Empty", function () { it("matches an empty map", function () { jasmine.getEnv().requireFunctioningMaps(); var empty = new jasmineUnderTest.Empty(); - var fullMap = new Map(); + var fullMap = new Map(); // eslint-disable-line compat/compat fullMap.set('thing', 2); - expect(empty.asymmetricMatch(new Map())).toBe(true); + expect(empty.asymmetricMatch(new Map())).toBe(true); // eslint-disable-line compat/compat expect(empty.asymmetricMatch(fullMap)).toBe(false); }); it("matches an empty set", function () { jasmine.getEnv().requireFunctioningSets(); var empty = new jasmineUnderTest.Empty(); - var fullSet = new Set(); + var fullSet = new Set(); // eslint-disable-line compat/compat fullSet.add(3); - expect(empty.asymmetricMatch(new Set())).toBe(true); + expect(empty.asymmetricMatch(new Set())).toBe(true); // eslint-disable-line compat/compat expect(empty.asymmetricMatch(fullSet)).toBe(false); }); @@ -45,7 +45,7 @@ describe("Empty", function () { jasmine.getEnv().requireFunctioningTypedArrays(); var empty = new jasmineUnderTest.Empty(); - expect(empty.asymmetricMatch(new Int16Array())).toBe(true); - expect(empty.asymmetricMatch(new Int16Array([1,2]))).toBe(false); + expect(empty.asymmetricMatch(new Int16Array())).toBe(true); // eslint-disable-line compat/compat + expect(empty.asymmetricMatch(new Int16Array([1,2]))).toBe(false); // eslint-disable-line compat/compat }); }); diff --git a/spec/core/asymmetric_equality/MapContainingSpec.js b/spec/core/asymmetric_equality/MapContainingSpec.js index c9ea83a6..dc89218d 100644 --- a/spec/core/asymmetric_equality/MapContainingSpec.js +++ b/spec/core/asymmetric_equality/MapContainingSpec.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ describe('MapContaining', function() { function MapI(iterable) { // for IE11 var map = new Map(); diff --git a/spec/core/asymmetric_equality/NotEmptySpec.js b/spec/core/asymmetric_equality/NotEmptySpec.js index 04c05966..d00ee013 100644 --- a/spec/core/asymmetric_equality/NotEmptySpec.js +++ b/spec/core/asymmetric_equality/NotEmptySpec.js @@ -24,9 +24,9 @@ describe("NotEmpty", function () { it("matches a non empty map", function () { jasmine.getEnv().requireFunctioningMaps(); var notEmpty = new jasmineUnderTest.NotEmpty(); - var fullMap = new Map(); + var fullMap = new Map(); // eslint-disable-line compat/compat fullMap.set('one', 1); - var emptyMap = new Map(); + var emptyMap = new Map(); // eslint-disable-line compat/compat expect(notEmpty.asymmetricMatch(fullMap)).toBe(true); expect(notEmpty.asymmetricMatch(emptyMap)).toBe(false); @@ -35,9 +35,9 @@ describe("NotEmpty", function () { it("matches a non empty set", function () { jasmine.getEnv().requireFunctioningSets(); var notEmpty = new jasmineUnderTest.NotEmpty(); - var filledSet = new Set(); + var filledSet = new Set(); // eslint-disable-line compat/compat filledSet.add(1); - var emptySet = new Set(); + var emptySet = new Set(); // eslint-disable-line compat/compat expect(notEmpty.asymmetricMatch(filledSet)).toBe(true); expect(notEmpty.asymmetricMatch(emptySet)).toBe(false); @@ -47,7 +47,7 @@ describe("NotEmpty", function () { jasmine.getEnv().requireFunctioningTypedArrays(); var notEmpty = new jasmineUnderTest.NotEmpty(); - expect(notEmpty.asymmetricMatch(new Int16Array([1,2,3]))).toBe(true); - expect(notEmpty.asymmetricMatch(new Int16Array())).toBe(false); + expect(notEmpty.asymmetricMatch(new Int16Array([1,2,3]))).toBe(true); // eslint-disable-line compat/compat + expect(notEmpty.asymmetricMatch(new Int16Array())).toBe(false); // eslint-disable-line compat/compat }); }); diff --git a/spec/core/asymmetric_equality/SetContainingSpec.js b/spec/core/asymmetric_equality/SetContainingSpec.js index 50ee9d5b..3f7b1b16 100644 --- a/spec/core/asymmetric_equality/SetContainingSpec.js +++ b/spec/core/asymmetric_equality/SetContainingSpec.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ describe('SetContaining', function() { function SetI(iterable) { // for IE11 var set = new Set(); diff --git a/spec/core/baseSpec.js b/spec/core/baseSpec.js index b85721b9..fbdf9d9d 100644 --- a/spec/core/baseSpec.js +++ b/spec/core/baseSpec.js @@ -55,7 +55,7 @@ describe('base helpers', function() { describe('isSet', function() { it('returns true when the object is a Set', function() { jasmine.getEnv().requireFunctioningSets(); - expect(jasmineUnderTest.isSet(new Set())).toBe(true); + expect(jasmineUnderTest.isSet(new Set())).toBe(true); // eslint-disable-line compat/compat }); it('returns false when the object is not a Set', function() { diff --git a/spec/core/integration/CustomAsyncMatchersSpec.js b/spec/core/integration/CustomAsyncMatchersSpec.js index e1a8286c..1b60bb45 100644 --- a/spec/core/integration/CustomAsyncMatchersSpec.js +++ b/spec/core/integration/CustomAsyncMatchersSpec.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ describe('Custom Async Matchers (Integration)', function() { var env; diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index c811c9bf..090bb54c 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -2581,7 +2581,7 @@ describe("Env integration", function() { function fail(innerDone) { var resolve; - var p = new Promise(function(res, rej) { resolve = res }); + var p = new Promise(function(res, rej) { resolve = res }); // eslint-disable-line compat/compat env.expectAsync(p).toBeRejected().then(innerDone); resolve(); } @@ -2613,7 +2613,7 @@ describe("Env integration", function() { env.it('has an async failure', function() { env.addCustomEqualityTester(function() { return true; }); - var p = Promise.resolve('something'); + var p = Promise.resolve('something'); // eslint-disable-line compat/compat return env.expectAsync(p).toBeResolvedTo('something else'); }); @@ -2639,7 +2639,7 @@ describe("Env integration", function() { env.it('has an async failure', function() { env.addCustomEqualityTester(function() { return true; }); - var p = Promise.resolve(); + var p = Promise.resolve(); // eslint-disable-line compat/compat return env.expectAsync(p).toBeRejected(); }); @@ -2650,7 +2650,7 @@ describe("Env integration", function() { jasmine.getEnv().requirePromises(); var resolve, - promise = new Promise(function(res) { resolve = res; }); + promise = new Promise(function(res) { resolve = res; }); // eslint-disable-line compat/compat env.describe('a suite', function() { env.it('does not wait', function() { @@ -2698,7 +2698,7 @@ describe("Env integration", function() { jasmine.getEnv().requirePromises(); var resolve, - promise = new Promise(function(res) { resolve = res; }); + promise = new Promise(function(res) { resolve = res; }); // eslint-disable-line compat/compat env.describe('a suite', function() { env.afterAll(function() { diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js index 5e253e08..92b7307f 100644 --- a/spec/core/integration/MatchersSpec.js +++ b/spec/core/integration/MatchersSpec.js @@ -335,11 +335,11 @@ describe('Matchers (Integration)', function() { describe('toBeResolved', function() { verifyPassesAsync(function(env) { - return env.expectAsync(Promise.resolve()).toBeResolved(); + return env.expectAsync(Promise.resolve()).toBeResolved(); // eslint-disable-line compat/compat }); verifyFailsAsync(function(env) { - return env.expectAsync(Promise.reject()).toBeResolved(); + return env.expectAsync(Promise.reject()).toBeResolved(); // eslint-disable-line compat/compat }); }); @@ -348,11 +348,11 @@ describe('Matchers (Integration)', function() { env.addCustomEqualityTester(function(a, b) { return a.toString() === b.toString(); }); - return env.expectAsync(Promise.resolve('5')).toBeResolvedTo(5); + return env.expectAsync(Promise.resolve('5')).toBeResolvedTo(5); // eslint-disable-line compat/compat }); verifyFailsAsync(function(env) { - return env.expectAsync(Promise.resolve('foo')).toBeResolvedTo('bar'); + return env.expectAsync(Promise.resolve('foo')).toBeResolvedTo('bar'); // eslint-disable-line compat/compat }); verifyFailsWithCustomObjectFormattersAsync({ @@ -360,7 +360,7 @@ describe('Matchers (Integration)', function() { return '|' + val + '|'; }, expectations: function(env) { - return env.expectAsync(Promise.resolve('x')).toBeResolvedTo('y'); + return env.expectAsync(Promise.resolve('x')).toBeResolvedTo('y'); // eslint-disable-line compat/compat }, expectedMessage: 'Expected a promise to be resolved to |y| ' + 'but it was resolved to |x|.' @@ -369,11 +369,11 @@ describe('Matchers (Integration)', function() { describe('toBeRejected', function() { verifyPassesAsync(function(env) { - return env.expectAsync(Promise.reject('nope')).toBeRejected(); + return env.expectAsync(Promise.reject('nope')).toBeRejected(); // eslint-disable-line compat/compat }); verifyFailsAsync(function(env) { - return env.expectAsync(Promise.resolve()).toBeRejected(); + return env.expectAsync(Promise.resolve()).toBeRejected(); // eslint-disable-line compat/compat }); }); @@ -382,11 +382,11 @@ describe('Matchers (Integration)', function() { env.addCustomEqualityTester(function(a, b) { return a.toString() === b.toString(); }); - return env.expectAsync(Promise.reject('5')).toBeRejectedWith(5); + return env.expectAsync(Promise.reject('5')).toBeRejectedWith(5); // eslint-disable-line compat/compat }); verifyFailsAsync(function(env) { - return env.expectAsync(Promise.resolve()).toBeRejectedWith('nope'); + return env.expectAsync(Promise.resolve()).toBeRejectedWith('nope'); // eslint-disable-line compat/compat }); verifyFailsWithCustomObjectFormattersAsync({ @@ -394,7 +394,7 @@ describe('Matchers (Integration)', function() { return '|' + val + '|'; }, expectations: function(env) { - return env.expectAsync(Promise.reject('x')).toBeRejectedWith('y'); + return env.expectAsync(Promise.reject('x')).toBeRejectedWith('y'); // eslint-disable-line compat/compat }, expectedMessage: 'Expected a promise to be rejected with |y| ' + 'but it was rejected with |x|.' @@ -403,11 +403,11 @@ describe('Matchers (Integration)', function() { describe('toBeRejectedWithError', function() { verifyPassesAsync(function(env) { - return env.expectAsync(Promise.reject(new Error())).toBeRejectedWithError(Error); + return env.expectAsync(Promise.reject(new Error())).toBeRejectedWithError(Error); // eslint-disable-line compat/compat }); verifyFailsAsync(function(env) { - return env.expectAsync(Promise.resolve()).toBeRejectedWithError(Error); + return env.expectAsync(Promise.resolve()).toBeRejectedWithError(Error); // eslint-disable-line compat/compat }); verifyFailsWithCustomObjectFormattersAsync({ @@ -415,7 +415,7 @@ describe('Matchers (Integration)', function() { return '|' + val + '|'; }, expectations: function(env) { - return env.expectAsync(Promise.reject('foo')).toBeRejectedWithError('foo'); + return env.expectAsync(Promise.reject('foo')).toBeRejectedWithError('foo'); // eslint-disable-line compat/compat }, expectedMessage: 'Expected a promise to be rejected with Error: |foo| ' + 'but it was rejected with |foo|.' diff --git a/spec/core/matchers/async/toBePendingSpec.js b/spec/core/matchers/async/toBePendingSpec.js index 318e22b7..285414f1 100644 --- a/spec/core/matchers/async/toBePendingSpec.js +++ b/spec/core/matchers/async/toBePendingSpec.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ describe('toBePending', function() { it('passes if the actual promise is pending', function() { jasmine.getEnv().requirePromises(); diff --git a/spec/core/matchers/async/toBeRejectedSpec.js b/spec/core/matchers/async/toBeRejectedSpec.js index 61bd2a5a..6ecf9ebc 100644 --- a/spec/core/matchers/async/toBeRejectedSpec.js +++ b/spec/core/matchers/async/toBeRejectedSpec.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ describe('toBeRejected', function() { it('passes if the actual is rejected', function() { jasmine.getEnv().requirePromises(); diff --git a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js index 71c53d55..d09a05fd 100644 --- a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ describe('#toBeRejectedWithError', function () { it('passes when Error type matches', function () { jasmine.getEnv().requirePromises(); diff --git a/spec/core/matchers/async/toBeRejectedWithSpec.js b/spec/core/matchers/async/toBeRejectedWithSpec.js index 2c02a03a..69003c59 100644 --- a/spec/core/matchers/async/toBeRejectedWithSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithSpec.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ describe('#toBeRejectedWith', function () { it('should return true if the promise is rejected with the expected value', function () { jasmine.getEnv().requirePromises(); diff --git a/spec/core/matchers/async/toBeResolvedSpec.js b/spec/core/matchers/async/toBeResolvedSpec.js index a6ab25ba..8dbff1c9 100644 --- a/spec/core/matchers/async/toBeResolvedSpec.js +++ b/spec/core/matchers/async/toBeResolvedSpec.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ describe('toBeResolved', function() { it('passes if the actual is resolved', function() { jasmine.getEnv().requirePromises(); diff --git a/spec/core/matchers/async/toBeResolvedToSpec.js b/spec/core/matchers/async/toBeResolvedToSpec.js index b721c89e..ee57abe1 100644 --- a/spec/core/matchers/async/toBeResolvedToSpec.js +++ b/spec/core/matchers/async/toBeResolvedToSpec.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ describe('#toBeResolvedTo', function() { it('passes if the promise is resolved to the expected value', function() { jasmine.getEnv().requirePromises(); diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index 10bd0ec0..e3ee9e8c 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -282,8 +282,8 @@ describe("matchersUtil", function() { it("passes for equivalent Promises (GitHub issue #1314)", function() { if (typeof Promise === 'undefined') { return; } - var p1 = new Promise(function () {}), - p2 = new Promise(function () {}), + var p1 = new Promise(function () {}), // eslint-disable-line compat/compat + p2 = new Promise(function () {}), // eslint-disable-line compat/compat matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(p1, p1)).toBe(true); @@ -418,10 +418,10 @@ describe("matchersUtil", function() { jasmine.getEnv().requireFunctioningMaps(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var obj = new Map(); + var obj = new Map(); // eslint-disable-line compat/compat obj.set(1, 2); obj.set('foo', 'bar'); - var containing = new jasmineUnderTest.MapContaining(new Map()); + var containing = new jasmineUnderTest.MapContaining(new Map()); // eslint-disable-line compat/compat containing.sample.set('foo', 'bar'); expect(matchersUtil.equals(obj, containing)).toBe(true); @@ -432,10 +432,10 @@ describe("matchersUtil", function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var obj = new Set(); + var obj = new Set(); // eslint-disable-line compat/compat obj.add(1); obj.add('foo'); - var containing = new jasmineUnderTest.SetContaining(new Set()); + var containing = new jasmineUnderTest.SetContaining(new Set()); // eslint-disable-line compat/compat containing.sample.add(1); expect(matchersUtil.equals(obj, containing)).toBe(true); @@ -603,17 +603,17 @@ describe("matchersUtil", function() { it("passes when comparing two empty sets", function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals(new Set(), new Set())).toBe(true); + expect(matchersUtil.equals(new Set(), new Set())).toBe(true); // eslint-disable-line compat/compat }); it("passes when comparing identical sets", function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var setA = new Set(); + var setA = new Set(); // eslint-disable-line compat/compat setA.add(6); setA.add(5); - var setB = new Set(); + var setB = new Set(); // eslint-disable-line compat/compat setB.add(6); setB.add(5); @@ -624,10 +624,10 @@ describe("matchersUtil", function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var setA = new Set(); + var setA = new Set(); // eslint-disable-line compat/compat setA.add(3); setA.add(6); - var setB = new Set(); + var setB = new Set(); // eslint-disable-line compat/compat setB.add(6); setB.add(3); @@ -638,24 +638,23 @@ describe("matchersUtil", function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var setA1 = new Set(); + var setA1 = new Set(); // eslint-disable-line compat/compat setA1.add(['a',3]); setA1.add([6,1]); - var setA2 = new Set(); + var setA2 = new Set(); // eslint-disable-line compat/compat setA1.add(['y',3]); setA1.add([6,1]); - var setA = new Set(); + var setA = new Set(); // eslint-disable-line compat/compat setA.add(setA1); setA.add(setA2); - - var setB1 = new Set(); + var setB1 = new Set(); // eslint-disable-line compat/compat setB1.add([6,1]); setB1.add(['a',3]); - var setB2 = new Set(); + var setB2 = new Set(); // eslint-disable-line compat/compat setB1.add([6,1]); setB1.add(['y',3]); - var setB = new Set(); + var setB = new Set(); // eslint-disable-line compat/compat setB.add(setB1); setB.add(setB2); @@ -666,10 +665,10 @@ describe("matchersUtil", function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var setA = new Set(); + var setA = new Set(); // eslint-disable-line compat/compat setA.add([[1,2], [3,4]]); setA.add([[5,6], [7,8]]); - var setB = new Set(); + var setB = new Set(); // eslint-disable-line compat/compat setB.add([[5,6], [7,8]]); setB.add([[1,2], [3,4]]); @@ -679,11 +678,11 @@ describe("matchersUtil", function() { it("fails for sets with different elements", function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var setA = new Set(); + var setA = new Set(); // eslint-disable-line compat/compat setA.add(6); setA.add(3); setA.add(5); - var setB = new Set(); + var setB = new Set(); // eslint-disable-line compat/compat setB.add(6); setB.add(4); setB.add(5); @@ -694,10 +693,10 @@ describe("matchersUtil", function() { it("fails for sets of different size", function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var setA = new Set(); + var setA = new Set(); // eslint-disable-line compat/compat setA.add(6); setA.add(3); - var setB = new Set(); + var setB = new Set(); // eslint-disable-line compat/compat setB.add(6); setB.add(4); setB.add(5); @@ -708,15 +707,15 @@ describe("matchersUtil", function() { it("passes when comparing two empty maps", function() { jasmine.getEnv().requireFunctioningMaps(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals(new Map(), new Map())).toBe(true); + expect(matchersUtil.equals(new Map(), new Map())).toBe(true); // eslint-disable-line compat/compat }); it("passes when comparing identical maps", function() { jasmine.getEnv().requireFunctioningMaps(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var mapA = new Map(); + var mapA = new Map(); // eslint-disable-line compat/compat mapA.set(6, 5); - var mapB = new Map(); + var mapB = new Map(); // eslint-disable-line compat/compat mapB.set(6, 5); expect(matchersUtil.equals(mapA, mapB)).toBe(true); }); @@ -724,10 +723,10 @@ describe("matchersUtil", function() { it("passes when comparing identical maps with different insertion order", function() { jasmine.getEnv().requireFunctioningMaps(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var mapA = new Map(); + var mapA = new Map(); // eslint-disable-line compat/compat mapA.set("a", 3); mapA.set(6, 1); - var mapB = new Map(); + var mapB = new Map(); // eslint-disable-line compat/compat mapB.set(6, 1); mapB.set("a", 3); expect(matchersUtil.equals(mapA, mapB)).toBe(true); @@ -736,10 +735,10 @@ describe("matchersUtil", function() { it("fails for maps with different elements", function() { jasmine.getEnv().requireFunctioningMaps(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var mapA = new Map(); + var mapA = new Map(); // eslint-disable-line compat/compat mapA.set(6, 3); mapA.set(5, 1); - var mapB = new Map(); + var mapB = new Map(); // eslint-disable-line compat/compat mapB.set(6, 4); mapB.set(5, 1); @@ -749,9 +748,9 @@ describe("matchersUtil", function() { it("fails for maps of different size", function() { jasmine.getEnv().requireFunctioningMaps(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var mapA = new Map(); + var mapA = new Map(); // eslint-disable-line compat/compat mapA.set(6, 3); - var mapB = new Map(); + var mapB = new Map(); // eslint-disable-line compat/compat mapB.set(6, 4); mapB.set(5, 1); expect(matchersUtil.equals(mapA, mapB)).toBe(false); @@ -937,7 +936,7 @@ describe("matchersUtil", function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); var setItem = {'foo': 'bar'}; - var set = new Set(); + var set = new Set(); // eslint-disable-line compat/compat set.add(setItem); expect(matchersUtil.contains(set, setItem)).toBe(true); @@ -948,7 +947,7 @@ describe("matchersUtil", function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var set = new Set(); + var set = new Set(); // eslint-disable-line compat/compat set.add({'foo': 'bar'}); expect(matchersUtil.contains(set, {'foo': 'bar'})).toBe(false); diff --git a/spec/core/matchers/toEqualSpec.js b/spec/core/matchers/toEqualSpec.js index 3a249364..081329d9 100644 --- a/spec/core/matchers/toEqualSpec.js +++ b/spec/core/matchers/toEqualSpec.js @@ -261,8 +261,8 @@ describe("toEqual", function() { it("reports mismatches between arrays of different types", function() { jasmine.getEnv().requireFunctioningTypedArrays(); - var actual = new Uint32Array([1, 2, 3]), - expected = new Uint16Array([1, 2, 3]), + var actual = new Uint32Array([1, 2, 3]), // eslint-disable-line compat/compat + expected = new Uint16Array([1, 2, 3]), // eslint-disable-line compat/compat message = "Expected Uint32Array [ 1, 2, 3 ] to equal Uint16Array [ 1, 2, 3 ]."; expect(compareEquals(actual, expected).message).toEqual(message); @@ -448,9 +448,9 @@ describe("toEqual", function() { it("reports mismatches between Sets", function() { jasmine.getEnv().requireFunctioningSets(); - var actual = new Set(); + var actual = new Set(); // eslint-disable-line compat/compat actual.add(1); - var expected = new Set(); + var expected = new Set(); // eslint-disable-line compat/compat expected.add(2); var message = 'Expected Set( 1 ) to equal Set( 2 ).'; @@ -460,9 +460,9 @@ describe("toEqual", function() { it("reports deep mismatches within Sets", function() { jasmine.getEnv().requireFunctioningSets(); - var actual = new Set(); + var actual = new Set(); // eslint-disable-line compat/compat actual.add({x: 1}); - var expected = new Set(); + var expected = new Set(); // eslint-disable-line compat/compat expected.add({x: 2}); var message = 'Expected Set( Object({ x: 1 }) ) to equal Set( Object({ x: 2 }) ).'; @@ -472,9 +472,9 @@ describe("toEqual", function() { it("reports mismatches between Sets nested in objects", function() { jasmine.getEnv().requireFunctioningSets(); - var actualSet = new Set(); + var actualSet = new Set(); // eslint-disable-line compat/compat actualSet.add(1); - var expectedSet = new Set(); + var expectedSet = new Set(); // eslint-disable-line compat/compat expectedSet.add(2); var actual = { sets: [actualSet] }; @@ -487,10 +487,10 @@ describe("toEqual", function() { it("reports mismatches between Sets of different lengths", function() { jasmine.getEnv().requireFunctioningSets(); - var actual = new Set(); + var actual = new Set(); // eslint-disable-line compat/compat actual.add(1); actual.add(2); - var expected = new Set(); + var expected = new Set(); // eslint-disable-line compat/compat expected.add(2); var message = 'Expected Set( 1, 2 ) to equal Set( 2 ).'; @@ -501,10 +501,10 @@ describe("toEqual", function() { jasmine.getEnv().requireFunctioningSets(); // Use 'duplicate' object in actual so sizes match - var actual = new Set(); + var actual = new Set(); // eslint-disable-line compat/compat actual.add({x: 1}); actual.add({x: 1}); - var expected = new Set(); + var expected = new Set(); // eslint-disable-line compat/compat expected.add({x: 1}); expected.add({x: 2}); var message = 'Expected Set( Object({ x: 1 }), Object({ x: 1 }) ) to equal Set( Object({ x: 1 }), Object({ x: 2 }) ).'; @@ -516,10 +516,10 @@ describe("toEqual", function() { jasmine.getEnv().requireFunctioningSets(); // Use 'duplicate' object in expected so sizes match - var actual = new Set(); + var actual = new Set(); // eslint-disable-line compat/compat actual.add({x: 1}); actual.add({x: 2}); - var expected = new Set(); + var expected = new Set(); // eslint-disable-line compat/compat expected.add({x: 1}); expected.add({x: 1}); var message = 'Expected Set( Object({ x: 1 }), Object({ x: 2 }) ) to equal Set( Object({ x: 1 }), Object({ x: 1 }) ).'; @@ -533,9 +533,9 @@ describe("toEqual", function() { jasmine.getEnv().requireFunctioningMaps(); // values are the same but with different object identity - var actual = new Map(); + var actual = new Map(); // eslint-disable-line compat/compat actual.set('a',{x:1}); - var expected = new Map(); + var expected = new Map(); // eslint-disable-line compat/compat expected.set('a',{x:1}); expect(compareEquals(actual, expected).pass).toBe(true); @@ -544,9 +544,9 @@ describe("toEqual", function() { it("reports deep mismatches within Maps", function() { jasmine.getEnv().requireFunctioningMaps(); - var actual = new Map(); + var actual = new Map(); // eslint-disable-line compat/compat actual.set('a',{x:1}); - var expected = new Map(); + var expected = new Map(); // eslint-disable-line compat/compat expected.set('a',{x:2}); var message = "Expected Map( [ 'a', Object({ x: 1 }) ] ) to equal Map( [ 'a', Object({ x: 2 }) ] )."; @@ -556,9 +556,9 @@ describe("toEqual", function() { it("reports mismatches between Maps nested in objects", function() { jasmine.getEnv().requireFunctioningMaps(); - var actual = {Maps:[new Map()]}; + var actual = {Maps:[new Map()]}; // eslint-disable-line compat/compat actual.Maps[0].set('a',1); - var expected = {Maps:[new Map()]}; + var expected = {Maps:[new Map()]}; // eslint-disable-line compat/compat expected.Maps[0].set('a',2); var message = "Expected $.Maps[0] = Map( [ 'a', 1 ] ) to equal Map( [ 'a', 2 ] )."; @@ -569,9 +569,9 @@ describe("toEqual", function() { it("reports mismatches between Maps of different lengths", function() { jasmine.getEnv().requireFunctioningMaps(); - var actual = new Map(); + var actual = new Map(); // eslint-disable-line compat/compat actual.set('a',1); - var expected = new Map(); + var expected = new Map(); // eslint-disable-line compat/compat expected.set('a',2); expected.set('b',1); var message = "Expected Map( [ 'a', 1 ] ) to equal Map( [ 'a', 2 ], [ 'b', 1 ] )."; @@ -582,9 +582,9 @@ describe("toEqual", function() { it("reports mismatches between Maps with equal values but differing keys", function() { jasmine.getEnv().requireFunctioningMaps(); - var actual = new Map(); + var actual = new Map(); // eslint-disable-line compat/compat actual.set('a',1); - var expected = new Map(); + var expected = new Map(); // eslint-disable-line compat/compat expected.set('b',1); var message = "Expected Map( [ 'a', 1 ] ) to equal Map( [ 'b', 1 ] )."; @@ -594,9 +594,9 @@ describe("toEqual", function() { it("does not report mismatches between Maps with keys with same object identity", function() { jasmine.getEnv().requireFunctioningMaps(); var key = {x: 1}; - var actual = new Map(); + var actual = new Map(); // eslint-disable-line compat/compat actual.set(key,2); - var expected = new Map(); + var expected = new Map(); // eslint-disable-line compat/compat expected.set(key,2); expect(compareEquals(actual, expected).pass).toBe(true); @@ -605,9 +605,9 @@ describe("toEqual", function() { it("reports mismatches between Maps with identical keys with different object identity", function() { jasmine.getEnv().requireFunctioningMaps(); - var actual = new Map(); + var actual = new Map(); // eslint-disable-line compat/compat actual.set({x:1},2); - var expected = new Map(); + var expected = new Map(); // eslint-disable-line compat/compat expected.set({x:1},2); var message = "Expected Map( [ Object({ x: 1 }), 2 ] ) to equal Map( [ Object({ x: 1 }), 2 ] )."; @@ -617,9 +617,9 @@ describe("toEqual", function() { it("does not report mismatches when comparing Map key to jasmine.anything()", function() { jasmine.getEnv().requireFunctioningMaps(); - var actual = new Map(); + var actual = new Map(); // eslint-disable-line compat/compat actual.set('a',1); - var expected = new Map(); + var expected = new Map(); // eslint-disable-line compat/compat expected.set(jasmineUnderTest.anything(),1); expect(compareEquals(actual, expected).pass).toBe(true); @@ -629,10 +629,10 @@ describe("toEqual", function() { jasmine.getEnv().requireFunctioningMaps(); jasmine.getEnv().requireFunctioningSymbols(); - var key = Symbol(); - var actual = new Map(); + var key = Symbol(); // eslint-disable-line compat/compat + var actual = new Map(); // eslint-disable-line compat/compat actual.set(key,1); - var expected = new Map(); + var expected = new Map(); // eslint-disable-line compat/compat expected.set(key,1); expect(compareEquals(actual, expected).pass).toBe(true); @@ -642,10 +642,10 @@ describe("toEqual", function() { jasmine.getEnv().requireFunctioningMaps(); jasmine.getEnv().requireFunctioningSymbols(); - var actual = new Map(); - actual.set(Symbol(),1); - var expected = new Map(); - expected.set(Symbol(),1); + var actual = new Map(); // eslint-disable-line compat/compat + actual.set(Symbol(),1); // eslint-disable-line compat/compat + var expected = new Map(); // eslint-disable-line compat/compat + expected.set(Symbol(),1); // eslint-disable-line compat/compat var message = "Expected Map( [ Symbol(), 1 ] ) to equal Map( [ Symbol(), 1 ] )."; expect(compareEquals(actual, expected).message).toBe(message); @@ -655,9 +655,9 @@ describe("toEqual", function() { jasmine.getEnv().requireFunctioningMaps(); jasmine.getEnv().requireFunctioningSymbols(); - var actual = new Map(); - actual.set(Symbol(),1); - var expected = new Map(); + var actual = new Map(); // eslint-disable-line compat/compat + actual.set(Symbol(),1); // eslint-disable-line compat/compat + var expected = new Map(); // eslint-disable-line compat/compat expected.set(jasmineUnderTest.anything(),1); expect(compareEquals(actual, expected).pass).toBe(true); diff --git a/spec/core/matchers/toHaveSizeSpec.js b/spec/core/matchers/toHaveSizeSpec.js index a14a24e5..d25e39e7 100644 --- a/spec/core/matchers/toHaveSizeSpec.js +++ b/spec/core/matchers/toHaveSizeSpec.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ describe('toHaveSize', function() { 'use strict'; diff --git a/spec/helpers/checkForMap.js b/spec/helpers/checkForMap.js index 77fa1233..b8bdacd3 100644 --- a/spec/helpers/checkForMap.js +++ b/spec/helpers/checkForMap.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ (function(env) { env.hasFunctioningMaps = function() { if (typeof Map === 'undefined') { diff --git a/spec/helpers/checkForSet.js b/spec/helpers/checkForSet.js index 8656342d..cae95db7 100644 --- a/spec/helpers/checkForSet.js +++ b/spec/helpers/checkForSet.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ (function(env) { env.hasFunctioningSets = function() { if (typeof Set === 'undefined') { diff --git a/spec/helpers/checkForSymbol.js b/spec/helpers/checkForSymbol.js index c1ed5415..8b5e4b1e 100644 --- a/spec/helpers/checkForSymbol.js +++ b/spec/helpers/checkForSymbol.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ (function(env) { function hasFunctioningSymbols() { if (typeof Symbol === 'undefined') { diff --git a/spec/helpers/checkForTypedArrays.js b/spec/helpers/checkForTypedArrays.js index 3b5d6b35..6902120b 100644 --- a/spec/helpers/checkForTypedArrays.js +++ b/spec/helpers/checkForTypedArrays.js @@ -1,3 +1,4 @@ +/* eslint-disable compat/compat */ (function(env) { function hasFunctioningTypedArrays() { if (typeof Uint32Array === 'undefined') { diff --git a/src/core/asymmetricEqualityTesterArgCompatShim.js b/src/core/asymmetricEqualityTesterArgCompatShim.js index faa4bf79..162d9651 100644 --- a/src/core/asymmetricEqualityTesterArgCompatShim.js +++ b/src/core/asymmetricEqualityTesterArgCompatShim.js @@ -91,7 +91,7 @@ getJasmineRequireObj().asymmetricEqualityTesterArgCompatShim = function(j$) { }); } - props = Object.getOwnPropertyDescriptors(Array.prototype); + props = Object.getOwnPropertyDescriptors(Array.prototype); // eslint-disable-line compat/compat a = []; for (k in props) { diff --git a/src/core/matchers/async/toBePending.js b/src/core/matchers/async/toBePending.js index 7ea12df9..758eb99e 100644 --- a/src/core/matchers/async/toBePending.js +++ b/src/core/matchers/async/toBePending.js @@ -1,10 +1,11 @@ +/* eslint-disable compat/compat */ getJasmineRequireObj().toBePending = function(j$) { /** * Expect a promise to be pending, ie. the promise is neither resolved nor rejected. * @function * @async * @name async-matchers#toBePending - * @since 3.5.1 (should this be the next version or the version when it was added?) + * @since 3.6 * @example * await expectAsync(aPromise).toBePending(); */ diff --git a/src/core/matchers/toHaveSize.js b/src/core/matchers/toHaveSize.js index 4f6ace0c..680e5144 100644 --- a/src/core/matchers/toHaveSize.js +++ b/src/core/matchers/toHaveSize.js @@ -33,7 +33,7 @@ getJasmineRequireObj().toHaveSize = function(j$) { }; } - var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || 9007199254740991; + var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || 9007199254740991; // eslint-disable-line compat/compat function isLength(value) { return (typeof value == 'number') && value > -1 && value % 1 === 0 && value <= MAX_SAFE_INTEGER; } From db6aa8f3f83838c327751d074dda5352e5bccc9d Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 2 Jul 2020 08:49:23 -0700 Subject: [PATCH 158/201] Use a version of eslint that works on Node 8 --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index a7d89f70..74dd08c1 100644 --- a/package.json +++ b/package.json @@ -28,7 +28,7 @@ "devDependencies": { "acorn": "^6.0.0", "ejs": "^2.5.5", - "eslint": "7.3.1", + "eslint": "^6.8.0", "eslint-plugin-compat": "^3.8.0", "express": "^4.16.4", "fast-check": "^1.21.0", From f8ae3eaeaaa7d9224b3f52a85270ffe761fec715 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 8 Jul 2020 16:53:53 -0700 Subject: [PATCH 159/201] Built distribution --- lib/jasmine-core/jasmine.js | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index f618cced..26125ea1 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -2831,7 +2831,7 @@ getJasmineRequireObj().asymmetricEqualityTesterArgCompatShim = function(j$) { }); } - props = Object.getOwnPropertyDescriptors(Array.prototype); + props = Object.getOwnPropertyDescriptors(Array.prototype); // eslint-disable-line compat/compat a = []; for (k in props) { @@ -4114,13 +4114,14 @@ getJasmineRequireObj().GlobalErrors = function(j$) { return GlobalErrors; }; +/* eslint-disable compat/compat */ getJasmineRequireObj().toBePending = function(j$) { /** * Expect a promise to be pending, ie. the promise is neither resolved nor rejected. * @function * @async * @name async-matchers#toBePending - * @since 3.5.1 (should this be the next version or the version when it was added?) + * @since 3.6 * @example * await expectAsync(aPromise).toBePending(); */ @@ -4471,7 +4472,7 @@ getJasmineRequireObj().DiffBuilder = function (j$) { }; function dereferencePath(objectPath, actual, expected, pp) { - var i, asymmetricResult + var i, asymmetricResult; for (i = 0; i < objectPath.components.length; i++) { actual = actual[objectPath.components[i]]; @@ -6055,7 +6056,7 @@ getJasmineRequireObj().toHaveSize = function(j$) { }; } - var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || 9007199254740991; + var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || 9007199254740991; // eslint-disable-line compat/compat function isLength(value) { return (typeof value == 'number') && value > -1 && value % 1 === 0 && value <= MAX_SAFE_INTEGER; } From aa6cc31057ccbef9c2d6fe38c114b90e057dd1e6 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 8 Jul 2020 17:02:11 -0700 Subject: [PATCH 160/201] Show diffs involving root-level asymmetric equality testers * Fixes #1831 --- lib/jasmine-core/jasmine.js | 16 ++++--- .../ObjectContainingSpec.js | 2 +- spec/core/matchers/DiffBuilderSpec.js | 46 +++++++++++++++++++ spec/core/matchers/toEqualSpec.js | 27 ++++++++--- src/core/matchers/DiffBuilder.js | 16 ++++--- 5 files changed, 87 insertions(+), 20 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 26125ea1..edab42b4 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -4472,12 +4472,7 @@ getJasmineRequireObj().DiffBuilder = function (j$) { }; function dereferencePath(objectPath, actual, expected, pp) { - var i, asymmetricResult; - - for (i = 0; i < objectPath.components.length; i++) { - actual = actual[objectPath.components[i]]; - expected = expected[objectPath.components[i]]; - + function handleAsymmetricExpected() { if (j$.isAsymmetricEqualityTester_(expected) && j$.isFunction_(expected.valuesForDiff_)) { var asymmetricResult = expected.valuesForDiff_(actual, pp); expected = asymmetricResult.self; @@ -4485,6 +4480,15 @@ getJasmineRequireObj().DiffBuilder = function (j$) { } } + var i; + handleAsymmetricExpected(); + + for (i = 0; i < objectPath.components.length; i++) { + actual = actual[objectPath.components[i]]; + expected = expected[objectPath.components[i]]; + handleAsymmetricExpected(); + } + return {actual: actual, expected: expected}; } diff --git a/spec/core/asymmetric_equality/ObjectContainingSpec.js b/spec/core/asymmetric_equality/ObjectContainingSpec.js index 8cad948d..97df2555 100644 --- a/spec/core/asymmetric_equality/ObjectContainingSpec.js +++ b/spec/core/asymmetric_equality/ObjectContainingSpec.js @@ -149,7 +149,7 @@ describe("ObjectContaining", function() { }); }); - it("includes keys that are present in only sample", function() { + it("includes keys that are present only in sample", function() { var sample = {a: 1, b: 2}, other = {a: 3}, containing = new jasmineUnderTest.ObjectContaining(sample), diff --git a/spec/core/matchers/DiffBuilderSpec.js b/spec/core/matchers/DiffBuilderSpec.js index 6d82c3f8..01220ce0 100644 --- a/spec/core/matchers/DiffBuilderSpec.js +++ b/spec/core/matchers/DiffBuilderSpec.js @@ -133,4 +133,50 @@ describe("DiffBuilder", function () { expect(diffBuilder.getMessage()).toEqual(expectedMsg); }); + + it('builds diffs involving asymmetric equality testers that implement valuesForDiff_ at the root', function() { + var prettyPrinter = jasmineUnderTest.makePrettyPrinter([]), + diffBuilder = new jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}), + expectedMsg = 'Expected $.foo = 1 to equal 2.\n' + + "Expected $.baz = undefined to equal 3."; + + + diffBuilder.setRoots( + {foo: 1, bar: 2}, + jasmine.objectContaining({foo: 2, baz: 3}) + ); + + diffBuilder.withPath('foo', function() { + diffBuilder.recordMismatch(); + }); + diffBuilder.withPath('baz', function() { + diffBuilder.recordMismatch(); + }); + + expect(diffBuilder.getMessage()).toEqual(expectedMsg); + }); + + it('builds diffs involving asymmetric equality testers that implement valuesForDiff_ below the root', function() { + var prettyPrinter = jasmineUnderTest.makePrettyPrinter([]), + diffBuilder = new jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}), + expectedMsg = 'Expected $.x.foo = 1 to equal 2.\n' + + "Expected $.x.baz = undefined to equal 3."; + + + diffBuilder.setRoots( + {x: {foo: 1, bar: 2}}, + {x: jasmine.objectContaining({foo: 2, baz: 3})} + ); + + diffBuilder.withPath('x', function() { + diffBuilder.withPath('foo', function () { + diffBuilder.recordMismatch(); + }); + diffBuilder.withPath('baz', function () { + diffBuilder.recordMismatch(); + }); + }); + + expect(diffBuilder.getMessage()).toEqual(expectedMsg); + }); }); diff --git a/spec/core/matchers/toEqualSpec.js b/spec/core/matchers/toEqualSpec.js index 081329d9..db7f3ffb 100644 --- a/spec/core/matchers/toEqualSpec.js +++ b/spec/core/matchers/toEqualSpec.js @@ -429,17 +429,30 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches involving objectContaining and an object", function() { - var actual = {x: {a: 1, b: 4, c: 3, extra: 'ignored'}}; - var expected = {x: jasmineUnderTest.objectContaining({a: 1, b: 2, c: 3})}; - expect(compareEquals(actual, expected).message).toEqual('Expected $.x.b = 4 to equal 2.'); + it('reports mismatches between an object and objectContaining', function() { + var actual = {a: 1, b: 4, c: 3, extra: 'ignored'}; + var expected = jasmineUnderTest.objectContaining({a: 1, b: 2, c: 3, d: 4}); + expect(compareEquals(actual, expected).message) + .toEqual( + 'Expected $.b = 4 to equal 2.\n' + + 'Expected $.d = undefined to equal 4.' + ); }); it("reports mismatches between a non-object and objectContaining", function() { - var actual = {x: 1}; - var expected = {x: jasmineUnderTest.objectContaining({a: 1})}; + var actual = 1; + var expected = jasmineUnderTest.objectContaining({a: 1}); expect(compareEquals(actual, expected).message).toEqual( - "Expected $.x = 1 to equal ''." + "Expected 1 to equal ''." + ); + }); + + it("reports mismatches involving a nested objectContaining", function() { + var actual = {x: {a: 1, b: 4, c: 3, extra: 'ignored'}}; + var expected = {x: jasmineUnderTest.objectContaining({a: 1, b: 2, c: 3, d: 4})}; + expect(compareEquals(actual, expected).message).toEqual( + 'Expected $.x.b = 4 to equal 2.\n' + + 'Expected $.x.d = undefined to equal 4.' ); }); diff --git a/src/core/matchers/DiffBuilder.js b/src/core/matchers/DiffBuilder.js index 83333d8a..70b52ea7 100644 --- a/src/core/matchers/DiffBuilder.js +++ b/src/core/matchers/DiffBuilder.js @@ -72,12 +72,7 @@ getJasmineRequireObj().DiffBuilder = function (j$) { }; function dereferencePath(objectPath, actual, expected, pp) { - var i, asymmetricResult; - - for (i = 0; i < objectPath.components.length; i++) { - actual = actual[objectPath.components[i]]; - expected = expected[objectPath.components[i]]; - + function handleAsymmetricExpected() { if (j$.isAsymmetricEqualityTester_(expected) && j$.isFunction_(expected.valuesForDiff_)) { var asymmetricResult = expected.valuesForDiff_(actual, pp); expected = asymmetricResult.self; @@ -85,6 +80,15 @@ getJasmineRequireObj().DiffBuilder = function (j$) { } } + var i; + handleAsymmetricExpected(); + + for (i = 0; i < objectPath.components.length; i++) { + actual = actual[objectPath.components[i]]; + expected = expected[objectPath.components[i]]; + handleAsymmetricExpected(); + } + return {actual: actual, expected: expected}; } From 226d3ba939217570d5d5e89a7d71982d14e370a9 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 9 Jul 2020 11:25:54 -0700 Subject: [PATCH 161/201] Added IE back to the Travis matrix Now that jasmine-browser works correctly with IE, we can resume testing against it. --- .travis.yml | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/.travis.yml b/.travis.yml index bfeccecd..3a2cb0db 100644 --- a/.travis.yml +++ b/.travis.yml @@ -19,6 +19,14 @@ env: matrix: include: + - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=11 SAUCE_OS="Windows 8.1" + if: type != pull_request + addons: + sauce_connect: true + - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=10 SAUCE_OS="Windows 8" + if: type != pull_request + addons: + sauce_connect: true - env: JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='' SAUCE_OS="Windows 10" if: type != pull_request addons: From 70c416d5c9a755a7240e8c902866ece652654642 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Fri, 10 Jul 2020 15:41:02 -0700 Subject: [PATCH 162/201] Fixed jsdocs for recent additions --- lib/jasmine-core/jasmine.js | 14 +++++++------- src/core/Env.js | 4 ++-- src/core/matchers/toHaveSize.js | 2 +- src/core/requireInterface.js | 8 ++++---- 4 files changed, 14 insertions(+), 14 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index edab42b4..dd1b255b 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -2077,7 +2077,7 @@ getJasmineRequireObj().Env = function(j$) { }; /** - * Sets a user-defined property that will be provided to reporters as part of {@link SpecResult#properties} + * Sets a user-defined property that will be provided to reporters as part of the properties field of {@link SpecResult} * @name Env#setSpecProperty * @since 3.6.0 * @function @@ -2094,7 +2094,7 @@ getJasmineRequireObj().Env = function(j$) { }; /** - * Sets a user-defined property that will be provided to reporters as part of {@link SuiteResult#properties} + * Sets a user-defined property that will be provided to reporters as part of the properties field of {@link SuiteResult} * @name Env#setSuiteProperty * @since 3.6.0 * @function @@ -6030,7 +6030,7 @@ getJasmineRequireObj().toHaveSize = function(j$) { * {@link expect} the actual size to be equal to the expected, using array-like length or object keys size. * @function * @name matchers#toHaveSize - * @since 3.5.1 + * @since 3.6.0 * @param {Object} expected - Expected size * @example * array = [1,2]; @@ -7370,8 +7370,8 @@ getJasmineRequireObj().interface = function(jasmine, env) { }, /** - * Sets a user-defined property that will be provided to reporters as part of {@link SpecResult#properties} - * @name Env#setSpecProperty + * Sets a user-defined property that will be provided to reporters as part of the properties field of {@link SpecResult} + * @name setSpecProperty * @since 3.6.0 * @function * @param {String} key The name of the property @@ -7382,8 +7382,8 @@ getJasmineRequireObj().interface = function(jasmine, env) { }, /** - * Sets a user-defined property that will be provided to reporters as part of {@link SuiteResult#properties} - * @name Env#setSuiteProperty + * Sets a user-defined property that will be provided to reporters as part of the properties field of {@link SuiteResult} + * @name setSuiteProperty * @since 3.6.0 * @function * @param {String} key The name of the property diff --git a/src/core/Env.js b/src/core/Env.js index 60025850..d7fdd4c0 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -1125,7 +1125,7 @@ getJasmineRequireObj().Env = function(j$) { }; /** - * Sets a user-defined property that will be provided to reporters as part of {@link SpecResult#properties} + * Sets a user-defined property that will be provided to reporters as part of the properties field of {@link SpecResult} * @name Env#setSpecProperty * @since 3.6.0 * @function @@ -1142,7 +1142,7 @@ getJasmineRequireObj().Env = function(j$) { }; /** - * Sets a user-defined property that will be provided to reporters as part of {@link SuiteResult#properties} + * Sets a user-defined property that will be provided to reporters as part of the properties field of {@link SuiteResult} * @name Env#setSuiteProperty * @since 3.6.0 * @function diff --git a/src/core/matchers/toHaveSize.js b/src/core/matchers/toHaveSize.js index 680e5144..03c8d431 100644 --- a/src/core/matchers/toHaveSize.js +++ b/src/core/matchers/toHaveSize.js @@ -3,7 +3,7 @@ getJasmineRequireObj().toHaveSize = function(j$) { * {@link expect} the actual size to be equal to the expected, using array-like length or object keys size. * @function * @name matchers#toHaveSize - * @since 3.5.1 + * @since 3.6.0 * @param {Object} expected - Expected size * @example * array = [1,2]; diff --git a/src/core/requireInterface.js b/src/core/requireInterface.js index adc503f8..a468d880 100644 --- a/src/core/requireInterface.js +++ b/src/core/requireInterface.js @@ -169,8 +169,8 @@ getJasmineRequireObj().interface = function(jasmine, env) { }, /** - * Sets a user-defined property that will be provided to reporters as part of {@link SpecResult#properties} - * @name Env#setSpecProperty + * Sets a user-defined property that will be provided to reporters as part of the properties field of {@link SpecResult} + * @name setSpecProperty * @since 3.6.0 * @function * @param {String} key The name of the property @@ -181,8 +181,8 @@ getJasmineRequireObj().interface = function(jasmine, env) { }, /** - * Sets a user-defined property that will be provided to reporters as part of {@link SuiteResult#properties} - * @name Env#setSuiteProperty + * Sets a user-defined property that will be provided to reporters as part of the properties field of {@link SuiteResult} + * @name setSuiteProperty * @since 3.6.0 * @function * @param {String} key The name of the property From 6f3e85f755554c4b52b2449a6d2d66bb1327ac4e Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 16 Jul 2020 12:42:05 -0700 Subject: [PATCH 163/201] Only run long property tests once on CI --- .travis.yml | 15 +++++++-------- 1 file changed, 7 insertions(+), 8 deletions(-) diff --git a/.travis.yml b/.travis.yml index 3a2cb0db..dadd8965 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,8 +1,5 @@ language: node_js -node_js: - - "10" - - "8" - - "12" +node_js: 10 script: $TEST_COMMAND @@ -10,15 +7,17 @@ env: global: - USE_SAUCE=true - TEST_COMMAND="bash travis-core-script.sh" - - JASMINE_LONG_PROPERTY_TESTS="y" - secure: WSPWhlnC4mWSnSPquX+m1/BCu5ch5NygkaHuM2Nea7lD8oS3XLX8QncZZAsQ4lnNfqoDDuBOizG0AESiqNvE4y6x5qvLLTS6q+ce255ZEMZ71TBdZgDEEvGMEjOPPsVXiXyTQOP1lwOPlrbZvaPgWV7e11KIBab6DfFcQpnvDgo= - secure: SW7CJhZnwaNT749Gdnhvqb5rbXlAOsygUAzh9qhtyvbqXKkmJdBIEsO01YF6pbju1X2twE9JvWCOxeZju43NgQChJlPsGbjY2j3k/TdQeTAJesQe2K7ytwghunI30gjEovtRH0T3w1EmcKPH8yj5eBIcB2OYoJHx8KEC7e68q1g= - matrix: - - TEST_COMMAND="npm test" - matrix: include: + - node_js: "10" + env: JASMINE_LONG_PROPERTY_TESTS="y" TEST_COMMAND="npm test" + - node_js: "12" + env: TEST_COMMAND="npm test" + - node_js: "8" + env: TEST_COMMAND="npm test" - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=11 SAUCE_OS="Windows 8.1" if: type != pull_request addons: From d51da1880870ed07b2c898a261e96524e99ecc49 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 23 Jul 2020 16:02:30 -0700 Subject: [PATCH 164/201] Bump version to 3.6.0 --- lib/jasmine-core/jasmine.js | 2 +- lib/jasmine-core/version.rb | 2 +- package.json | 2 +- release_notes/3.6.0.md | 146 ++++++++++++++++++++++++++++++++++++ 4 files changed, 149 insertions(+), 3 deletions(-) create mode 100644 release_notes/3.6.0.md diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index dd1b255b..a68f1b20 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -8961,5 +8961,5 @@ getJasmineRequireObj().UserContext = function(j$) { }; getJasmineRequireObj().version = function() { - return '3.5.1'; + return '3.6.0'; }; diff --git a/lib/jasmine-core/version.rb b/lib/jasmine-core/version.rb index b757b251..5dd3e13b 100644 --- a/lib/jasmine-core/version.rb +++ b/lib/jasmine-core/version.rb @@ -4,6 +4,6 @@ # module Jasmine module Core - VERSION = "3.5.0" + VERSION = "3.6.0" end end diff --git a/package.json b/package.json index 74dd08c1..7ed0c766 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "jasmine-core", "license": "MIT", - "version": "3.5.1", + "version": "3.6.0", "repository": { "type": "git", "url": "https://github.com/jasmine/jasmine.git" diff --git a/release_notes/3.6.0.md b/release_notes/3.6.0.md new file mode 100644 index 00000000..cfa8628d --- /dev/null +++ b/release_notes/3.6.0.md @@ -0,0 +1,146 @@ +# Jasmine Core 3.6 Release Notes + +## Summary + +This is a maintenance release of Jasmine with a number of new features and fixes. + +## Highlights + +* Added support for custom object formatters + * Allows customizing how an object is stringified in matcher failure messages + * [Tutorial](https://jasmine.github.io/tutorials/custom_object_formatter) + * [API reference](https://jasmine.github.io/api/3.6/jasmine.html#.addCustomObjectFormatter) + +* Don't require matchers and asymmetric equality testers to pass custom object formatters back to Jasmine + - Supports custom object formatters. + - Makes it easier to write high quality matchers and asymmetric equality testers. + - The old API will still work until 4.0. + +* Properly import jasmineRequire object before using + - Improves compatibility with Webpack + - Merges [#1766](https://github.com/jasmine/jasmine/pull/1766) from @amilligan + +* Added a toHaveBeenCalledOnceWith matcher + - Merges [#1801](https://github.com/jasmine/jasmine/pull/1801) from @Maximaximum + - Fixes [#1717](https://github.com/jasmine/jasmine/issues/1717) + +* Added a toHaveSize matcher + - Merges [#1796](https://github.com/jasmine/jasmine/pull/1796) from @wokier + +* Added a toBePending async matcher + - Merges [#1808](https://github.com/jasmine/jasmine/pull/1808) from @DCtheTall + - Fixes [#1803](https://github.com/jasmine/jasmine/issues/1803) + +* Added support for user-defined spec/suite properties + - Allows specs/suites to pass data to custom reporters + - Merges [#1763](https://github.com/jasmine/jasmine/pull/1763) from @johnjbarton + +* Route unhandled promise rejections to onerror + - Merges [#1778](https://github.com/jasmine/jasmine/pull/1778) from @johnjbarton + - Fixes [#1777](https://github.com/jasmine/jasmine/issues/1777) + + +## Internal notes + +* Use a version of eslint that works on Node 8 + +* Check for syntax and standard library objects that don't work in IE + +* Run eslint against all files + +* Add Additional Test for equals Matcher + - Merges [#1829](https://github.com/jasmine/jasmine/pull/1829) from @tobiasschweizer + - Fixes [#1821](https://github.com/jasmine/jasmine/issues/1821) + +* Depend on head of jasmine-browser to fix IE failures in CI + +* Fixed test failure in Firefox 74 + +* Added test for resolveTo/rejectWith with empty parameters + - Merges [#1802](https://github.com/jasmine/jasmine/pull/1802) from @chivesrs + +* Removed unnecessary uses of new in tests + +* Realigned the browser testing matrix to match current reality + - Use Windows instead of Linux so we can get current browsers from Sauce. + - Test against the version of Firefox that corresponds to ESR as well as + latest. + - Test the latest Edge rather than a specific older version. + - Test Safari 8 and 13 instead of 8, 9 and 10. What works in those versions + is likely to work in the ones in between. + +* Don't leak global error handlers between Jasmine's own tests + +* Added basic property tests for matchersUtil.equals + +* Added integration tests for existing matcher interfaces + +* Added integration tests for asymmetric equality testers + +* Test IE before other browsers on Travis + + +## Other Changes + +* Show diffs involving root-level asymmetric equality testers + - Fixes [#1831](https://github.com/jasmine/jasmine/issues/1831) + +* Fixed references to master in docs + +* Allow spy throwError to throw an Object + - Merges [#1822](https://github.com/jasmine/jasmine/pull/1822) from @terencehonles + +* Added missing periods to README + - Merges [#1828](https://github.com/jasmine/jasmine/pull/1828) from @dirkpuge + + +* Expose setSpec/SuiteProperty on interface + - Merges [#1820](https://github.com/jasmine/jasmine/pull/1820) from @johnjbarton + +* Prevent undesired reloads when karma-jasmine-html-reporter is used + - Merges [#1807](https://github.com/jasmine/jasmine/pull/1807) from @parloti + - Fixes [#1775](https://github.com/jasmine/jasmine/issues/1775) + +* Correctly report spec and suite duration + - Fixes [#1676](https://github.com/jasmine/jasmine/issues/1676). + +* Added jsdocs for MatchersUtil + +* Allow the .callThrough spy strategy to call constructor functions without errors + - Merges [#1782](https://github.com/jasmine/jasmine/pull/1782) from @enelson + - Fixes [#1760](https://github.com/jasmine/jasmine/issues/1760) + +* Inject a per-runable pretty printer into MatchersUtil + - Supports custom object formatters + +* Include stack traces in unhandled promise rejection messages + +* Describe the naming for the function it + - Merges [#1772](https://github.com/jasmine/jasmine/pull/1772) from @johnlinp + +* Correctly extract error messages from stack traces that don't start with `Error` + - Merges [#1776](https://github.com/jasmine/jasmine/pull/1776) from @vhermannitk + - Fixes [#1771](https://github.com/jasmine/jasmine/issues/1771) + +* Fixed objectContaining to not match when the expected is the empty object and the actual is a non-object + +* Fixed toEqual(0, Number.MIN_VALUE) to fail instead of passing + - Merges [#1764](https://github.com/jasmine/jasmine/pull/1764) from @dubzzz + +* Fixed comparison between ObjectContaining and non-objects on IE + +* Provide better diffs for object graphs that include `objectContaining` + +* Indent multiline failure messages in the output of `withContext` + * This makes it easier to see where each failure message begins and ends. + +* Report async expectations that complete after the runable completes + - See [#1752](https://github.com/jasmine/jasmine/issues/1752). + +* Treat NodeJS assertion failures as expectation failures + - Merges [#1678](https://github.com/jasmine/jasmine/pull/1678) from @apla + + +------ + +_Release Notes generated with _[Anchorman](http://github.com/infews/anchorman)_ From 0cfeb0b9c39663dadefdce74d18e7ff783a2ed7b Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 23 Jul 2020 16:35:36 -0700 Subject: [PATCH 165/201] Fixed link to custom object formatter tutorial --- lib/jasmine-core/jasmine.js | 2 +- src/core/requireInterface.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index a68f1b20..6fb31080 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -7552,7 +7552,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * @since 3.6.0 * @function * @param {Function} formatter - A function which takes a value to format and returns a string if it knows how to format it, and `undefined` otherwise. - * @see custom_object_formatter + * @see custom_object_formatters */ jasmine.addCustomObjectFormatter = function(formatter) { return env.addCustomObjectFormatter(formatter); diff --git a/src/core/requireInterface.js b/src/core/requireInterface.js index a468d880..6473ffaa 100644 --- a/src/core/requireInterface.js +++ b/src/core/requireInterface.js @@ -351,7 +351,7 @@ getJasmineRequireObj().interface = function(jasmine, env) { * @since 3.6.0 * @function * @param {Function} formatter - A function which takes a value to format and returns a string if it knows how to format it, and `undefined` otherwise. - * @see custom_object_formatter + * @see custom_object_formatters */ jasmine.addCustomObjectFormatter = function(formatter) { return env.addCustomObjectFormatter(formatter); From c4e65e4a9a004b4df720f24833322007d59f6722 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 23 Jul 2020 16:50:54 -0700 Subject: [PATCH 166/201] wip --- RELEASE.md | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/RELEASE.md b/RELEASE.md index 61ffbadc..00fda1b0 100644 --- a/RELEASE.md +++ b/RELEASE.md @@ -60,8 +60,10 @@ Install [twine](https://github.com/pypa/twine) Probably only need to do this when releasing a minor version, and not a patch version. -1. `cp -R edge ${version}` to copy the current edge docs to the new version -1. Add a link to the new version in `index.html` +1. `rake update_edge_jasmine` +1. `npm run jsdoc` +1. `rake release[${version}]` to copy the current edge docs to the new version +1. Commit and push. ### Finally From 1f68ed836e0c4e2ced39f5daa05dfc5d13d489f3 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 23 Jul 2020 17:26:43 -0700 Subject: [PATCH 167/201] Updated the release docs --- RELEASE.md | 59 ++++++++++++++++++++++++++++++++++++------------------ 1 file changed, 40 insertions(+), 19 deletions(-) diff --git a/RELEASE.md b/RELEASE.md index 00fda1b0..b388cf85 100644 --- a/RELEASE.md +++ b/RELEASE.md @@ -29,29 +29,32 @@ When jasmine-core revs its major or minor version, the binding libraries should When ready to release - specs are all green and the stories are done: 1. Update the release notes in `release_notes` - use the Anchorman gem to generate the markdown file and edit accordingly -1. Update the version in `package.json` to a release candidate -1. Update any links or top-level landing page for the Github Pages +1. Update the version in `package.json` +1. Copy version to the Ruby gem with `grunt build:copyVersionToGem` + +### Commit and push core changes + +1. Commit release notes and version changes (jasmine.js, version.rb, package.json) +1. Push +1. Wait for Travis to go green ### Build standalone distribution 1. Build the standalone distribution with `grunt buildStandaloneDist` -### Release the Python egg +### Release the core Ruby gem + +1. __NOTE__: You will likely need to push a new jasmine gem with a dependent version right after this release. See below. +1. `rake release` - tags the repo with the version, builds the `jasmine-core` gem, pushes the gem to Rubygems.org. In order to release you will have to ensure you have rubygems creds locally. + +### Release the core Python egg Install [twine](https://github.com/pypa/twine) 1. `python setup.py sdist` 1. `twine upload dist/jasmine-core-.tar.gz` You will need pypi credentials to upload the egg. -### Release the Ruby gem - -1. Copy version to the Ruby gem with `grunt build:copyVersionToGem` -1. __NOTE__: You will likely need to point to a local jasmine gem in order to run tests locally. _Do not_ push this version of the Gemfile. -1. __NOTE__: You will likely need to push a new jasmine gem with a dependent version right after this release. -1. Push these changes to GitHub and verify that this SHA is green -1. `rake release` - tags the repo with the version, builds the `jasmine-core` gem, pushes the gem to Rubygems.org. In order to release you will have to ensure you have rubygems creds locally. - -### Release the NPM +### Release the core NPM module 1. `npm adduser` to save your credentials locally 1. `npm publish .` to publish what's in `package.json` @@ -65,12 +68,30 @@ Probably only need to do this when releasing a minor version, and not a patch ve 1. `rake release[${version}]` to copy the current edge docs to the new version 1. Commit and push. +### Release the binding libraries + +#### NPM + +1. Create release notes using Anchorman as above +1. In `package.json`, update both the package version and the jasmine-core dependency version +1. Commit and push. +1. Wait for Travis to go green again. +1. `grunt release ` +1. `npm publish .` + +#### Gem + +1. Create release notes using Anchorman as above +1. Update the version number in `lib/jasmine/version.rb`. +1. Update the jasmine-core dependency version in `jasmine.gemspec`. +1. Commit and push. +1. Wait for Travis to go green again. +1. `rake release` + ### Finally -1. Visit the [Releases page for Jasmine](https://github.com/jasmine/jasmine/releases), find the tag just pushed. - 1. Paste in a link to the correct release notes for this release. The link should reference the blob and tag correctly, and the markdown file for the notes. - 1. If it is a pre-release, mark it as such. - 1. Attach the standalone zipfile - - -There should be a post to Pivotal Labs blog and a tweet to that link. +For each of the above GitHub repos: +1. Visit the releases page and find the tag just published. +1. Paste in a link to the correct release notes for this release. The link should reference the blob and tag correctly, and the markdown file for the notes. +1. If it is a pre-release, mark it as such. +1. For core, attach the standalone zipfile. From e5bb89847f09856512f00934319fbdab28b5af46 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 23 Jul 2020 17:28:38 -0700 Subject: [PATCH 168/201] Use jasmine-browser from npm The current released version now works with IE, so we no longer need to depend on main. --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 7ed0c766..0ef7ddd8 100644 --- a/package.json +++ b/package.json @@ -40,7 +40,7 @@ "grunt-css-url-embed": "^1.11.1", "grunt-sass": "^3.0.2", "jasmine": "^3.4.0", - "jasmine-browser-runner": "github:jasmine/jasmine-browser", + "jasmine-browser-runner": "^0.4.0", "jsdom": "^15.0.0", "load-grunt-tasks": "^4.0.0", "node-sass": "^4.11.0", From dfdcfc5be561b9c929b1318d525853703eef7392 Mon Sep 17 00:00:00 2001 From: snowman Date: Sat, 25 Jul 2020 13:27:00 +0800 Subject: [PATCH 169/201] Update README.md Remove extra "jasmine/" directory in code example --- README.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index e8b7fd53..c7189c1d 100644 --- a/README.md +++ b/README.md @@ -42,12 +42,12 @@ To install Jasmine standalone on your local box (where **_{#.#.#}_** below is su Add the following to your HTML file: ```html - - + + - - - + + + ``` ## Supported environments From 6b9739030ddabdfc7aee679d99d4307b5fc9fa3b Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sun, 2 Aug 2020 12:57:28 -0700 Subject: [PATCH 170/201] Fixed future deprecations --- lib/jasmine-core/jasmine.js | 8 ++++---- spec/core/integration/EnvSpec.js | 1 + .../matchers/toHaveBeenCalledOnceWithSpec.js | 19 +++++++++++++------ src/core/matchers/toHaveBeenCalledOnceWith.js | 8 ++++---- 4 files changed, 22 insertions(+), 14 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 6fb31080..eb2b160d 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -5829,18 +5829,18 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { expectedArgs = args.slice(1); if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); + throw new Error(getErrorMsg('Expected a spy, but got ' + util.pp(actual) + '.')); } var prettyPrintedCalls = actual.calls.allArgs().map(function (argsForCall) { - return ' ' + j$.pp(argsForCall); + return ' ' + util.pp(argsForCall); }); if (actual.calls.count() === 1 && util.contains(actual.calls.allArgs(), expectedArgs)) { return { pass: true, message: 'Expected spy ' + actual.and.identity + ' to have been called 0 times, multiple times, or once, but with arguments different from:\n' - + ' ' + j$.pp(expectedArgs) + '\n' + + ' ' + util.pp(expectedArgs) + '\n' + 'But the actual call was:\n' + prettyPrintedCalls.join(',\n') + '.\n\n' }; @@ -5868,7 +5868,7 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { return { pass: false, message: 'Expected spy ' + actual.and.identity + ' to have been called only once, and with given args:\n' - + ' ' + j$.pp(expectedArgs) + '\n' + + ' ' + util.pp(expectedArgs) + '\n' + butString() }; } diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index 090bb54c..ae7cd0d6 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -1992,6 +1992,7 @@ describe("Env integration", function() { exception; env.describe("a suite", function () { + env.it('a spec'); try { env.setSpecProperty('a prop', 'val'); } catch(e) { diff --git a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js index be0e95bc..d79711a5 100644 --- a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js @@ -1,7 +1,8 @@ describe("toHaveBeenCalledOnceWith", function () { it("passes when the actual was called only once and with matching parameters", function () { - var util = jasmineUnderTest.matchersUtil, + var pp = jasmineUnderTest.makePrettyPrinter(), + util = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), calledSpy = new jasmineUnderTest.Spy('called-spy'), result; @@ -27,7 +28,8 @@ describe("toHaveBeenCalledOnceWith", function () { }); it("fails when the actual was never called", function () { - var util = jasmineUnderTest.matchersUtil, + var pp = jasmineUnderTest.makePrettyPrinter(), + util = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), calledSpy = new jasmineUnderTest.Spy('called-spy'), result; @@ -39,7 +41,8 @@ describe("toHaveBeenCalledOnceWith", function () { }); it("fails when the actual was called once with different parameters", function () { - var util = jasmineUnderTest.matchersUtil, + var pp = jasmineUnderTest.makePrettyPrinter(), + util = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), calledSpy = new jasmineUnderTest.Spy('called-spy'), result; @@ -52,7 +55,8 @@ describe("toHaveBeenCalledOnceWith", function () { }); it("fails when the actual was called multiple times with expected parameters", function () { - var util = jasmineUnderTest.matchersUtil, + var pp = jasmineUnderTest.makePrettyPrinter(), + util = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), calledSpy = new jasmineUnderTest.Spy('called-spy'), result; @@ -66,7 +70,8 @@ describe("toHaveBeenCalledOnceWith", function () { }); it("fails when the actual was called multiple times (one of them - with expected parameters)", function () { - var util = jasmineUnderTest.matchersUtil, + var pp = jasmineUnderTest.makePrettyPrinter(), + util = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), calledSpy = new jasmineUnderTest.Spy('called-spy'), result; @@ -80,7 +85,9 @@ describe("toHaveBeenCalledOnceWith", function () { }); it("throws an exception when the actual is not a spy", function () { - var matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(), + var pp = jasmineUnderTest.makePrettyPrinter(), + util = new jasmineUnderTest.MatchersUtil({ pp: pp }), + matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), fn = function () { }; expect(function () { matcher.compare(fn) }).toThrowError(/Expected a spy, but got Function./); diff --git a/src/core/matchers/toHaveBeenCalledOnceWith.js b/src/core/matchers/toHaveBeenCalledOnceWith.js index d7be3782..2cd607f8 100644 --- a/src/core/matchers/toHaveBeenCalledOnceWith.js +++ b/src/core/matchers/toHaveBeenCalledOnceWith.js @@ -19,18 +19,18 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { expectedArgs = args.slice(1); if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + j$.pp(actual) + '.')); + throw new Error(getErrorMsg('Expected a spy, but got ' + util.pp(actual) + '.')); } var prettyPrintedCalls = actual.calls.allArgs().map(function (argsForCall) { - return ' ' + j$.pp(argsForCall); + return ' ' + util.pp(argsForCall); }); if (actual.calls.count() === 1 && util.contains(actual.calls.allArgs(), expectedArgs)) { return { pass: true, message: 'Expected spy ' + actual.and.identity + ' to have been called 0 times, multiple times, or once, but with arguments different from:\n' - + ' ' + j$.pp(expectedArgs) + '\n' + + ' ' + util.pp(expectedArgs) + '\n' + 'But the actual call was:\n' + prettyPrintedCalls.join(',\n') + '.\n\n' }; @@ -58,7 +58,7 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { return { pass: false, message: 'Expected spy ' + actual.and.identity + ' to have been called only once, and with given args:\n' - + ' ' + j$.pp(expectedArgs) + '\n' + + ' ' + util.pp(expectedArgs) + '\n' + butString() }; } From 627704621349987c7317fe3c3e25a48ba1cf790d Mon Sep 17 00:00:00 2001 From: Aaron Snailwood Date: Thu, 20 Aug 2020 10:07:35 -0700 Subject: [PATCH 171/201] fix typo in asyncMatcher toBePending comment --- src/core/matchers/async/toBePending.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/core/matchers/async/toBePending.js b/src/core/matchers/async/toBePending.js index 758eb99e..c73aa3d3 100644 --- a/src/core/matchers/async/toBePending.js +++ b/src/core/matchers/async/toBePending.js @@ -1,7 +1,7 @@ /* eslint-disable compat/compat */ getJasmineRequireObj().toBePending = function(j$) { /** - * Expect a promise to be pending, ie. the promise is neither resolved nor rejected. + * Expect a promise to be pending, i.e. the promise is neither resolved nor rejected. * @function * @async * @name async-matchers#toBePending From 53d8073707d90da6941ed15cb97e3fbf87b77de3 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 29 Aug 2020 13:05:57 -0700 Subject: [PATCH 172/201] Allow generator functions to be passed to `.and.callFake` Fixes #1848. --- lib/jasmine-core/jasmine.js | 12 +++++++++++- spec/core/SpyStrategySpec.js | 11 +++++++++++ spec/helpers/generator.js | 22 ++++++++++++++++++++++ spec/support/jasmine-browser.js | 1 + spec/support/jasmine.json | 1 + src/core/SpyStrategy.js | 8 +++++++- src/core/base.js | 4 ++++ 7 files changed, 57 insertions(+), 2 deletions(-) create mode 100644 spec/helpers/generator.js diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 2a50a3cf..197929cb 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -244,6 +244,10 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return j$.isA_('AsyncFunction', value); }; + j$.isGeneratorFunction_ = function(value) { + return j$.isA_('GeneratorFunction', value); + }; + j$.isTypedArray_ = function(value) { return ( j$.isA_('Float32Array', value) || @@ -8308,7 +8312,13 @@ getJasmineRequireObj().SpyStrategy = function(j$) { * @param {Function} fn The function to invoke with the passed parameters. */ SpyStrategy.prototype.callFake = function(fn) { - if (!(j$.isFunction_(fn) || j$.isAsyncFunction_(fn))) { + if ( + !( + j$.isFunction_(fn) || + j$.isAsyncFunction_(fn) || + j$.isGeneratorFunction_(fn) + ) + ) { throw new Error( 'Argument passed to callFake should be a function, got ' + fn ); diff --git a/spec/core/SpyStrategySpec.js b/spec/core/SpyStrategySpec.js index 76a3a1e2..85624083 100644 --- a/spec/core/SpyStrategySpec.js +++ b/spec/core/SpyStrategySpec.js @@ -334,6 +334,17 @@ describe('SpyStrategy', function() { }).toThrowError(/^Argument passed to callFake should be a function, got/); }); + it('allows generator functions to be passed to callFake strategy', function() { + jasmine.getEnv().requireGeneratorFunctions(); + + var generator = jasmine.getEnv().makeGeneratorFunction('yield "ok";'), + spyStrategy = new jasmineUnderTest.SpyStrategy({ fn: function() {} }); + + spyStrategy.callFake(generator); + + expect(spyStrategy.exec().next().value).toEqual('ok'); + }); + it('allows a return to plan stubbing after another strategy', function() { var originalFn = jasmine.createSpy('original'), fakeFn = jasmine.createSpy('fake').and.returnValue(67), diff --git a/spec/helpers/generator.js b/spec/helpers/generator.js new file mode 100644 index 00000000..b62f5acd --- /dev/null +++ b/spec/helpers/generator.js @@ -0,0 +1,22 @@ +(function(env) { + function getGeneratorFuncCtor() { + try { + eval('var func = function*() {}'); + } catch (e) { + return null; + } + + return Object.getPrototypeOf(func).constructor; + } + + env.makeGeneratorFunction = function(text) { + var GeneratorFunction = getGeneratorFuncCtor(); + return new GeneratorFunction(text || ''); + }; + + env.requireGeneratorFunctions = function() { + if (!getGeneratorFuncCtor()) { + env.pending('Environment does not support generator functions'); + } + }; +})(jasmine.getEnv()); diff --git a/spec/support/jasmine-browser.js b/spec/support/jasmine-browser.js index 61076dbb..2f5f7146 100644 --- a/spec/support/jasmine-browser.js +++ b/spec/support/jasmine-browser.js @@ -18,6 +18,7 @@ module.exports = { specFiles: ['**/*[Ss]pec.js', '!npmPackage/**/*'], helpers: [ 'helpers/asyncAwait.js', + 'helpers/generator.js', 'helpers/BrowserFlags.js', 'helpers/checkForMap.js', 'helpers/checkForSet.js', diff --git a/spec/support/jasmine.json b/spec/support/jasmine.json index b48efde5..0276ca92 100644 --- a/spec/support/jasmine.json +++ b/spec/support/jasmine.json @@ -6,6 +6,7 @@ ], "helpers": [ "helpers/asyncAwait.js", + "helpers/generator.js", "helpers/checkForMap.js", "helpers/checkForSet.js", "helpers/checkForSymbol.js", diff --git a/src/core/SpyStrategy.js b/src/core/SpyStrategy.js index 41aa9258..382164b6 100644 --- a/src/core/SpyStrategy.js +++ b/src/core/SpyStrategy.js @@ -168,7 +168,13 @@ getJasmineRequireObj().SpyStrategy = function(j$) { * @param {Function} fn The function to invoke with the passed parameters. */ SpyStrategy.prototype.callFake = function(fn) { - if (!(j$.isFunction_(fn) || j$.isAsyncFunction_(fn))) { + if ( + !( + j$.isFunction_(fn) || + j$.isAsyncFunction_(fn) || + j$.isGeneratorFunction_(fn) + ) + ) { throw new Error( 'Argument passed to callFake should be a function, got ' + fn ); diff --git a/src/core/base.js b/src/core/base.js index 121ff614..d02606d5 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -76,6 +76,10 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return j$.isA_('AsyncFunction', value); }; + j$.isGeneratorFunction_ = function(value) { + return j$.isA_('GeneratorFunction', value); + }; + j$.isTypedArray_ = function(value) { return ( j$.isA_('Float32Array', value) || From 8cb44582bcbbb812a0140ce39212efed740815e3 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 1 Sep 2020 15:18:53 -0700 Subject: [PATCH 173/201] Don't overwrite MatchersUtil methods with ones that were added to Array.prototype, esp. contains Fixes #1849. --- lib/jasmine-core/jasmine.js | 4 +- ...ymmetricEqualityTesterArgCompatShimSpec.js | 48 +++++++++++++++++-- .../asymmetricEqualityTesterArgCompatShim.js | 4 +- 3 files changed, 51 insertions(+), 5 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 197929cb..5a8e11b4 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -2810,7 +2810,9 @@ getJasmineRequireObj().asymmetricEqualityTesterArgCompatShim = function(j$) { for (i = 0; i < props.length; i++) { k = props[i]; - if (k !== 'length') { + // Skip length (dealt with above), and anything that collides with + // MatchesUtil e.g. an Array.prototype.contains method added by user code + if (k !== 'length' && !self[k]) { copy(self, Array.prototype, k); } } diff --git a/spec/core/asymmetricEqualityTesterArgCompatShimSpec.js b/spec/core/asymmetricEqualityTesterArgCompatShimSpec.js index c7c4d9b6..7a9a039c 100644 --- a/spec/core/asymmetricEqualityTesterArgCompatShimSpec.js +++ b/spec/core/asymmetricEqualityTesterArgCompatShimSpec.js @@ -36,7 +36,6 @@ describe('asymmetricEqualityTesterArgCompatShim', function() { it('provides properties of Array.prototype', function() { var keys = [ 'concat', - 'constructor', 'every', 'filter', 'forEach', @@ -55,8 +54,6 @@ describe('asymmetricEqualityTesterArgCompatShim', function() { 'some', 'sort', 'splice', - 'toLocaleString', - 'toString', 'unshift' ], optionalKeys = [ @@ -98,4 +95,49 @@ describe('asymmetricEqualityTesterArgCompatShim', function() { } } }); + + describe('When Array.prototype additions collide with MatchersUtil methods', function() { + function keys() { + return [ + 'contains', + 'buildFailureMessage', + 'asymmetricDiff_', + 'asymmetricMatch_', + 'equals', + 'eq_' + ]; + } + + beforeEach(function() { + keys().forEach(function(k) { + if (Array.prototype[k]) { + console.log(Array.prototype[k].toString()); + } + expect(Array.prototype[k]) + .withContext('Array.prototype already had ' + k) + .toBeUndefined(); + Array.prototype[k] = function() {}; + }); + }); + + afterEach(function() { + keys().forEach(function(k) { + delete Array.prototype[k]; + }); + }); + + it('uses the MatchersUtil methods', function() { + var matchersUtil = new jasmineUnderTest.MatchersUtil({}), + shim = jasmineUnderTest.asymmetricEqualityTesterArgCompatShim( + matchersUtil, + [] + ); + + keys().forEach(function(k) { + expect(shim[k]) + .withContext(k + ' was overwritten') + .toBe(jasmineUnderTest.MatchersUtil.prototype[k]); + }); + }); + }); }); diff --git a/src/core/asymmetricEqualityTesterArgCompatShim.js b/src/core/asymmetricEqualityTesterArgCompatShim.js index 162d9651..e487f3df 100644 --- a/src/core/asymmetricEqualityTesterArgCompatShim.js +++ b/src/core/asymmetricEqualityTesterArgCompatShim.js @@ -66,7 +66,9 @@ getJasmineRequireObj().asymmetricEqualityTesterArgCompatShim = function(j$) { for (i = 0; i < props.length; i++) { k = props[i]; - if (k !== 'length') { + // Skip length (dealt with above), and anything that collides with + // MatchesUtil e.g. an Array.prototype.contains method added by user code + if (k !== 'length' && !self[k]) { copy(self, Array.prototype, k); } } From 5a715aecee30eb7d553703ae194735d629ba0e05 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 1 Sep 2020 15:25:44 -0700 Subject: [PATCH 174/201] Removed unnecessary console.log --- spec/core/asymmetricEqualityTesterArgCompatShimSpec.js | 3 --- 1 file changed, 3 deletions(-) diff --git a/spec/core/asymmetricEqualityTesterArgCompatShimSpec.js b/spec/core/asymmetricEqualityTesterArgCompatShimSpec.js index 7a9a039c..34186c12 100644 --- a/spec/core/asymmetricEqualityTesterArgCompatShimSpec.js +++ b/spec/core/asymmetricEqualityTesterArgCompatShimSpec.js @@ -110,9 +110,6 @@ describe('asymmetricEqualityTesterArgCompatShim', function() { beforeEach(function() { keys().forEach(function(k) { - if (Array.prototype[k]) { - console.log(Array.prototype[k].toString()); - } expect(Array.prototype[k]) .withContext('Array.prototype already had ' + k) .toBeUndefined(); From 00feef8632a8b59ee44eb12aa28d9c9810b72c86 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 2 Sep 2020 09:31:35 -0700 Subject: [PATCH 175/201] Fixed global error handler stack corruption in Jasmine's own tests --- lib/jasmine-core/jasmine.js | 12 +- spec/core/EnvSpec.js | 44 +- spec/core/ExceptionsSpec.js | 6 +- .../AsymmetricEqualityTestersSpec.js | 8 +- .../integration/CustomAsyncMatchersSpec.js | 20 +- spec/core/integration/CustomMatchersSpec.js | 40 +- .../integration/CustomObjectFormatterSpec.js | 8 +- .../integration/CustomSpyStrategiesSpec.js | 27 +- .../integration/DefaultSpyStrategySpec.js | 12 +- spec/core/integration/EnvSpec.js | 1387 ++++++++--------- spec/core/integration/MatchersSpec.js | 24 +- spec/core/integration/SpecRunningSpec.js | 218 +-- src/core/Env.js | 9 +- src/core/QueueRunner.js | 3 + 14 files changed, 833 insertions(+), 985 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 5a8e11b4..8b449d97 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1661,7 +1661,8 @@ getJasmineRequireObj().Env = function(j$) { queueRunnerFactory ); - this.execute = function(runnablesToRun) { + // Both params are optional. + this.execute = function(runnablesToRun, onComplete) { installGlobalErrors(); if (!runnablesToRun) { @@ -1769,7 +1770,11 @@ getJasmineRequireObj().Env = function(j$) { failedExpectations: topSuite.result.failedExpectations, deprecationWarnings: topSuite.result.deprecationWarnings }, - function() {} + function() { + if (onComplete) { + onComplete(); + } + } ); }); } @@ -6917,6 +6922,8 @@ getJasmineRequireObj().makePrettyPrinter = function(j$) { }; getJasmineRequireObj().QueueRunner = function(j$) { + var nextid = 1; + function StopExecutionError() {} StopExecutionError.prototype = new Error(); j$.StopExecutionError = StopExecutionError; @@ -6936,6 +6943,7 @@ getJasmineRequireObj().QueueRunner = function(j$) { function emptyFn() {} function QueueRunner(attrs) { + this.id_ = nextid++; var queueableFns = attrs.queueableFns || []; this.queueableFns = queueableFns.concat(attrs.cleanupFns || []); this.firstCleanupIx = queueableFns.length; diff --git a/spec/core/EnvSpec.js b/spec/core/EnvSpec.js index e32d8eda..77ae38a2 100644 --- a/spec/core/EnvSpec.js +++ b/spec/core/EnvSpec.js @@ -334,20 +334,16 @@ describe('Env', function() { expectationFactory('actual', specInstance); }); - env.addReporter({ - jasmineDone: function() { - expect(jasmineUnderTest.makePrettyPrinter).toHaveBeenCalledWith([ - customObjectFormatter - ]); - expect(jasmineUnderTest.MatchersUtil).toHaveBeenCalledWith({ - customTesters: [customEqualityTester], - pp: prettyPrinter - }); - done(); - } + env.execute(null, function() { + expect(jasmineUnderTest.makePrettyPrinter).toHaveBeenCalledWith([ + customObjectFormatter + ]); + expect(jasmineUnderTest.MatchersUtil).toHaveBeenCalledWith({ + customTesters: [customEqualityTester], + pp: prettyPrinter + }); + done(); }); - - env.execute(); }); it('creates an asyncExpectationFactory that uses the current custom equality testers and object formatters', function(done) { @@ -371,19 +367,15 @@ describe('Env', function() { asyncExpectationFactory('actual', specInstance); }); - env.addReporter({ - jasmineDone: function() { - expect(jasmineUnderTest.makePrettyPrinter).toHaveBeenCalledWith([ - customObjectFormatter - ]); - expect(jasmineUnderTest.MatchersUtil).toHaveBeenCalledWith({ - customTesters: [customEqualityTester], - pp: prettyPrinter - }); - done(); - } + env.execute(null, function() { + expect(jasmineUnderTest.makePrettyPrinter).toHaveBeenCalledWith([ + customObjectFormatter + ]); + expect(jasmineUnderTest.MatchersUtil).toHaveBeenCalledWith({ + customTesters: [customEqualityTester], + pp: prettyPrinter + }); + done(); }); - - env.execute(); }); }); diff --git a/spec/core/ExceptionsSpec.js b/spec/core/ExceptionsSpec.js index c5e65754..d950d2e2 100644 --- a/spec/core/ExceptionsSpec.js +++ b/spec/core/ExceptionsSpec.js @@ -29,8 +29,7 @@ describe('Exceptions:', function() { done(); }; - env.addReporter({ jasmineDone: expectations }); - env.execute(); + env.execute(null, expectations); }); it('should handle exceptions thrown directly in top-level describe blocks and continue', function(done) { @@ -49,7 +48,6 @@ describe('Exceptions:', function() { done(); }; - env.addReporter({ jasmineDone: expectations }); - env.execute(); + env.execute(null, expectations); }); }); diff --git a/spec/core/integration/AsymmetricEqualityTestersSpec.js b/spec/core/integration/AsymmetricEqualityTestersSpec.js index 1ccf2801..518c5bde 100644 --- a/spec/core/integration/AsymmetricEqualityTestersSpec.js +++ b/spec/core/integration/AsymmetricEqualityTestersSpec.js @@ -19,8 +19,8 @@ describe('Asymmetric equality testers (Integration)', function () { .toBeUndefined(); }; - env.addReporter({specDone: specExpectations, jasmineDone: done}); - env.execute(); + env.addReporter({specDone: specExpectations}); + env.execute(null, done); }); } @@ -43,8 +43,8 @@ describe('Asymmetric equality testers (Integration)', function () { .not.toEqual(''); }; - env.addReporter({specDone: specExpectations, jasmineDone: done}); - env.execute(); + env.addReporter({specDone: specExpectations}); + env.execute(null, done); }); } diff --git a/spec/core/integration/CustomAsyncMatchersSpec.js b/spec/core/integration/CustomAsyncMatchersSpec.js index 1b60bb45..4e97185f 100644 --- a/spec/core/integration/CustomAsyncMatchersSpec.js +++ b/spec/core/integration/CustomAsyncMatchersSpec.js @@ -28,8 +28,8 @@ describe('Custom Async Matchers (Integration)', function() { expect(result.status).toEqual('passed'); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); it('uses the negative compare function for a negative comparison, if provided', function(done) { @@ -52,8 +52,8 @@ describe('Custom Async Matchers (Integration)', function() { expect(result.status).toEqual('passed'); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); it('generates messages with the same rules as built in matchers absent a custom message', function(done) { @@ -77,8 +77,8 @@ describe('Custom Async Matchers (Integration)', function() { expect(result.failedExpectations[0].message).toEqual("Expected 'a' to be real."); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); // TODO: remove this in the next major release. @@ -113,8 +113,8 @@ describe('Custom Async Matchers (Integration)', function() { ); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); it("provides custom equality testers to the matcher factory via matchersUtil", function(done) { @@ -145,7 +145,7 @@ describe('Custom Async Matchers (Integration)', function() { expect(result.failedExpectations).toEqual([]); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); }); diff --git a/spec/core/integration/CustomMatchersSpec.js b/spec/core/integration/CustomMatchersSpec.js index c9812949..c299c6ac 100644 --- a/spec/core/integration/CustomMatchersSpec.js +++ b/spec/core/integration/CustomMatchersSpec.js @@ -37,9 +37,9 @@ describe("Custom Matchers (Integration)", function () { expect(firstSpecResult.failedExpectations[0].message).toEqual("matcherForSpec: actual: zzz; expected: yyy"); done(); }; - env.addReporter({ specDone:specDoneSpy, jasmineDone: expectations}); + env.addReporter({ specDone:specDoneSpy }); - env.execute(); + env.execute(null, expectations); }); it("passes the spec if the custom matcher passes", function(done) { @@ -57,8 +57,8 @@ describe("Custom Matchers (Integration)", function () { expect(result.status).toEqual('passed'); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); it("passes the spec if the custom equality matcher passes for types nested inside asymmetric equality testers", function(done) { @@ -81,8 +81,8 @@ describe("Custom Matchers (Integration)", function () { expect(result.status).toEqual('passed'); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); it("supports asymmetric equality testers that take a list of custom equality testers", function(done) { @@ -111,8 +111,8 @@ describe("Custom Matchers (Integration)", function () { expect(result.status).toEqual('passed'); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); it("displays an appropriate failure message if a custom equality matcher fails", function(done) { @@ -135,8 +135,8 @@ describe("Custom Matchers (Integration)", function () { ); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); it("uses the negative compare function for a negative comparison, if provided", function(done) { @@ -157,8 +157,8 @@ describe("Custom Matchers (Integration)", function () { expect(result.status).toEqual('passed'); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); it("generates messages with the same rules as built in matchers absent a custom message", function(done) { @@ -180,8 +180,8 @@ describe("Custom Matchers (Integration)", function () { expect(result.failedExpectations[0].message).toEqual("Expected 'a' to be real."); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); it("passes the expected and actual arguments to the comparison function", function(done) { @@ -205,8 +205,8 @@ describe("Custom Matchers (Integration)", function () { expect(argumentSpy).toHaveBeenCalledWith(true, "arg1", "arg2"); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); // TODO: remove this in the next major release. @@ -232,8 +232,8 @@ describe("Custom Matchers (Integration)", function () { ); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); it("provides custom equality testers to the matcher factory via matchersUtil", function (done) { @@ -262,7 +262,7 @@ describe("Custom Matchers (Integration)", function () { expect(result.failedExpectations).toEqual([]); }; - env.addReporter({specDone: specExpectations, jasmineDone: done}); - env.execute(); + env.addReporter({specDone: specExpectations}); + env.execute(null, done); }); }); diff --git a/spec/core/integration/CustomObjectFormatterSpec.js b/spec/core/integration/CustomObjectFormatterSpec.js index 10ed4d71..3337f452 100644 --- a/spec/core/integration/CustomObjectFormatterSpec.js +++ b/spec/core/integration/CustomObjectFormatterSpec.js @@ -25,9 +25,9 @@ describe("Custom object formatters", function() { expect(specResults[1].failedExpectations[0].message).toEqual("Expected 42 to be undefined."); done(); }; - env.addReporter({ specDone:specDone, jasmineDone: expectations}); + env.addReporter({ specDone:specDone }); - env.execute(); + env.execute(null, expectations); }); it("scopes custom object formatters to a suite", function(done) { @@ -54,9 +54,9 @@ describe("Custom object formatters", function() { expect(specResults[1].failedExpectations[0].message).toEqual("Expected custom(42) to be undefined."); done(); }; - env.addReporter({ specDone:specDone, jasmineDone: expectations}); + env.addReporter({ specDone:specDone }); - env.execute(); + env.execute(null, expectations); }); it("throws an exception if you try to add a custom object formatter outside a runable", function() { diff --git a/spec/core/integration/CustomSpyStrategiesSpec.js b/spec/core/integration/CustomSpyStrategiesSpec.js index 7ab4d28d..e05b0773 100644 --- a/spec/core/integration/CustomSpyStrategiesSpec.js +++ b/spec/core/integration/CustomSpyStrategiesSpec.js @@ -15,6 +15,7 @@ describe('Custom Spy Strategies (Integration)', function() { .and.returnValue(42); var strategy = jasmine.createSpy('custom strategy') .and.returnValue(plan); + var jasmineDone = jasmine.createSpy('jasmineDone'); env.describe('suite defining a custom spy strategy', function() { env.beforeEach(function() { @@ -33,13 +34,14 @@ describe('Custom Spy Strategies (Integration)', function() { expect(env.createSpy('something').and.frobnicate).toBeUndefined(); }); - function jasmineDone(result) { + function expectations() { + var result = jasmineDone.calls.argsFor(0)[0]; expect(result.overallStatus).toEqual('passed'); done(); } env.addReporter({ jasmineDone: jasmineDone }); - env.execute(); + env.execute(null, expectations); }); it('allows adding more strategies local to a spec', function(done) { @@ -47,6 +49,7 @@ describe('Custom Spy Strategies (Integration)', function() { .and.returnValue(42); var strategy = jasmine.createSpy('custom strategy') .and.returnValue(plan); + var jasmineDone = jasmine.createSpy('jasmineDone'); env.it('spec defining a custom spy strategy', function() { env.addSpyStrategy('frobnicate', strategy); @@ -60,13 +63,14 @@ describe('Custom Spy Strategies (Integration)', function() { expect(env.createSpy('something').and.frobnicate).toBeUndefined(); }); - function jasmineDone(result) { + function expectations() { + var result = jasmineDone.calls.argsFor(0)[0]; expect(result.overallStatus).toEqual('passed'); done(); } env.addReporter({ jasmineDone: jasmineDone }); - env.execute(); + env.execute(null, expectations); }); it('allows using custom strategies on a per-argument basis', function(done) { @@ -74,6 +78,7 @@ describe('Custom Spy Strategies (Integration)', function() { .and.returnValue(42); var strategy = jasmine.createSpy('custom strategy') .and.returnValue(plan); + var jasmineDone = jasmine.createSpy('jasmineDone'); env.it('spec defining a custom spy strategy', function() { env.addSpyStrategy('frobnicate', strategy); @@ -91,13 +96,14 @@ describe('Custom Spy Strategies (Integration)', function() { expect(env.createSpy('something').and.frobnicate).toBeUndefined(); }); - function jasmineDone(result) { + function expectations() { + var result = jasmineDone.calls.argsFor(0)[0]; expect(result.overallStatus).toEqual('passed'); done(); } env.addReporter({ jasmineDone: jasmineDone }); - env.execute(); + env.execute(null, expectations); }); it('allows multiple custom strategies to be used', function(done) { @@ -105,7 +111,9 @@ describe('Custom Spy Strategies (Integration)', function() { strategy1 = jasmine.createSpy('strat 1').and.returnValue(plan1), plan2 = jasmine.createSpy('plan 2').and.returnValue(24), strategy2 = jasmine.createSpy('strat 2').and.returnValue(plan2), - specDone = jasmine.createSpy('specDone'); + specDone = jasmine.createSpy('specDone'), + jasmineDone = jasmine.createSpy('jasmineDone'); + env.beforeEach(function() { env.addSpyStrategy('frobnicate', strategy1); @@ -130,13 +138,14 @@ describe('Custom Spy Strategies (Integration)', function() { expect(plan2).toHaveBeenCalled(); }); - function jasmineDone(result) { + function expectations() { + var result = jasmineDone.calls.argsFor(0)[0]; expect(result.overallStatus).toEqual('passed'); expect(specDone.calls.count()).toBe(2); done(); } env.addReporter({ jasmineDone: jasmineDone, specDone: specDone }); - env.execute(); + env.execute(null, expectations); }); }); diff --git a/spec/core/integration/DefaultSpyStrategySpec.js b/spec/core/integration/DefaultSpyStrategySpec.js index 584b25b2..50a11544 100644 --- a/spec/core/integration/DefaultSpyStrategySpec.js +++ b/spec/core/integration/DefaultSpyStrategySpec.js @@ -29,13 +29,15 @@ describe('Default Spy Strategy (Integration)', function() { expect(spy()).toBeUndefined(); }); - function jasmineDone(result) { + function expectations() { + var result = jasmineDone.calls.argsFor(0)[0]; expect(result.overallStatus).toEqual('passed'); done(); } + var jasmineDone = jasmine.createSpy('jasmineDone'); env.addReporter({ jasmineDone: jasmineDone }); - env.execute(); + env.execute(null, expectations); }); it('uses the default spy strategy defined when the spy is created', function (done) { @@ -61,12 +63,14 @@ describe('Default Spy Strategy (Integration)', function() { expect(d.and.isConfigured()).toBe(false); }); - function jasmineDone(result) { + function expectations() { + var result = jasmineDone.calls.argsFor(0)[0]; expect(result.overallStatus).toEqual('passed'); done(); } + var jasmineDone = jasmine.createSpy('jasmineDone'); env.addReporter({ jasmineDone: jasmineDone }); - env.execute(); + env.execute(null, expectations); }); }); diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index ae7cd0d6..cf1e997d 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -22,7 +22,6 @@ describe("Env integration", function() { done(); }; - env.addReporter({ jasmineDone: assertions}); env.configure({random: false}); env.describe("A Suite", function() { @@ -34,7 +33,7 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, assertions); }); it("Nested Suites execute as expected", function(done) { @@ -50,7 +49,6 @@ describe("Env integration", function() { done(); }; - env.addReporter({ jasmineDone: assertions }); env.configure({random: false}); env.describe("Outer suite", function() { @@ -67,7 +65,7 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, assertions); }); it("Multiple top-level Suites execute as expected", function(done) { @@ -84,7 +82,6 @@ describe("Env integration", function() { done(); }; - env.addReporter({ jasmineDone: assertions }); env.configure({random: false}); @@ -108,57 +105,13 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, assertions); }); it('explicitly fails a spec', function(done) { var specDone = jasmine.createSpy('specDone'); - env.addReporter({ - specDone: specDone, - jasmineDone: function() { - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'has a default message', - failedExpectations: [jasmine.objectContaining({ - message: 'Failed' - })] - })); - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'specifies a message', - failedExpectations: [jasmine.objectContaining({ - message: 'Failed: messy message' - })] - })); - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'has a message and stack trace from an Error', - failedExpectations: [jasmine.objectContaining({ - message: 'Failed: error message', - stack: { - asymmetricMatch: function(other) { - if (!other) { - // IE doesn't give us a stacktrace so just ignore it. - return true; - } - var split = other.split('\n'), - firstLine = split[0]; - if (firstLine.indexOf('error message') >= 0) { - // Chrome inserts the message and a newline before the first stacktrace line. - firstLine = split[1]; - } - return firstLine.indexOf('EnvSpec') >= 0; - } - } - })] - })); - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'pretty prints objects', - failedExpectations: [jasmine.objectContaining({ - message: 'Failed: Object({ prop: \'value\', arr: [ \'works\', true ] })' - })] - })); - done(); - } - }); + env.addReporter({specDone: specDone}); env.describe('failing', function() { env.it('has a default message', function() { @@ -178,15 +131,51 @@ describe("Env integration", function() { }) }); - env.execute(); + env.execute(null, function() { + expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ + description: 'has a default message', + failedExpectations: [jasmine.objectContaining({ + message: 'Failed' + })] + })); + expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ + description: 'specifies a message', + failedExpectations: [jasmine.objectContaining({ + message: 'Failed: messy message' + })] + })); + expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ + description: 'has a message and stack trace from an Error', + failedExpectations: [jasmine.objectContaining({ + message: 'Failed: error message', + stack: { + asymmetricMatch: function(other) { + if (!other) { + // IE doesn't give us a stacktrace so just ignore it. + return true; + } + var split = other.split('\n'), + firstLine = split[0]; + if (firstLine.indexOf('error message') >= 0) { + // Chrome inserts the message and a newline before the first stacktrace line. + firstLine = split[1]; + } + return firstLine.indexOf('EnvSpec') >= 0; + } + } + })] + })); + expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ + description: 'pretty prints objects', + failedExpectations: [jasmine.objectContaining({ + message: 'Failed: Object({ prop: \'value\', arr: [ \'works\', true ] })' + })] + })); + done(); + }); }); it("produces an understandable error message when 'fail' is used outside of a current spec", function(done) { - var reporter = jasmine.createSpyObj('fakeReporter', ['jasmineDone']); - - reporter.jasmineDone.and.callFake(done); - env.addReporter(reporter); - env.describe("A Suite", function() { env.it("an async spec that is actually synchronous", function(underTestCallback) { underTestCallback(); @@ -194,12 +183,11 @@ describe("Env integration", function() { expect(function() { env.fail(); }).toThrowError(/'fail' was used when there was no current spec/); }); - env.execute(); + env.execute(null, done); }); it("calls associated befores/specs/afters with the same 'this'", function(done) { - env.addReporter({jasmineDone: done}); env.configure({random: false}); env.describe("tests", function() { var firstTimeThrough = true, firstSpecContext, secondSpecContext; @@ -231,12 +219,10 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, done); }); it("calls associated befores/its/afters with the same 'this' for an async spec", function(done) { - env.addReporter({jasmineDone: done}); - env.describe("with an async spec", function() { var specContext; @@ -255,22 +241,13 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, done); }); it("calls associated beforeAlls/afterAlls only once per suite", function(done) { var before = jasmine.createSpy('beforeAll'), after = jasmine.createSpy('afterAll'); - env.addReporter({ - jasmineDone: function() { - expect(after).toHaveBeenCalled(); - expect(after.calls.count()).toBe(1); - expect(before.calls.count()).toBe(1); - done(); - } - }); - env.describe("with beforeAll and afterAll", function() { env.it("spec", function() { expect(before).toHaveBeenCalled(); @@ -286,22 +263,18 @@ describe("Env integration", function() { env.afterAll(after); }); - env.execute(); + env.execute(null, function() { + expect(after).toHaveBeenCalled(); + expect(after.calls.count()).toBe(1); + expect(before.calls.count()).toBe(1); + done(); + }); }); it("calls associated beforeAlls/afterAlls only once per suite for async", function(done) { var before = jasmine.createSpy('beforeAll'), after = jasmine.createSpy('afterAll'); - env.addReporter({ - jasmineDone: function() { - expect(after).toHaveBeenCalled(); - expect(after.calls.count()).toBe(1); - expect(before.calls.count()).toBe(1); - done(); - } - }); - env.describe("with beforeAll and afterAll", function() { env.it("spec", function() { expect(before).toHaveBeenCalled(); @@ -324,12 +297,15 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, function() { + expect(after).toHaveBeenCalled(); + expect(after.calls.count()).toBe(1); + expect(before.calls.count()).toBe(1); + done(); + }); }); it("calls associated beforeAlls/afterAlls with the cascaded 'this'", function(done) { - env.addReporter({jasmineDone: done}); - env.describe("with beforeAll and afterAll", function() { env.beforeAll(function() { this.x = 1; @@ -376,14 +352,11 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, done); }); it("tags top-level afterAll failures with a type", function(done) { - env.addReporter({jasmineDone: function(result) { - expect(result.failedExpectations[0].globalErrorType).toEqual('afterAll'); - done(); - }}); + var jasmineDone = jasmine.createSpy('jasmineDone'); env.it('has a spec', function() {}); @@ -391,20 +364,22 @@ describe("Env integration", function() { throw 'nope'; }); - env.execute(); + env.addReporter({ jasmineDone: jasmineDone }); + env.execute(null, function() {{ + var result = jasmineDone.calls.argsFor(0)[0]; + expect(result.failedExpectations[0].globalErrorType).toEqual('afterAll'); + done(); + }}); }); it("does not tag suite afterAll failures with a type", function(done) { var reporter = { - jasmineDone: function() { - expect(reporter.suiteDone).toHaveBeenCalled(); - done(); - }, suiteDone: jasmine.createSpy('suiteDone').and.callFake(function(result) { expect(result.failedExpectations[0].globalErrorType).toBeFalsy(); }) }; + env.addReporter(reporter); env.describe('a suite', function() { @@ -415,20 +390,23 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, function() { + expect(reporter.suiteDone).toHaveBeenCalled(); + done(); + }); }); it("when the beforeAll fails, error at suite level", function (done) { - var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "suiteDone", "jasmineDone" ]); + var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "suiteDone" ]); - reporter.jasmineDone.and.callFake(function() { + var assertions = function() { expect(reporter.specDone.calls.count()).toEqual(2); expect(reporter.specDone).toHaveFailedExpectationsForRunnable('A suite spec that will pass', []); expect(reporter.specDone).toHaveFailedExpectationsForRunnable('A suite nesting another spec to pass', []); expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('A suite', ['Expected 1 to be 2.']); done(); - }); + }; env.addReporter(reporter); @@ -446,7 +424,7 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, assertions); }); it("copes with async failures after done has been called", function(done) { @@ -457,13 +435,13 @@ describe("Env integration", function() { spyOn(jasmineUnderTest, 'getGlobal').and.returnValue(global); env.cleanup_(); env = new jasmineUnderTest.Env(); - var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "jasmineDone", "suiteDone" ]); + var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "suiteDone" ]); - reporter.jasmineDone.and.callFake(function() { + var assertions = function() { expect(reporter.specDone).not.toHaveFailedExpectationsForRunnable('A suite fails', ['fail thrown']); expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('A suite', ['fail thrown']); done(); - }); + }; env.addReporter(reporter); @@ -484,20 +462,20 @@ describe("Env integration", function() { env.it('is not run', function() {}); }); - env.execute(); + env.execute(null, assertions); }); describe('suiteDone reporting', function(){ it("reports when an afterAll fails an expectation", function(done) { - var reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); + var reporter = jasmine.createSpyObj('fakeReport', ['suiteDone']); - reporter.jasmineDone.and.callFake(function() { + var assertions = function() { expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('my suite', [ 'Expected 1 to equal 2.', 'Expected 2 to equal 3.' ]); done(); - }); + }; env.addReporter(reporter); @@ -511,19 +489,19 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, assertions); }); it("if there are no specs, it still reports correctly", function(done) { - var reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); + var reporter = jasmine.createSpyObj('fakeReport', ['suiteDone']); - reporter.jasmineDone.and.callFake(function() { + var assertions = function() { expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('outer suite', [ 'Expected 1 to equal 2.', 'Expected 2 to equal 3.' ]); done(); - }); + }; env.addReporter(reporter); @@ -538,19 +516,19 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, assertions); }); it("reports when afterAll throws an exception", function(done) { var error = new Error('After All Exception'), - reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); + reporter = jasmine.createSpyObj('fakeReport', ['suiteDone']); - reporter.jasmineDone.and.callFake(function() { + var assertions = function() { expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('my suite', [ (/^Error: After All Exception/) ]); done(); - }); + }; env.addReporter(reporter); @@ -563,18 +541,18 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, assertions); }); it("reports when an async afterAll fails an expectation", function(done) { - var reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); + var reporter = jasmine.createSpyObj('fakeReport', ['suiteDone']); - reporter.jasmineDone.and.callFake(function() { + var assertions = function() { expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('my suite', [ 'Expected 1 to equal 2.' ]); done(); - }); + }; env.addReporter(reporter); @@ -588,20 +566,20 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, assertions); }); it("reports when an async afterAll throws an exception", function(done) { var error = new Error('After All Exception'), - reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone']); + reporter = jasmine.createSpyObj('fakeReport', ['suiteDone']); - reporter.jasmineDone.and.callFake(function() { + var assertions = function() { expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('my suite', [ (/^Error: After All Exception/) ]); done(); - }); + }; env.addReporter(reporter); @@ -614,7 +592,7 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, assertions); }); it('reports the duration of the suite', function(done) { @@ -624,10 +602,6 @@ describe("Env integration", function() { suiteDone: function(result) { expect(duration).toBeUndefined(); duration = result.duration; - }, - jasmineDone: function() { - expect(duration).toBeGreaterThanOrEqual(10); - done(); } }); @@ -639,7 +613,10 @@ describe("Env integration", function() { }) }); - env.execute(); + env.execute(null, function() { + expect(duration).toBeGreaterThanOrEqual(10); + done(); + }); }); }); @@ -651,10 +628,6 @@ describe("Env integration", function() { specDone: function(result) { expect(duration).toBeUndefined(); duration = result.duration; - }, - jasmineDone: function() { - expect(duration).toBeGreaterThanOrEqual(10); - done(); } }); @@ -666,19 +639,16 @@ describe("Env integration", function() { }) }); - env.execute(); + env.execute(null, function() { + expect(duration).toBeGreaterThanOrEqual(10); + done(); + }); }); }); it('reports expectation failures in global beforeAll', function(done) { var reporter = jasmine.createSpyObj(['specDone', 'jasmineDone']); - reporter.jasmineDone.and.callFake(function(results) { - expect(results.failedExpectations).toEqual([jasmine.objectContaining({ message: 'Expected 1 to be 0.' })]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('is a spec', []); - done(); - }); - env.beforeAll(function() { env.expect(1).toBe(0); }); @@ -689,17 +659,17 @@ describe("Env integration", function() { env.addReporter(reporter); - env.execute(); + env.execute(null, function() { + var results = reporter.jasmineDone.calls.argsFor(0)[0]; + expect(results.failedExpectations).toEqual([jasmine.objectContaining({ message: 'Expected 1 to be 0.' })]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('is a spec', []); + done(); + }); }); it('reports expectation failures in global afterAll', function(done) { var reporter = jasmine.createSpyObj(['jasmineDone']); - reporter.jasmineDone.and.callFake(function(results) { - expect(results.failedExpectations).toEqual([jasmine.objectContaining({ message: 'Expected 1 to be 0.' })]); - done(); - }); - env.afterAll(function() { env.expect(1).toBe(0); }); @@ -710,7 +680,11 @@ describe("Env integration", function() { env.addReporter(reporter); - env.execute(); + env.execute(null, function() { + var results = reporter.jasmineDone.calls.argsFor(0)[0]; + expect(results.failedExpectations).toEqual([jasmine.objectContaining({ message: 'Expected 1 to be 0.' })]); + done(); + }); }); it("Allows specifying which specs and suites to run", function(done) { @@ -719,16 +693,7 @@ describe("Env integration", function() { firstSpec, secondSuite; - var assertions = function() { - expect(calls).toEqual([ - 'third spec', - 'first spec' - ]); - expect(suiteCallback).toHaveBeenCalled(); - done(); - }; - - env.addReporter({jasmineDone: assertions, suiteDone: suiteCallback}); + env.addReporter({ suiteDone: suiteCallback}); env.describe("first suite", function() { firstSpec = env.it("first spec", function() { @@ -745,7 +710,14 @@ describe("Env integration", function() { }); }); - env.execute([secondSuite.id, firstSpec.id]); + env.execute([secondSuite.id, firstSpec.id], function() { + expect(calls).toEqual([ + 'third spec', + 'first spec' + ]); + expect(suiteCallback).toHaveBeenCalled(); + done(); + }); }); it('runs before and after all functions for runnables provided to .execute()', function(done) { @@ -753,18 +725,6 @@ describe("Env integration", function() { first_spec, second_spec; - var assertions = function() { - expect(calls).toEqual([ - "before", - "first spec", - "second spec", - "after" - ]); - done(); - }; - - env.addReporter({jasmineDone: assertions}); - env.describe("first suite", function() { env.beforeAll(function() { calls.push("before"); @@ -780,7 +740,15 @@ describe("Env integration", function() { }); }); - env.execute([first_spec.id, second_spec.id]); + env.execute([first_spec.id, second_spec.id], function() { + expect(calls).toEqual([ + "before", + "first spec", + "second spec", + "after" + ]); + done(); + }); }); it("Allows filtering out specs and suites to run programmatically", function(done) { @@ -789,17 +757,7 @@ describe("Env integration", function() { firstSpec, secondSuite; - var assertions = function() { - expect(calls.length).toEqual(2); - expect(calls).toEqual(jasmine.arrayContaining([ - 'first spec', - 'second spec' - ])); - expect(suiteCallback).toHaveBeenCalled(); - done(); - }; - - env.addReporter({jasmineDone: assertions, suiteDone: suiteCallback}); + env.addReporter({suiteDone: suiteCallback}); env.describe("first suite", function() { env.it("first spec", function() { @@ -822,7 +780,15 @@ describe("Env integration", function() { } }); - env.execute(); + env.execute(null, function() { + expect(calls.length).toEqual(2); + expect(calls).toEqual(jasmine.arrayContaining([ + 'first spec', + 'second spec' + ])); + expect(suiteCallback).toHaveBeenCalled(); + done(); + }); }); it("Functions can be spied on and have their calls tracked", function (done) { @@ -834,8 +800,6 @@ describe("Env integration", function() { } }; - env.addReporter({jasmineDone: done}); - env.it("works with spies", function() { var spy = env.spyOn(subject, 'spiedFunc').and.returnValue("stubbed result"); @@ -885,7 +849,7 @@ describe("Env integration", function() { }).toThrowError('You must use the new keyword.'); }); - env.execute(); + env.execute(null, done); }); it('can be configured to allow respying on functions', function (done) { @@ -896,7 +860,6 @@ describe("Env integration", function() { }; env.allowRespy(true); - env.addReporter({ jasmineDone: done }); env.describe('test suite', function() { env.it('spec 0', function() { @@ -910,7 +873,7 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, done); }); it('removes all spies added in a spec after the spec is complete', function(done) { @@ -929,15 +892,11 @@ describe("Env integration", function() { env.it('spec 1', secondSpec); }); - var assertions = function() { + env.execute(null, function() { expect(firstSpec).toHaveBeenCalled(); expect(secondSpec).toHaveBeenCalled(); done(); - }; - - env.addReporter({ jasmineDone: assertions }); - - env.execute(); + }); }); it('removes all spies added in a suite after the suite is complete', function(done) { @@ -964,9 +923,7 @@ describe("Env integration", function() { }); }); - env.addReporter({ jasmineDone: done }); - - env.execute(); + env.execute(null, done); }); it('removes a spy from the top suite after the run is complete', function(done) { @@ -983,14 +940,10 @@ describe("Env integration", function() { expect(jasmineUnderTest.isSpy(testObj.foo)).toBe(true); }); - env.addReporter({ - jasmineDone: function() { - expect(jasmineUnderTest.isSpy(testObj.foo)).toBe(false); - done(); - } + env.execute(null, function() { + expect(jasmineUnderTest.isSpy(testObj.foo)).toBe(false); + done(); }); - - env.execute(); }); it("Mock clock can be installed and used in tests", function(done) { @@ -1001,14 +954,6 @@ describe("Env integration", function() { env.cleanup_(); env = new jasmineUnderTest.Env({global: { setTimeout: globalSetTimeout, clearTimeout: clearTimeout, setImmediate: function(cb) { setTimeout(cb, 0); } }}); - var assertions = function() { - expect(delayedFunctionForMockClock).toHaveBeenCalled(); - expect(globalSetTimeout).toHaveBeenCalledWith(delayedFunctionForGlobalClock, 100); - - done(); - }; - - env.addReporter({ jasmineDone: assertions }); env.configure({random: false}); env.describe("tests", function() { @@ -1026,17 +971,16 @@ describe("Env integration", function() { expect(globalSetTimeout).not.toHaveBeenCalled(); expect(delayedFunctionForMockClock).not.toHaveBeenCalled(); - env.execute(); + env.execute(null, function() { + expect(delayedFunctionForMockClock).toHaveBeenCalled(); + expect(globalSetTimeout).toHaveBeenCalledWith(delayedFunctionForGlobalClock, 100); + + done(); + }); }); it("should run async specs in order, waiting for them to complete", function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone']), - mutatedVar; - - reporter.jasmineDone.and.callFake(function() { - done(); - }); - env.addReporter(reporter); + var mutatedVar; env.describe("tests", function() { env.beforeEach(function() { @@ -1055,7 +999,7 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, done); }); describe("with a mock clock", function() { @@ -1068,9 +1012,9 @@ describe("Env integration", function() { setTimeout: function(cb, t) { var stack = jasmine.util.errorWithStack().stack; if (stack.indexOf('ClearStack') >= 0) { - realSetTimeout(cb, t); + return realSetTimeout(cb, t); } else { - setTimeout(cb, t); + return setTimeout(cb, t); } }, clearTimeout: clearTimeout, @@ -1095,7 +1039,7 @@ describe("Env integration", function() { it("should wait a default interval before failing specs that haven't called done yet", function(done) { createMockedEnv(); - var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "jasmineDone" ]); + var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone" ]); reporter.specDone.and.callFake(function(result) { expect(result).toEqual(jasmine.objectContaining({status: 'failed'})); @@ -1104,12 +1048,6 @@ describe("Env integration", function() { }, 0); }); - reporter.jasmineDone.and.callFake(function() { - expect(reporter.specDone.calls.count()).toEqual(1); - jasmine.clock().tick(1); - realSetTimeout(done); - }); - env.addReporter(reporter); jasmineUnderTest.DEFAULT_TIMEOUT_INTERVAL = 8414; @@ -1119,12 +1057,16 @@ describe("Env integration", function() { jasmine.clock().tick(1); }); - env.execute(); + env.execute(null, function() { + expect(reporter.specDone.calls.count()).toEqual(1); + jasmine.clock().tick(1); + realSetTimeout(done); + }); }); it("should not use the mock clock for asynchronous timeouts", function(done){ createMockedEnv(); - var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "jasmineDone" ]), + var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone" ]), clock = env.clock; reporter.specDone.and.callFake(function() { @@ -1133,13 +1075,6 @@ describe("Env integration", function() { }, 0); }); - reporter.jasmineDone.and.callFake(function() { - expect(reporter.specDone).toHaveBeenCalledTimes(1); - expect(reporter.specDone.calls.argsFor(0)[0]).toEqual(jasmine.objectContaining({status: 'passed'})); - jasmine.clock().tick(1); - realSetTimeout(done); - }); - env.addReporter(reporter); jasmineUnderTest.DEFAULT_TIMEOUT_INTERVAL = 5; @@ -1157,25 +1092,18 @@ describe("Env integration", function() { realSetTimeout(innerDone); }); - env.execute(); + env.execute(null, function() { + expect(reporter.specDone).toHaveBeenCalledTimes(1); + expect(reporter.specDone.calls.argsFor(0)[0]).toEqual(jasmine.objectContaining({status: 'passed'})); + jasmine.clock().tick(1); + realSetTimeout(done); + }); }); it('should wait a custom interval before reporting async functions that fail to complete', function(done) { createMockedEnv(); var reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(r) { - expect(r.failedExpectations).toEqual([]); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('suite beforeAll', [ /^Error: Timeout - Async function did not complete within 5000ms \(custom timeout\)/ ]); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('suite afterAll', [ /^Error: Timeout - Async function did not complete within 2000ms \(custom timeout\)/ ]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite beforeEach times out', [/^Error: Timeout - Async function did not complete within 1000ms \(custom timeout\)/]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite afterEach times out', [ /^Error: Timeout - Async function did not complete within 4000ms \(custom timeout\)/ ]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite it times out', [ /^Error: Timeout - Async function did not complete within 6000ms \(custom timeout\)/ ]); - - jasmine.clock().tick(1); - realSetTimeout(done); - }); - env.addReporter(reporter); jasmineUnderTest.DEFAULT_TIMEOUT_INTERVAL = 10000; @@ -1256,35 +1184,25 @@ describe("Env integration", function() { }, 6000); }); - env.execute(); + env.execute(null, function() { + var r = reporter.jasmineDone.calls.argsFor(0)[0]; + expect(r.failedExpectations).toEqual([]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('suite beforeAll', [ /^Error: Timeout - Async function did not complete within 5000ms \(custom timeout\)/ ]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('suite afterAll', [ /^Error: Timeout - Async function did not complete within 2000ms \(custom timeout\)/ ]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite beforeEach times out', [/^Error: Timeout - Async function did not complete within 1000ms \(custom timeout\)/]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite afterEach times out', [ /^Error: Timeout - Async function did not complete within 4000ms \(custom timeout\)/ ]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite it times out', [ /^Error: Timeout - Async function did not complete within 6000ms \(custom timeout\)/ ]); + + jasmine.clock().tick(1); + realSetTimeout(done); + }); }); }); it('explicitly fails an async spec', function(done) { var specDone = jasmine.createSpy('specDone'); - env.addReporter({ - specDone: specDone, - jasmineDone: function() { - expect(specDone).toHaveFailedExpectationsForRunnable('failing has a default message', - ['Failed'] - ); - expect(specDone).toHaveFailedExpectationsForRunnable('failing specifies a message', - ['Failed: messy message'] - ); - expect(specDone).toHaveFailedExpectationsForRunnable('failing fails via the done callback', - ['Failed: done failed'] - ); - expect(specDone).toHaveFailedExpectationsForRunnable('failing has a message from an Error', - ['Failed: error message'] - ); - expect(specDone).toHaveFailedExpectationsForRunnable('failing has a message from an Error to done', - ['Failed: done error'] - ); - - setTimeout(done); - } - }); + env.addReporter({specDone: specDone}); env.describe('failing', function() { env.it('has a default message', function(innerDone) { @@ -1321,20 +1239,31 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, function() { + expect(specDone).toHaveFailedExpectationsForRunnable('failing has a default message', + ['Failed'] + ); + expect(specDone).toHaveFailedExpectationsForRunnable('failing specifies a message', + ['Failed: messy message'] + ); + expect(specDone).toHaveFailedExpectationsForRunnable('failing fails via the done callback', + ['Failed: done failed'] + ); + expect(specDone).toHaveFailedExpectationsForRunnable('failing has a message from an Error', + ['Failed: error message'] + ); + expect(specDone).toHaveFailedExpectationsForRunnable('failing has a message from an Error to done', + ['Failed: done error'] + ); + + setTimeout(done); + }); }); describe('focused tests', function() { it('should only run the focused tests', function(done) { var calls = []; - var assertions = function() { - expect(calls).toEqual(['focused']); - done(); - }; - - env.addReporter({jasmineDone: assertions}); - env.describe('a suite', function() { env.fit('is focused', function() { calls.push('focused'); @@ -1345,19 +1274,15 @@ describe("Env integration", function() { }) }); - env.execute(); + env.execute(null, function() { + expect(calls).toEqual(['focused']); + done(); + }); }); it('should only run focused suites', function(done){ var calls = []; - var assertions = function() { - expect(calls).toEqual(['focused']); - done(); - }; - - env.addReporter({jasmineDone: assertions}); - env.fdescribe('a focused suite', function() { env.it('is focused', function() { calls.push('focused'); @@ -1370,20 +1295,30 @@ describe("Env integration", function() { }) }); - env.execute(); + env.execute(null, function() { + expect(calls).toEqual(['focused']); + done(); + }); }); it('should run focused tests inside an xdescribe', function(done) { var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineStarted", - "jasmineDone", "suiteStarted", "suiteDone", "specStarted", "specDone" ]); - reporter.jasmineDone.and.callFake(function() { + env.addReporter(reporter); + + env.xdescribe("xd suite", function() { + env.fit("with a fit spec", function() { + env.expect(true).toBe(false); + }); + }); + + env.execute(null, function() { expect(reporter.jasmineStarted).toHaveBeenCalledWith({ totalSpecsDefined: 1, order: jasmine.any(jasmineUnderTest.Order) @@ -1396,29 +1331,28 @@ describe("Env integration", function() { done(); }); - - env.addReporter(reporter); - - env.xdescribe("xd suite", function() { - env.fit("with a fit spec", function() { - env.expect(true).toBe(false); - }); - }); - - env.execute(); }); it('should run focused suites inside an xdescribe', function(done) { var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineStarted", - "jasmineDone", "suiteStarted", "suiteDone", "specStarted", "specDone" ]); - reporter.jasmineDone.and.callFake(function() { + env.addReporter(reporter); + + env.xdescribe("xd suite", function() { + env.fdescribe("fd suite", function() { + env.it("with a spec", function() { + env.expect(true).toBe(false); + }); + }); + }); + + env.execute(null, function() { expect(reporter.jasmineStarted).toHaveBeenCalledWith({ totalSpecsDefined: 1, order: jasmine.any(jasmineUnderTest.Order) @@ -1431,32 +1365,42 @@ describe("Env integration", function() { done(); }); - - env.addReporter(reporter); - - env.xdescribe("xd suite", function() { - env.fdescribe("fd suite", function() { - env.it("with a spec", function() { - env.expect(true).toBe(false); - }); - }); - }); - - env.execute(); }); }); it("should report as expected", function(done) { var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineStarted", - "jasmineDone", "suiteStarted", "suiteDone", "specStarted", "specDone" ]); - reporter.jasmineDone.and.callFake(function() { + env.addReporter(reporter); + + env.describe("A Suite", function() { + env.it("with a top level spec", function() { + env.expect(true).toBe(true); + }); + env.describe("with a nested suite", function() { + env.xit("with an x'ed spec", function() { + env.expect(true).toBe(true); + }); + env.it("with a spec", function() { + env.expect(true).toBe(false); + }); + }); + + env.describe('with only non-executable specs', function() { + env.it('is pending'); + env.xit('is xed', function() { + env.expect(true).toBe(true); + }); + }); + }); + + env.execute(null, function() { expect(reporter.jasmineStarted).toHaveBeenCalledWith({ totalSpecsDefined: 5, order: jasmine.any(jasmineUnderTest.Order) @@ -1492,31 +1436,6 @@ describe("Env integration", function() { done(); }); - - env.addReporter(reporter); - - env.describe("A Suite", function() { - env.it("with a top level spec", function() { - env.expect(true).toBe(true); - }); - env.describe("with a nested suite", function() { - env.xit("with an x'ed spec", function() { - env.expect(true).toBe(true); - }); - env.it("with a spec", function() { - env.expect(true).toBe(false); - }); - }); - - env.describe('with only non-executable specs', function() { - env.it('is pending'); - env.xit('is xed', function() { - env.expect(true).toBe(true); - }); - }); - }); - - env.execute(); }); it("should report the random seed at the beginning and end of execution", function(done) { @@ -1530,36 +1449,23 @@ describe("Env integration", function() { ]); env.configure({random: true, seed: '123456'}); - reporter.jasmineDone.and.callFake(function(doneArg) { + env.addReporter(reporter); + env.configure({random: true}); + env.execute(null, function() { expect(reporter.jasmineStarted).toHaveBeenCalled(); var startedArg = reporter.jasmineStarted.calls.argsFor(0)[0]; expect(startedArg.order.random).toEqual(true); expect(startedArg.order.seed).toEqual('123456'); + var doneArg = reporter.jasmineDone.calls.argsFor(0)[0]; expect(doneArg.order.random).toEqual(true); expect(doneArg.order.seed).toEqual('123456'); done(); }); - - env.addReporter(reporter); - env.configure({random: true}); - env.execute(); }); it('should report pending spec messages', function(done) { - var reporter = jasmine.createSpyObj('fakeReporter', [ - 'specDone', - 'jasmineDone' - ]); - - reporter.jasmineDone.and.callFake(function() { - var specStatus = reporter.specDone.calls.argsFor(0)[0]; - - expect(specStatus.status).toBe('pending'); - expect(specStatus.pendingReason).toBe('with a message'); - - done(); - }); + var reporter = jasmine.createSpyObj('fakeReporter', ['specDone']); env.addReporter(reporter); @@ -1567,7 +1473,14 @@ describe("Env integration", function() { env.pending('with a message'); }); - env.execute(); + env.execute(null, function() { + var specStatus = reporter.specDone.calls.argsFor(0)[0]; + + expect(specStatus.status).toBe('pending'); + expect(specStatus.pendingReason).toBe('with a message'); + + done(); + }); }); it('should report pending spec messages from promise-returning functions', function(done) { @@ -1583,19 +1496,7 @@ describe("Env integration", function() { reject(this.exception); }; - var reporter = jasmine.createSpyObj('fakeReporter', [ - 'specDone', - 'jasmineDone' - ]); - - reporter.jasmineDone.and.callFake(function() { - var specStatus = reporter.specDone.calls.argsFor(0)[0]; - - expect(specStatus.status).toBe('pending'); - expect(specStatus.pendingReason).toBe('with a message'); - - done(); - }); + var reporter = jasmine.createSpyObj('fakeReporter', ['specDone']); env.addReporter(reporter); @@ -1605,7 +1506,14 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, function() { + var specStatus = reporter.specDone.calls.argsFor(0)[0]; + + expect(specStatus.status).toBe('pending'); + expect(specStatus.pendingReason).toBe('with a message'); + + done(); + }); }); it('should report using fallback reporter', function(done) { @@ -1632,26 +1540,12 @@ describe("Env integration", function() { it('should report xdescribes as expected', function(done) { var reporter = jasmine.createSpyObj('fakeReporter', [ "jasmineStarted", - "jasmineDone", "suiteStarted", "suiteDone", "specStarted", "specDone" ]); - reporter.jasmineDone.and.callFake(function() { - expect(reporter.jasmineStarted).toHaveBeenCalledWith({ - totalSpecsDefined: 1, - order: jasmine.any(jasmineUnderTest.Order) - }); - - expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ status: 'pending' })); - expect(reporter.suiteDone).toHaveBeenCalledWith(jasmine.objectContaining({ description: 'xd out', status: 'pending' })); - expect(reporter.suiteDone.calls.count()).toBe(4); - - done(); - }); - env.addReporter(reporter); env.describe("A Suite", function() { @@ -1666,7 +1560,18 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, function() { + expect(reporter.jasmineStarted).toHaveBeenCalledWith({ + totalSpecsDefined: 1, + order: jasmine.any(jasmineUnderTest.Order) + }); + + expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ status: 'pending' })); + expect(reporter.suiteDone).toHaveBeenCalledWith(jasmine.objectContaining({ description: 'xd out', status: 'pending' })); + expect(reporter.suiteDone.calls.count()).toBe(4); + + done(); + }); }); it("should be possible to get full name from a spec", function() { @@ -1691,20 +1596,7 @@ describe("Env integration", function() { }); it("Custom equality testers should be per spec", function(done) { - var reporter = jasmine.createSpyObj('fakeReporter', [ - "jasmineDone", - "specDone" - ]); - - reporter.jasmineDone.and.callFake(function() { - var firstSpecResult = reporter.specDone.calls.first().args[0], - secondSpecResult = reporter.specDone.calls.mostRecent().args[0]; - - expect(firstSpecResult.status).toEqual("passed"); - expect(secondSpecResult.status).toEqual("failed"); - - done(); - }); + var reporter = jasmine.createSpyObj('fakeReporter', ["specDone"]); env.addReporter(reporter); env.configure({random: false}); @@ -1720,26 +1612,20 @@ describe("Env integration", function() { }); }); - env.execute(); - }); - - it("Custom equality testers should be per suite", function(done) { - var reporter = jasmine.createSpyObj('fakeReporter', [ - "jasmineDone", - "specDone" - ]); - - reporter.jasmineDone.and.callFake(function() { + env.execute(null, function() { var firstSpecResult = reporter.specDone.calls.first().args[0], - secondSpecResult = reporter.specDone.calls.argsFor(0)[0], - thirdSpecResult = reporter.specDone.calls.mostRecent().args[0]; + secondSpecResult = reporter.specDone.calls.mostRecent().args[0]; expect(firstSpecResult.status).toEqual("passed"); - expect(secondSpecResult.status).toEqual("passed"); - expect(thirdSpecResult.status).toEqual("failed"); + expect(secondSpecResult.status).toEqual("failed"); done(); }); + }); + + it("Custom equality testers should be per suite", function(done) { + var reporter = jasmine.createSpyObj('fakeReporter', ["specDone"]); + env.addReporter(reporter); env.configure({random: false}); @@ -1762,24 +1648,21 @@ describe("Env integration", function() { }); }); - env.execute(); - }); - - it("Custom equality testers for toContain should be per spec", function(done) { - var reporter = jasmine.createSpyObj('fakeReporter', [ - "jasmineDone", - "specDone" - ]); - - reporter.jasmineDone.and.callFake(function() { + env.execute(null, function() { var firstSpecResult = reporter.specDone.calls.first().args[0], - secondSpecResult = reporter.specDone.calls.mostRecent().args[0]; + secondSpecResult = reporter.specDone.calls.argsFor(0)[0], + thirdSpecResult = reporter.specDone.calls.mostRecent().args[0]; expect(firstSpecResult.status).toEqual("passed"); - expect(secondSpecResult.status).toEqual("failed"); + expect(secondSpecResult.status).toEqual("passed"); + expect(thirdSpecResult.status).toEqual("failed"); done(); }); + }); + + it("Custom equality testers for toContain should be per spec", function(done) { + var reporter = jasmine.createSpyObj('fakeReporter', ["specDone"]); env.addReporter(reporter); env.configure({random: false}); @@ -1795,15 +1678,18 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, function() { + var firstSpecResult = reporter.specDone.calls.first().args[0], + secondSpecResult = reporter.specDone.calls.mostRecent().args[0]; + + expect(firstSpecResult.status).toEqual("passed"); + expect(secondSpecResult.status).toEqual("failed"); + + done(); + }); }); it("produces an understandable error message when an 'expect' is used outside of a current spec", function(done) { - var reporter = jasmine.createSpyObj('fakeReporter', ['jasmineDone']); - - reporter.jasmineDone.and.callFake(done); - env.addReporter(reporter); - env.describe("A Suite", function() { env.it("an async spec that is actually synchronous", function(underTestCallback) { underTestCallback(); @@ -1811,26 +1697,11 @@ describe("Env integration", function() { expect(function() { env.expect('a').toEqual('a'); }).toThrowError(/'expect' was used when there was no current spec/); }); - env.execute(); + env.execute(null, done); }); it("Custom equality testers for toContain should be per suite", function(done) { - var reporter = jasmine.createSpyObj('fakeReporter', [ - "jasmineDone", - "specDone" - ]); - - reporter.jasmineDone.and.callFake(function() { - var firstSpecResult = reporter.specDone.calls.first().args[0], - secondSpecResult = reporter.specDone.calls.argsFor(1)[0], - thirdSpecResult = reporter.specDone.calls.mostRecent().args[0]; - - expect(firstSpecResult.status).toEqual("passed"); - expect(secondSpecResult.status).toEqual("passed"); - expect(thirdSpecResult.status).toEqual("failed"); - - done(); - }); + var reporter = jasmine.createSpyObj('fakeReporter', ["specDone"]); env.addReporter(reporter); env.configure({random: false}); @@ -1853,7 +1724,17 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, function() { + var firstSpecResult = reporter.specDone.calls.first().args[0], + secondSpecResult = reporter.specDone.calls.argsFor(1)[0], + thirdSpecResult = reporter.specDone.calls.mostRecent().args[0]; + + expect(firstSpecResult.status).toEqual("passed"); + expect(secondSpecResult.status).toEqual("passed"); + expect(thirdSpecResult.status).toEqual("failed"); + + done(); + }); }); it("Custom matchers should be per spec", function(done) { @@ -1872,9 +1753,7 @@ describe("Env integration", function() { }); }); - env.addReporter({jasmineDone: done}); - - env.execute(); + env.execute(null, done); }); it("Custom matchers should be per suite", function(done) { @@ -1900,9 +1779,7 @@ describe("Env integration", function() { }); }); - env.addReporter({jasmineDone: done}); - - env.execute(); + env.execute(null, done); }); it('throws an exception if you try to create a spy outside of a runnable', function (done) { @@ -1917,14 +1794,10 @@ describe("Env integration", function() { } }); - var assertions = function() { + env.execute(null, function() { expect(exception.message).toBe('Spies must be created in a before function or a spec'); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it('throws an exception if you try to add a matcher outside of a runnable', function (done) { @@ -1939,14 +1812,10 @@ describe("Env integration", function() { } }); - var assertions = function() { + env.execute(null, function() { expect(exception.message).toBe('Matchers must be added in a before function or a spec'); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it('throws an exception if you try to add a custom equality outside of a runnable', function (done) { @@ -1961,30 +1830,28 @@ describe("Env integration", function() { } }); - var assertions = function() { + env.execute(null, function() { expect(exception.message).toBe('Custom Equalities must be added in a before function or a spec'); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it('reports test properties on specs', function(done) { var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + reporter = jasmine.createSpyObj('reporter', ['suiteDone', 'specDone']); reporter.specDone.and.callFake(function(e) { expect(e.properties).toEqual({a: 'Bee'}); - done(); }); env.addReporter(reporter); env.it('calls setSpecProperty', function() { env.setSpecProperty('a', 'Bee') }); - env.execute(); + env.execute(null, function() { + expect(reporter.specDone).toHaveBeenCalled(); + done(); + }); }); it('throws an exception if you try to setSpecProperty outside of a spec', function (done) { @@ -2000,14 +1867,10 @@ describe("Env integration", function() { } }); - var assertions = function() { + env.execute(null, function() { expect(exception.message).toBe("'setSpecProperty' was used when there was no current spec"); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it('reports test properties on suites', function(done) { @@ -2016,7 +1879,6 @@ describe("Env integration", function() { reporter.suiteDone.and.callFake(function(e) { expect(e.properties).toEqual({b: 'Sweet'}); - done(); }); env.addReporter(reporter); @@ -2029,7 +1891,10 @@ describe("Env integration", function() { }); }); - env.execute(); + env.execute(null, function() { + expect(reporter.suiteDone).toHaveBeenCalled(); + done(); + }); }); it('throws an exception if you try to setSuiteProperty outside of a suite', function (done) { @@ -2044,17 +1909,7 @@ describe("Env integration", function() { }); it("should associate errors thrown from async code with the correct runnable", function(done) { - var reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone','suiteDone','specDone']); - - reporter.jasmineDone.and.callFake(function() { - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('async suite', [ - /^(((Uncaught )?(exception: )?Error: suite( thrown)?)|(suite thrown))$/ - ]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite async spec', [ - /^(((Uncaught )?(exception: )?Error: spec( thrown)?)|(spec thrown))$/ - ]); - done(); - }); + var reporter = jasmine.createSpyObj('fakeReport', ['suiteDone','specDone']); env.addReporter(reporter); @@ -2072,31 +1927,19 @@ describe("Env integration", function() { }, 10); }); - env.execute(); + env.execute(null, function() { + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('async suite', [ + /^(((Uncaught )?(exception: )?Error: suite( thrown)?)|(suite thrown))$/ + ]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite async spec', [ + /^(((Uncaught )?(exception: )?Error: spec( thrown)?)|(spec thrown))$/ + ]); + done(); + }); }); it('should throw on suites/specs/befores/afters nested in methods other than \'describe\'', function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - - reporter.jasmineDone.and.callFake(function() { - var msg = /\'.*\' should only be used in \'describe\' function/; - - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite describe', [msg]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite xdescribe', [msg]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite fdescribe', [msg]); - - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('spec it', [msg]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('spec xit', [msg]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('spec fit', [msg]); - - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('beforeAll', [msg]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('beforeEach spec', [msg]); - - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('afterAll', [msg]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('afterEach spec', [msg]); - - done(); - }); + var reporter = jasmine.createSpyObj('reporter', ['suiteDone', 'specDone']); env.addReporter(reporter); @@ -2132,7 +1975,25 @@ describe("Env integration", function() { env.it('spec', function() {}); }); - env.execute(); + env.execute(null, function() { + var msg = /\'.*\' should only be used in \'describe\' function/; + + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite describe', [msg]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite xdescribe', [msg]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite fdescribe', [msg]); + + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('spec it', [msg]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('spec xit', [msg]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('spec fit', [msg]); + + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('beforeAll', [msg]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('beforeEach spec', [msg]); + + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('afterAll', [msg]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('afterEach spec', [msg]); + + done(); + }); }); it('reports errors that occur during loading', function(done) { @@ -2147,7 +2008,12 @@ describe("Env integration", function() { env = new jasmineUnderTest.Env(); var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(e) { + env.addReporter(reporter); + global.onerror('Uncaught SyntaxError: Unexpected end of input', 'borkenSpec.js', 42, undefined, {stack: 'a stack'}); + global.onerror('Uncaught Error: ENOCHEESE'); + + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; expect(e.failedExpectations).toEqual([ { passed: false, @@ -2169,12 +2035,6 @@ describe("Env integration", function() { done(); }); - - env.addReporter(reporter); - global.onerror('Uncaught SyntaxError: Unexpected end of input', 'borkenSpec.js', 42, undefined, {stack: 'a stack'}); - global.onerror('Uncaught Error: ENOCHEESE'); - - env.execute(); }); describe('If suppressLoadErrors: true was passed', function() { @@ -2195,16 +2055,15 @@ describe("Env integration", function() { env = new jasmineUnderTest.Env({suppressLoadErrors: true}); var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(e) { + env.addReporter(reporter); + global.onerror('Uncaught Error: ENOCHEESE'); + + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; expect(e.failedExpectations).toEqual([]); expect(originalOnerror).toHaveBeenCalledWith('Uncaught Error: ENOCHEESE'); done(); }); - - env.addReporter(reporter); - global.onerror('Uncaught Error: ENOCHEESE'); - - env.execute(); }); }); @@ -2213,14 +2072,13 @@ describe("Env integration", function() { it('is "passed"', function(done) { var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(e) { + env.addReporter(reporter); + env.it('passes', function() {}); + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; expect(e.overallStatus).toEqual('passed'); done(); }); - - env.addReporter(reporter); - env.it('passes', function() {}); - env.execute(); }); }); @@ -2228,16 +2086,15 @@ describe("Env integration", function() { it('is "failed"', function(done) { var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(e) { - expect(e.overallStatus).toEqual('failed'); - done(); - }); - env.addReporter(reporter); env.it('fails', function() { env.expect(true).toBe(false); }); - env.execute(); + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; + expect(e.overallStatus).toEqual('failed'); + done(); + }) }); }); @@ -2255,23 +2112,21 @@ describe("Env integration", function() { }); it('should report "failed" status if "failSpecWithNoExpectations" is enabled', function(done) { - reporter.jasmineDone.and.callFake(function(e) { + env.configure({ failSpecWithNoExpectations: true }); + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; expect(e.overallStatus).toEqual('failed'); done(); }); - - env.configure({ failSpecWithNoExpectations: true }); - env.execute(); }); it('should report "passed" status if "failSpecWithNoExpectations" is disabled', function(done) { - reporter.jasmineDone.and.callFake(function(e) { + env.configure({ failSpecWithNoExpectations: false }); + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; expect(e.overallStatus).toEqual('passed'); done(); }); - - env.configure({ failSpecWithNoExpectations: false }); - env.execute(); }); }); @@ -2279,17 +2134,16 @@ describe("Env integration", function() { it('is "failed"', function(done) { var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(e) { - expect(e.overallStatus).toEqual('failed'); - done(); - }); - env.addReporter(reporter); env.beforeAll(function() { throw new Error('nope'); }); env.it('does not run', function() {}); - env.execute(); + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; + expect(e.overallStatus).toEqual('failed'); + done(); + }); }); }); @@ -2297,11 +2151,6 @@ describe("Env integration", function() { it('is "failed"', function(done) { var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(e) { - expect(e.overallStatus).toEqual('failed'); - done(); - }); - env.addReporter(reporter); env.describe('something', function() { env.beforeAll(function() { @@ -2309,7 +2158,11 @@ describe("Env integration", function() { }); env.it('does not run', function() {}); }); - env.execute(); + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; + expect(e.overallStatus).toEqual('failed'); + done(); + }); }); }); @@ -2317,17 +2170,16 @@ describe("Env integration", function() { it('is "failed"', function(done) { var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(e) { - expect(e.overallStatus).toEqual('failed'); - done(); - }); - env.addReporter(reporter); env.afterAll(function() { throw new Error('nope'); }); env.it('does not run', function() {}); - env.execute(); + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; + expect(e.overallStatus).toEqual('failed'); + done(); + }); }); }); @@ -2335,11 +2187,6 @@ describe("Env integration", function() { it('is "failed"', function(done) { var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(e) { - expect(e.overallStatus).toEqual('failed'); - done(); - }); - env.addReporter(reporter); env.describe('something', function() { env.afterAll(function() { @@ -2347,7 +2194,11 @@ describe("Env integration", function() { }); env.it('does not run', function() {}); }); - env.execute(); + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; + expect(e.overallStatus).toEqual('failed'); + done(); + }); }); }); @@ -2365,13 +2216,15 @@ describe("Env integration", function() { reporter.jasmineDone.and.callFake(function(e) { expect(e.overallStatus).toEqual('failed'); - done(); }); env.addReporter(reporter); env.it('passes', function() {}); global.onerror('Uncaught Error: ENOCHEESE'); - env.execute(); + env.execute(null, function() { + expect(reporter.jasmineDone).toHaveBeenCalled(); + done(); + }); }); }); @@ -2379,14 +2232,13 @@ describe("Env integration", function() { it('is "incomplete"', function(done) { var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(e) { + env.addReporter(reporter); + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; expect(e.overallStatus).toEqual('incomplete'); expect(e.incompleteReason).toEqual('No specs found'); done(); }); - - env.addReporter(reporter); - env.execute(); }); }); @@ -2394,15 +2246,14 @@ describe("Env integration", function() { it('is "incomplete"', function(done) { var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(e) { + env.addReporter(reporter); + env.fit('is focused', function() {}); + env.execute(null, function(e) { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; expect(e.overallStatus).toEqual('incomplete'); expect(e.incompleteReason).toEqual('fit() or fdescribe() was found'); done(); }); - - env.addReporter(reporter); - env.fit('is focused', function() {}); - env.execute(); }); }); @@ -2410,17 +2261,16 @@ describe("Env integration", function() { it('is "incomplete"', function(done) { var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(e) { - expect(e.overallStatus).toEqual('incomplete'); - expect(e.incompleteReason).toEqual('fit() or fdescribe() was found'); - done(); - }); - env.addReporter(reporter); env.fdescribe('something focused', function() { env.it('does a thing', function() {}); }); - env.execute(); + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; + expect(e.overallStatus).toEqual('incomplete'); + expect(e.incompleteReason).toEqual('fit() or fdescribe() was found'); + done(); + }); }); }); @@ -2428,17 +2278,16 @@ describe("Env integration", function() { it('is "failed"', function(done) { var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - reporter.jasmineDone.and.callFake(function(e) { - expect(e.overallStatus).toEqual('failed'); - expect(e.incompleteReason).toBeUndefined(); - done(); - }); - env.addReporter(reporter); env.fit('is focused', function() { env.expect(true).toBe(false); }); - env.execute(); + env.execute(null, function() { + var e = reporter.jasmineDone.calls.argsFor(0)[0]; + expect(e.overallStatus).toEqual('failed'); + expect(e.incompleteReason).toBeUndefined(); + done(); + }); }); }); }); @@ -2449,7 +2298,22 @@ describe("Env integration", function() { // prevent deprecation from being displayed spyOn(console, "error"); - reporter.jasmineDone.and.callFake(function(result) { + env.addReporter(reporter); + + env.deprecated('top level deprecation'); + + env.describe('suite', function() { + env.beforeAll(function() { + env.deprecated('suite level deprecation'); + }); + + env.it('spec', function() { + env.deprecated('spec level deprecation'); + }); + }); + + env.execute(null, function() { + var result = reporter.jasmineDone.calls.argsFor(0)[0]; expect(result.deprecationWarnings).toEqual([ jasmine.objectContaining({ message: 'top level deprecation' }) ]); @@ -2470,22 +2334,6 @@ describe("Env integration", function() { done(); }); - - env.addReporter(reporter); - - env.deprecated('top level deprecation'); - - env.describe('suite', function() { - env.beforeAll(function() { - env.deprecated('suite level deprecation'); - }); - - env.it('spec', function() { - env.deprecated('spec level deprecation'); - }); - }); - - env.execute(); }); it('should report deprecation stack with an error object', function(done) { @@ -2500,7 +2348,22 @@ describe("Env integration", function() { // prevent deprecation from being displayed spyOn(console, "error"); - reporter.jasmineDone.and.callFake(function(result) { + env.addReporter(reporter); + + env.deprecated(topLevelError); + + env.describe('suite', function() { + env.beforeAll(function() { + env.deprecated(suiteLevelError); + }); + + env.it('spec', function() { + env.deprecated(specLevelError); + }); + }); + + env.execute(null, function() { + var result = reporter.jasmineDone.calls.argsFor(0)[0]; expect(result.deprecationWarnings).toEqual([ jasmine.objectContaining({ message: topLevelError.message, @@ -2530,54 +2393,19 @@ describe("Env integration", function() { done(); }); - - env.addReporter(reporter); - - env.deprecated(topLevelError); - - env.describe('suite', function() { - env.beforeAll(function() { - env.deprecated(suiteLevelError); - }); - - env.it('spec', function() { - env.deprecated(specLevelError); - }); - }); - - env.execute(); }); it('supports async matchers', function(done) { jasmine.getEnv().requirePromises(); var specDone = jasmine.createSpy('specDone'), - suiteDone = jasmine.createSpy('suiteDone'); + suiteDone = jasmine.createSpy('suiteDone'), + jasmineDone = jasmine.createSpy('jasmineDone'); env.addReporter({ specDone: specDone, suiteDone: suiteDone, - jasmineDone: function(result) { - expect(result.failedExpectations).toEqual([jasmine.objectContaining({ - message: 'Expected [object Promise] to be rejected.' - })]); - - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'has an async failure', - failedExpectations: [jasmine.objectContaining({ - message: 'Expected [object Promise] to be rejected.' - })] - })); - - expect(suiteDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'a suite', - failedExpectations: [jasmine.objectContaining({ - message: 'Expected [object Promise] to be rejected.' - })] - })); - - done(); - } + jasmineDone: jasmineDone }); function fail(innerDone) { @@ -2593,7 +2421,28 @@ describe("Env integration", function() { env.it('has an async failure', fail); }); - env.execute(); + env.execute(null, function() { + var result = jasmineDone.calls.argsFor(0)[0]; + expect(result.failedExpectations).toEqual([jasmine.objectContaining({ + message: 'Expected [object Promise] to be rejected.' + })]); + + expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ + description: 'has an async failure', + failedExpectations: [jasmine.objectContaining({ + message: 'Expected [object Promise] to be rejected.' + })] + })); + + expect(suiteDone).toHaveBeenCalledWith(jasmine.objectContaining({ + description: 'a suite', + failedExpectations: [jasmine.objectContaining({ + message: 'Expected [object Promise] to be rejected.' + })] + })); + + done(); + }); }); it('provides custom equality testers to async matchers', function(done) { @@ -2601,16 +2450,7 @@ describe("Env integration", function() { var specDone = jasmine.createSpy('specDone'); - env.addReporter({ - specDone: specDone, - jasmineDone: function() { - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'has an async failure', - failedExpectations: [] - })); - done(); - } - }); + env.addReporter({specDone: specDone}); env.it('has an async failure', function() { env.addCustomEqualityTester(function() { return true; }); @@ -2618,7 +2458,13 @@ describe("Env integration", function() { return env.expectAsync(p).toBeResolvedTo('something else'); }); - env.execute(); + env.execute(null, function() { + expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ + description: 'has an async failure', + failedExpectations: [] + })); + done(); + }); }); it('includes useful stack frames in async matcher failures', function(done) { @@ -2626,17 +2472,7 @@ describe("Env integration", function() { var specDone = jasmine.createSpy('specDone'); - env.addReporter({ - specDone: specDone, - jasmineDone: function() { - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - failedExpectations: [jasmine.objectContaining({ - stack: jasmine.stringMatching('EnvSpec.js') - })] - })); - done(); - } - }); + env.addReporter({specDone: specDone}); env.it('has an async failure', function() { env.addCustomEqualityTester(function() { return true; }); @@ -2644,13 +2480,21 @@ describe("Env integration", function() { return env.expectAsync(p).toBeRejected(); }); - env.execute(); + env.execute(null, function() { + expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ + failedExpectations: [jasmine.objectContaining({ + stack: jasmine.stringMatching('EnvSpec.js') + })] + })); + done(); + }); }); it('reports an error when an async expectation occurs after the spec finishes', function(done) { jasmine.getEnv().requirePromises(); var resolve, + jasmineDone = jasmine.createSpy('jasmineDone'), promise = new Promise(function(res) { resolve = res; }); // eslint-disable-line compat/compat env.describe('a suite', function() { @@ -2666,39 +2510,41 @@ describe("Env integration", function() { specDone: function() { resolve(); }, - jasmineDone: function (result) { - expect(result.failedExpectations).toEqual([ - jasmine.objectContaining({ - passed: false, - globalErrorType: 'lateExpectation', - message: 'Spec "a suite does not wait" ran a "toBeResolved" expectation ' + - 'after it finished.\n' + - 'Did you forget to return or await the result of expectAsync?', - matcherName: 'toBeResolved' - }), - jasmine.objectContaining({ - passed: false, - globalErrorType: 'lateExpectation', - message: 'Spec "a suite does not wait" ran a "toBeResolvedTo" expectation ' + - 'after it finished.\n' + - 'Message: "Expected a promise to be resolved to \'something else\' ' + - 'but it was resolved to undefined."\n' + - 'Did you forget to return or await the result of expectAsync?', - matcherName: 'toBeResolvedTo' - }) - ]); - - done(); - } + jasmineDone: jasmineDone }); - env.execute(); + env.execute(null, function () { + var result = jasmineDone.calls.argsFor(0)[0]; + expect(result.failedExpectations).toEqual([ + jasmine.objectContaining({ + passed: false, + globalErrorType: 'lateExpectation', + message: 'Spec "a suite does not wait" ran a "toBeResolved" expectation ' + + 'after it finished.\n' + + 'Did you forget to return or await the result of expectAsync?', + matcherName: 'toBeResolved' + }), + jasmine.objectContaining({ + passed: false, + globalErrorType: 'lateExpectation', + message: 'Spec "a suite does not wait" ran a "toBeResolvedTo" expectation ' + + 'after it finished.\n' + + 'Message: "Expected a promise to be resolved to \'something else\' ' + + 'but it was resolved to undefined."\n' + + 'Did you forget to return or await the result of expectAsync?', + matcherName: 'toBeResolvedTo' + }) + ]); + + done(); + }); }); it('reports an error when an async expectation occurs after the suite finishes', function(done) { jasmine.getEnv().requirePromises(); var resolve, + jasmineDone = jasmine.createSpy('jasmineDone'), promise = new Promise(function(res) { resolve = res; }); // eslint-disable-line compat/compat env.describe('a suite', function() { @@ -2715,23 +2561,24 @@ describe("Env integration", function() { suiteDone: function() { resolve(); }, - jasmineDone: function (result) { - expect(result.failedExpectations).toEqual([ - jasmine.objectContaining({ - passed: false, - globalErrorType: 'lateExpectation', - message: 'Suite "a suite" ran a "toBeResolved" expectation ' + - 'after it finished.\n' + - 'Did you forget to return or await the result of expectAsync?', - matcherName: 'toBeResolved' - }) - ]); - - done(); - } + jasmineDone: jasmineDone }); - env.execute(); + env.execute(null, function () { + var result = jasmineDone.calls.argsFor(0)[0]; + expect(result.failedExpectations).toEqual([ + jasmine.objectContaining({ + passed: false, + globalErrorType: 'lateExpectation', + message: 'Suite "a suite" ran a "toBeResolved" expectation ' + + 'after it finished.\n' + + 'Did you forget to return or await the result of expectAsync?', + matcherName: 'toBeResolved' + }) + ]); + + done(); + }); }); it("supports asymmetric equality testers that take a matchersUtil", function(done) { @@ -2759,7 +2606,89 @@ describe("Env integration", function() { expect(result.status).toEqual('passed'); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); + }); + + describe('The optional callback argument to #execute', function() { + beforeEach(function() { + this.savedInterval = jasmineUnderTest.DEFAULT_TIMEOUT_INTERVAL; + }); + + afterEach(function() { + jasmineUnderTest.DEFAULT_TIMEOUT_INTERVAL = this.savedInterval; + }); + + it('is called after reporter events are dispatched', function(done) { + var reporter = jasmine.createSpyObj( + 'reporter', + ['specDone', 'suiteDone', 'jasmineDone'] + ); + + env.addReporter(reporter); + env.describe('suite', function () { + env.it('spec', function() {}); + }); + + env.execute(null, function() { + expect(reporter.specDone).toHaveBeenCalled(); + expect(reporter.suiteDone).toHaveBeenCalled(); + expect(reporter.jasmineDone).toHaveBeenCalled(); + done(); + }); + }); + + it('is called after the stack is cleared', function(done) { + var realClearStack = jasmineUnderTest.getClearStack(jasmineUnderTest.getGlobal()), + clearStackSpy = jasmine.createSpy('clearStack').and.callFake(realClearStack); + spyOn(jasmineUnderTest, 'getClearStack').and.returnValue(clearStackSpy); + + // Create a new env that has the clearStack defined above + env.cleanup_(); + env = new jasmineUnderTest.Env(); + + env.describe('suite', function () { + env.it('spec', function() {}); + }); + + env.execute(null, function() { + expect(clearStackSpy).toHaveBeenCalled(); // (many times) + clearStackSpy.calls.reset(); + setTimeout(function() { + expect(clearStackSpy).not.toHaveBeenCalled(); + done(); + }); + }); + }); + + it('is called after QueueRunner timeouts are cleared', function(done) { + var setTimeoutSpy = spyOn(jasmineUnderTest.getGlobal(), 'setTimeout') + .and.callThrough(); + var clearTimeoutSpy = spyOn(jasmineUnderTest.getGlobal(), 'clearTimeout') + .and.callThrough(); + + jasmineUnderTest.DEFAULT_TIMEOUT_INTERVAL = 123456; // a distinctive value + + env = new jasmineUnderTest.Env(); + + env.describe('suite', function () { + env.it('spec', function () { + }); + }); + + env.execute(null, function () { + var timeoutIds = setTimeoutSpy.calls.all() + .filter(function(call) { return call.args[1] === 123456; }) + .map(function(call) { return call.returnValue; }); + + expect(timeoutIds.length).toBeGreaterThan(0); + + timeoutIds.forEach(function(timeoutId) { + expect(clearTimeoutSpy).toHaveBeenCalledWith(timeoutId); + }); + + done(); + }); + }); }); }); diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js index 92b7307f..8174faf8 100644 --- a/spec/core/integration/MatchersSpec.js +++ b/spec/core/integration/MatchersSpec.js @@ -28,8 +28,8 @@ describe('Matchers (Integration)', function() { .toBeUndefined(); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); } @@ -54,8 +54,8 @@ describe('Matchers (Integration)', function() { .not.toEqual(''); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); } @@ -75,8 +75,8 @@ describe('Matchers (Integration)', function() { .toEqual(config.expectedMessage); }; - env.addReporter({specDone: specExpectations, jasmineDone: done}); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); } @@ -101,8 +101,8 @@ describe('Matchers (Integration)', function() { .toBeUndefined(); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); } @@ -126,8 +126,8 @@ describe('Matchers (Integration)', function() { .not.toEqual(''); }; - env.addReporter({ specDone: specExpectations, jasmineDone: done }); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); } @@ -149,8 +149,8 @@ describe('Matchers (Integration)', function() { .toEqual(config.expectedMessage); }; - env.addReporter({specDone: specExpectations, jasmineDone: done}); - env.execute(); + env.addReporter({ specDone: specExpectations }); + env.execute(null, done); }); } diff --git a/spec/core/integration/SpecRunningSpec.js b/spec/core/integration/SpecRunningSpec.js index d522cf86..33459d02 100644 --- a/spec/core/integration/SpecRunningSpec.js +++ b/spec/core/integration/SpecRunningSpec.js @@ -66,17 +66,14 @@ describe("spec running", function () { expect(bar).toEqual(0); expect(baz).toEqual(0); expect(quux).toEqual(0); - var assertions = function() { + + env.execute(null, function() { expect(foo).toEqual(1); expect(bar).toEqual(1); expect(baz).toEqual(1); expect(quux).toEqual(1); done(); - }; - - env.addReporter({ jasmineDone: assertions }); - - env.execute(); + }); }); it("should permit nested describes", function(done) { @@ -136,7 +133,7 @@ describe("spec running", function () { }); }); - var assertions = function() { + env.execute(null, function() { var expected = [ "topSuite beforeEach", "outer beforeEach", @@ -168,11 +165,7 @@ describe("spec running", function () { ]; expect(actions).toEqual(expected); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it("should run multiple befores and afters ordered so functions declared later are treated as more specific", function(done) { @@ -232,7 +225,7 @@ describe("spec running", function () { }); }); - var assertions = function() { + env.execute(null, function() { var expected = [ "runner beforeAll1", "runner beforeAll2", @@ -250,11 +243,7 @@ describe("spec running", function () { ]; expect(actions).toEqual(expected); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it('should run beforeAlls before beforeEachs and afterAlls after afterEachs', function(done) { @@ -298,7 +287,7 @@ describe("spec running", function () { }); }); - var assertions = function() { + env.execute(null, function() { var expected = [ "runner beforeAll", "inner beforeAll", @@ -312,10 +301,7 @@ describe("spec running", function () { ]; expect(actions).toEqual(expected); done(); - }; - - env.addReporter({jasmineDone: assertions}); - env.execute(); + }); }); it('should run beforeAlls and afterAlls in the order declared when runnablesToRun is provided', function(done) { @@ -365,7 +351,7 @@ describe("spec running", function () { }); }); - var assertions = function() { + env.execute([spec2.id, spec.id], function() { var expected = [ "runner beforeAll", "inner beforeAll", @@ -385,10 +371,7 @@ describe("spec running", function () { ]; expect(actions).toEqual(expected); done(); - }; - - env.addReporter({jasmineDone: assertions}); - env.execute([spec2.id, spec.id]); + }); }); it('only runs *Alls once in a focused suite', function(done){ @@ -406,13 +389,10 @@ describe("spec running", function () { }); }); - var assertions = function() { + env.execute(null, function() { expect(actions).toEqual(['beforeAll', 'spec', 'afterAll']); done(); - }; - - env.addReporter({jasmineDone: assertions}); - env.execute(); + }); }); describe('focused runnables', function() { @@ -435,7 +415,7 @@ describe("spec running", function () { }); }); - var assertions = function() { + env.execute(null, function() { var expected = [ 'beforeAll', 'beforeEach', @@ -449,10 +429,7 @@ describe("spec running", function () { ]; expect(actions).toEqual(expected); done(); - }; - - env.addReporter({jasmineDone: assertions}); - env.execute(); + }); }); it('focused specs in focused suites cause non-focused siblings to not run', function(done){ @@ -467,14 +444,11 @@ describe("spec running", function () { }); }); - var assertions = function() { + env.execute(null, function() { var expected = ['focused spec']; expect(actions).toEqual(expected); done(); - }; - - env.addReporter({jasmineDone: assertions}); - env.execute(); + }); }); it('focused suites in focused suites cause non-focused siblings to not run', function(done){ @@ -491,14 +465,11 @@ describe("spec running", function () { }); }); - var assertions = function() { + env.execute(null, function() { var expected = ['inner spec']; expect(actions).toEqual(expected); done(); - }; - - env.addReporter({jasmineDone: assertions}); - env.execute(); + }); }); it('focused runnables unfocus ancestor focused suites', function(done) { @@ -515,14 +486,11 @@ describe("spec running", function () { }); }); - var assertions = function() { + env.execute(null, function() { var expected = ['focused spec']; expect(actions).toEqual(expected); done(); - }; - - env.addReporter({jasmineDone: assertions}); - env.execute(); + }); }); }); @@ -534,14 +502,10 @@ describe("spec running", function () { }); }); - var assertions = function() { + env.execute(null, function() { expect(specInADisabledSuite).not.toHaveBeenCalled(); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it("shouldn't run before/after functions in disabled suites", function(done) { @@ -556,14 +520,10 @@ describe("spec running", function () { env.it('spec inside a disabled suite', shouldNotRun); }); - var assertions = function() { + env.execute(null, function() { expect(shouldNotRun).not.toHaveBeenCalled(); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it("should allow top level suites to be disabled", function(done) { @@ -577,15 +537,11 @@ describe("spec running", function () { env.it('another spec', otherSpec); }); - var assertions = function() { + env.execute(null, function() { expect(specInADisabledSuite).not.toHaveBeenCalled(); expect(otherSpec).toHaveBeenCalled(); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it("should set all pending specs to pending when a suite is run", function(done) { @@ -594,31 +550,20 @@ describe("spec running", function () { pendingSpec = env.it("I am a pending spec"); }); - var assertions = function() { + env.execute(null, function() { expect(pendingSpec.status()).toBe("pending"); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it("should recover gracefully when there are errors in describe functions", function(done) { var specs = [], - reporter = jasmine.createSpyObj(['specDone', 'suiteDone', 'jasmineDone']); + reporter = jasmine.createSpyObj(['specDone', 'suiteDone']); reporter.specDone.and.callFake(function(result) { specs.push(result.fullName); }); - reporter.jasmineDone.and.callFake(function() { - expect(specs).toEqual(['outer1 inner1 should thingy', 'outer1 inner2 should other thingy', 'outer2 should xxx']); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('outer1 inner1', [/inner error/]); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('outer1', [/outer error/]); - done(); - }); - expect(function() { env.describe("outer1", function() { env.describe("inner1", function() { @@ -647,7 +592,12 @@ describe("spec running", function () { }); env.addReporter(reporter); - env.execute(); + env.execute(null, function() { + expect(specs).toEqual(['outer1 inner1 should thingy', 'outer1 inner2 should other thingy', 'outer2 should xxx']); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('outer1 inner1', [/inner error/]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('outer1', [/outer error/]); + done(); + }); }); it("re-enters suites that have no *Alls", function(done) { @@ -668,14 +618,10 @@ describe("spec running", function () { actions.push("spec3"); }); - env.addReporter({ - jasmineDone: function() { - expect(actions).toEqual(["spec2", "spec3", "spec1"]); - done(); - } + env.execute([spec2.id, spec3.id, spec1.id], function() { + expect(actions).toEqual(["spec2", "spec3", "spec1"]); + done(); }); - - env.execute([spec2.id, spec3.id, spec1.id]); }); it("refuses to re-enter suites with a beforeAll", function() { @@ -698,16 +644,10 @@ describe("spec running", function () { actions.push("spec3"); }); - env.addReporter({ - jasmineDone: function() { - expect(actions).toEqual([]); - done(); - } - }); - expect(function() { env.execute([spec2.id, spec3.id, spec1.id]); }).toThrowError(/beforeAll/); + expect(actions).toEqual([]); }); it("refuses to re-enter suites with a afterAll", function() { @@ -730,16 +670,10 @@ describe("spec running", function () { actions.push("spec3"); }); - env.addReporter({ - jasmineDone: function() { - expect(actions).toEqual([]); - done(); - } - }); - expect(function() { env.execute([spec2.id, spec3.id, spec1.id]); }).toThrowError(/afterAll/); + expect(actions).toEqual([]); }); it("should run the tests in a consistent order when a seed is supplied", function(done) { @@ -800,7 +734,7 @@ describe("spec running", function () { }); }); - var assertions = function() { + env.execute(null, function() { var expected = [ 'topSuite beforeEach', 'outer beforeEach', @@ -832,11 +766,7 @@ describe("spec running", function () { ]; expect(actions).toEqual(expected); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); describe("When throwOnExpectationFailure is set", function() { @@ -870,18 +800,14 @@ describe("spec running", function () { env.configure({oneFailurePerSpec: true}); - var assertions = function() { + env.execute(null, function() { expect(actions).toEqual([ 'outer beforeEach', 'inner afterEach', 'outer afterEach' ]); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it("skips to cleanup functions after done.fail is called", function(done) { @@ -905,17 +831,13 @@ describe("spec running", function () { env.configure({oneFailurePerSpec: true}); - var assertions = function() { + env.execute(null, function() { expect(actions).toEqual([ 'beforeEach', 'afterEach' ]); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it("skips to cleanup functions when an async function times out", function(done) { @@ -937,17 +859,13 @@ describe("spec running", function () { env.configure({oneFailurePerSpec: true}); - var assertions = function() { + env.execute(null, function() { expect(actions).toEqual([ 'beforeEach', 'afterEach' ]); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it("skips to cleanup functions after an error with deprecations", function(done) { @@ -982,7 +900,7 @@ describe("spec running", function () { env.throwOnExpectationFailure(true); - var assertions = function() { + env.execute(null, function() { expect(actions).toEqual([ 'outer beforeEach', 'inner afterEach', @@ -990,11 +908,7 @@ describe("spec running", function () { ]); expect(env.deprecated).toHaveBeenCalled(); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it("skips to cleanup functions after done.fail is called with deprecations", function(done) { @@ -1020,18 +934,14 @@ describe("spec running", function () { env.throwOnExpectationFailure(true); - var assertions = function() { + env.execute(null, function() { expect(actions).toEqual([ 'beforeEach', 'afterEach' ]); expect(env.deprecated).toHaveBeenCalled(); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); it("skips to cleanup functions when an async function times out with deprecations", function(done) { @@ -1055,18 +965,14 @@ describe("spec running", function () { env.throwOnExpectationFailure(true); - var assertions = function() { + env.execute(null, function() { expect(actions).toEqual([ 'beforeEach', 'afterEach' ]); expect(env.deprecated).toHaveBeenCalled(); done(); - }; - - env.addReporter({jasmineDone: assertions}); - - env.execute(); + }); }); }); @@ -1089,13 +995,10 @@ describe("spec running", function () { env.configure({random: false, failFast: true}); - var assertions = function() { + env.execute(null, function() { expect(actions).toEqual(['fails']); done(); - }; - - env.addReporter({ jasmineDone: assertions }); - env.execute(); + }); }); it("does not run further specs when one fails when configured with deprecated option", function(done) { @@ -1119,14 +1022,11 @@ describe("spec running", function () { env.configure({random: false}); env.stopOnSpecFailure(true); - var assertions = function() { + env.execute(null, function() { expect(actions).toEqual(['fails']); expect(env.deprecated).toHaveBeenCalled(); done(); - }; - - env.addReporter({ jasmineDone: assertions }); - env.execute(); + }); }); }); }); diff --git a/src/core/Env.js b/src/core/Env.js index d7fdd4c0..7e299717 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -705,7 +705,8 @@ getJasmineRequireObj().Env = function(j$) { queueRunnerFactory ); - this.execute = function(runnablesToRun) { + // Both params are optional. + this.execute = function(runnablesToRun, onComplete) { installGlobalErrors(); if (!runnablesToRun) { @@ -813,7 +814,11 @@ getJasmineRequireObj().Env = function(j$) { failedExpectations: topSuite.result.failedExpectations, deprecationWarnings: topSuite.result.deprecationWarnings }, - function() {} + function() { + if (onComplete) { + onComplete(); + } + } ); }); } diff --git a/src/core/QueueRunner.js b/src/core/QueueRunner.js index 28c1153f..df383632 100644 --- a/src/core/QueueRunner.js +++ b/src/core/QueueRunner.js @@ -1,4 +1,6 @@ getJasmineRequireObj().QueueRunner = function(j$) { + var nextid = 1; + function StopExecutionError() {} StopExecutionError.prototype = new Error(); j$.StopExecutionError = StopExecutionError; @@ -18,6 +20,7 @@ getJasmineRequireObj().QueueRunner = function(j$) { function emptyFn() {} function QueueRunner(attrs) { + this.id_ = nextid++; var queueableFns = attrs.queueableFns || []; this.queueableFns = queueableFns.concat(attrs.cleanupFns || []); this.firstCleanupIx = queueableFns.length; From 0b81705c112cb7d2b9da03112123174ed7f25841 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 2 Sep 2020 14:43:17 -0700 Subject: [PATCH 176/201] Detect global error handler stack corruption --- lib/jasmine-core/jasmine.js | 12 +++++++++++- spec/core/GlobalErrorsSpec.js | 19 ++++++++++++++++++- spec/core/integration/EnvSpec.js | 1 - src/core/GlobalErrors.js | 12 +++++++++++- 4 files changed, 40 insertions(+), 4 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 8b449d97..fb91318e 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -4117,7 +4117,17 @@ getJasmineRequireObj().GlobalErrors = function(j$) { handlers.push(listener); }; - this.popListener = function popListener() { + this.popListener = function popListener(listener) { + if (!listener) { + throw new Error('popListener expects a listener'); + } + + if (listener !== handlers[handlers.length - 1]) { + throw new Error( + 'popListener was passed a different listener than the current one' + ); + } + handlers.pop(); }; } diff --git a/spec/core/GlobalErrorsSpec.js b/spec/core/GlobalErrorsSpec.js index 3effa537..16657a7f 100644 --- a/spec/core/GlobalErrorsSpec.js +++ b/spec/core/GlobalErrorsSpec.js @@ -58,7 +58,7 @@ describe('GlobalErrors', function() { errors.pushListener(handler1); errors.pushListener(handler2); - errors.popListener(); + errors.popListener(handler2); fakeGlobal.onerror('foo'); @@ -66,6 +66,23 @@ describe('GlobalErrors', function() { expect(handler2).not.toHaveBeenCalled(); }); + it('throws when no listener is passed to #popListener', function() { + var errors = new jasmineUnderTest.GlobalErrors({}); + expect(function() { + errors.popListener(); + }).toThrowError('popListener expects a listener'); + }); + + it('throws when the argument to #popListener is not the current listener', function() { + var errors = new jasmineUnderTest.GlobalErrors({}); + errors.pushListener(function() {}); + expect(function() { + errors.popListener(function() {}); + }).toThrowError( + 'popListener was passed a different listener than the current one' + ); + }); + it('uninstalls itself, putting back a previous callback', function() { var originalCallback = jasmine.createSpy('error'), fakeGlobal = { onerror: originalCallback }, diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index cf1e997d..b51a7297 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -974,7 +974,6 @@ describe("Env integration", function() { env.execute(null, function() { expect(delayedFunctionForMockClock).toHaveBeenCalled(); expect(globalSetTimeout).toHaveBeenCalledWith(delayedFunctionForGlobalClock, 100); - done(); }); }); diff --git a/src/core/GlobalErrors.js b/src/core/GlobalErrors.js index 282eb262..b79976d9 100644 --- a/src/core/GlobalErrors.js +++ b/src/core/GlobalErrors.js @@ -96,7 +96,17 @@ getJasmineRequireObj().GlobalErrors = function(j$) { handlers.push(listener); }; - this.popListener = function popListener() { + this.popListener = function popListener(listener) { + if (!listener) { + throw new Error('popListener expects a listener'); + } + + if (listener !== handlers[handlers.length - 1]) { + throw new Error( + 'popListener was passed a different listener than the current one' + ); + } + handlers.pop(); }; } From 51ad18cb2814e6ed04b266e34526674f53703aba Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 12 Sep 2020 20:34:21 -0700 Subject: [PATCH 177/201] Warn if a runable both takes a callback and returns a promise --- lib/jasmine-core/jasmine.js | 27 ++++++++++++++++++++--- spec/core/QueueRunnerSpec.js | 42 ++++++++++++++++++++++++++++++++++++ src/core/QueueRunner.js | 27 ++++++++++++++++++++--- 3 files changed, 90 insertions(+), 6 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index fb91318e..71194eeb 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -7056,7 +7056,8 @@ getJasmineRequireObj().QueueRunner = function(j$) { }), errored = false, queueableFn = self.queueableFns[iterativeIndex], - timeoutId; + timeoutId, + maybeThenable; next.fail = function nextFail() { self.fail.apply(null, arguments); @@ -7084,7 +7085,7 @@ getJasmineRequireObj().QueueRunner = function(j$) { try { if (queueableFn.fn.length === 0) { - var maybeThenable = queueableFn.fn.call(self.userContext); + maybeThenable = queueableFn.fn.call(self.userContext); if (maybeThenable && j$.isFunction_(maybeThenable.then)) { maybeThenable.then(next, onPromiseRejection); @@ -7092,7 +7093,8 @@ getJasmineRequireObj().QueueRunner = function(j$) { return { completedSynchronously: false }; } } else { - queueableFn.fn.call(self.userContext, next); + maybeThenable = queueableFn.fn.call(self.userContext, next); + this.diagnoseConflictingAsync_(queueableFn.fn, maybeThenable); completedSynchronously = false; return { completedSynchronously: false }; } @@ -7145,6 +7147,25 @@ getJasmineRequireObj().QueueRunner = function(j$) { }); }; + QueueRunner.prototype.diagnoseConflictingAsync_ = function(fn, retval) { + if (retval && j$.isFunction_(retval.then)) { + // Issue a warning that matches the user's code + if (j$.isAsyncFunction_(fn)) { + this.deprecated('An asynchronous before/it/after ' + + 'function was defined with the async keyword but also took a ' + + 'done callback. This is not supported and will stop working in' + + ' the future. Either remove the done callback (recommended) or ' + + 'remove the async keyword.'); + } else { + this.deprecated('An asynchronous before/it/after ' + + 'function took a done callback but also returned a promise. ' + + 'This is not supported and will stop working in the future. ' + + 'Either remove the done callback (recommended) or change the ' + + 'function to not return a promise.'); + } + } + }; + return QueueRunner; }; diff --git a/spec/core/QueueRunnerSpec.js b/spec/core/QueueRunnerSpec.js index ac18b81d..c722aaff 100644 --- a/spec/core/QueueRunnerSpec.js +++ b/spec/core/QueueRunnerSpec.js @@ -512,6 +512,48 @@ describe('QueueRunner', function() { expect(onExceptionCallback).toHaveBeenCalledWith('foo'); expect(queueableFn2.fn).toHaveBeenCalled(); }); + + it('issues a deprecation if the function also takes a parameter', function() { + var queueableFn = { + fn: function(done) { + return new StubPromise(); + } + }, + deprecated = jasmine.createSpy('deprecated'), + queueRunner = new jasmineUnderTest.QueueRunner({ + queueableFns: [queueableFn], + deprecated: deprecated + }), + env = jasmineUnderTest.getEnv(); + + queueRunner.execute(); + + expect(deprecated).toHaveBeenCalledWith('An asynchronous ' + + 'before/it/after function took a done callback but also returned a '+ + 'promise. This is not supported and will stop working in the future. ' + + 'Either remove the done callback (recommended) or change the function ' + + 'to not return a promise.' + ); + }); + + it('issues a more specific deprecation if the function is `async`', function() { + jasmine.getEnv().requireAsyncAwait(); + eval('var fn = async function(done){};'); + var deprecated = jasmine.createSpy('deprecated'), + queueRunner = new jasmineUnderTest.QueueRunner({ + queueableFns: [{fn: fn}], + deprecated: deprecated + }); + + queueRunner.execute(); + + expect(deprecated).toHaveBeenCalledWith('An asynchronous ' + + 'before/it/after function was defined with the async keyword but ' + + 'also took a done callback. This is not supported and will stop ' + + 'working in the future. Either remove the done callback ' + + '(recommended) or remove the async keyword.' + ); + }); }); it('passes the error instance to exception handlers in HTML browsers', function() { diff --git a/src/core/QueueRunner.js b/src/core/QueueRunner.js index df383632..f009c3b5 100644 --- a/src/core/QueueRunner.js +++ b/src/core/QueueRunner.js @@ -123,7 +123,8 @@ getJasmineRequireObj().QueueRunner = function(j$) { }), errored = false, queueableFn = self.queueableFns[iterativeIndex], - timeoutId; + timeoutId, + maybeThenable; next.fail = function nextFail() { self.fail.apply(null, arguments); @@ -151,7 +152,7 @@ getJasmineRequireObj().QueueRunner = function(j$) { try { if (queueableFn.fn.length === 0) { - var maybeThenable = queueableFn.fn.call(self.userContext); + maybeThenable = queueableFn.fn.call(self.userContext); if (maybeThenable && j$.isFunction_(maybeThenable.then)) { maybeThenable.then(next, onPromiseRejection); @@ -159,7 +160,8 @@ getJasmineRequireObj().QueueRunner = function(j$) { return { completedSynchronously: false }; } } else { - queueableFn.fn.call(self.userContext, next); + maybeThenable = queueableFn.fn.call(self.userContext, next); + this.diagnoseConflictingAsync_(queueableFn.fn, maybeThenable); completedSynchronously = false; return { completedSynchronously: false }; } @@ -212,5 +214,24 @@ getJasmineRequireObj().QueueRunner = function(j$) { }); }; + QueueRunner.prototype.diagnoseConflictingAsync_ = function(fn, retval) { + if (retval && j$.isFunction_(retval.then)) { + // Issue a warning that matches the user's code + if (j$.isAsyncFunction_(fn)) { + this.deprecated('An asynchronous before/it/after ' + + 'function was defined with the async keyword but also took a ' + + 'done callback. This is not supported and will stop working in' + + ' the future. Either remove the done callback (recommended) or ' + + 'remove the async keyword.'); + } else { + this.deprecated('An asynchronous before/it/after ' + + 'function took a done callback but also returned a promise. ' + + 'This is not supported and will stop working in the future. ' + + 'Either remove the done callback (recommended) or change the ' + + 'function to not return a promise.'); + } + } + }; + return QueueRunner; }; From e7daa429a1808dc1b4a672d745133d1f3f826e2d Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sun, 13 Sep 2020 12:39:42 -0700 Subject: [PATCH 178/201] Show the name of the spec/suite that caused a deprecation --- lib/jasmine-core/jasmine-html.js | 35 ++++++++++++++++++++++++------- lib/jasmine-core/jasmine.js | 36 ++++++++++++++++++++++---------- spec/core/QueueRunnerSpec.js | 24 +++++++++++---------- spec/core/integration/EnvSpec.js | 5 ++++- spec/html/HtmlReporterSpec.js | 11 ++++++++-- src/core/Env.js | 12 ++++++++++- src/core/QueueRunner.js | 24 ++++++++++++--------- src/html/HtmlReporter.js | 35 ++++++++++++++++++++++++------- 8 files changed, 130 insertions(+), 52 deletions(-) diff --git a/lib/jasmine-core/jasmine-html.js b/lib/jasmine-core/jasmine-html.js index 307f20e0..26ae6ac9 100644 --- a/lib/jasmine-core/jasmine-html.js +++ b/lib/jasmine-core/jasmine-html.js @@ -132,7 +132,7 @@ jasmineRequire.HtmlReporter = function(j$) { if (result.status === 'failed') { failures.push(failureDom(result)); } - addDeprecationWarnings(result); + addDeprecationWarnings(result, 'suite'); }; this.specStarted = function(result) { @@ -168,7 +168,7 @@ jasmineRequire.HtmlReporter = function(j$) { failures.push(failureDom(result)); } - addDeprecationWarnings(result); + addDeprecationWarnings(result, 'spec'); }; this.displaySpecInCorrectFormat = function(result) { @@ -307,14 +307,27 @@ jasmineRequire.HtmlReporter = function(j$) { addDeprecationWarnings(doneResult); - var warningBarClassName = 'jasmine-bar jasmine-warning'; for (i = 0; i < deprecationWarnings.length; i++) { - var warning = deprecationWarnings[i]; + var context; + + switch (deprecationWarnings[i].runnableType) { + case 'spec': + context = '(in spec: ' + deprecationWarnings[i].runnableName + ')'; + break; + case 'suite': + context = '(in suite: ' + deprecationWarnings[i].runnableName + ')'; + break; + default: + context = ''; + } + alert.appendChild( createDom( 'span', - { className: warningBarClassName }, - 'DEPRECATION: ' + warning + { className: 'jasmine-bar jasmine-warning' }, + 'DEPRECATION: ' + deprecationWarnings[i].message, + createDom('br'), + context ) ); } @@ -625,12 +638,18 @@ jasmineRequire.HtmlReporter = function(j$) { return addToExistingQueryString('spec', els.join(' ')); } - function addDeprecationWarnings(result) { + function addDeprecationWarnings(result, runnableType) { if (result && result.deprecationWarnings) { for (var i = 0; i < result.deprecationWarnings.length; i++) { var warning = result.deprecationWarnings[i].message; + debugger; if (!j$.util.arrayContains(warning)) { - deprecationWarnings.push(warning); + debugger; + deprecationWarnings.push({ + message: warning, + runnableName: result.fullName, + runnableType: runnableType + }); } } } diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 71194eeb..f86e9f55 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1537,12 +1537,22 @@ getJasmineRequireObj().Env = function(j$) { this.deprecated = function(deprecation) { var runnable = currentRunnable() || topSuite; + var context; + + if (runnable === topSuite) { + context = ''; + } else if (runnable === currentSuite()) { + context = ' (in suite: ' + runnable.getFullName() + ')'; + } else { + context = ' (in spec: ' + runnable.getFullName() + ')'; + } + runnable.addDeprecationWarning(deprecation); if ( typeof console !== 'undefined' && typeof console.error === 'function' ) { - console.error('DEPRECATION:', deprecation); + console.error('DEPRECATION: ' + deprecation + context); } }; @@ -7151,17 +7161,21 @@ getJasmineRequireObj().QueueRunner = function(j$) { if (retval && j$.isFunction_(retval.then)) { // Issue a warning that matches the user's code if (j$.isAsyncFunction_(fn)) { - this.deprecated('An asynchronous before/it/after ' + - 'function was defined with the async keyword but also took a ' + - 'done callback. This is not supported and will stop working in' + - ' the future. Either remove the done callback (recommended) or ' + - 'remove the async keyword.'); + this.deprecated( + 'An asynchronous before/it/after ' + + 'function was defined with the async keyword but also took a ' + + 'done callback. This is not supported and will stop working in' + + ' the future. Either remove the done callback (recommended) or ' + + 'remove the async keyword.' + ); } else { - this.deprecated('An asynchronous before/it/after ' + - 'function took a done callback but also returned a promise. ' + - 'This is not supported and will stop working in the future. ' + - 'Either remove the done callback (recommended) or change the ' + - 'function to not return a promise.'); + this.deprecated( + 'An asynchronous before/it/after ' + + 'function took a done callback but also returned a promise. ' + + 'This is not supported and will stop working in the future. ' + + 'Either remove the done callback (recommended) or change the ' + + 'function to not return a promise.' + ); } } }; diff --git a/spec/core/QueueRunnerSpec.js b/spec/core/QueueRunnerSpec.js index c722aaff..7333b02a 100644 --- a/spec/core/QueueRunnerSpec.js +++ b/spec/core/QueueRunnerSpec.js @@ -528,11 +528,12 @@ describe('QueueRunner', function() { queueRunner.execute(); - expect(deprecated).toHaveBeenCalledWith('An asynchronous ' + - 'before/it/after function took a done callback but also returned a '+ - 'promise. This is not supported and will stop working in the future. ' + - 'Either remove the done callback (recommended) or change the function ' + - 'to not return a promise.' + expect(deprecated).toHaveBeenCalledWith( + 'An asynchronous ' + + 'before/it/after function took a done callback but also returned a ' + + 'promise. This is not supported and will stop working in the future. ' + + 'Either remove the done callback (recommended) or change the function ' + + 'to not return a promise.' ); }); @@ -541,17 +542,18 @@ describe('QueueRunner', function() { eval('var fn = async function(done){};'); var deprecated = jasmine.createSpy('deprecated'), queueRunner = new jasmineUnderTest.QueueRunner({ - queueableFns: [{fn: fn}], + queueableFns: [{ fn: fn }], deprecated: deprecated }); queueRunner.execute(); - expect(deprecated).toHaveBeenCalledWith('An asynchronous ' + - 'before/it/after function was defined with the async keyword but ' + - 'also took a done callback. This is not supported and will stop ' + - 'working in the future. Either remove the done callback ' + - '(recommended) or remove the async keyword.' + expect(deprecated).toHaveBeenCalledWith( + 'An asynchronous ' + + 'before/it/after function was defined with the async keyword but ' + + 'also took a done callback. This is not supported and will stop ' + + 'working in the future. Either remove the done callback ' + + '(recommended) or remove the async keyword.' ); }); }); diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index b51a7297..a11897b3 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -2294,7 +2294,7 @@ describe("Env integration", function() { it('should report deprecation warnings on the correct specs and suites', function(done) { var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); - // prevent deprecation from being displayed + // prevent deprecation from being displayed, as well as letting us observe calls spyOn(console, "error"); env.addReporter(reporter); @@ -2316,6 +2316,7 @@ describe("Env integration", function() { expect(result.deprecationWarnings).toEqual([ jasmine.objectContaining({ message: 'top level deprecation' }) ]); + expect(console.error).toHaveBeenCalledWith('DEPRECATION: top level deprecation'); expect(reporter.suiteDone).toHaveBeenCalledWith(jasmine.objectContaining({ fullName: 'suite', @@ -2323,6 +2324,7 @@ describe("Env integration", function() { jasmine.objectContaining({ message: 'suite level deprecation' }) ] })); + expect(console.error).toHaveBeenCalledWith('DEPRECATION: suite level deprecation (in suite: suite)'); expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ fullName: 'suite spec', @@ -2330,6 +2332,7 @@ describe("Env integration", function() { jasmine.objectContaining({ message: 'spec level deprecation' }) ] })); + expect(console.error).toHaveBeenCalledWith('DEPRECATION: spec level deprecation (in spec: suite spec)'); done(); }); diff --git a/spec/html/HtmlReporterSpec.js b/spec/html/HtmlReporterSpec.js index 3b4f20e5..c41b68bb 100644 --- a/spec/html/HtmlReporterSpec.js +++ b/spec/html/HtmlReporterSpec.js @@ -270,12 +270,14 @@ describe('HtmlReporter', function() { reporter.jasmineStarted({}); reporter.specDone({ status: 'passed', + fullName: 'a spec with a deprecation', deprecationWarnings: [{ message: 'spec deprecation' }], failedExpectations: [], passedExpectations: [] }); reporter.suiteDone({ status: 'passed', + fullName: 'a suite with a deprecation', deprecationWarnings: [{ message: 'suite deprecation' }], failedExpectations: [] }); @@ -287,12 +289,17 @@ describe('HtmlReporter', function() { var alertBars = container.querySelectorAll('.jasmine-alert .jasmine-bar'); expect(alertBars.length).toEqual(4); - expect(alertBars[1].innerHTML).toMatch(/spec deprecation/); + expect(alertBars[1].innerHTML).toMatch( + /spec deprecation.*\(in spec: a spec with a deprecation\)/ + ); expect(alertBars[1].getAttribute('class')).toEqual( 'jasmine-bar jasmine-warning' ); - expect(alertBars[2].innerHTML).toMatch(/suite deprecation/); + expect(alertBars[2].innerHTML).toMatch( + /suite deprecation.*\(in suite: a suite with a deprecation\)/ + ); expect(alertBars[3].innerHTML).toMatch(/global deprecation/); + expect(alertBars[3].innerHTML).not.toMatch(/in /); }); }); diff --git a/src/core/Env.js b/src/core/Env.js index 7e299717..a70413b8 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -581,12 +581,22 @@ getJasmineRequireObj().Env = function(j$) { this.deprecated = function(deprecation) { var runnable = currentRunnable() || topSuite; + var context; + + if (runnable === topSuite) { + context = ''; + } else if (runnable === currentSuite()) { + context = ' (in suite: ' + runnable.getFullName() + ')'; + } else { + context = ' (in spec: ' + runnable.getFullName() + ')'; + } + runnable.addDeprecationWarning(deprecation); if ( typeof console !== 'undefined' && typeof console.error === 'function' ) { - console.error('DEPRECATION:', deprecation); + console.error('DEPRECATION: ' + deprecation + context); } }; diff --git a/src/core/QueueRunner.js b/src/core/QueueRunner.js index f009c3b5..be9e7f62 100644 --- a/src/core/QueueRunner.js +++ b/src/core/QueueRunner.js @@ -218,17 +218,21 @@ getJasmineRequireObj().QueueRunner = function(j$) { if (retval && j$.isFunction_(retval.then)) { // Issue a warning that matches the user's code if (j$.isAsyncFunction_(fn)) { - this.deprecated('An asynchronous before/it/after ' + - 'function was defined with the async keyword but also took a ' + - 'done callback. This is not supported and will stop working in' + - ' the future. Either remove the done callback (recommended) or ' + - 'remove the async keyword.'); + this.deprecated( + 'An asynchronous before/it/after ' + + 'function was defined with the async keyword but also took a ' + + 'done callback. This is not supported and will stop working in' + + ' the future. Either remove the done callback (recommended) or ' + + 'remove the async keyword.' + ); } else { - this.deprecated('An asynchronous before/it/after ' + - 'function took a done callback but also returned a promise. ' + - 'This is not supported and will stop working in the future. ' + - 'Either remove the done callback (recommended) or change the ' + - 'function to not return a promise.'); + this.deprecated( + 'An asynchronous before/it/after ' + + 'function took a done callback but also returned a promise. ' + + 'This is not supported and will stop working in the future. ' + + 'Either remove the done callback (recommended) or change the ' + + 'function to not return a promise.' + ); } } }; diff --git a/src/html/HtmlReporter.js b/src/html/HtmlReporter.js index 24d3a404..7cb2227e 100644 --- a/src/html/HtmlReporter.js +++ b/src/html/HtmlReporter.js @@ -101,7 +101,7 @@ jasmineRequire.HtmlReporter = function(j$) { if (result.status === 'failed') { failures.push(failureDom(result)); } - addDeprecationWarnings(result); + addDeprecationWarnings(result, 'suite'); }; this.specStarted = function(result) { @@ -137,7 +137,7 @@ jasmineRequire.HtmlReporter = function(j$) { failures.push(failureDom(result)); } - addDeprecationWarnings(result); + addDeprecationWarnings(result, 'spec'); }; this.displaySpecInCorrectFormat = function(result) { @@ -276,14 +276,27 @@ jasmineRequire.HtmlReporter = function(j$) { addDeprecationWarnings(doneResult); - var warningBarClassName = 'jasmine-bar jasmine-warning'; for (i = 0; i < deprecationWarnings.length; i++) { - var warning = deprecationWarnings[i]; + var context; + + switch (deprecationWarnings[i].runnableType) { + case 'spec': + context = '(in spec: ' + deprecationWarnings[i].runnableName + ')'; + break; + case 'suite': + context = '(in suite: ' + deprecationWarnings[i].runnableName + ')'; + break; + default: + context = ''; + } + alert.appendChild( createDom( 'span', - { className: warningBarClassName }, - 'DEPRECATION: ' + warning + { className: 'jasmine-bar jasmine-warning' }, + 'DEPRECATION: ' + deprecationWarnings[i].message, + createDom('br'), + context ) ); } @@ -594,12 +607,18 @@ jasmineRequire.HtmlReporter = function(j$) { return addToExistingQueryString('spec', els.join(' ')); } - function addDeprecationWarnings(result) { + function addDeprecationWarnings(result, runnableType) { if (result && result.deprecationWarnings) { for (var i = 0; i < result.deprecationWarnings.length; i++) { var warning = result.deprecationWarnings[i].message; + debugger; if (!j$.util.arrayContains(warning)) { - deprecationWarnings.push(warning); + debugger; + deprecationWarnings.push({ + message: warning, + runnableName: result.fullName, + runnableType: runnableType + }); } } } From 795651d3b6d2b49c8278d01b61ef7384443e5157 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sun, 13 Sep 2020 13:40:15 -0700 Subject: [PATCH 179/201] Removed debugger statements --- lib/jasmine-core/jasmine-html.js | 2 -- src/html/HtmlReporter.js | 2 -- 2 files changed, 4 deletions(-) diff --git a/lib/jasmine-core/jasmine-html.js b/lib/jasmine-core/jasmine-html.js index 26ae6ac9..5e436b3e 100644 --- a/lib/jasmine-core/jasmine-html.js +++ b/lib/jasmine-core/jasmine-html.js @@ -642,9 +642,7 @@ jasmineRequire.HtmlReporter = function(j$) { if (result && result.deprecationWarnings) { for (var i = 0; i < result.deprecationWarnings.length; i++) { var warning = result.deprecationWarnings[i].message; - debugger; if (!j$.util.arrayContains(warning)) { - debugger; deprecationWarnings.push({ message: warning, runnableName: result.fullName, diff --git a/src/html/HtmlReporter.js b/src/html/HtmlReporter.js index 7cb2227e..e591ccac 100644 --- a/src/html/HtmlReporter.js +++ b/src/html/HtmlReporter.js @@ -611,9 +611,7 @@ jasmineRequire.HtmlReporter = function(j$) { if (result && result.deprecationWarnings) { for (var i = 0; i < result.deprecationWarnings.length; i++) { var warning = result.deprecationWarnings[i].message; - debugger; if (!j$.util.arrayContains(warning)) { - debugger; deprecationWarnings.push({ message: warning, runnableName: result.fullName, From 7d5ca27b9db253174811b4a601f0a01115beec08 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 17 Sep 2020 13:33:25 -0700 Subject: [PATCH 180/201] Check for forgotten console and debugger statements --- spec/.eslintrc.js | 8 +++++++- spec/core/integration/EnvSpec.js | 3 +++ spec/core/matchers/matchersUtilSpec.js | 1 + spec/html/HtmlReporterSpec.js | 2 ++ 4 files changed, 13 insertions(+), 1 deletion(-) diff --git a/spec/.eslintrc.js b/spec/.eslintrc.js index bfbec213..636eed53 100644 --- a/spec/.eslintrc.js +++ b/spec/.eslintrc.js @@ -13,5 +13,11 @@ module.exports = { "no-unused-vars": "off", "no-trailing-spaces": "off", "block-spacing": "off", + + // Since linting is done at the end of the process and doesn't stop us + // from running tests, it makes sense to fail if debugger statements + // or console references are present. + "no-debugger": "error", + "no-console": "error", } -} +}; diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index a11897b3..2c09affd 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -2316,6 +2316,7 @@ describe("Env integration", function() { expect(result.deprecationWarnings).toEqual([ jasmine.objectContaining({ message: 'top level deprecation' }) ]); + /* eslint-disable-next-line no-console */ expect(console.error).toHaveBeenCalledWith('DEPRECATION: top level deprecation'); expect(reporter.suiteDone).toHaveBeenCalledWith(jasmine.objectContaining({ @@ -2324,6 +2325,7 @@ describe("Env integration", function() { jasmine.objectContaining({ message: 'suite level deprecation' }) ] })); + /* eslint-disable-next-line no-console */ expect(console.error).toHaveBeenCalledWith('DEPRECATION: suite level deprecation (in suite: suite)'); expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ @@ -2332,6 +2334,7 @@ describe("Env integration", function() { jasmine.objectContaining({ message: 'spec level deprecation' }) ] })); + /* eslint-disable-next-line no-console */ expect(console.error).toHaveBeenCalledWith('DEPRECATION: spec level deprecation (in spec: suite spec)'); done(); diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index e3ee9e8c..387aa3e2 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -32,6 +32,7 @@ describe("matchersUtil", function() { // Be thorough but very slow when specified (usually on CI). if (process.env.JASMINE_LONG_PROPERTY_TESTS) { + /* eslint-disable-next-line no-console */ console.log( 'Using', many, diff --git a/spec/html/HtmlReporterSpec.js b/spec/html/HtmlReporterSpec.js index c41b68bb..2db0e160 100644 --- a/spec/html/HtmlReporterSpec.js +++ b/spec/html/HtmlReporterSpec.js @@ -104,6 +104,7 @@ describe('HtmlReporter', function() { passedExpectations: [], failedExpectations: [] }); + /* eslint-disable-next-line no-console */ expect(console.warn).toHaveBeenCalledWith( "Spec 'Some Name' has no expectations." ); @@ -118,6 +119,7 @@ describe('HtmlReporter', function() { passedExpectations: [], failedExpectations: [] }); + /* eslint-disable-next-line no-console */ expect(console.error).toHaveBeenCalledWith( "Spec 'Some Name' has no expectations." ); From d27bb8fa964c5287dfa6fb5ac6988872aaab90eb Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 29 Sep 2020 18:05:38 -0700 Subject: [PATCH 181/201] Run Prettier on all files --- package.json | 4 +- spec/.eslintrc.js | 23 +- spec/core/asymmetric_equality/AnySpec.js | 32 +- spec/core/asymmetric_equality/AnythingSpec.js | 22 +- .../ArrayContainingSpec.js | 54 +- .../ArrayWithExactContentsSpec.js | 36 +- spec/core/asymmetric_equality/EmptySpec.js | 20 +- spec/core/asymmetric_equality/FalsySpec.js | 56 +- .../asymmetric_equality/MapContainingSpec.js | 114 +- spec/core/asymmetric_equality/NotEmptySpec.js | 20 +- .../ObjectContainingSpec.js | 143 +- .../asymmetric_equality/SetContainingSpec.js | 63 +- .../asymmetric_equality/StringMatchingSpec.js | 12 +- spec/core/asymmetric_equality/TruthySpec.js | 28 +- .../AsymmetricEqualityTestersSpec.js | 153 +- .../integration/CustomAsyncMatchersSpec.js | 60 +- spec/core/integration/CustomMatchersSpec.js | 182 +- .../integration/CustomObjectFormatterSpec.js | 42 +- .../integration/CustomSpyStrategiesSpec.js | 27 +- .../integration/DefaultSpyStrategySpec.js | 14 +- spec/core/integration/EnvSpec.js | 1812 ++++++++++------- spec/core/integration/MatchersSpec.js | 171 +- spec/core/integration/SpecRunningSpec.js | 430 ++-- spec/core/matchers/DiffBuilderSpec.js | 161 +- spec/core/matchers/MismatchTreeSpec.js | 52 +- spec/core/matchers/NullDiffBuilderSpec.js | 5 +- spec/core/matchers/async/toBePendingSpec.js | 14 +- spec/core/matchers/async/toBeRejectedSpec.js | 8 +- .../async/toBeRejectedWithErrorSpec.js | 261 ++- .../matchers/async/toBeRejectedWithSpec.js | 67 +- spec/core/matchers/async/toBeResolvedSpec.js | 8 +- .../core/matchers/async/toBeResolvedToSpec.js | 66 +- spec/core/matchers/matchersUtilSpec.js | 635 +++--- spec/core/matchers/toBeCloseToSpec.js | 30 +- spec/core/matchers/toBeDefinedSpec.js | 9 +- spec/core/matchers/toBeFalseSpec.js | 8 +- spec/core/matchers/toBeFalsySpec.js | 4 +- .../matchers/toBeGreaterThanOrEqualSpec.js | 8 +- spec/core/matchers/toBeGreaterThanSpec.js | 6 +- spec/core/matchers/toBeInstanceOfSpec.js | 27 +- spec/core/matchers/toBeLessThanOrEqualSpec.js | 8 +- spec/core/matchers/toBeLessThanSpec.js | 6 +- spec/core/matchers/toBeNaNSpec.js | 12 +- .../core/matchers/toBeNegativeInfinitySpec.js | 11 +- spec/core/matchers/toBeNullSpec.js | 6 +- .../core/matchers/toBePositiveInfinitySpec.js | 11 +- spec/core/matchers/toBeSpec.js | 64 +- spec/core/matchers/toBeTrueSpec.js | 6 +- spec/core/matchers/toBeTruthySpec.js | 4 +- spec/core/matchers/toBeUndefinedSpec.js | 9 +- spec/core/matchers/toContainSpec.js | 16 +- spec/core/matchers/toEqualSpec.js | 678 +++--- .../matchers/toHaveBeenCalledBeforeSpec.js | 62 +- .../matchers/toHaveBeenCalledOnceWithSpec.js | 57 +- spec/core/matchers/toHaveBeenCalledSpec.js | 29 +- .../matchers/toHaveBeenCalledTimesSpec.js | 45 +- .../core/matchers/toHaveBeenCalledWithSpec.js | 105 +- spec/core/matchers/toHaveClassSpec.js | 9 +- spec/core/matchers/toHaveSizeSpec.js | 16 +- spec/core/matchers/toMatchSpec.js | 14 +- spec/core/matchers/toThrowErrorSpec.js | 169 +- spec/core/matchers/toThrowMatchingSpec.js | 54 +- spec/core/matchers/toThrowSpec.js | 39 +- src/core/asymmetric_equality/Any.js | 3 +- src/core/asymmetric_equality/Anything.js | 1 - .../asymmetric_equality/ArrayContaining.js | 10 +- .../ArrayWithExactContents.js | 12 +- src/core/asymmetric_equality/Empty.js | 7 +- src/core/asymmetric_equality/Falsy.js | 1 - src/core/asymmetric_equality/MapContaining.js | 8 +- src/core/asymmetric_equality/NotEmpty.js | 7 +- .../asymmetric_equality/ObjectContaining.js | 23 +- src/core/asymmetric_equality/SetContaining.js | 4 +- .../asymmetric_equality/StringMatching.js | 1 - src/core/asymmetric_equality/Truthy.js | 1 - src/core/matchers/DiffBuilder.js | 59 +- src/core/matchers/MismatchTree.js | 11 +- src/core/matchers/ObjectPath.js | 2 +- src/core/matchers/async/toBePending.js | 8 +- src/core/matchers/async/toBeRejected.js | 8 +- src/core/matchers/async/toBeRejectedWith.js | 43 +- .../matchers/async/toBeRejectedWithError.js | 45 +- src/core/matchers/async/toBeResolved.js | 8 +- src/core/matchers/async/toBeResolvedTo.js | 13 +- src/core/matchers/matchersUtil.js | 240 ++- src/core/matchers/toBe.js | 11 +- src/core/matchers/toBeCloseTo.js | 9 +- src/core/matchers/toBeDefined.js | 2 +- src/core/matchers/toBeGreaterThan.js | 1 - src/core/matchers/toBeInstanceOf.js | 38 +- src/core/matchers/toBeLessThan.js | 1 - src/core/matchers/toBeLessThanOrEqual.js | 1 - src/core/matchers/toBeNaN.js | 6 +- src/core/matchers/toBeNegativeInfinity.js | 6 +- src/core/matchers/toBePositiveInfinity.js | 6 +- src/core/matchers/toContain.js | 1 - src/core/matchers/toEqual.js | 2 +- src/core/matchers/toHaveBeenCalled.js | 22 +- src/core/matchers/toHaveBeenCalledBefore.js | 53 +- src/core/matchers/toHaveBeenCalledOnceWith.js | 68 +- src/core/matchers/toHaveBeenCalledTimes.js | 36 +- src/core/matchers/toHaveBeenCalledWith.js | 76 +- src/core/matchers/toHaveClass.js | 6 +- src/core/matchers/toHaveSize.js | 19 +- src/core/matchers/toMatch.js | 6 +- src/core/matchers/toThrow.js | 32 +- src/core/matchers/toThrowError.js | 63 +- src/core/matchers/toThrowMatching.js | 28 +- 108 files changed, 4399 insertions(+), 2926 deletions(-) diff --git a/package.json b/package.json index 0ef7ddd8..ae77c27f 100644 --- a/package.json +++ b/package.json @@ -13,9 +13,9 @@ "bdd" ], "scripts": { - "posttest": "eslint \"src/**/*.js\" \"spec/**/*.js\" && prettier --check src/**/*.js spec/**/*.js", + "posttest": "eslint \"src/**/*.js\" \"spec/**/*.js\" && prettier --check \"src/**/*.js\" \"spec/**/*.js\"", "test": "grunt --stack execSpecsInNode", - "cleanup": "prettier --write src/**/*.js spec/**/*.js", + "cleanup": "prettier --write \"src/**/*.js\" \"spec/**/*.js\"", "build": "grunt buildDistribution", "serve": "node spec/support/localJasmineBrowser.js", "serve:performance": "node spec/support/localJasmineBrowser.js jasmine-browser-performance.json", diff --git a/spec/.eslintrc.js b/spec/.eslintrc.js index 636eed53..20f58dfa 100644 --- a/spec/.eslintrc.js +++ b/spec/.eslintrc.js @@ -1,23 +1,20 @@ module.exports = { - "ignorePatterns": [ - "support/ci.js", - "support/jasmine-browser.js" - ], + ignorePatterns: ['support/ci.js', 'support/jasmine-browser.js'], rules: { // Relax rules for now to allow for the quirks of the test suite // TODO: We should probably remove these & fix the resulting errors - "quotes": "off", - "semi": "off", - "key-spacing": "off", - "space-before-blocks": "off", - "no-unused-vars": "off", - "no-trailing-spaces": "off", - "block-spacing": "off", + quotes: 'off', + semi: 'off', + 'key-spacing': 'off', + 'space-before-blocks': 'off', + 'no-unused-vars': 'off', + 'no-trailing-spaces': 'off', + 'block-spacing': 'off', // Since linting is done at the end of the process and doesn't stop us // from running tests, it makes sense to fail if debugger statements // or console references are present. - "no-debugger": "error", - "no-console": "error", + 'no-debugger': 'error', + 'no-console': 'error' } }; diff --git a/spec/core/asymmetric_equality/AnySpec.js b/spec/core/asymmetric_equality/AnySpec.js index 8e28c306..0903cf84 100644 --- a/spec/core/asymmetric_equality/AnySpec.js +++ b/spec/core/asymmetric_equality/AnySpec.js @@ -1,35 +1,35 @@ -describe("Any", function() { - it("matches a string", function() { +describe('Any', function() { + it('matches a string', function() { var any = new jasmineUnderTest.Any(String); - expect(any.asymmetricMatch("foo")).toBe(true); + expect(any.asymmetricMatch('foo')).toBe(true); }); - it("matches a number", function() { + it('matches a number', function() { var any = new jasmineUnderTest.Any(Number); expect(any.asymmetricMatch(1)).toBe(true); }); - it("matches a function", function() { + it('matches a function', function() { var any = new jasmineUnderTest.Any(Function); - expect(any.asymmetricMatch(function(){})).toBe(true); + expect(any.asymmetricMatch(function() {})).toBe(true); }); - it("matches an Object", function() { + it('matches an Object', function() { var any = new jasmineUnderTest.Any(Object); expect(any.asymmetricMatch({})).toBe(true); }); - it("matches a Boolean", function() { + it('matches a Boolean', function() { var any = new jasmineUnderTest.Any(Boolean); expect(any.asymmetricMatch(true)).toBe(true); }); - it("matches a Map", function() { + it('matches a Map', function() { jasmine.getEnv().requireFunctioningMaps(); var any = new jasmineUnderTest.Any(Map); @@ -37,7 +37,7 @@ describe("Any", function() { expect(any.asymmetricMatch(new Map())).toBe(true); // eslint-disable-line compat/compat }); - it("matches a Set", function() { + it('matches a Set', function() { jasmine.getEnv().requireFunctioningSets(); var any = new jasmineUnderTest.Any(Set); @@ -45,7 +45,7 @@ describe("Any", function() { expect(any.asymmetricMatch(new Set())).toBe(true); // eslint-disable-line compat/compat }); - it("matches a TypedArray", function() { + it('matches a TypedArray', function() { jasmine.getEnv().requireFunctioningTypedArrays(); var any = new jasmineUnderTest.Any(Uint32Array); // eslint-disable-line compat/compat @@ -53,7 +53,7 @@ describe("Any", function() { expect(any.asymmetricMatch(new Uint32Array([]))).toBe(true); // eslint-disable-line compat/compat }); - it("matches a Symbol", function() { + it('matches a Symbol', function() { jasmine.getEnv().requireFunctioningSymbols(); var any = new jasmineUnderTest.Any(Symbol); // eslint-disable-line compat/compat @@ -61,14 +61,14 @@ describe("Any", function() { expect(any.asymmetricMatch(Symbol())).toBe(true); // eslint-disable-line compat/compat }); - it("matches another constructed object", function() { + it('matches another constructed object', function() { var Thing = function() {}, any = new jasmineUnderTest.Any(Thing); expect(any.asymmetricMatch(new Thing())).toBe(true); }); - it("does not treat null as an Object", function() { + it('does not treat null as an Object', function() { var any = new jasmineUnderTest.Any(Object); expect(any.asymmetricMatch(null)).toBe(false); @@ -81,8 +81,8 @@ describe("Any", function() { expect(any.jasmineToString()).toEqual(''); }); - describe("when called without an argument", function() { - it("tells the user to pass a constructor or use jasmine.anything()", function() { + describe('when called without an argument', function() { + it('tells the user to pass a constructor or use jasmine.anything()', function() { expect(function() { new jasmineUnderTest.Any(); }).toThrowError(TypeError, /constructor.*anything/); diff --git a/spec/core/asymmetric_equality/AnythingSpec.js b/spec/core/asymmetric_equality/AnythingSpec.js index 4e251b91..61ac14e5 100644 --- a/spec/core/asymmetric_equality/AnythingSpec.js +++ b/spec/core/asymmetric_equality/AnythingSpec.js @@ -1,29 +1,29 @@ -describe("Anything", function() { - it("matches a string", function() { +describe('Anything', function() { + it('matches a string', function() { var anything = new jasmineUnderTest.Anything(); expect(anything.asymmetricMatch('foo')).toBe(true); }); - it("matches a number", function() { + it('matches a number', function() { var anything = new jasmineUnderTest.Anything(); expect(anything.asymmetricMatch(42)).toBe(true); }); - it("matches an object", function() { + it('matches an object', function() { var anything = new jasmineUnderTest.Anything(); expect(anything.asymmetricMatch({ foo: 'bar' })).toBe(true); }); - it("matches an array", function() { + it('matches an array', function() { var anything = new jasmineUnderTest.Anything(); - expect(anything.asymmetricMatch([1,2,3])).toBe(true); + expect(anything.asymmetricMatch([1, 2, 3])).toBe(true); }); - it("matches a Map", function() { + it('matches a Map', function() { jasmine.getEnv().requireFunctioningMaps(); var anything = new jasmineUnderTest.Anything(); @@ -31,7 +31,7 @@ describe("Anything", function() { expect(anything.asymmetricMatch(new Map())).toBe(true); // eslint-disable-line compat/compat }); - it("matches a Set", function() { + it('matches a Set', function() { jasmine.getEnv().requireFunctioningSets(); var anything = new jasmineUnderTest.Anything(); @@ -39,7 +39,7 @@ describe("Anything", function() { expect(anything.asymmetricMatch(new Set())).toBe(true); // eslint-disable-line compat/compat }); - it("matches a TypedArray", function() { + it('matches a TypedArray', function() { jasmine.getEnv().requireFunctioningTypedArrays(); var anything = new jasmineUnderTest.Anything(); @@ -47,7 +47,7 @@ describe("Anything", function() { expect(anything.asymmetricMatch(new Uint32Array([]))).toBe(true); // eslint-disable-line compat/compat }); - it("matches a Symbol", function() { + it('matches a Symbol', function() { jasmine.getEnv().requireFunctioningSymbols(); var anything = new jasmineUnderTest.Anything(); @@ -71,6 +71,6 @@ describe("Anything", function() { it("jasmineToString's itself", function() { var anything = new jasmineUnderTest.Anything(); - expect(anything.jasmineToString()).toEqual(""); + expect(anything.jasmineToString()).toEqual(''); }); }); diff --git a/spec/core/asymmetric_equality/ArrayContainingSpec.js b/spec/core/asymmetric_equality/ArrayContainingSpec.js index 33e411e6..71d44df3 100644 --- a/spec/core/asymmetric_equality/ArrayContainingSpec.js +++ b/spec/core/asymmetric_equality/ArrayContainingSpec.js @@ -1,47 +1,47 @@ -describe("ArrayContaining", function() { - it("matches any actual to an empty array", function() { +describe('ArrayContaining', function() { + it('matches any actual to an empty array', function() { var containing = new jasmineUnderTest.ArrayContaining([]); - expect(containing.asymmetricMatch("foo")).toBe(true); + expect(containing.asymmetricMatch('foo')).toBe(true); }); - it("does not work when not passed an array", function() { - var containing = new jasmineUnderTest.ArrayContaining("foo"); + it('does not work when not passed an array', function() { + var containing = new jasmineUnderTest.ArrayContaining('foo'); expect(function() { containing.asymmetricMatch([]); }).toThrowError(/not 'foo'/); }); - it("matches when the item is in the actual", function() { - var containing = new jasmineUnderTest.ArrayContaining(["foo"]); + it('matches when the item is in the actual', function() { + var containing = new jasmineUnderTest.ArrayContaining(['foo']); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(["foo"], matchersUtil)).toBe(true); + expect(containing.asymmetricMatch(['foo'], matchersUtil)).toBe(true); }); - it("matches when additional items are in the actual", function() { - var containing = new jasmineUnderTest.ArrayContaining(["foo"]); + it('matches when additional items are in the actual', function() { + var containing = new jasmineUnderTest.ArrayContaining(['foo']); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(["foo", "bar"], matchersUtil)).toBe(true); + expect(containing.asymmetricMatch(['foo', 'bar'], matchersUtil)).toBe(true); }); - it("does not match when the item is not in the actual", function() { - var containing = new jasmineUnderTest.ArrayContaining(["foo"]); + it('does not match when the item is not in the actual', function() { + var containing = new jasmineUnderTest.ArrayContaining(['foo']); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch(["bar"], matchersUtil)).toBe(false); + expect(containing.asymmetricMatch(['bar'], matchersUtil)).toBe(false); }); - it("does not match when the actual is not an array", function() { - var containing = new jasmineUnderTest.ArrayContaining(["foo"]); + it('does not match when the actual is not an array', function() { + var containing = new jasmineUnderTest.ArrayContaining(['foo']); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch("foo", matchersUtil)).toBe(false); + expect(containing.asymmetricMatch('foo', matchersUtil)).toBe(false); }); - it("jasmineToStrings itself", function() { + it('jasmineToStrings itself', function() { var sample = [], matcher = new jasmineUnderTest.ArrayContaining(sample), pp = jasmine.createSpy('pp').and.returnValue('sample'); @@ -52,17 +52,23 @@ describe("ArrayContaining", function() { expect(pp).toHaveBeenCalledWith(sample); }); - it("uses custom equality testers", function() { + it('uses custom equality testers', function() { var tester = function(a, b) { // All "foo*" strings match each other. - if (typeof a == "string" && typeof b == "string" && - a.substr(0, 3) == "foo" && b.substr(0, 3) == "foo") { + if ( + typeof a == 'string' && + typeof b == 'string' && + a.substr(0, 3) == 'foo' && + b.substr(0, 3) == 'foo' + ) { return true; } }; - var containing = new jasmineUnderTest.ArrayContaining(["fooVal"]); - var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); + var containing = new jasmineUnderTest.ArrayContaining(['fooVal']); + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [tester] + }); - expect(containing.asymmetricMatch(["fooBar"], matchersUtil)).toBe(true); + expect(containing.asymmetricMatch(['fooBar'], matchersUtil)).toBe(true); }); }); diff --git a/spec/core/asymmetric_equality/ArrayWithExactContentsSpec.js b/spec/core/asymmetric_equality/ArrayWithExactContentsSpec.js index fd0bb30c..c25470ae 100644 --- a/spec/core/asymmetric_equality/ArrayWithExactContentsSpec.js +++ b/spec/core/asymmetric_equality/ArrayWithExactContentsSpec.js @@ -1,35 +1,37 @@ -describe("ArrayWithExactContents", function() { - it("matches an array with the same items in a different order", function() { +describe('ArrayWithExactContents', function() { + it('matches an array with the same items in a different order', function() { var matcher = new jasmineUnderTest.ArrayWithExactContents(['a', 2, /a/]); var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matcher.asymmetricMatch([2, 'a', /a/], matchersUtil)).toBe(true); }); - it("does not work when not passed an array", function() { - var matcher = new jasmineUnderTest.ArrayWithExactContents("foo"); + it('does not work when not passed an array', function() { + var matcher = new jasmineUnderTest.ArrayWithExactContents('foo'); expect(function() { matcher.asymmetricMatch([]); }).toThrowError(/not 'foo'/); }); - it("does not match when an item is missing", function() { + it('does not match when an item is missing', function() { var matcher = new jasmineUnderTest.ArrayWithExactContents(['a', 2, /a/]); var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matcher.asymmetricMatch(['a', 2], matchersUtil)).toBe(false); - expect(matcher.asymmetricMatch(['a', 2, undefined], matchersUtil)).toBe(false); + expect(matcher.asymmetricMatch(['a', 2, undefined], matchersUtil)).toBe( + false + ); }); - it("does not match when there is an extra item", function() { + it('does not match when there is an extra item', function() { var matcher = new jasmineUnderTest.ArrayWithExactContents(['a']); var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matcher.asymmetricMatch(['a', 2], matchersUtil)).toBe(false); }); - it("jasmineToStrings itself", function() { + it('jasmineToStrings itself', function() { var sample = [], matcher = new jasmineUnderTest.ArrayWithExactContents(sample), pp = jasmine.createSpy('pp').and.returnValue('sample'); @@ -40,17 +42,23 @@ describe("ArrayWithExactContents", function() { expect(pp).toHaveBeenCalledWith(sample); }); - it("uses custom equality testers", function() { + it('uses custom equality testers', function() { var tester = function(a, b) { // All "foo*" strings match each other. - if (typeof a == "string" && typeof b == "string" && - a.substr(0, 3) == "foo" && b.substr(0, 3) == "foo") { + if ( + typeof a == 'string' && + typeof b == 'string' && + a.substr(0, 3) == 'foo' && + b.substr(0, 3) == 'foo' + ) { return true; } }; - var matcher = new jasmineUnderTest.ArrayWithExactContents(["fooVal"]); - var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); + var matcher = new jasmineUnderTest.ArrayWithExactContents(['fooVal']); + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [tester] + }); - expect(matcher.asymmetricMatch(["fooBar"], matchersUtil)).toBe(true); + expect(matcher.asymmetricMatch(['fooBar'], matchersUtil)).toBe(true); }); }); diff --git a/spec/core/asymmetric_equality/EmptySpec.js b/spec/core/asymmetric_equality/EmptySpec.js index 48271ce5..4ef48a86 100644 --- a/spec/core/asymmetric_equality/EmptySpec.js +++ b/spec/core/asymmetric_equality/EmptySpec.js @@ -1,27 +1,27 @@ -describe("Empty", function () { - it("matches an empty object", function () { +describe('Empty', function() { + it('matches an empty object', function() { var empty = new jasmineUnderTest.Empty(); expect(empty.asymmetricMatch({})).toBe(true); - expect(empty.asymmetricMatch({undefined: false})).toBe(false); + expect(empty.asymmetricMatch({ undefined: false })).toBe(false); }); - it("matches an empty array", function () { + it('matches an empty array', function() { var empty = new jasmineUnderTest.Empty(); expect(empty.asymmetricMatch([])).toBe(true); expect(empty.asymmetricMatch([1, 12, 3])).toBe(false); }); - it("matches an empty string", function () { + it('matches an empty string', function() { var empty = new jasmineUnderTest.Empty(); - expect(empty.asymmetricMatch("")).toBe(true); + expect(empty.asymmetricMatch('')).toBe(true); expect(empty.asymmetricMatch('')).toBe(true); expect(empty.asymmetricMatch('12312')).toBe(false); }); - it("matches an empty map", function () { + it('matches an empty map', function() { jasmine.getEnv().requireFunctioningMaps(); var empty = new jasmineUnderTest.Empty(); var fullMap = new Map(); // eslint-disable-line compat/compat @@ -31,7 +31,7 @@ describe("Empty", function () { expect(empty.asymmetricMatch(fullMap)).toBe(false); }); - it("matches an empty set", function () { + it('matches an empty set', function() { jasmine.getEnv().requireFunctioningSets(); var empty = new jasmineUnderTest.Empty(); var fullSet = new Set(); // eslint-disable-line compat/compat @@ -41,11 +41,11 @@ describe("Empty", function () { expect(empty.asymmetricMatch(fullSet)).toBe(false); }); - it("matches an empty typed array", function() { + it('matches an empty typed array', function() { jasmine.getEnv().requireFunctioningTypedArrays(); var empty = new jasmineUnderTest.Empty(); expect(empty.asymmetricMatch(new Int16Array())).toBe(true); // eslint-disable-line compat/compat - expect(empty.asymmetricMatch(new Int16Array([1,2]))).toBe(false); // eslint-disable-line compat/compat + expect(empty.asymmetricMatch(new Int16Array([1, 2]))).toBe(false); // eslint-disable-line compat/compat }); }); diff --git a/spec/core/asymmetric_equality/FalsySpec.js b/spec/core/asymmetric_equality/FalsySpec.js index 581bedcb..f511c145 100644 --- a/spec/core/asymmetric_equality/FalsySpec.js +++ b/spec/core/asymmetric_equality/FalsySpec.js @@ -1,38 +1,38 @@ -describe("Falsy", function() { - it("is true for an empty string", function() { - var falsy = new jasmineUnderTest.Falsy(); +describe('Falsy', function() { + it('is true for an empty string', function() { + var falsy = new jasmineUnderTest.Falsy(); - expect(falsy.asymmetricMatch("")).toBe(true); - expect(falsy.asymmetricMatch('')).toBe(true); - expect(falsy.asymmetricMatch('asdasdad')).toBe(false); - }); + expect(falsy.asymmetricMatch('')).toBe(true); + expect(falsy.asymmetricMatch('')).toBe(true); + expect(falsy.asymmetricMatch('asdasdad')).toBe(false); + }); - it("is false for a number that is 0", function() { - var falsy = new jasmineUnderTest.Falsy(Number); + it('is false for a number that is 0', function() { + var falsy = new jasmineUnderTest.Falsy(Number); - expect(falsy.asymmetricMatch(1)).toBe(false); - expect(falsy.asymmetricMatch(0)).toBe(true); - expect(falsy.asymmetricMatch(-23)).toBe(false); - expect(falsy.asymmetricMatch(-3.1)).toBe(false); - }); + expect(falsy.asymmetricMatch(1)).toBe(false); + expect(falsy.asymmetricMatch(0)).toBe(true); + expect(falsy.asymmetricMatch(-23)).toBe(false); + expect(falsy.asymmetricMatch(-3.1)).toBe(false); + }); - it("is true for a null or undefined", function() { - var falsy = new jasmineUnderTest.Falsy(Function); + it('is true for a null or undefined', function() { + var falsy = new jasmineUnderTest.Falsy(Function); - expect(falsy.asymmetricMatch(null)).toBe(true); - expect(falsy.asymmetricMatch(undefined )).toBe(true); - }); + expect(falsy.asymmetricMatch(null)).toBe(true); + expect(falsy.asymmetricMatch(undefined)).toBe(true); + }); - it("is true for NaN", function() { - var falsy = new jasmineUnderTest.Falsy(Object); + it('is true for NaN', function() { + var falsy = new jasmineUnderTest.Falsy(Object); - expect(falsy.asymmetricMatch(NaN)).toBe(true); - }); + expect(falsy.asymmetricMatch(NaN)).toBe(true); + }); - it("is true for a false Boolean", function() { - var falsy = new jasmineUnderTest.Falsy(Boolean); + it('is true for a false Boolean', function() { + var falsy = new jasmineUnderTest.Falsy(Boolean); - expect(falsy.asymmetricMatch(false)).toBe(true); - expect(falsy.asymmetricMatch(true)).toBe(false); - }); + expect(falsy.asymmetricMatch(false)).toBe(true); + expect(falsy.asymmetricMatch(true)).toBe(false); + }); }); diff --git a/spec/core/asymmetric_equality/MapContainingSpec.js b/spec/core/asymmetric_equality/MapContainingSpec.js index dc89218d..d55c450b 100644 --- a/spec/core/asymmetric_equality/MapContainingSpec.js +++ b/spec/core/asymmetric_equality/MapContainingSpec.js @@ -1,6 +1,7 @@ /* eslint-disable compat/compat */ describe('MapContaining', function() { - function MapI(iterable) { // for IE11 + function MapI(iterable) { + // for IE11 var map = new Map(); iterable.forEach(function(kv) { map.set(kv[0], kv[1]); @@ -12,7 +13,6 @@ describe('MapContaining', function() { jasmine.getEnv().requireFunctioningMaps(); }); - it('matches any actual map to an empty map', function() { var actualMap = new MapI([['foo', 'bar']]); var containing = new jasmineUnderTest.MapContaining(new Map()); @@ -23,14 +23,11 @@ describe('MapContaining', function() { it('matches when all the key/value pairs in sample have matches in actual', function() { var actualMap = new MapI([ ['foo', [1, 2, 3]], - [{'foo': 'bar'}, 'baz'], - ['other', 'any'], + [{ foo: 'bar' }, 'baz'], + ['other', 'any'] ]); - var containingMap = new MapI([ - [{'foo': 'bar'}, 'baz'], - ['foo', [1, 2, 3]], - ]); + var containingMap = new MapI([[{ foo: 'bar' }, 'baz'], ['foo', [1, 2, 3]]]); var containing = new jasmineUnderTest.MapContaining(containingMap); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -40,13 +37,10 @@ describe('MapContaining', function() { it('does not match when a key is not in actual', function() { var actualMap = new MapI([ ['foo', [1, 2, 3]], - [{'foo': 'not a bar'}, 'baz'], + [{ foo: 'not a bar' }, 'baz'] ]); - var containingMap = new MapI([ - [{'foo': 'bar'}, 'baz'], - ['foo', [1, 2, 3]], - ]); + var containingMap = new MapI([[{ foo: 'bar' }, 'baz'], ['foo', [1, 2, 3]]]); var containing = new jasmineUnderTest.MapContaining(containingMap); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -54,15 +48,9 @@ describe('MapContaining', function() { }); it('does not match when a value is not in actual', function() { - var actualMap = new MapI([ - ['foo', [1, 2, 3]], - [{'foo': 'bar'}, 'baz'], - ]); + var actualMap = new MapI([['foo', [1, 2, 3]], [{ foo: 'bar' }, 'baz']]); - var containingMap = new MapI([ - [{'foo': 'bar'}, 'baz'], - ['foo', [1, 2]], - ]); + var containingMap = new MapI([[{ foo: 'bar' }, 'baz'], ['foo', [1, 2]]]); var containing = new jasmineUnderTest.MapContaining(containingMap); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -73,18 +61,12 @@ describe('MapContaining', function() { var actualMap = new MapI([ ['foo1', 'not a bar'], ['foo2', 'bar'], - ['baz', [1, 2, 3, 4]], + ['baz', [1, 2, 3, 4]] ]); var containingMap = new MapI([ - [ - jasmineUnderTest.stringMatching(/^foo\d/), - 'bar' - ], - [ - 'baz', - jasmineUnderTest.arrayContaining([2, 3]) - ], + [jasmineUnderTest.stringMatching(/^foo\d/), 'bar'], + ['baz', jasmineUnderTest.arrayContaining([2, 3])] ]); var containing = new jasmineUnderTest.MapContaining(containingMap); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -93,20 +75,11 @@ describe('MapContaining', function() { }); it('does not match when a key in sample has no asymmetric matches in actual', function() { - var actualMap = new MapI([ - ['a-foo1', 'bar'], - ['baz', [1, 2, 3, 4]], - ]); + var actualMap = new MapI([['a-foo1', 'bar'], ['baz', [1, 2, 3, 4]]]); var containingMap = new MapI([ - [ - jasmineUnderTest.stringMatching(/^foo\d/), - 'bar' - ], - [ - 'baz', - jasmineUnderTest.arrayContaining([2, 3]) - ], + [jasmineUnderTest.stringMatching(/^foo\d/), 'bar'], + ['baz', jasmineUnderTest.arrayContaining([2, 3])] ]); var containing = new jasmineUnderTest.MapContaining(containingMap); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -115,20 +88,11 @@ describe('MapContaining', function() { }); it('does not match when a value in sample has no asymmetric matches in actual', function() { - var actualMap = new MapI([ - ['foo1', 'bar'], - ['baz', [1, 2, 3, 4]], - ]); + var actualMap = new MapI([['foo1', 'bar'], ['baz', [1, 2, 3, 4]]]); var containingMap = new MapI([ - [ - jasmineUnderTest.stringMatching(/^foo\d/), - 'bar' - ], - [ - 'baz', - jasmineUnderTest.arrayContaining([4, 5]) - ], + [jasmineUnderTest.stringMatching(/^foo\d/), 'bar'], + ['baz', jasmineUnderTest.arrayContaining([4, 5])] ]); var containing = new jasmineUnderTest.MapContaining(containingMap); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -140,18 +104,12 @@ describe('MapContaining', function() { var actualMap = new MapI([ ['foo', new MapI([['foo1', 1], ['foo2', 2]])], [new MapI([[1, 'bar1'], [2, 'bar2']]), 'bar'], - ['other', 'any'], + ['other', 'any'] ]); var containingMap = new MapI([ - [ - 'foo', - new jasmineUnderTest.MapContaining(new MapI([['foo1', 1]])) - ], - [ - new jasmineUnderTest.MapContaining(new MapI([[2, 'bar2']])), - 'bar' - ], + ['foo', new jasmineUnderTest.MapContaining(new MapI([['foo1', 1]]))], + [new jasmineUnderTest.MapContaining(new MapI([[2, 'bar2']])), 'bar'] ]); var containing = new jasmineUnderTest.MapContaining(containingMap); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -162,25 +120,41 @@ describe('MapContaining', function() { it('uses custom equality testers', function() { function tester(a, b) { // treat all negative numbers as equal - return (typeof a == 'number' && typeof b == 'number') ? (a < 0 && b < 0) : a === b; + return typeof a == 'number' && typeof b == 'number' + ? a < 0 && b < 0 + : a === b; } var actualMap = new MapI([['foo', -1]]); - var containing = new jasmineUnderTest.MapContaining(new MapI([['foo', -2]])); - var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); + var containing = new jasmineUnderTest.MapContaining( + new MapI([['foo', -2]]) + ); + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [tester] + }); expect(containing.asymmetricMatch(actualMap, matchersUtil)).toBe(true); }); it('does not match when actual is not a map', function() { var containingMap = new MapI([['foo', 'bar']]); - expect(new jasmineUnderTest.MapContaining(containingMap).asymmetricMatch('foo')).toBe(false); - expect(new jasmineUnderTest.MapContaining(containingMap).asymmetricMatch(-1)).toBe(false); - expect(new jasmineUnderTest.MapContaining(containingMap).asymmetricMatch({'foo': 'bar'})).toBe(false); + expect( + new jasmineUnderTest.MapContaining(containingMap).asymmetricMatch('foo') + ).toBe(false); + expect( + new jasmineUnderTest.MapContaining(containingMap).asymmetricMatch(-1) + ).toBe(false); + expect( + new jasmineUnderTest.MapContaining(containingMap).asymmetricMatch({ + foo: 'bar' + }) + ).toBe(false); }); it('throws an error when sample is not a map', function() { expect(function() { - new jasmineUnderTest.MapContaining({'foo': 'bar'}).asymmetricMatch(new Map()); + new jasmineUnderTest.MapContaining({ foo: 'bar' }).asymmetricMatch( + new Map() + ); }).toThrowError(/You must provide a map/); }); diff --git a/spec/core/asymmetric_equality/NotEmptySpec.js b/spec/core/asymmetric_equality/NotEmptySpec.js index d00ee013..fdb0a99e 100644 --- a/spec/core/asymmetric_equality/NotEmptySpec.js +++ b/spec/core/asymmetric_equality/NotEmptySpec.js @@ -1,27 +1,27 @@ -describe("NotEmpty", function () { - it("matches a non empty object", function () { +describe('NotEmpty', function() { + it('matches a non empty object', function() { var notEmpty = new jasmineUnderTest.NotEmpty(); - expect(notEmpty.asymmetricMatch({undefined: false})).toBe(true); + expect(notEmpty.asymmetricMatch({ undefined: false })).toBe(true); expect(notEmpty.asymmetricMatch({})).toBe(false); }); - it("matches a non empty array", function () { + it('matches a non empty array', function() { var notEmpty = new jasmineUnderTest.NotEmpty(); expect(notEmpty.asymmetricMatch([1, 12, 3])).toBe(true); expect(notEmpty.asymmetricMatch([])).toBe(false); }); - it("matches a non empty string", function () { + it('matches a non empty string', function() { var notEmpty = new jasmineUnderTest.NotEmpty(); expect(notEmpty.asymmetricMatch('12312')).toBe(true); - expect(notEmpty.asymmetricMatch("")).toBe(false); + expect(notEmpty.asymmetricMatch('')).toBe(false); expect(notEmpty.asymmetricMatch('')).toBe(false); }); - it("matches a non empty map", function () { + it('matches a non empty map', function() { jasmine.getEnv().requireFunctioningMaps(); var notEmpty = new jasmineUnderTest.NotEmpty(); var fullMap = new Map(); // eslint-disable-line compat/compat @@ -32,7 +32,7 @@ describe("NotEmpty", function () { expect(notEmpty.asymmetricMatch(emptyMap)).toBe(false); }); - it("matches a non empty set", function () { + it('matches a non empty set', function() { jasmine.getEnv().requireFunctioningSets(); var notEmpty = new jasmineUnderTest.NotEmpty(); var filledSet = new Set(); // eslint-disable-line compat/compat @@ -43,11 +43,11 @@ describe("NotEmpty", function () { expect(notEmpty.asymmetricMatch(emptySet)).toBe(false); }); - it("matches a non empty typed array", function() { + it('matches a non empty typed array', function() { jasmine.getEnv().requireFunctioningTypedArrays(); var notEmpty = new jasmineUnderTest.NotEmpty(); - expect(notEmpty.asymmetricMatch(new Int16Array([1,2,3]))).toBe(true); // eslint-disable-line compat/compat + expect(notEmpty.asymmetricMatch(new Int16Array([1, 2, 3]))).toBe(true); // eslint-disable-line compat/compat expect(notEmpty.asymmetricMatch(new Int16Array())).toBe(false); // eslint-disable-line compat/compat }); }); diff --git a/spec/core/asymmetric_equality/ObjectContainingSpec.js b/spec/core/asymmetric_equality/ObjectContainingSpec.js index 97df2555..07b86148 100644 --- a/spec/core/asymmetric_equality/ObjectContainingSpec.js +++ b/spec/core/asymmetric_equality/ObjectContainingSpec.js @@ -1,47 +1,55 @@ -describe("ObjectContaining", function() { - - it("matches any object actual to an empty object", function() { +describe('ObjectContaining', function() { + it('matches any object actual to an empty object', function() { var containing = new jasmineUnderTest.ObjectContaining({}); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch({foo: 1}, matchersUtil)).toBe(true); + expect(containing.asymmetricMatch({ foo: 1 }, matchersUtil)).toBe(true); }); - it("does not match when the actual is not an object", function() { + it('does not match when the actual is not an object', function() { var containing = new jasmineUnderTest.ObjectContaining({}); - [1, true, undefined, "a string"].forEach(function(actual) { + [1, true, undefined, 'a string'].forEach(function(actual) { expect(containing.asymmetricMatch(actual)).toBe(false); }); }); - it("does not match an empty object actual", function() { - var containing = new jasmineUnderTest.ObjectContaining("foo"); + it('does not match an empty object actual', function() { + var containing = new jasmineUnderTest.ObjectContaining('foo'); expect(function() { - containing.asymmetricMatch({}) - }).toThrowError(/not 'foo'/) + containing.asymmetricMatch({}); + }).toThrowError(/not 'foo'/); }); - it("matches when the key/value pair is present in the actual", function() { - var containing = new jasmineUnderTest.ObjectContaining({foo: "fooVal"}); + it('matches when the key/value pair is present in the actual', function() { + var containing = new jasmineUnderTest.ObjectContaining({ foo: 'fooVal' }); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch({foo: "fooVal", bar: "barVal"}, matchersUtil)).toBe(true); + expect( + containing.asymmetricMatch({ foo: 'fooVal', bar: 'barVal' }, matchersUtil) + ).toBe(true); }); - it("does not match when the key/value pair is not present in the actual", function() { - var containing = new jasmineUnderTest.ObjectContaining({foo: "fooVal"}); + it('does not match when the key/value pair is not present in the actual', function() { + var containing = new jasmineUnderTest.ObjectContaining({ foo: 'fooVal' }); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch({bar: "barVal", quux: "quuxVal"}, matchersUtil)).toBe(false); + expect( + containing.asymmetricMatch( + { bar: 'barVal', quux: 'quuxVal' }, + matchersUtil + ) + ).toBe(false); }); - it("does not match when the key is present but the value is different in the actual", function() { - var containing = new jasmineUnderTest.ObjectContaining({foo: "other"}); + it('does not match when the key is present but the value is different in the actual', function() { + var containing = new jasmineUnderTest.ObjectContaining({ foo: 'other' }); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch({foo: "fooVal", bar: "barVal"}, matchersUtil)).toBe(false); + expect( + containing.asymmetricMatch({ foo: 'fooVal', bar: 'barVal' }, matchersUtil) + ).toBe(false); }); it("jasmineToString's itself", function() { @@ -53,46 +61,55 @@ describe("ObjectContaining", function() { '' ); expect(pp).toHaveBeenCalledWith(sample); - }); - it("matches recursively", function() { - var containing = new jasmineUnderTest.ObjectContaining({one: new jasmineUnderTest.ObjectContaining({two: {}})}); + it('matches recursively', function() { + var containing = new jasmineUnderTest.ObjectContaining({ + one: new jasmineUnderTest.ObjectContaining({ two: {} }) + }); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch({one: {two: {}}}, matchersUtil)).toBe(true); + expect(containing.asymmetricMatch({ one: { two: {} } }, matchersUtil)).toBe( + true + ); }); - it("matches when key is present with undefined value", function() { + it('matches when key is present with undefined value', function() { var containing = new jasmineUnderTest.ObjectContaining({ one: undefined }); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(containing.asymmetricMatch({ one: undefined }, matchersUtil)).toBe(true); + expect(containing.asymmetricMatch({ one: undefined }, matchersUtil)).toBe( + true + ); }); - it("does not match when key with undefined value is not present", function() { + it('does not match when key with undefined value is not present', function() { var containing = new jasmineUnderTest.ObjectContaining({ one: undefined }); var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(containing.asymmetricMatch({}, matchersUtil)).toBe(false); }); - it("matches defined properties", function(){ - var containing = new jasmineUnderTest.ObjectContaining({ foo: "fooVal" }); + it('matches defined properties', function() { + var containing = new jasmineUnderTest.ObjectContaining({ foo: 'fooVal' }); var matchersUtil = new jasmineUnderTest.MatchersUtil(); var definedPropertyObject = {}; - Object.defineProperty(definedPropertyObject, "foo", { - get: function() { return "fooVal" } + Object.defineProperty(definedPropertyObject, 'foo', { + get: function() { + return 'fooVal'; + } }); - expect(containing.asymmetricMatch(definedPropertyObject, matchersUtil)).toBe(true); + expect( + containing.asymmetricMatch(definedPropertyObject, matchersUtil) + ).toBe(true); }); - it("matches prototype properties", function(){ - var containing = new jasmineUnderTest.ObjectContaining({ foo: "fooVal" }); + it('matches prototype properties', function() { + var containing = new jasmineUnderTest.ObjectContaining({ foo: 'fooVal' }); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var prototypeObject = {foo: "fooVal"}; + var prototypeObject = { foo: 'fooVal' }; var obj; if (Object.create) { @@ -107,23 +124,31 @@ describe("ObjectContaining", function() { expect(containing.asymmetricMatch(obj, matchersUtil)).toBe(true); }); - it("uses custom equality testers", function() { + it('uses custom equality testers', function() { var tester = function(a, b) { // All "foo*" strings match each other. - if (typeof a == "string" && typeof b == "string" && - a.substr(0, 3) == "foo" && b.substr(0, 3) == "foo") { + if ( + typeof a == 'string' && + typeof b == 'string' && + a.substr(0, 3) == 'foo' && + b.substr(0, 3) == 'foo' + ) { return true; } }; - var containing = new jasmineUnderTest.ObjectContaining({foo: "fooVal"}); - var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); + var containing = new jasmineUnderTest.ObjectContaining({ foo: 'fooVal' }); + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [tester] + }); - expect(containing.asymmetricMatch({foo: "fooBar"}, matchersUtil)).toBe(true); + expect(containing.asymmetricMatch({ foo: 'fooBar' }, matchersUtil)).toBe( + true + ); }); - describe("valuesForDiff_", function() { - describe("when other is not an object", function() { - it("sets self to jasmineToString()", function () { + describe('valuesForDiff_', function() { + describe('when other is not an object', function() { + it('sets self to jasmineToString()', function() { var containing = new jasmineUnderTest.ObjectContaining({}), pp = jasmineUnderTest.makePrettyPrinter(), result = containing.valuesForDiff_('a', pp); @@ -135,27 +160,31 @@ describe("ObjectContaining", function() { }); }); - describe("when other is an object", function() { - it("includes keys that are present in both other and sample", function() { - var sample = {a: 1, b: 2}, - other = {a: 3, b: 4}, + describe('when other is an object', function() { + it('includes keys that are present in both other and sample', function() { + var sample = { a: 1, b: 2 }, + other = { a: 3, b: 4 }, containing = new jasmineUnderTest.ObjectContaining(sample), result = containing.valuesForDiff_(other); - expect(result.self).not.toBeInstanceOf(jasmineUnderTest.ObjectContaining); + expect(result.self).not.toBeInstanceOf( + jasmineUnderTest.ObjectContaining + ); expect(result).toEqual({ self: sample, other: other }); }); - it("includes keys that are present only in sample", function() { - var sample = {a: 1, b: 2}, - other = {a: 3}, + it('includes keys that are present only in sample', function() { + var sample = { a: 1, b: 2 }, + other = { a: 3 }, containing = new jasmineUnderTest.ObjectContaining(sample), result = containing.valuesForDiff_(other); - expect(result.self).not.toBeInstanceOf(jasmineUnderTest.ObjectContaining); + expect(result.self).not.toBeInstanceOf( + jasmineUnderTest.ObjectContaining + ); expect(containing.valuesForDiff_(other)).toEqual({ self: sample, other: { @@ -165,13 +194,15 @@ describe("ObjectContaining", function() { }); }); - it("omits keys that are present only in other", function() { - var sample = {a: 1, b: 2}, - other = {a: 3, b: 4, c: 5}, + it('omits keys that are present only in other', function() { + var sample = { a: 1, b: 2 }, + other = { a: 3, b: 4, c: 5 }, containing = new jasmineUnderTest.ObjectContaining(sample), result = containing.valuesForDiff_(other); - expect(result.self).not.toBeInstanceOf(jasmineUnderTest.ObjectContaining); + expect(result.self).not.toBeInstanceOf( + jasmineUnderTest.ObjectContaining + ); expect(result).toEqual({ self: sample, other: { diff --git a/spec/core/asymmetric_equality/SetContainingSpec.js b/spec/core/asymmetric_equality/SetContainingSpec.js index 3f7b1b16..37925c46 100644 --- a/spec/core/asymmetric_equality/SetContainingSpec.js +++ b/spec/core/asymmetric_equality/SetContainingSpec.js @@ -1,6 +1,7 @@ /* eslint-disable compat/compat */ describe('SetContaining', function() { - function SetI(iterable) { // for IE11 + function SetI(iterable) { + // for IE11 var set = new Set(); iterable.forEach(function(v) { set.add(v); @@ -12,7 +13,6 @@ describe('SetContaining', function() { jasmine.getEnv().requireFunctioningSets(); }); - it('matches any actual set to an empty set', function() { var actualSet = new SetI(['foo', 'bar']); var containing = new jasmineUnderTest.SetContaining(new Set()); @@ -21,13 +21,9 @@ describe('SetContaining', function() { }); it('matches when all the values in sample have matches in actual', function() { - var actualSet = new SetI([ - {'foo': 'bar'}, 'baz', [1, 2, 3] - ]); + var actualSet = new SetI([{ foo: 'bar' }, 'baz', [1, 2, 3]]); - var containingSet = new SetI([ - [1, 2, 3], {'foo': 'bar'} - ]); + var containingSet = new SetI([[1, 2, 3], { foo: 'bar' }]); var containing = new jasmineUnderTest.SetContaining(containingSet); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -35,13 +31,9 @@ describe('SetContaining', function() { }); it('does not match when a value is not in actual', function() { - var actualSet = new SetI([ - {'foo': 'bar'}, 'baz', [1, 2, 3] - ]); + var actualSet = new SetI([{ foo: 'bar' }, 'baz', [1, 2, 3]]); - var containingSet = new SetI([ - [1, 2], {'foo': 'bar'} - ]); + var containingSet = new SetI([[1, 2], { foo: 'bar' }]); var containing = new jasmineUnderTest.SetContaining(containingSet); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -49,13 +41,11 @@ describe('SetContaining', function() { }); it('matches when all the values in sample have asymmetric matches in actual', function() { - var actualSet = new SetI([ - [1, 2, 3, 4], 'other', 'foo1' - ]); + var actualSet = new SetI([[1, 2, 3, 4], 'other', 'foo1']); var containingSet = new SetI([ jasmineUnderTest.stringMatching(/^foo\d/), - jasmineUnderTest.arrayContaining([2, 3]), + jasmineUnderTest.arrayContaining([2, 3]) ]); var containing = new jasmineUnderTest.SetContaining(containingSet); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -64,13 +54,11 @@ describe('SetContaining', function() { }); it('does not match when a value in sample has no asymmetric matches in actual', function() { - var actualSet = new SetI([ - 'a-foo1', [1, 2, 3, 4], 'other' - ]); + var actualSet = new SetI(['a-foo1', [1, 2, 3, 4], 'other']); var containingSet = new SetI([ jasmine.stringMatching(/^foo\d/), - jasmine.arrayContaining([2, 3]), + jasmine.arrayContaining([2, 3]) ]); var containing = new jasmineUnderTest.SetContaining(containingSet); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -79,12 +67,11 @@ describe('SetContaining', function() { }); it('matches recursively', function() { - var actualSet = new SetI([ - 'foo', new SetI([1, 'bar', 2]), 'other' - ]); + var actualSet = new SetI(['foo', new SetI([1, 'bar', 2]), 'other']); var containingSet = new SetI([ - new jasmineUnderTest.SetContaining(new SetI(['bar'])), 'foo' + new jasmineUnderTest.SetContaining(new SetI(['bar'])), + 'foo' ]); var containing = new jasmineUnderTest.SetContaining(containingSet); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -95,25 +82,37 @@ describe('SetContaining', function() { it('uses custom equality testers', function() { function tester(a, b) { // treat all negative numbers as equal - return (typeof a == 'number' && typeof b == 'number') ? (a < 0 && b < 0) : a === b; + return typeof a == 'number' && typeof b == 'number' + ? a < 0 && b < 0 + : a === b; } var actualSet = new SetI(['foo', -1]); var containing = new jasmineUnderTest.SetContaining(new SetI([-2, 'foo'])); - var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}); + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [tester] + }); expect(containing.asymmetricMatch(actualSet, matchersUtil)).toBe(true); }); it('does not match when actual is not a set', function() { var containingSet = new SetI(['foo']); - expect(new jasmineUnderTest.SetContaining(containingSet).asymmetricMatch('foo')).toBe(false); - expect(new jasmineUnderTest.SetContaining(containingSet).asymmetricMatch(1)).toBe(false); - expect(new jasmineUnderTest.SetContaining(containingSet).asymmetricMatch(['foo'])).toBe(false); + expect( + new jasmineUnderTest.SetContaining(containingSet).asymmetricMatch('foo') + ).toBe(false); + expect( + new jasmineUnderTest.SetContaining(containingSet).asymmetricMatch(1) + ).toBe(false); + expect( + new jasmineUnderTest.SetContaining(containingSet).asymmetricMatch(['foo']) + ).toBe(false); }); it('throws an error when sample is not a set', function() { expect(function() { - new jasmineUnderTest.SetContaining({'foo': 'bar'}).asymmetricMatch(new Set()); + new jasmineUnderTest.SetContaining({ foo: 'bar' }).asymmetricMatch( + new Set() + ); }).toThrowError(/You must provide a set/); }); diff --git a/spec/core/asymmetric_equality/StringMatchingSpec.js b/spec/core/asymmetric_equality/StringMatchingSpec.js index 9c231b74..656b0e50 100644 --- a/spec/core/asymmetric_equality/StringMatchingSpec.js +++ b/spec/core/asymmetric_equality/StringMatchingSpec.js @@ -1,19 +1,19 @@ -describe("StringMatching", function() { - it("matches a string against a provided regexp", function() { +describe('StringMatching', function() { + it('matches a string against a provided regexp', function() { var matcher = new jasmineUnderTest.StringMatching(/foo/); expect(matcher.asymmetricMatch('barfoobaz')).toBe(true); expect(matcher.asymmetricMatch('barbaz')).toBe(false); }); - it("matches a string against provided string", function() { + it('matches a string against provided string', function() { var matcher = new jasmineUnderTest.StringMatching('foo'); expect(matcher.asymmetricMatch('barfoobaz')).toBe(true); expect(matcher.asymmetricMatch('barbaz')).toBe(false); }); - it("raises an Error when the expected is not a String or RegExp", function() { + it('raises an Error when the expected is not a String or RegExp', function() { expect(function() { new jasmineUnderTest.StringMatching({}); }).toThrowError(/not a String or a RegExp/); @@ -22,6 +22,8 @@ describe("StringMatching", function() { it("jasmineToString's itself", function() { var matching = new jasmineUnderTest.StringMatching(/^foo/); - expect(matching.jasmineToString()).toEqual(""); + expect(matching.jasmineToString()).toEqual( + '' + ); }); }); diff --git a/spec/core/asymmetric_equality/TruthySpec.js b/spec/core/asymmetric_equality/TruthySpec.js index af1bddee..b2ac2775 100644 --- a/spec/core/asymmetric_equality/TruthySpec.js +++ b/spec/core/asymmetric_equality/TruthySpec.js @@ -1,12 +1,12 @@ -describe("Truthy", function () { - it("is true for a non empty string", function () { +describe('Truthy', function() { + it('is true for a non empty string', function() { var truthy = new jasmineUnderTest.Truthy(); - expect(truthy.asymmetricMatch("foo")).toBe(true); - expect(truthy.asymmetricMatch("")).toBe(false); + expect(truthy.asymmetricMatch('foo')).toBe(true); + expect(truthy.asymmetricMatch('')).toBe(false); }); - it("is true for a number that is not 0", function () { + it('is true for a number that is not 0', function() { var truthy = new jasmineUnderTest.Truthy(); expect(truthy.asymmetricMatch(1)).toBe(true); @@ -15,49 +15,47 @@ describe("Truthy", function () { expect(truthy.asymmetricMatch(-3.1)).toBe(true); }); - it("is true for a function", function () { + it('is true for a function', function() { var truthy = new jasmineUnderTest.Truthy(); - expect(truthy.asymmetricMatch(function () { - })).toBe(true); + expect(truthy.asymmetricMatch(function() {})).toBe(true); }); - it("is true for an Object", function () { + it('is true for an Object', function() { var truthy = new jasmineUnderTest.Truthy(); expect(truthy.asymmetricMatch({})).toBe(true); }); - it("is true for a truthful Boolean", function () { + it('is true for a truthful Boolean', function() { var truthy = new jasmineUnderTest.Truthy(); expect(truthy.asymmetricMatch(true)).toBe(true); expect(truthy.asymmetricMatch(false)).toBe(false); }); - it("is true for an empty object", function () { + it('is true for an empty object', function() { var truthy = new jasmineUnderTest.Truthy(); expect(truthy.asymmetricMatch({})).toBe(true); }); - it("is true for an empty array", function () { + it('is true for an empty array', function() { var truthy = new jasmineUnderTest.Truthy(); expect(truthy.asymmetricMatch([])).toBe(true); }); - it("is true for a date", function () { + it('is true for a date', function() { var truthy = new jasmineUnderTest.Truthy(); expect(truthy.asymmetricMatch(new Date())).toBe(true); }); - it("is true for a infiniti", function () { + it('is true for a infiniti', function() { var truthy = new jasmineUnderTest.Truthy(); expect(truthy.asymmetricMatch(Infinity)).toBe(true); expect(truthy.asymmetricMatch(-Infinity)).toBe(true); }); }); - diff --git a/spec/core/integration/AsymmetricEqualityTestersSpec.js b/spec/core/integration/AsymmetricEqualityTestersSpec.js index 518c5bde..3d12f15d 100644 --- a/spec/core/integration/AsymmetricEqualityTestersSpec.js +++ b/spec/core/integration/AsymmetricEqualityTestersSpec.js @@ -1,12 +1,12 @@ -describe('Asymmetric equality testers (Integration)', function () { +describe('Asymmetric equality testers (Integration)', function() { function verifyPasses(expectations, setup) { - it('passes', function (done) { + it('passes', function(done) { var env = new jasmineUnderTest.Env(); - env.it('a spec', function () { + env.it('a spec', function() { expectations(env); }); - var specExpectations = function (result) { + var specExpectations = function(result) { expect(result.status).toEqual('passed'); expect(result.passedExpectations.length) .withContext('Number of passed expectations') @@ -14,115 +14,122 @@ describe('Asymmetric equality testers (Integration)', function () { expect(result.failedExpectations.length) .withContext('Number of failed expectations') .toEqual(0); - expect(result.failedExpectations[0] && result.failedExpectations[0].message) + expect( + result.failedExpectations[0] && result.failedExpectations[0].message + ) .withContext('Failure message') .toBeUndefined(); }; - env.addReporter({specDone: specExpectations}); + env.addReporter({ specDone: specExpectations }); env.execute(null, done); }); } function verifyFails(expectations) { - it('fails', function (done) { + it('fails', function(done) { var env = new jasmineUnderTest.Env(); - env.it('a spec', function () { + env.it('a spec', function() { expectations(env); }); - var specExpectations = function (result) { + var specExpectations = function(result) { expect(result.status).toEqual('failed'); expect(result.failedExpectations.length) .withContext('Number of failed expectations') .toEqual(1); expect(result.failedExpectations[0].message) - .withContext('Failed with a thrown error rather than a matcher failure') + .withContext( + 'Failed with a thrown error rather than a matcher failure' + ) .not.toMatch(/^Error: /); - expect(result.failedExpectations[0].matcherName).withContext('Matcher name') + expect(result.failedExpectations[0].matcherName) + .withContext('Matcher name') .not.toEqual(''); }; - env.addReporter({specDone: specExpectations}); + env.addReporter({ specDone: specExpectations }); env.execute(null, done); }); } - describe('any', function () { - verifyPasses(function (env) { + describe('any', function() { + verifyPasses(function(env) { env.expect(5).toEqual(jasmineUnderTest.any(Number)); }); - verifyFails(function (env) { - env.expect("five").toEqual(jasmineUnderTest.any(Number)); + verifyFails(function(env) { + env.expect('five').toEqual(jasmineUnderTest.any(Number)); }); }); - describe('anything', function () { - verifyPasses(function (env) { + describe('anything', function() { + verifyPasses(function(env) { env.expect('').toEqual(jasmineUnderTest.anything()); }); - verifyFails(function (env) { + verifyFails(function(env) { env.expect(null).toEqual(jasmineUnderTest.anything()); }); }); - describe('arrayContaining', function () { - verifyPasses(function (env) { - env.addCustomEqualityTester(function (a, b) { + describe('arrayContaining', function() { + verifyPasses(function(env) { + env.addCustomEqualityTester(function(a, b) { return a.toString() === b.toString(); }); - env.expect([1, 2, 3]).toEqual(jasmineUnderTest.arrayContaining(["2"])); + env.expect([1, 2, 3]).toEqual(jasmineUnderTest.arrayContaining(['2'])); }); - verifyFails(function (env) { + verifyFails(function(env) { env.expect(null).toEqual(jasmineUnderTest.arrayContaining([2])); }); }); - describe('arrayWithExactContents', function () { - verifyPasses(function (env) { - env.addCustomEqualityTester(function (a, b) { + describe('arrayWithExactContents', function() { + verifyPasses(function(env) { + env.addCustomEqualityTester(function(a, b) { return a.toString() === b.toString(); }); - env.expect([1, 2]).toEqual(jasmineUnderTest.arrayWithExactContents(["2", "1"])); + env + .expect([1, 2]) + .toEqual(jasmineUnderTest.arrayWithExactContents(['2', '1'])); }); - verifyFails(function (env) { + verifyFails(function(env) { env.expect([]).toEqual(jasmineUnderTest.arrayWithExactContents([2])); }); }); - describe('empty', function () { - verifyPasses(function (env) { + describe('empty', function() { + verifyPasses(function(env) { env.expect([]).toEqual(jasmineUnderTest.empty()); }); - verifyFails(function (env) { + verifyFails(function(env) { env.expect([1]).toEqual(jasmineUnderTest.empty()); }); }); - describe('falsy', function () { - verifyPasses(function (env) { + describe('falsy', function() { + verifyPasses(function(env) { env.expect(false).toEqual(jasmineUnderTest.falsy()); }); - verifyFails(function (env) { + verifyFails(function(env) { env.expect(true).toEqual(jasmineUnderTest.falsy()); }); }); - describe('mapContaining', function () { + describe('mapContaining', function() { if (jasmine.getEnv().hasFunctioningMaps()) { - verifyPasses(function (env) { + verifyPasses(function(env) { var actual = new Map(); - actual.set('a', "2"); + actual.set('a', '2'); var expected = new Map(); expected.set('a', 2); - env.addCustomEqualityTester(function (a, b) { + env.addCustomEqualityTester(function(a, b) { return a.toString() === b.toString(); }); @@ -130,54 +137,62 @@ describe('Asymmetric equality testers (Integration)', function () { }); } else { it('passes', function() { - jasmine.getEnv().pending('Browser has incomplete or missing support for Maps'); + jasmine + .getEnv() + .pending('Browser has incomplete or missing support for Maps'); }); } if (jasmine.getEnv().hasFunctioningMaps()) { - verifyFails(function (env) { - env.expect('something').toEqual(jasmineUnderTest.mapContaining(new Map())); + verifyFails(function(env) { + env + .expect('something') + .toEqual(jasmineUnderTest.mapContaining(new Map())); }); } else { it('fails', function() { - jasmine.getEnv().pending('Browser has incomplete or missing support for Maps'); + jasmine + .getEnv() + .pending('Browser has incomplete or missing support for Maps'); }); } }); - describe('notEmpty', function () { - verifyPasses(function (env) { + describe('notEmpty', function() { + verifyPasses(function(env) { env.expect([1]).toEqual(jasmineUnderTest.notEmpty()); }); - verifyFails(function (env) { + verifyFails(function(env) { env.expect([]).toEqual(jasmineUnderTest.notEmpty()); }); }); - describe('objectContaining', function () { - verifyPasses(function (env) { - env.addCustomEqualityTester(function (a, b) { + describe('objectContaining', function() { + verifyPasses(function(env) { + env.addCustomEqualityTester(function(a, b) { return a.toString() === b.toString(); }); - env.expect({a: 1, b: 2}).toEqual(jasmineUnderTest.objectContaining({a: "1"})); + env + .expect({ a: 1, b: 2 }) + .toEqual(jasmineUnderTest.objectContaining({ a: '1' })); }); - verifyFails(function (env) { - env.expect({}).toEqual(jasmineUnderTest.objectContaining({a: "1"})); + verifyFails(function(env) { + env.expect({}).toEqual(jasmineUnderTest.objectContaining({ a: '1' })); }); }); - describe('setContaining', function () { + describe('setContaining', function() { if (jasmine.getEnv().hasFunctioningSets()) { - verifyPasses(function (env) { + verifyPasses(function(env) { var actual = new Set(); - actual.add("1"); + actual.add('1'); var expected = new Set(); actual.add(1); - env.addCustomEqualityTester(function (a, b) { + env.addCustomEqualityTester(function(a, b) { return a.toString() === b.toString(); }); @@ -185,37 +200,43 @@ describe('Asymmetric equality testers (Integration)', function () { }); } else { it('pases', function() { - jasmine.getEnv().pending('Browser has incomplete or missing support for Sets'); + jasmine + .getEnv() + .pending('Browser has incomplete or missing support for Sets'); }); } if (jasmine.getEnv().hasFunctioningSets()) { - verifyFails(function (env) { - env.expect('something').toEqual(jasmineUnderTest.setContaining(new Set())); + verifyFails(function(env) { + env + .expect('something') + .toEqual(jasmineUnderTest.setContaining(new Set())); }); } else { it('fails', function() { - jasmine.getEnv().pending('Browser has incomplete or missing support for Sets'); + jasmine + .getEnv() + .pending('Browser has incomplete or missing support for Sets'); }); } }); - describe('stringMatching', function () { - verifyPasses(function (env) { + describe('stringMatching', function() { + verifyPasses(function(env) { env.expect('foo').toEqual(jasmineUnderTest.stringMatching(/o/)); }); - verifyFails(function (env) { + verifyFails(function(env) { env.expect('bar').toEqual(jasmineUnderTest.stringMatching(/o/)); }); }); - describe('truthy', function () { - verifyPasses(function (env) { + describe('truthy', function() { + verifyPasses(function(env) { env.expect(true).toEqual(jasmineUnderTest.truthy()); }); - verifyFails(function (env) { + verifyFails(function(env) { env.expect(false).toEqual(jasmineUnderTest.truthy()); }); }); diff --git a/spec/core/integration/CustomAsyncMatchersSpec.js b/spec/core/integration/CustomAsyncMatchersSpec.js index 4e97185f..a38c8d15 100644 --- a/spec/core/integration/CustomAsyncMatchersSpec.js +++ b/spec/core/integration/CustomAsyncMatchersSpec.js @@ -4,7 +4,7 @@ describe('Custom Async Matchers (Integration)', function() { beforeEach(function() { env = new jasmineUnderTest.Env(); - env.configure({random: false}); + env.configure({ random: false }); }); afterEach(function() { @@ -17,7 +17,11 @@ describe('Custom Async Matchers (Integration)', function() { env.it('spec using custom async matcher', function() { env.addAsyncMatchers({ toBeReal: function() { - return { compare: function() { return Promise.resolve({ pass: true }); } }; + return { + compare: function() { + return Promise.resolve({ pass: true }); + } + }; } }); @@ -39,8 +43,12 @@ describe('Custom Async Matchers (Integration)', function() { env.addAsyncMatchers({ toBeReal: function() { return { - compare: function() { return Promise.resolve({ pass: true }); }, - negativeCompare: function() { return Promise.resolve({ pass: true }); } + compare: function() { + return Promise.resolve({ pass: true }); + }, + negativeCompare: function() { + return Promise.resolve({ pass: true }); + } }; } }); @@ -74,7 +82,9 @@ describe('Custom Async Matchers (Integration)', function() { }); var specExpectations = function(result) { - expect(result.failedExpectations[0].message).toEqual("Expected 'a' to be real."); + expect(result.failedExpectations[0].message).toEqual( + "Expected 'a' to be real." + ); }; env.addReporter({ specDone: specExpectations }); @@ -82,22 +92,24 @@ describe('Custom Async Matchers (Integration)', function() { }); // TODO: remove this in the next major release. - it("passes the jasmine utility and current equality testers to the matcher factory", function(done) { + it('passes the jasmine utility and current equality testers to the matcher factory', function(done) { jasmine.getEnv().requirePromises(); - var matcherFactory = function () { + var matcherFactory = function() { return { - compare: function () { - return Promise.resolve({pass: true}); + compare: function() { + return Promise.resolve({ pass: true }); } }; }, - matcherFactorySpy = jasmine.createSpy("matcherFactorySpy").and.callFake(matcherFactory), - customEqualityFn = function () { + matcherFactorySpy = jasmine + .createSpy('matcherFactorySpy') + .and.callFake(matcherFactory), + customEqualityFn = function() { return true; }; - env.it("spec with expectation", function() { + env.it('spec with expectation', function() { env.addCustomEqualityTester(customEqualityFn); env.addAsyncMatchers({ toBeReal: matcherFactorySpy @@ -117,31 +129,35 @@ describe('Custom Async Matchers (Integration)', function() { env.execute(null, done); }); - it("provides custom equality testers to the matcher factory via matchersUtil", function(done) { + it('provides custom equality testers to the matcher factory via matchersUtil', function(done) { jasmine.getEnv().requirePromises(); - var matcherFactory = function (matchersUtil) { + var matcherFactory = function(matchersUtil) { return { - compare: function (actual, expected) { - return Promise.resolve({pass: matchersUtil.equals(actual[0], expected)}); + compare: function(actual, expected) { + return Promise.resolve({ + pass: matchersUtil.equals(actual[0], expected) + }); } }; }, - customEqualityFn = jasmine.createSpy("customEqualityFn").and.callFake(function (a, b) { - return a.toString() === b; - }); + customEqualityFn = jasmine + .createSpy('customEqualityFn') + .and.callFake(function(a, b) { + return a.toString() === b; + }); - env.it("spec with expectation", function() { + env.it('spec with expectation', function() { env.addCustomEqualityTester(customEqualityFn); env.addAsyncMatchers({ toBeArrayWithFirstElement: matcherFactory }); - return env.expectAsync([1, 2]).toBeArrayWithFirstElement("1"); + return env.expectAsync([1, 2]).toBeArrayWithFirstElement('1'); }); var specExpectations = function(result) { - expect(customEqualityFn).toHaveBeenCalledWith(1, "1"); + expect(customEqualityFn).toHaveBeenCalledWith(1, '1'); expect(result.failedExpectations).toEqual([]); }; diff --git a/spec/core/integration/CustomMatchersSpec.js b/spec/core/integration/CustomMatchersSpec.js index c299c6ac..046ce079 100644 --- a/spec/core/integration/CustomMatchersSpec.js +++ b/spec/core/integration/CustomMatchersSpec.js @@ -1,52 +1,65 @@ -describe("Custom Matchers (Integration)", function () { +describe('Custom Matchers (Integration)', function() { var env; var fakeTimer; - beforeEach(function () { + beforeEach(function() { env = new jasmineUnderTest.Env(); - env.configure({random: false}); + env.configure({ random: false }); }); afterEach(function() { env.cleanup_(); }); - it("allows adding more matchers local to a spec", function (done) { - env.it('spec defining a custom matcher', function () { + it('allows adding more matchers local to a spec', function(done) { + env.it('spec defining a custom matcher', function() { env.addMatchers({ - matcherForSpec: function () { + matcherForSpec: function() { return { - compare: function (actual, expected) { - return {pass: false, message: "matcherForSpec: actual: " + actual + "; expected: " + expected}; + compare: function(actual, expected) { + return { + pass: false, + message: + 'matcherForSpec: actual: ' + + actual + + '; expected: ' + + expected + }; } - } + }; } }); - env.expect("zzz").matcherForSpec("yyy"); + env.expect('zzz').matcherForSpec('yyy'); }); - env.it("spec without custom matcher defined", function() { - expect(env.expect("zzz").matcherForSpec).toBeUndefined(); + env.it('spec without custom matcher defined', function() { + expect(env.expect('zzz').matcherForSpec).toBeUndefined(); }); - var specDoneSpy = jasmine.createSpy("specDoneSpy"); + var specDoneSpy = jasmine.createSpy('specDoneSpy'); var expectations = function() { var firstSpecResult = specDoneSpy.calls.first().args[0]; - expect(firstSpecResult.status).toEqual("failed"); - expect(firstSpecResult.failedExpectations[0].message).toEqual("matcherForSpec: actual: zzz; expected: yyy"); + expect(firstSpecResult.status).toEqual('failed'); + expect(firstSpecResult.failedExpectations[0].message).toEqual( + 'matcherForSpec: actual: zzz; expected: yyy' + ); done(); }; - env.addReporter({ specDone:specDoneSpy }); + env.addReporter({ specDone: specDoneSpy }); env.execute(null, expectations); }); - it("passes the spec if the custom matcher passes", function(done) { - env.it("spec using custom matcher", function() { + it('passes the spec if the custom matcher passes', function(done) { + env.it('spec using custom matcher', function() { env.addMatchers({ toBeReal: function() { - return { compare: function() { return { pass: true }; } }; + return { + compare: function() { + return { pass: true }; + } + }; } }); @@ -61,20 +74,30 @@ describe("Custom Matchers (Integration)", function () { env.execute(null, done); }); - it("passes the spec if the custom equality matcher passes for types nested inside asymmetric equality testers", function(done) { - env.it("spec using custom equality matcher", function() { + it('passes the spec if the custom equality matcher passes for types nested inside asymmetric equality testers', function(done) { + env.it('spec using custom equality matcher', function() { var customEqualityFn = function(a, b) { // All "foo*" strings match each other. - if (typeof a == "string" && typeof b == "string" && - a.substr(0, 3) == "foo" && b.substr(0, 3) == "foo") { + if ( + typeof a == 'string' && + typeof b == 'string' && + a.substr(0, 3) == 'foo' && + b.substr(0, 3) == 'foo' + ) { return true; } }; env.addCustomEqualityTester(customEqualityFn); - env.expect({foo: 'fooValue'}).toEqual(jasmineUnderTest.objectContaining({foo: 'fooBar'})); - env.expect(['fooValue', 'things']).toEqual(jasmineUnderTest.arrayContaining(['fooBar'])); - env.expect(['fooValue']).toEqual(jasmineUnderTest.arrayWithExactContents(['fooBar'])); + env + .expect({ foo: 'fooValue' }) + .toEqual(jasmineUnderTest.objectContaining({ foo: 'fooBar' })); + env + .expect(['fooValue', 'things']) + .toEqual(jasmineUnderTest.arrayContaining(['fooBar'])); + env + .expect(['fooValue']) + .toEqual(jasmineUnderTest.arrayWithExactContents(['fooBar'])); }); var specExpectations = function(result) { @@ -85,26 +108,30 @@ describe("Custom Matchers (Integration)", function () { env.execute(null, done); }); - it("supports asymmetric equality testers that take a list of custom equality testers", function(done) { + it('supports asymmetric equality testers that take a list of custom equality testers', function(done) { // TODO: remove this in the next major release. spyOn(jasmineUnderTest, 'getEnv').and.returnValue(env); - env.it("spec using custom asymmetric equality tester", function() { + env.it('spec using custom asymmetric equality tester', function() { var customEqualityFn = function(a, b) { - if (a === 2 && b === "two") { + if (a === 2 && b === 'two') { return true; } }; var arrayWithFirstElement = function(sample) { return { - asymmetricMatch: function (actual, customEqualityTesters) { - return jasmineUnderTest.matchersUtil.equals(sample, actual[0], customEqualityTesters); + asymmetricMatch: function(actual, customEqualityTesters) { + return jasmineUnderTest.matchersUtil.equals( + sample, + actual[0], + customEqualityTesters + ); } }; }; env.addCustomEqualityTester(customEqualityFn); - env.expect(["two"]).toEqual(arrayWithFirstElement(2)); + env.expect(['two']).toEqual(arrayWithFirstElement(2)); }); var specExpectations = function(result) { @@ -115,8 +142,8 @@ describe("Custom Matchers (Integration)", function () { env.execute(null, done); }); - it("displays an appropriate failure message if a custom equality matcher fails", function(done) { - env.it("spec using custom equality matcher", function() { + it('displays an appropriate failure message if a custom equality matcher fails', function(done) { + env.it('spec using custom equality matcher', function() { var customEqualityFn = function(a, b) { // "foo" is not equal to anything if (a === 'foo' || b === 'foo') { @@ -125,7 +152,7 @@ describe("Custom Matchers (Integration)", function () { }; env.addCustomEqualityTester(customEqualityFn); - env.expect({foo: 'foo'}).toEqual({foo: 'foo'}); + env.expect({ foo: 'foo' }).toEqual({ foo: 'foo' }); }); var specExpectations = function(result) { @@ -139,13 +166,17 @@ describe("Custom Matchers (Integration)", function () { env.execute(null, done); }); - it("uses the negative compare function for a negative comparison, if provided", function(done) { - env.it("spec with custom negative comparison matcher", function() { + it('uses the negative compare function for a negative comparison, if provided', function(done) { + env.it('spec with custom negative comparison matcher', function() { env.addMatchers({ toBeReal: function() { return { - compare: function() { return { pass: true }; }, - negativeCompare: function() { return { pass: true }; } + compare: function() { + return { pass: true }; + }, + negativeCompare: function() { + return { pass: true }; + } }; } }); @@ -161,7 +192,7 @@ describe("Custom Matchers (Integration)", function () { env.execute(null, done); }); - it("generates messages with the same rules as built in matchers absent a custom message", function(done) { + it('generates messages with the same rules as built in matchers absent a custom message', function(done) { env.it('spec with an expectation', function() { env.addMatchers({ toBeReal: function() { @@ -169,25 +200,29 @@ describe("Custom Matchers (Integration)", function () { compare: function() { return { pass: false }; } - } + }; } }); - env.expect("a").toBeReal(); + env.expect('a').toBeReal(); }); var specExpectations = function(result) { - expect(result.failedExpectations[0].message).toEqual("Expected 'a' to be real."); + expect(result.failedExpectations[0].message).toEqual( + "Expected 'a' to be real." + ); }; env.addReporter({ specDone: specExpectations }); env.execute(null, done); }); - it("passes the expected and actual arguments to the comparison function", function(done) { - var argumentSpy = jasmine.createSpy("argument spy").and.returnValue({ pass: true }); + it('passes the expected and actual arguments to the comparison function', function(done) { + var argumentSpy = jasmine + .createSpy('argument spy') + .and.returnValue({ pass: true }); - env.it('spec with an expectation', function () { + env.it('spec with an expectation', function() { env.addMatchers({ toBeReal: function() { return { compare: argumentSpy }; @@ -195,14 +230,14 @@ describe("Custom Matchers (Integration)", function () { }); env.expect(true).toBeReal(); - env.expect(true).toBeReal("arg"); - env.expect(true).toBeReal("arg1", "arg2"); + env.expect(true).toBeReal('arg'); + env.expect(true).toBeReal('arg1', 'arg2'); }); var specExpectations = function() { expect(argumentSpy).toHaveBeenCalledWith(true); - expect(argumentSpy).toHaveBeenCalledWith(true, "arg"); - expect(argumentSpy).toHaveBeenCalledWith(true, "arg1", "arg2"); + expect(argumentSpy).toHaveBeenCalledWith(true, 'arg'); + expect(argumentSpy).toHaveBeenCalledWith(true, 'arg1', 'arg2'); }; env.addReporter({ specDone: specExpectations }); @@ -210,13 +245,22 @@ describe("Custom Matchers (Integration)", function () { }); // TODO: remove this in the next major release. - it("passes the jasmine utility and current equality testers to the matcher factory", function(done) { - var matcherFactory = function() { return { compare: function() { return {pass: true}; }}; }, - matcherFactorySpy = jasmine.createSpy("matcherFactorySpy").and.callFake(matcherFactory), - customEqualityFn = function() { return true; }; + it('passes the jasmine utility and current equality testers to the matcher factory', function(done) { + var matcherFactory = function() { + return { + compare: function() { + return { pass: true }; + } + }; + }, + matcherFactorySpy = jasmine + .createSpy('matcherFactorySpy') + .and.callFake(matcherFactory), + customEqualityFn = function() { + return true; + }; - - env.it("spec with expectation", function() { + env.it('spec with expectation', function() { env.addCustomEqualityTester(customEqualityFn); env.addMatchers({ toBeReal: matcherFactorySpy @@ -236,33 +280,35 @@ describe("Custom Matchers (Integration)", function () { env.execute(null, done); }); - it("provides custom equality testers to the matcher factory via matchersUtil", function (done) { - var matcherFactory = function (matchersUtil) { + it('provides custom equality testers to the matcher factory via matchersUtil', function(done) { + var matcherFactory = function(matchersUtil) { return { - compare: function (actual, expected) { - return {pass: matchersUtil.equals(actual[0], expected)}; + compare: function(actual, expected) { + return { pass: matchersUtil.equals(actual[0], expected) }; } }; }, - customEqualityFn = jasmine.createSpy("customEqualityFn").and.callFake(function (a, b) { - return a.toString() === b; - }); + customEqualityFn = jasmine + .createSpy('customEqualityFn') + .and.callFake(function(a, b) { + return a.toString() === b; + }); - env.it("spec with expectation", function () { + env.it('spec with expectation', function() { env.addCustomEqualityTester(customEqualityFn); env.addMatchers({ toBeArrayWithFirstElement: matcherFactory }); - env.expect([1, 2]).toBeArrayWithFirstElement("1"); + env.expect([1, 2]).toBeArrayWithFirstElement('1'); }); - var specExpectations = function (result) { - expect(customEqualityFn).toHaveBeenCalledWith(1, "1"); + var specExpectations = function(result) { + expect(customEqualityFn).toHaveBeenCalledWith(1, '1'); expect(result.failedExpectations).toEqual([]); }; - env.addReporter({specDone: specExpectations}); + env.addReporter({ specDone: specExpectations }); env.execute(null, done); }); }); diff --git a/spec/core/integration/CustomObjectFormatterSpec.js b/spec/core/integration/CustomObjectFormatterSpec.js index 3337f452..2c61d9e0 100644 --- a/spec/core/integration/CustomObjectFormatterSpec.js +++ b/spec/core/integration/CustomObjectFormatterSpec.js @@ -1,14 +1,16 @@ -describe("Custom object formatters", function() { +describe('Custom object formatters', function() { var env; beforeEach(function() { env = new jasmineUnderTest.Env(); - env.configure({random: false}); + env.configure({ random: false }); }); - it("scopes custom object formatters to a spec", function(done) { + it('scopes custom object formatters to a spec', function(done) { env.it('a spec with custom pretty-printer', function() { - env.addCustomObjectFormatter(function(obj) { return 'custom(' + obj + ')'; }); + env.addCustomObjectFormatter(function(obj) { + return 'custom(' + obj + ')'; + }); env.expect(42).toBeUndefined(); }); @@ -21,23 +23,29 @@ describe("Custom object formatters", function() { specResults.push(result); }; var expectations = function() { - expect(specResults[0].failedExpectations[0].message).toEqual("Expected custom(42) to be undefined."); - expect(specResults[1].failedExpectations[0].message).toEqual("Expected 42 to be undefined."); + expect(specResults[0].failedExpectations[0].message).toEqual( + 'Expected custom(42) to be undefined.' + ); + expect(specResults[1].failedExpectations[0].message).toEqual( + 'Expected 42 to be undefined.' + ); done(); }; - env.addReporter({ specDone:specDone }); + env.addReporter({ specDone: specDone }); env.execute(null, expectations); }); - it("scopes custom object formatters to a suite", function(done) { + it('scopes custom object formatters to a suite', function(done) { env.it('a spec without custom pretty-printer', function() { env.expect(42).toBeUndefined(); }); env.describe('with custom pretty-printer', function() { env.beforeEach(function() { - env.addCustomObjectFormatter(function(obj) { return 'custom(' + obj + ')'; }); + env.addCustomObjectFormatter(function(obj) { + return 'custom(' + obj + ')'; + }); }); env.it('a spec', function() { @@ -50,18 +58,24 @@ describe("Custom object formatters", function() { specResults.push(result); }; var expectations = function() { - expect(specResults[0].failedExpectations[0].message).toEqual("Expected 42 to be undefined."); - expect(specResults[1].failedExpectations[0].message).toEqual("Expected custom(42) to be undefined."); + expect(specResults[0].failedExpectations[0].message).toEqual( + 'Expected 42 to be undefined.' + ); + expect(specResults[1].failedExpectations[0].message).toEqual( + 'Expected custom(42) to be undefined.' + ); done(); }; - env.addReporter({ specDone:specDone }); + env.addReporter({ specDone: specDone }); env.execute(null, expectations); }); - it("throws an exception if you try to add a custom object formatter outside a runable", function() { + it('throws an exception if you try to add a custom object formatter outside a runable', function() { expect(function() { env.addCustomObjectFormatter(function() {}); - }).toThrowError('Custom object formatters must be added in a before function or a spec') + }).toThrowError( + 'Custom object formatters must be added in a before function or a spec' + ); }); }); diff --git a/spec/core/integration/CustomSpyStrategiesSpec.js b/spec/core/integration/CustomSpyStrategiesSpec.js index e05b0773..92372c3f 100644 --- a/spec/core/integration/CustomSpyStrategiesSpec.js +++ b/spec/core/integration/CustomSpyStrategiesSpec.js @@ -3,7 +3,7 @@ describe('Custom Spy Strategies (Integration)', function() { beforeEach(function() { env = new jasmineUnderTest.Env(); - env.configure({random: false}); + env.configure({ random: false }); }); afterEach(function() { @@ -11,10 +11,8 @@ describe('Custom Spy Strategies (Integration)', function() { }); it('allows adding more strategies local to a suite', function(done) { - var plan = jasmine.createSpy('custom strategy plan') - .and.returnValue(42); - var strategy = jasmine.createSpy('custom strategy') - .and.returnValue(plan); + var plan = jasmine.createSpy('custom strategy plan').and.returnValue(42); + var strategy = jasmine.createSpy('custom strategy').and.returnValue(plan); var jasmineDone = jasmine.createSpy('jasmineDone'); env.describe('suite defining a custom spy strategy', function() { @@ -45,10 +43,8 @@ describe('Custom Spy Strategies (Integration)', function() { }); it('allows adding more strategies local to a spec', function(done) { - var plan = jasmine.createSpy('custom strategy plan') - .and.returnValue(42); - var strategy = jasmine.createSpy('custom strategy') - .and.returnValue(plan); + var plan = jasmine.createSpy('custom strategy plan').and.returnValue(42); + var strategy = jasmine.createSpy('custom strategy').and.returnValue(plan); var jasmineDone = jasmine.createSpy('jasmineDone'); env.it('spec defining a custom spy strategy', function() { @@ -74,17 +70,17 @@ describe('Custom Spy Strategies (Integration)', function() { }); it('allows using custom strategies on a per-argument basis', function(done) { - var plan = jasmine.createSpy('custom strategy plan') - .and.returnValue(42); - var strategy = jasmine.createSpy('custom strategy') - .and.returnValue(plan); + var plan = jasmine.createSpy('custom strategy plan').and.returnValue(42); + var strategy = jasmine.createSpy('custom strategy').and.returnValue(plan); var jasmineDone = jasmine.createSpy('jasmineDone'); env.it('spec defining a custom spy strategy', function() { env.addSpyStrategy('frobnicate', strategy); - var spy = env.createSpy('something') + var spy = env + .createSpy('something') .and.returnValue('no args return') - .withArgs(1, 2, 3).and.frobnicate(17); + .withArgs(1, 2, 3) + .and.frobnicate(17); expect(spy()).toEqual('no args return'); expect(plan).not.toHaveBeenCalled(); @@ -114,7 +110,6 @@ describe('Custom Spy Strategies (Integration)', function() { specDone = jasmine.createSpy('specDone'), jasmineDone = jasmine.createSpy('jasmineDone'); - env.beforeEach(function() { env.addSpyStrategy('frobnicate', strategy1); env.addSpyStrategy('jiggle', strategy2); diff --git a/spec/core/integration/DefaultSpyStrategySpec.js b/spec/core/integration/DefaultSpyStrategySpec.js index 50a11544..3f17a1d4 100644 --- a/spec/core/integration/DefaultSpyStrategySpec.js +++ b/spec/core/integration/DefaultSpyStrategySpec.js @@ -3,7 +3,7 @@ describe('Default Spy Strategy (Integration)', function() { beforeEach(function() { env = new jasmineUnderTest.Env(); - env.configure({random: false}); + env.configure({ random: false }); }); afterEach(function() { @@ -13,7 +13,7 @@ describe('Default Spy Strategy (Integration)', function() { it('allows defining a default spy strategy', function(done) { env.describe('suite with default strategy', function() { env.beforeEach(function() { - env.setDefaultSpyStrategy(function (and) { + env.setDefaultSpyStrategy(function(and) { and.returnValue(42); }); }); @@ -40,12 +40,16 @@ describe('Default Spy Strategy (Integration)', function() { env.execute(null, expectations); }); - it('uses the default spy strategy defined when the spy is created', function (done) { + it('uses the default spy strategy defined when the spy is created', function(done) { env.it('spec', function() { var a = env.createSpy('a'); - env.setDefaultSpyStrategy(function (and) { and.returnValue(42); }); + env.setDefaultSpyStrategy(function(and) { + and.returnValue(42); + }); var b = env.createSpy('b'); - env.setDefaultSpyStrategy(function (and) { and.stub(); }); + env.setDefaultSpyStrategy(function(and) { + and.stub(); + }); var c = env.createSpy('c'); env.setDefaultSpyStrategy(); var d = env.createSpy('d'); diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index 2c09affd..a8497985 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -1,4 +1,4 @@ -describe("Env integration", function() { +describe('Env integration', function() { var env; beforeEach(function() { @@ -10,33 +10,30 @@ describe("Env integration", function() { env.cleanup_(); }); - it("Suites execute as expected (no nesting)", function(done) { + it('Suites execute as expected (no nesting)', function(done) { var calls = []; var assertions = function() { - expect(calls).toEqual([ - "with a spec", - "and another spec" - ]); + expect(calls).toEqual(['with a spec', 'and another spec']); done(); }; - env.configure({random: false}); + env.configure({ random: false }); - env.describe("A Suite", function() { - env.it("with a spec", function() { - calls.push("with a spec"); + env.describe('A Suite', function() { + env.it('with a spec', function() { + calls.push('with a spec'); }); - env.it("and another spec", function() { - calls.push("and another spec"); + env.it('and another spec', function() { + calls.push('and another spec'); }); }); env.execute(null, assertions); }); - it("Nested Suites execute as expected", function(done) { + it('Nested Suites execute as expected', function(done) { var calls = []; var assertions = function() { @@ -49,17 +46,17 @@ describe("Env integration", function() { done(); }; - env.configure({random: false}); + env.configure({ random: false }); - env.describe("Outer suite", function() { - env.it("an outer spec", function() { - calls.push('an outer spec') + env.describe('Outer suite', function() { + env.it('an outer spec', function() { + calls.push('an outer spec'); }); - env.describe("Inner suite", function() { - env.it("an inner spec", function() { + env.describe('Inner suite', function() { + env.it('an inner spec', function() { calls.push('an inner spec'); }); - env.it("another inner spec", function() { + env.it('another inner spec', function() { calls.push('another inner spec'); }); }); @@ -68,7 +65,7 @@ describe("Env integration", function() { env.execute(null, assertions); }); - it("Multiple top-level Suites execute as expected", function(done) { + it('Multiple top-level Suites execute as expected', function(done) { var calls = []; var assertions = function() { @@ -82,26 +79,25 @@ describe("Env integration", function() { done(); }; - env.configure({random: false}); + env.configure({ random: false }); - - env.describe("Outer suite", function() { - env.it("an outer spec", function() { + env.describe('Outer suite', function() { + env.it('an outer spec', function() { calls.push('an outer spec'); }); - env.describe("Inner suite", function() { - env.it("an inner spec", function() { + env.describe('Inner suite', function() { + env.it('an inner spec', function() { calls.push('an inner spec'); }); - env.it("another inner spec", function() { + env.it('another inner spec', function() { calls.push('another inner spec'); }); }); }); - env.describe("Another outer suite", function() { - env.it("a 2nd outer spec", function() { - calls.push('a 2nd outer spec') + env.describe('Another outer suite', function() { + env.it('a 2nd outer spec', function() { + calls.push('a 2nd outer spec'); }); }); @@ -111,7 +107,7 @@ describe("Env integration", function() { it('explicitly fails a spec', function(done) { var specDone = jasmine.createSpy('specDone'); - env.addReporter({specDone: specDone}); + env.addReporter({ specDone: specDone }); env.describe('failing', function() { env.it('has a default message', function() { @@ -127,70 +123,92 @@ describe("Env integration", function() { }); env.it('pretty prints objects', function() { - env.fail({prop: 'value', arr: ['works', true]}); - }) + env.fail({ prop: 'value', arr: ['works', true] }); + }); }); env.execute(null, function() { - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'has a default message', - failedExpectations: [jasmine.objectContaining({ - message: 'Failed' - })] - })); - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'specifies a message', - failedExpectations: [jasmine.objectContaining({ - message: 'Failed: messy message' - })] - })); - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'has a message and stack trace from an Error', - failedExpectations: [jasmine.objectContaining({ - message: 'Failed: error message', - stack: { - asymmetricMatch: function(other) { - if (!other) { - // IE doesn't give us a stacktrace so just ignore it. - return true; + expect(specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: 'has a default message', + failedExpectations: [ + jasmine.objectContaining({ + message: 'Failed' + }) + ] + }) + ); + expect(specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: 'specifies a message', + failedExpectations: [ + jasmine.objectContaining({ + message: 'Failed: messy message' + }) + ] + }) + ); + expect(specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: 'has a message and stack trace from an Error', + failedExpectations: [ + jasmine.objectContaining({ + message: 'Failed: error message', + stack: { + asymmetricMatch: function(other) { + if (!other) { + // IE doesn't give us a stacktrace so just ignore it. + return true; + } + var split = other.split('\n'), + firstLine = split[0]; + if (firstLine.indexOf('error message') >= 0) { + // Chrome inserts the message and a newline before the first stacktrace line. + firstLine = split[1]; + } + return firstLine.indexOf('EnvSpec') >= 0; + } } - var split = other.split('\n'), - firstLine = split[0]; - if (firstLine.indexOf('error message') >= 0) { - // Chrome inserts the message and a newline before the first stacktrace line. - firstLine = split[1]; - } - return firstLine.indexOf('EnvSpec') >= 0; - } - } - })] - })); - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'pretty prints objects', - failedExpectations: [jasmine.objectContaining({ - message: 'Failed: Object({ prop: \'value\', arr: [ \'works\', true ] })' - })] - })); + }) + ] + }) + ); + expect(specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: 'pretty prints objects', + failedExpectations: [ + jasmine.objectContaining({ + message: + "Failed: Object({ prop: 'value', arr: [ 'works', true ] })" + }) + ] + }) + ); done(); }); }); it("produces an understandable error message when 'fail' is used outside of a current spec", function(done) { - env.describe("A Suite", function() { - env.it("an async spec that is actually synchronous", function(underTestCallback) { + env.describe('A Suite', function() { + env.it('an async spec that is actually synchronous', function( + underTestCallback + ) { underTestCallback(); }); - expect(function() { env.fail(); }).toThrowError(/'fail' was used when there was no current spec/); + expect(function() { + env.fail(); + }).toThrowError(/'fail' was used when there was no current spec/); }); env.execute(null, done); }); - it("calls associated befores/specs/afters with the same 'this'", function(done) { - env.configure({random: false}); - env.describe("tests", function() { - var firstTimeThrough = true, firstSpecContext, secondSpecContext; + env.configure({ random: false }); + env.describe('tests', function() { + var firstTimeThrough = true, + firstSpecContext, + secondSpecContext; env.beforeEach(function() { if (firstTimeThrough) { @@ -201,11 +219,11 @@ describe("Env integration", function() { expect(this).toEqual(new jasmineUnderTest.UserContext()); }); - env.it("sync spec", function() { + env.it('sync spec', function() { expect(this).toBe(firstSpecContext); }); - env.it("another sync spec", function() { + env.it('another sync spec', function() { expect(this).toBe(secondSpecContext); }); @@ -223,7 +241,7 @@ describe("Env integration", function() { }); it("calls associated befores/its/afters with the same 'this' for an async spec", function(done) { - env.describe("with an async spec", function() { + env.describe('with an async spec', function() { var specContext; env.beforeEach(function() { @@ -231,7 +249,7 @@ describe("Env integration", function() { expect(this).toEqual(new jasmineUnderTest.UserContext()); }); - env.it("sync spec", function(underTestCallback) { + env.it('sync spec', function(underTestCallback) { expect(this).toBe(specContext); underTestCallback(); }); @@ -244,17 +262,17 @@ describe("Env integration", function() { env.execute(null, done); }); - it("calls associated beforeAlls/afterAlls only once per suite", function(done) { + it('calls associated beforeAlls/afterAlls only once per suite', function(done) { var before = jasmine.createSpy('beforeAll'), - after = jasmine.createSpy('afterAll'); + after = jasmine.createSpy('afterAll'); - env.describe("with beforeAll and afterAll", function() { - env.it("spec", function() { + env.describe('with beforeAll and afterAll', function() { + env.it('spec', function() { expect(before).toHaveBeenCalled(); expect(after).not.toHaveBeenCalled(); }); - env.it("another spec", function() { + env.it('another spec', function() { expect(before).toHaveBeenCalled(); expect(after).not.toHaveBeenCalled(); }); @@ -271,17 +289,17 @@ describe("Env integration", function() { }); }); - it("calls associated beforeAlls/afterAlls only once per suite for async", function(done) { + it('calls associated beforeAlls/afterAlls only once per suite for async', function(done) { var before = jasmine.createSpy('beforeAll'), - after = jasmine.createSpy('afterAll'); + after = jasmine.createSpy('afterAll'); - env.describe("with beforeAll and afterAll", function() { - env.it("spec", function() { + env.describe('with beforeAll and afterAll', function() { + env.it('spec', function() { expect(before).toHaveBeenCalled(); expect(after).not.toHaveBeenCalled(); }); - env.it("another spec", function() { + env.it('another spec', function() { expect(before).toHaveBeenCalled(); expect(after).not.toHaveBeenCalled(); }); @@ -306,42 +324,42 @@ describe("Env integration", function() { }); it("calls associated beforeAlls/afterAlls with the cascaded 'this'", function(done) { - env.describe("with beforeAll and afterAll", function() { + env.describe('with beforeAll and afterAll', function() { env.beforeAll(function() { this.x = 1; }); - env.it("has an x at the root", function() { + env.it('has an x at the root', function() { expect(this.x).toBe(1); }); - env.describe("child that deletes", function() { + env.describe('child that deletes', function() { env.beforeAll(function() { expect(this.x).toBe(1); delete this.x; }); - env.it("has no x", function() { + env.it('has no x', function() { expect(this.x).not.toBeDefined(); }); }); - env.describe("child should still have x", function() { + env.describe('child should still have x', function() { env.beforeAll(function(innerDone) { expect(this.x).toBe(1); innerDone(); }); - env.it("has an x", function() { + env.it('has an x', function() { expect(this.x).toBe(1); delete this.x; }); - env.it("still has an x", function() { + env.it('still has an x', function() { expect(this.x).toBe(1); }); - env.it("adds a y", function() { + env.it('adds a y', function() { this.y = 2; expect(this.y).toBe(2); }); @@ -355,7 +373,7 @@ describe("Env integration", function() { env.execute(null, done); }); - it("tags top-level afterAll failures with a type", function(done) { + it('tags top-level afterAll failures with a type', function(done) { var jasmineDone = jasmine.createSpy('jasmineDone'); env.it('has a spec', function() {}); @@ -365,20 +383,23 @@ describe("Env integration", function() { }); env.addReporter({ jasmineDone: jasmineDone }); - env.execute(null, function() {{ - var result = jasmineDone.calls.argsFor(0)[0]; - expect(result.failedExpectations[0].globalErrorType).toEqual('afterAll'); - done(); - }}); + env.execute(null, function() { + { + var result = jasmineDone.calls.argsFor(0)[0]; + expect(result.failedExpectations[0].globalErrorType).toEqual( + 'afterAll' + ); + done(); + } + }); }); - it("does not tag suite afterAll failures with a type", function(done) { + it('does not tag suite afterAll failures with a type', function(done) { var reporter = { - suiteDone: jasmine.createSpy('suiteDone').and.callFake(function(result) { - expect(result.failedExpectations[0].globalErrorType).toBeFalsy(); - }) - }; - + suiteDone: jasmine.createSpy('suiteDone').and.callFake(function(result) { + expect(result.failedExpectations[0].globalErrorType).toBeFalsy(); + }) + }; env.addReporter(reporter); @@ -396,50 +417,73 @@ describe("Env integration", function() { }); }); - it("when the beforeAll fails, error at suite level", function (done) { - var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "suiteDone" ]); + it('when the beforeAll fails, error at suite level', function(done) { + var reporter = jasmine.createSpyObj('fakeReporter', [ + 'specDone', + 'suiteDone' + ]); var assertions = function() { expect(reporter.specDone.calls.count()).toEqual(2); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('A suite spec that will pass', []); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('A suite nesting another spec to pass', []); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('A suite', ['Expected 1 to be 2.']); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'A suite spec that will pass', + [] + ); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'A suite nesting another spec to pass', + [] + ); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'A suite', + ['Expected 1 to be 2.'] + ); done(); }; env.addReporter(reporter); - env.describe('A suite', function(){ + env.describe('A suite', function() { env.beforeAll(function() { env.expect(1).toBe(2); }); - env.it("spec that will pass", function() { - }); + env.it('spec that will pass', function() {}); - env.describe("nesting", function() { - env.it("another spec to pass", function() { - }); + env.describe('nesting', function() { + env.it('another spec to pass', function() {}); }); }); env.execute(null, assertions); }); - it("copes with async failures after done has been called", function(done) { + it('copes with async failures after done has been called', function(done) { var global = { - setTimeout: function(fn, delay) { setTimeout(fn, delay) }, - clearTimeout: function(fn, delay) { clearTimeout(fn, delay) }, + setTimeout: function(fn, delay) { + setTimeout(fn, delay); + }, + clearTimeout: function(fn, delay) { + clearTimeout(fn, delay); + } }; spyOn(jasmineUnderTest, 'getGlobal').and.returnValue(global); env.cleanup_(); env = new jasmineUnderTest.Env(); - var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone", "suiteDone" ]); + var reporter = jasmine.createSpyObj('fakeReporter', [ + 'specDone', + 'suiteDone' + ]); var assertions = function() { - expect(reporter.specDone).not.toHaveFailedExpectationsForRunnable('A suite fails', ['fail thrown']); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('A suite', ['fail thrown']); + expect(reporter.specDone).not.toHaveFailedExpectationsForRunnable( + 'A suite fails', + ['fail thrown'] + ); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'A suite', + ['fail thrown'] + ); done(); }; @@ -450,9 +494,9 @@ describe("Env integration", function() { setTimeout(function() { specDone(); setTimeout(function() { - setTimeout(function() { - global.onerror('fail'); - }); + setTimeout(function() { + global.onerror('fail'); + }); }); }); }); @@ -465,23 +509,22 @@ describe("Env integration", function() { env.execute(null, assertions); }); - describe('suiteDone reporting', function(){ - it("reports when an afterAll fails an expectation", function(done) { + describe('suiteDone reporting', function() { + it('reports when an afterAll fails an expectation', function(done) { var reporter = jasmine.createSpyObj('fakeReport', ['suiteDone']); var assertions = function() { - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('my suite', [ - 'Expected 1 to equal 2.', - 'Expected 2 to equal 3.' - ]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'my suite', + ['Expected 1 to equal 2.', 'Expected 2 to equal 3.'] + ); done(); }; env.addReporter(reporter); env.describe('my suite', function() { - env.it('my spec', function() { - }); + env.it('my spec', function() {}); env.afterAll(function() { env.expect(1).toEqual(2); @@ -492,14 +535,14 @@ describe("Env integration", function() { env.execute(null, assertions); }); - it("if there are no specs, it still reports correctly", function(done) { + it('if there are no specs, it still reports correctly', function(done) { var reporter = jasmine.createSpyObj('fakeReport', ['suiteDone']); var assertions = function() { - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('outer suite', [ - 'Expected 1 to equal 2.', - 'Expected 2 to equal 3.' - ]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'outer suite', + ['Expected 1 to equal 2.', 'Expected 2 to equal 3.'] + ); done(); }; @@ -507,7 +550,7 @@ describe("Env integration", function() { env.describe('outer suite', function() { env.describe('inner suite', function() { - env.it('spec', function(){ }); + env.it('spec', function() {}); }); env.afterAll(function() { @@ -519,22 +562,22 @@ describe("Env integration", function() { env.execute(null, assertions); }); - it("reports when afterAll throws an exception", function(done) { + it('reports when afterAll throws an exception', function(done) { var error = new Error('After All Exception'), reporter = jasmine.createSpyObj('fakeReport', ['suiteDone']); var assertions = function() { - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('my suite', [ - (/^Error: After All Exception/) - ]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'my suite', + [/^Error: After All Exception/] + ); done(); }; env.addReporter(reporter); env.describe('my suite', function() { - env.it('my spec', function() { - }); + env.it('my spec', function() {}); env.afterAll(function() { throw error; @@ -544,21 +587,21 @@ describe("Env integration", function() { env.execute(null, assertions); }); - it("reports when an async afterAll fails an expectation", function(done) { + it('reports when an async afterAll fails an expectation', function(done) { var reporter = jasmine.createSpyObj('fakeReport', ['suiteDone']); var assertions = function() { - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('my suite', [ - 'Expected 1 to equal 2.' - ]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'my suite', + ['Expected 1 to equal 2.'] + ); done(); }; env.addReporter(reporter); env.describe('my suite', function() { - env.it('my spec', function() { - }); + env.it('my spec', function() {}); env.afterAll(function(afterAllDone) { env.expect(1).toEqual(2); @@ -569,23 +612,22 @@ describe("Env integration", function() { env.execute(null, assertions); }); - it("reports when an async afterAll throws an exception", function(done) { + it('reports when an async afterAll throws an exception', function(done) { var error = new Error('After All Exception'), reporter = jasmine.createSpyObj('fakeReport', ['suiteDone']); - var assertions = function() { - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('my suite', [ - (/^Error: After All Exception/) - ]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'my suite', + [/^Error: After All Exception/] + ); done(); }; env.addReporter(reporter); env.describe('my suite', function() { - env.it('my spec', function() { - }); + env.it('my spec', function() {}); env.afterAll(function(afterAllDone) { throw error; @@ -610,7 +652,7 @@ describe("Env integration", function() { // We can't just use the mock clock here because the timer is designed // to record real time even when the mock clock is installed. setTimeout(done, 10); - }) + }); }); env.execute(null, function() { @@ -636,7 +678,7 @@ describe("Env integration", function() { // We can't just use the mock clock here because the timer is designed // to record real time even when the mock clock is installed. setTimeout(done, 10); - }) + }); }); env.execute(null, function() { @@ -661,8 +703,13 @@ describe("Env integration", function() { env.execute(null, function() { var results = reporter.jasmineDone.calls.argsFor(0)[0]; - expect(results.failedExpectations).toEqual([jasmine.objectContaining({ message: 'Expected 1 to be 0.' })]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('is a spec', []); + expect(results.failedExpectations).toEqual([ + jasmine.objectContaining({ message: 'Expected 1 to be 0.' }) + ]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'is a spec', + [] + ); done(); }); }); @@ -682,39 +729,38 @@ describe("Env integration", function() { env.execute(null, function() { var results = reporter.jasmineDone.calls.argsFor(0)[0]; - expect(results.failedExpectations).toEqual([jasmine.objectContaining({ message: 'Expected 1 to be 0.' })]); + expect(results.failedExpectations).toEqual([ + jasmine.objectContaining({ message: 'Expected 1 to be 0.' }) + ]); done(); }); }); - it("Allows specifying which specs and suites to run", function(done) { + it('Allows specifying which specs and suites to run', function(done) { var calls = [], - suiteCallback = jasmine.createSpy('suite callback'), - firstSpec, - secondSuite; + suiteCallback = jasmine.createSpy('suite callback'), + firstSpec, + secondSuite; - env.addReporter({ suiteDone: suiteCallback}); + env.addReporter({ suiteDone: suiteCallback }); - env.describe("first suite", function() { - firstSpec = env.it("first spec", function() { + env.describe('first suite', function() { + firstSpec = env.it('first spec', function() { calls.push('first spec'); }); - env.it("second spec", function() { + env.it('second spec', function() { calls.push('second spec'); }); }); - secondSuite = env.describe("second suite", function() { - env.it("third spec", function() { + secondSuite = env.describe('second suite', function() { + env.it('third spec', function() { calls.push('third spec'); }); }); env.execute([secondSuite.id, firstSpec.id], function() { - expect(calls).toEqual([ - 'third spec', - 'first spec' - ]); + expect(calls).toEqual(['third spec', 'first spec']); expect(suiteCallback).toHaveBeenCalled(); done(); }); @@ -725,51 +771,46 @@ describe("Env integration", function() { first_spec, second_spec; - env.describe("first suite", function() { + env.describe('first suite', function() { env.beforeAll(function() { - calls.push("before"); + calls.push('before'); }); env.afterAll(function() { - calls.push("after") + calls.push('after'); }); - first_spec = env.it("spec", function() { + first_spec = env.it('spec', function() { calls.push('first spec'); }); - second_spec = env.it("spec 2", function() { - calls.push("second spec"); - }); - }); - - env.execute([first_spec.id, second_spec.id], function() { - expect(calls).toEqual([ - "before", - "first spec", - "second spec", - "after" - ]); - done(); - }); - }); - - it("Allows filtering out specs and suites to run programmatically", function(done) { - var calls = [], - suiteCallback = jasmine.createSpy('suite callback'), - firstSpec, - secondSuite; - - env.addReporter({suiteDone: suiteCallback}); - - env.describe("first suite", function() { - env.it("first spec", function() { - calls.push('first spec'); - }); - env.it("second spec", function() { + second_spec = env.it('spec 2', function() { calls.push('second spec'); }); }); - secondSuite = env.describe("second suite", function() { - env.it("third spec", function() { + env.execute([first_spec.id, second_spec.id], function() { + expect(calls).toEqual(['before', 'first spec', 'second spec', 'after']); + done(); + }); + }); + + it('Allows filtering out specs and suites to run programmatically', function(done) { + var calls = [], + suiteCallback = jasmine.createSpy('suite callback'), + firstSpec, + secondSuite; + + env.addReporter({ suiteDone: suiteCallback }); + + env.describe('first suite', function() { + env.it('first spec', function() { + calls.push('first spec'); + }); + env.it('second spec', function() { + calls.push('second spec'); + }); + }); + + secondSuite = env.describe('second suite', function() { + env.it('third spec', function() { calls.push('third spec'); }); }); @@ -782,26 +823,27 @@ describe("Env integration", function() { env.execute(null, function() { expect(calls.length).toEqual(2); - expect(calls).toEqual(jasmine.arrayContaining([ - 'first spec', - 'second spec' - ])); + expect(calls).toEqual( + jasmine.arrayContaining(['first spec', 'second spec']) + ); expect(suiteCallback).toHaveBeenCalled(); done(); }); }); - it("Functions can be spied on and have their calls tracked", function (done) { + it('Functions can be spied on and have their calls tracked', function(done) { var originalFunctionWasCalled = false; var subject = { spiedFunc: function() { originalFunctionWasCalled = true; - return "original result"; + return 'original result'; } }; - env.it("works with spies", function() { - var spy = env.spyOn(subject, 'spiedFunc').and.returnValue("stubbed result"); + env.it('works with spies', function() { + var spy = env + .spyOn(subject, 'spiedFunc') + .and.returnValue('stubbed result'); expect(subject.spiedFunc).toEqual(spy); expect(subject.spiedFunc.calls.any()).toEqual(false); @@ -813,57 +855,71 @@ describe("Env integration", function() { expect(subject.spiedFunc.calls.count()).toEqual(1); expect(subject.spiedFunc.calls.mostRecent().args).toEqual(['foo']); expect(subject.spiedFunc.calls.mostRecent().object).toEqual(subject); - expect(subject.spiedFunc.calls.mostRecent().returnValue).toEqual("stubbed result"); + expect(subject.spiedFunc.calls.mostRecent().returnValue).toEqual( + 'stubbed result' + ); expect(originalFunctionWasCalled).toEqual(false); subject.spiedFunc.and.callThrough(); subject.spiedFunc('bar'); expect(subject.spiedFunc.calls.count()).toEqual(2); expect(subject.spiedFunc.calls.mostRecent().args).toEqual(['bar']); - expect(subject.spiedFunc.calls.mostRecent().returnValue).toEqual("original result"); + expect(subject.spiedFunc.calls.mostRecent().returnValue).toEqual( + 'original result' + ); expect(originalFunctionWasCalled).toEqual(true); }); - env.it("works with constructors when using callThrough spy strategy", function() { - function MyClass(foo) { - if (!(this instanceof MyClass)) throw new Error('You must use the new keyword.'); - this.foo = foo; + env.it( + 'works with constructors when using callThrough spy strategy', + function() { + function MyClass(foo) { + if (!(this instanceof MyClass)) + throw new Error('You must use the new keyword.'); + this.foo = foo; + } + var subject = { MyClass: MyClass }; + var spy = env.spyOn(subject, 'MyClass').and.callThrough(); + + expect(function() { + var result = new spy('hello world'); + expect(result instanceof MyClass).toBeTruthy(); + expect(result.foo).toEqual('hello world'); + }).not.toThrow(); + + expect(function() { + var result = new spy( + 'passing', + 'extra', + 'arguments', + 'to', + 'constructor' + ); + expect(result instanceof MyClass).toBeTruthy(); + expect(result.foo).toEqual('passing'); + }).not.toThrow(); + + expect(function() { + spy('hello world'); + }).toThrowError('You must use the new keyword.'); } - var subject = { MyClass: MyClass }; - var spy = env.spyOn(subject, 'MyClass').and.callThrough(); - - expect(function() { - var result = new spy('hello world'); - expect(result instanceof MyClass).toBeTruthy(); - expect(result.foo).toEqual('hello world'); - }).not.toThrow(); - - expect(function() { - var result = new spy('passing', 'extra', 'arguments', 'to', 'constructor'); - expect(result instanceof MyClass).toBeTruthy(); - expect(result.foo).toEqual('passing'); - }).not.toThrow(); - - expect(function() { - spy('hello world'); - }).toThrowError('You must use the new keyword.'); - }); + ); env.execute(null, done); }); - it('can be configured to allow respying on functions', function (done) { + it('can be configured to allow respying on functions', function(done) { var foo = { - bar: function () { - return 1; - } - }; + bar: function() { + return 1; + } + }; env.allowRespy(true); env.describe('test suite', function() { env.it('spec 0', function() { - env.spyOn(foo,'bar'); + env.spyOn(foo, 'bar'); var error = null; @@ -887,10 +943,10 @@ describe("Env integration", function() { secondSpec = jasmine.createSpy('secondSpec').and.callFake(function() { expect(testObj.foo).toBe(originalFoo); }); - env.describe('test suite', function() { - env.it('spec 0', firstSpec); - env.it('spec 1', secondSpec); - }); + env.describe('test suite', function() { + env.it('spec 0', firstSpec); + env.it('spec 1', secondSpec); + }); env.execute(null, function() { expect(firstSpec).toHaveBeenCalled(); @@ -905,24 +961,26 @@ describe("Env integration", function() { foo: originalFoo }; - env.describe('test suite', function() { - env.beforeAll(function() { env.spyOn(testObj, 'foo');}); - - env.it('spec 0', function() { - expect(jasmineUnderTest.isSpy(testObj.foo)).toBe(true); - }); - - env.it('spec 1', function() { - expect(jasmineUnderTest.isSpy(testObj.foo)).toBe(true); - }); + env.describe('test suite', function() { + env.beforeAll(function() { + env.spyOn(testObj, 'foo'); }); - env.describe('another suite', function() { - env.it('spec 2', function() { - expect(jasmineUnderTest.isSpy(testObj.foo)).toBe(false); - }); + env.it('spec 0', function() { + expect(jasmineUnderTest.isSpy(testObj.foo)).toBe(true); }); + env.it('spec 1', function() { + expect(jasmineUnderTest.isSpy(testObj.foo)).toBe(true); + }); + }); + + env.describe('another suite', function() { + env.it('spec 2', function() { + expect(jasmineUnderTest.isSpy(testObj.foo)).toBe(false); + }); + }); + env.execute(null, done); }); @@ -946,24 +1004,40 @@ describe("Env integration", function() { }); }); - it("Mock clock can be installed and used in tests", function(done) { - var globalSetTimeout = jasmine.createSpy('globalSetTimeout').and.callFake(function(cb, t) { setTimeout(cb, t); }), - delayedFunctionForGlobalClock = jasmine.createSpy('delayedFunctionForGlobalClock'), - delayedFunctionForMockClock = jasmine.createSpy('delayedFunctionForMockClock'); + it('Mock clock can be installed and used in tests', function(done) { + var globalSetTimeout = jasmine + .createSpy('globalSetTimeout') + .and.callFake(function(cb, t) { + setTimeout(cb, t); + }), + delayedFunctionForGlobalClock = jasmine.createSpy( + 'delayedFunctionForGlobalClock' + ), + delayedFunctionForMockClock = jasmine.createSpy( + 'delayedFunctionForMockClock' + ); env.cleanup_(); - env = new jasmineUnderTest.Env({global: { setTimeout: globalSetTimeout, clearTimeout: clearTimeout, setImmediate: function(cb) { setTimeout(cb, 0); } }}); + env = new jasmineUnderTest.Env({ + global: { + setTimeout: globalSetTimeout, + clearTimeout: clearTimeout, + setImmediate: function(cb) { + setTimeout(cb, 0); + } + } + }); - env.configure({random: false}); + env.configure({ random: false }); - env.describe("tests", function() { - env.it("test with mock clock", function() { + env.describe('tests', function() { + env.it('test with mock clock', function() { env.clock.install(); env.clock.setTimeout(delayedFunctionForMockClock, 100); env.clock.tick(100); env.clock.uninstall(); }); - env.it("test without mock clock", function() { + env.it('test without mock clock', function() { env.clock.setTimeout(delayedFunctionForGlobalClock, 100); }); }); @@ -973,27 +1047,30 @@ describe("Env integration", function() { env.execute(null, function() { expect(delayedFunctionForMockClock).toHaveBeenCalled(); - expect(globalSetTimeout).toHaveBeenCalledWith(delayedFunctionForGlobalClock, 100); + expect(globalSetTimeout).toHaveBeenCalledWith( + delayedFunctionForGlobalClock, + 100 + ); done(); }); }); - it("should run async specs in order, waiting for them to complete", function(done) { + it('should run async specs in order, waiting for them to complete', function(done) { var mutatedVar; - env.describe("tests", function() { + env.describe('tests', function() { env.beforeEach(function() { mutatedVar = 2; }); - env.it("async spec", function(underTestCallback) { + env.it('async spec', function(underTestCallback) { setTimeout(function() { expect(mutatedVar).toEqual(2); underTestCallback(); }, 0); }); - env.it("after async spec", function() { + env.it('after async spec', function() { mutatedVar = 3; }); }); @@ -1001,13 +1078,14 @@ describe("Env integration", function() { env.execute(null, done); }); - describe("with a mock clock", function() { + describe('with a mock clock', function() { var realSetTimeout; function createMockedEnv() { env.cleanup_(); // explicitly pass in timing functions so we can make sure that clear stack always works // no matter how long the suite in the spec is - env = new jasmineUnderTest.Env({ global: { + env = new jasmineUnderTest.Env({ + global: { setTimeout: function(cb, t) { var stack = jasmine.util.errorWithStack().stack; if (stack.indexOf('ClearStack') >= 0) { @@ -1019,8 +1097,11 @@ describe("Env integration", function() { clearTimeout: clearTimeout, setInterval: setInterval, clearInterval: clearInterval, - setImmediate: function(cb) { realSetTimeout(cb, 0); } - }}); + setImmediate: function(cb) { + realSetTimeout(cb, 0); + } + } + }); } beforeEach(function() { @@ -1038,10 +1119,10 @@ describe("Env integration", function() { it("should wait a default interval before failing specs that haven't called done yet", function(done) { createMockedEnv(); - var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone" ]); + var reporter = jasmine.createSpyObj('fakeReporter', ['specDone']); reporter.specDone.and.callFake(function(result) { - expect(result).toEqual(jasmine.objectContaining({status: 'failed'})); + expect(result).toEqual(jasmine.objectContaining({ status: 'failed' })); realSetTimeout(function() { jasmine.clock().tick(1); }, 0); @@ -1063,9 +1144,9 @@ describe("Env integration", function() { }); }); - it("should not use the mock clock for asynchronous timeouts", function(done){ + it('should not use the mock clock for asynchronous timeouts', function(done) { createMockedEnv(); - var reporter = jasmine.createSpyObj('fakeReporter', [ "specDone" ]), + var reporter = jasmine.createSpyObj('fakeReporter', ['specDone']), clock = env.clock; reporter.specDone.and.callFake(function() { @@ -1085,7 +1166,7 @@ describe("Env integration", function() { clock.uninstall(); }); - env.it("spec that should not time out", function(innerDone) { + env.it('spec that should not time out', function(innerDone) { clock.tick(6); expect(true).toEqual(true); realSetTimeout(innerDone); @@ -1093,7 +1174,9 @@ describe("Env integration", function() { env.execute(null, function() { expect(reporter.specDone).toHaveBeenCalledTimes(1); - expect(reporter.specDone.calls.argsFor(0)[0]).toEqual(jasmine.objectContaining({status: 'passed'})); + expect(reporter.specDone.calls.argsFor(0)[0]).toEqual( + jasmine.objectContaining({ status: 'passed' }) + ); jasmine.clock().tick(1); realSetTimeout(done); }); @@ -1101,7 +1184,11 @@ describe("Env integration", function() { it('should wait a custom interval before reporting async functions that fail to complete', function(done) { createMockedEnv(); - var reporter = jasmine.createSpyObj('fakeReport', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('fakeReport', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); jasmineUnderTest.DEFAULT_TIMEOUT_INTERVAL = 10000; @@ -1111,7 +1198,7 @@ describe("Env integration", function() { realSetTimeout(function() { try { jasmine.clock().tick(10); - } catch(e) { + } catch (e) { // don't worry if the clock is already uninstalled } }, 100); @@ -1176,21 +1263,50 @@ describe("Env integration", function() { }); }); - env.it('it times out', function(innerDone) { - realSetTimeout(function() { - jasmine.clock().tick(6001); - }, 0); - }, 6000); + env.it( + 'it times out', + function(innerDone) { + realSetTimeout(function() { + jasmine.clock().tick(6001); + }, 0); + }, + 6000 + ); }); env.execute(null, function() { var r = reporter.jasmineDone.calls.argsFor(0)[0]; expect(r.failedExpectations).toEqual([]); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('suite beforeAll', [ /^Error: Timeout - Async function did not complete within 5000ms \(custom timeout\)/ ]); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('suite afterAll', [ /^Error: Timeout - Async function did not complete within 2000ms \(custom timeout\)/ ]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite beforeEach times out', [/^Error: Timeout - Async function did not complete within 1000ms \(custom timeout\)/]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite afterEach times out', [ /^Error: Timeout - Async function did not complete within 4000ms \(custom timeout\)/ ]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite it times out', [ /^Error: Timeout - Async function did not complete within 6000ms \(custom timeout\)/ ]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'suite beforeAll', + [ + /^Error: Timeout - Async function did not complete within 5000ms \(custom timeout\)/ + ] + ); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'suite afterAll', + [ + /^Error: Timeout - Async function did not complete within 2000ms \(custom timeout\)/ + ] + ); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'suite beforeEach times out', + [ + /^Error: Timeout - Async function did not complete within 1000ms \(custom timeout\)/ + ] + ); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'suite afterEach times out', + [ + /^Error: Timeout - Async function did not complete within 4000ms \(custom timeout\)/ + ] + ); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'suite it times out', + [ + /^Error: Timeout - Async function did not complete within 6000ms \(custom timeout\)/ + ] + ); jasmine.clock().tick(1); realSetTimeout(done); @@ -1201,7 +1317,7 @@ describe("Env integration", function() { it('explicitly fails an async spec', function(done) { var specDone = jasmine.createSpy('specDone'); - env.addReporter({specDone: specDone}); + env.addReporter({ specDone: specDone }); env.describe('failing', function() { env.it('has a default message', function(innerDone) { @@ -1239,19 +1355,24 @@ describe("Env integration", function() { }); env.execute(null, function() { - expect(specDone).toHaveFailedExpectationsForRunnable('failing has a default message', + expect(specDone).toHaveFailedExpectationsForRunnable( + 'failing has a default message', ['Failed'] ); - expect(specDone).toHaveFailedExpectationsForRunnable('failing specifies a message', + expect(specDone).toHaveFailedExpectationsForRunnable( + 'failing specifies a message', ['Failed: messy message'] ); - expect(specDone).toHaveFailedExpectationsForRunnable('failing fails via the done callback', + expect(specDone).toHaveFailedExpectationsForRunnable( + 'failing fails via the done callback', ['Failed: done failed'] ); - expect(specDone).toHaveFailedExpectationsForRunnable('failing has a message from an Error', + expect(specDone).toHaveFailedExpectationsForRunnable( + 'failing has a message from an Error', ['Failed: error message'] ); - expect(specDone).toHaveFailedExpectationsForRunnable('failing has a message from an Error to done', + expect(specDone).toHaveFailedExpectationsForRunnable( + 'failing has a message from an Error to done', ['Failed: done error'] ); @@ -1270,7 +1391,7 @@ describe("Env integration", function() { env.it('is not focused', function() { calls.push('freakout'); - }) + }); }); env.execute(null, function() { @@ -1279,7 +1400,7 @@ describe("Env integration", function() { }); }); - it('should only run focused suites', function(done){ + it('should only run focused suites', function(done) { var calls = []; env.fdescribe('a focused suite', function() { @@ -1291,7 +1412,7 @@ describe("Env integration", function() { env.describe('a regular suite', function() { env.it('is not focused', function() { calls.push('freakout'); - }) + }); }); env.execute(null, function() { @@ -1302,17 +1423,17 @@ describe("Env integration", function() { it('should run focused tests inside an xdescribe', function(done) { var reporter = jasmine.createSpyObj('fakeReporter', [ - "jasmineStarted", - "suiteStarted", - "suiteDone", - "specStarted", - "specDone" - ]); + 'jasmineStarted', + 'suiteStarted', + 'suiteDone', + 'specStarted', + 'specDone' + ]); env.addReporter(reporter); - env.xdescribe("xd suite", function() { - env.fit("with a fit spec", function() { + env.xdescribe('xd suite', function() { + env.fit('with a fit spec', function() { env.expect(true).toBe(false); }); }); @@ -1323,10 +1444,12 @@ describe("Env integration", function() { order: jasmine.any(jasmineUnderTest.Order) }); - expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'with a fit spec', - status: 'failed' - })); + expect(reporter.specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: 'with a fit spec', + status: 'failed' + }) + ); done(); }); @@ -1334,18 +1457,18 @@ describe("Env integration", function() { it('should run focused suites inside an xdescribe', function(done) { var reporter = jasmine.createSpyObj('fakeReporter', [ - "jasmineStarted", - "suiteStarted", - "suiteDone", - "specStarted", - "specDone" - ]); + 'jasmineStarted', + 'suiteStarted', + 'suiteDone', + 'specStarted', + 'specDone' + ]); env.addReporter(reporter); - env.xdescribe("xd suite", function() { - env.fdescribe("fd suite", function() { - env.it("with a spec", function() { + env.xdescribe('xd suite', function() { + env.fdescribe('fd suite', function() { + env.it('with a spec', function() { env.expect(true).toBe(false); }); }); @@ -1357,36 +1480,38 @@ describe("Env integration", function() { order: jasmine.any(jasmineUnderTest.Order) }); - expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'with a spec', - status: 'failed' - })); + expect(reporter.specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: 'with a spec', + status: 'failed' + }) + ); done(); }); }); }); - it("should report as expected", function(done) { + it('should report as expected', function(done) { var reporter = jasmine.createSpyObj('fakeReporter', [ - "jasmineStarted", - "suiteStarted", - "suiteDone", - "specStarted", - "specDone" - ]); + 'jasmineStarted', + 'suiteStarted', + 'suiteDone', + 'specStarted', + 'specDone' + ]); env.addReporter(reporter); - env.describe("A Suite", function() { - env.it("with a top level spec", function() { + env.describe('A Suite', function() { + env.it('with a top level spec', function() { env.expect(true).toBe(true); }); - env.describe("with a nested suite", function() { + env.describe('with a nested suite', function() { env.xit("with an x'ed spec", function() { env.expect(true).toBe(true); }); - env.it("with a spec", function() { + env.it('with a spec', function() { env.expect(true).toBe(false); }); }); @@ -1407,49 +1532,57 @@ describe("Env integration", function() { expect(reporter.specDone.calls.count()).toBe(5); - expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'with a top level spec', - status: 'passed' - })); + expect(reporter.specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: 'with a top level spec', + status: 'passed' + }) + ); - expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: "with an x'ed spec", - status: 'pending' - })); + expect(reporter.specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: "with an x'ed spec", + status: 'pending' + }) + ); - expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'with a spec', - status: 'failed' - })); + expect(reporter.specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: 'with a spec', + status: 'failed' + }) + ); - expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'is pending', - status: 'pending' - })); + expect(reporter.specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: 'is pending', + status: 'pending' + }) + ); var suiteDone = reporter.suiteDone.calls.argsFor(0)[0]; expect(typeof suiteDone.duration).toBe('number'); var suiteResult = reporter.suiteStarted.calls.argsFor(0)[0]; - expect(suiteResult.description).toEqual("A Suite"); + expect(suiteResult.description).toEqual('A Suite'); done(); }); }); - it("should report the random seed at the beginning and end of execution", function(done) { + it('should report the random seed at the beginning and end of execution', function(done) { var reporter = jasmine.createSpyObj('fakeReporter', [ - "jasmineStarted", - "jasmineDone", - "suiteStarted", - "suiteDone", - "specStarted", - "specDone" - ]); - env.configure({random: true, seed: '123456'}); + 'jasmineStarted', + 'jasmineDone', + 'suiteStarted', + 'suiteDone', + 'specStarted', + 'specDone' + ]); + env.configure({ random: true, seed: '123456' }); env.addReporter(reporter); - env.configure({random: true}); + env.configure({ random: true }); env.execute(null, function() { expect(reporter.jasmineStarted).toHaveBeenCalled(); var startedArg = reporter.jasmineStarted.calls.argsFor(0)[0]; @@ -1517,9 +1650,9 @@ describe("Env integration", function() { it('should report using fallback reporter', function(done) { var reporter = jasmine.createSpyObj('fakeReporter', [ - 'specDone', - 'jasmineDone' - ]); + 'specDone', + 'jasmineDone' + ]); reporter.jasmineDone.and.callFake(function() { expect(reporter.specDone).toHaveBeenCalled(); @@ -1538,20 +1671,20 @@ describe("Env integration", function() { it('should report xdescribes as expected', function(done) { var reporter = jasmine.createSpyObj('fakeReporter', [ - "jasmineStarted", - "suiteStarted", - "suiteDone", - "specStarted", - "specDone" - ]); + 'jasmineStarted', + 'suiteStarted', + 'suiteDone', + 'specStarted', + 'specDone' + ]); env.addReporter(reporter); - env.describe("A Suite", function() { - env.describe("nested", function() { - env.xdescribe("xd out", function() { - env.describe("nested again", function() { - env.it("with a spec", function() { + env.describe('A Suite', function() { + env.describe('nested', function() { + env.xdescribe('xd out', function() { + env.describe('nested again', function() { + env.it('with a spec', function() { env.expect(true).toBe(false); }); }); @@ -1565,49 +1698,56 @@ describe("Env integration", function() { order: jasmine.any(jasmineUnderTest.Order) }); - expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ status: 'pending' })); - expect(reporter.suiteDone).toHaveBeenCalledWith(jasmine.objectContaining({ description: 'xd out', status: 'pending' })); + expect(reporter.specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ status: 'pending' }) + ); + expect(reporter.suiteDone).toHaveBeenCalledWith( + jasmine.objectContaining({ description: 'xd out', status: 'pending' }) + ); expect(reporter.suiteDone.calls.count()).toBe(4); done(); }); }); - it("should be possible to get full name from a spec", function() { + it('should be possible to get full name from a spec', function() { var topLevelSpec, nestedSpec, doublyNestedSpec; - env.describe("my tests", function() { - topLevelSpec = env.it("are sometimes top level", function() { - }); - env.describe("are sometimes", function() { - nestedSpec = env.it("singly nested", function() { - }); - env.describe("even", function() { - doublyNestedSpec = env.it("doubly nested", function() { - }); + env.describe('my tests', function() { + topLevelSpec = env.it('are sometimes top level', function() {}); + env.describe('are sometimes', function() { + nestedSpec = env.it('singly nested', function() {}); + env.describe('even', function() { + doublyNestedSpec = env.it('doubly nested', function() {}); }); }); }); - expect(topLevelSpec.getFullName()).toBe("my tests are sometimes top level"); - expect(nestedSpec.getFullName()).toBe("my tests are sometimes singly nested"); - expect(doublyNestedSpec.getFullName()).toBe("my tests are sometimes even doubly nested"); + expect(topLevelSpec.getFullName()).toBe('my tests are sometimes top level'); + expect(nestedSpec.getFullName()).toBe( + 'my tests are sometimes singly nested' + ); + expect(doublyNestedSpec.getFullName()).toBe( + 'my tests are sometimes even doubly nested' + ); }); - it("Custom equality testers should be per spec", function(done) { - var reporter = jasmine.createSpyObj('fakeReporter', ["specDone"]); + it('Custom equality testers should be per spec', function(done) { + var reporter = jasmine.createSpyObj('fakeReporter', ['specDone']); env.addReporter(reporter); - env.configure({random: false}); + env.configure({ random: false }); - env.describe("testing custom equality testers", function() { - env.it("with a custom tester", function() { - env.addCustomEqualityTester(function(a, b) { return true; }); - env.expect("a").toEqual("b"); + env.describe('testing custom equality testers', function() { + env.it('with a custom tester', function() { + env.addCustomEqualityTester(function(a, b) { + return true; + }); + env.expect('a').toEqual('b'); }); - env.it("without a custom tester", function() { - env.expect("a").toEqual("b"); + env.it('without a custom tester', function() { + env.expect('a').toEqual('b'); }); }); @@ -1615,35 +1755,38 @@ describe("Env integration", function() { var firstSpecResult = reporter.specDone.calls.first().args[0], secondSpecResult = reporter.specDone.calls.mostRecent().args[0]; - expect(firstSpecResult.status).toEqual("passed"); - expect(secondSpecResult.status).toEqual("failed"); + expect(firstSpecResult.status).toEqual('passed'); + expect(secondSpecResult.status).toEqual('failed'); done(); }); }); - it("Custom equality testers should be per suite", function(done) { - var reporter = jasmine.createSpyObj('fakeReporter', ["specDone"]); - + it('Custom equality testers should be per suite', function(done) { + var reporter = jasmine.createSpyObj('fakeReporter', ['specDone']); env.addReporter(reporter); - env.configure({random: false}); + env.configure({ random: false }); - env.describe("testing custom equality testers", function() { - env.beforeAll(function() { env.addCustomEqualityTester(function(a, b) { return true; }); }); - - env.it("with a custom tester", function() { - env.expect("a").toEqual("b"); + env.describe('testing custom equality testers', function() { + env.beforeAll(function() { + env.addCustomEqualityTester(function(a, b) { + return true; + }); }); - env.it("with the same custom tester", function() { - env.expect("a").toEqual("b"); + env.it('with a custom tester', function() { + env.expect('a').toEqual('b'); + }); + + env.it('with the same custom tester', function() { + env.expect('a').toEqual('b'); }); }); - env.describe("another suite", function() { - env.it("without the custom tester", function(){ - env.expect("a").toEqual("b"); + env.describe('another suite', function() { + env.it('without the custom tester', function() { + env.expect('a').toEqual('b'); }); }); @@ -1652,28 +1795,30 @@ describe("Env integration", function() { secondSpecResult = reporter.specDone.calls.argsFor(0)[0], thirdSpecResult = reporter.specDone.calls.mostRecent().args[0]; - expect(firstSpecResult.status).toEqual("passed"); - expect(secondSpecResult.status).toEqual("passed"); - expect(thirdSpecResult.status).toEqual("failed"); + expect(firstSpecResult.status).toEqual('passed'); + expect(secondSpecResult.status).toEqual('passed'); + expect(thirdSpecResult.status).toEqual('failed'); done(); }); }); - it("Custom equality testers for toContain should be per spec", function(done) { - var reporter = jasmine.createSpyObj('fakeReporter', ["specDone"]); + it('Custom equality testers for toContain should be per spec', function(done) { + var reporter = jasmine.createSpyObj('fakeReporter', ['specDone']); env.addReporter(reporter); - env.configure({random: false}); + env.configure({ random: false }); - env.describe("testing custom equality testers", function() { - env.it("with a custom tester", function() { - env.addCustomEqualityTester(function(a, b) { return true; }); - env.expect(["a"]).toContain("b"); + env.describe('testing custom equality testers', function() { + env.it('with a custom tester', function() { + env.addCustomEqualityTester(function(a, b) { + return true; + }); + env.expect(['a']).toContain('b'); }); - env.it("without a custom tester", function() { - env.expect(["a"]).toContain("b"); + env.it('without a custom tester', function() { + env.expect(['a']).toContain('b'); }); }); @@ -1681,45 +1826,53 @@ describe("Env integration", function() { var firstSpecResult = reporter.specDone.calls.first().args[0], secondSpecResult = reporter.specDone.calls.mostRecent().args[0]; - expect(firstSpecResult.status).toEqual("passed"); - expect(secondSpecResult.status).toEqual("failed"); + expect(firstSpecResult.status).toEqual('passed'); + expect(secondSpecResult.status).toEqual('failed'); done(); }); }); it("produces an understandable error message when an 'expect' is used outside of a current spec", function(done) { - env.describe("A Suite", function() { - env.it("an async spec that is actually synchronous", function(underTestCallback) { + env.describe('A Suite', function() { + env.it('an async spec that is actually synchronous', function( + underTestCallback + ) { underTestCallback(); }); - expect(function() { env.expect('a').toEqual('a'); }).toThrowError(/'expect' was used when there was no current spec/); + expect(function() { + env.expect('a').toEqual('a'); + }).toThrowError(/'expect' was used when there was no current spec/); }); env.execute(null, done); }); - it("Custom equality testers for toContain should be per suite", function(done) { - var reporter = jasmine.createSpyObj('fakeReporter', ["specDone"]); + it('Custom equality testers for toContain should be per suite', function(done) { + var reporter = jasmine.createSpyObj('fakeReporter', ['specDone']); env.addReporter(reporter); - env.configure({random: false}); + env.configure({ random: false }); - env.describe("testing custom equality testers", function() { - env.beforeAll(function() { env.addCustomEqualityTester(function(a, b) { return true; })}); - - env.it("with a custom tester", function() { - env.expect(["a"]).toContain("b"); + env.describe('testing custom equality testers', function() { + env.beforeAll(function() { + env.addCustomEqualityTester(function(a, b) { + return true; + }); }); - env.it("also with the custom tester", function() { - env.expect(["a"]).toContain("b"); + env.it('with a custom tester', function() { + env.expect(['a']).toContain('b'); + }); + + env.it('also with the custom tester', function() { + env.expect(['a']).toContain('b'); }); }); - env.describe("another suite", function() { - env.it("without the custom tester", function() { - env.expect(["a"]).toContain("b"); + env.describe('another suite', function() { + env.it('without the custom tester', function() { + env.expect(['a']).toContain('b'); }); }); @@ -1728,26 +1881,26 @@ describe("Env integration", function() { secondSpecResult = reporter.specDone.calls.argsFor(1)[0], thirdSpecResult = reporter.specDone.calls.mostRecent().args[0]; - expect(firstSpecResult.status).toEqual("passed"); - expect(secondSpecResult.status).toEqual("passed"); - expect(thirdSpecResult.status).toEqual("failed"); + expect(firstSpecResult.status).toEqual('passed'); + expect(secondSpecResult.status).toEqual('passed'); + expect(thirdSpecResult.status).toEqual('failed'); done(); }); }); - it("Custom matchers should be per spec", function(done) { + it('Custom matchers should be per spec', function(done) { var matchers = { - toFoo: function() {} - }; + toFoo: function() {} + }; - env.describe("testing custom matchers", function() { - env.it("with a custom matcher", function() { + env.describe('testing custom matchers', function() { + env.it('with a custom matcher', function() { env.addMatchers(matchers); expect(env.expect().toFoo).toBeDefined(); }); - env.it("without a custom matcher", function() { + env.it('without a custom matcher', function() { expect(env.expect().toFoo).toBeUndefined(); }); }); @@ -1755,25 +1908,27 @@ describe("Env integration", function() { env.execute(null, done); }); - it("Custom matchers should be per suite", function(done) { + it('Custom matchers should be per suite', function(done) { var matchers = { - toFoo: function() {} - }; + toFoo: function() {} + }; - env.describe("testing custom matchers", function() { - env.beforeAll(function() { env.addMatchers(matchers); }); + env.describe('testing custom matchers', function() { + env.beforeAll(function() { + env.addMatchers(matchers); + }); - env.it("with a custom matcher", function() { + env.it('with a custom matcher', function() { expect(env.expect().toFoo).toBeDefined(); }); - env.it("with the same custom matcher", function() { + env.it('with the same custom matcher', function() { expect(env.expect().toFoo).toBeDefined(); }); }); - env.describe("another suite", function() { - env.it("no longer has the custom matcher", function() { + env.describe('another suite', function() { + env.it('no longer has the custom matcher', function() { expect(env.expect().toFoo).not.toBeDefined(); }); }); @@ -1781,215 +1936,299 @@ describe("Env integration", function() { env.execute(null, done); }); - it('throws an exception if you try to create a spy outside of a runnable', function (done) { - var obj = {fn: function () {}}, + it('throws an exception if you try to create a spy outside of a runnable', function(done) { + var obj = { fn: function() {} }, exception; - env.describe("a suite", function () { + env.describe('a suite', function() { try { env.spyOn(obj, 'fn'); - } catch(e) { + } catch (e) { exception = e; } }); env.execute(null, function() { - expect(exception.message).toBe('Spies must be created in a before function or a spec'); + expect(exception.message).toBe( + 'Spies must be created in a before function or a spec' + ); done(); }); }); - it('throws an exception if you try to add a matcher outside of a runnable', function (done) { - var obj = {fn: function () {}}, + it('throws an exception if you try to add a matcher outside of a runnable', function(done) { + var obj = { fn: function() {} }, exception; - env.describe("a suite", function () { + env.describe('a suite', function() { try { - env.addMatchers({myMatcher: function(actual,expected){return false;}}); - } catch(e) { + env.addMatchers({ + myMatcher: function(actual, expected) { + return false; + } + }); + } catch (e) { exception = e; } }); env.execute(null, function() { - expect(exception.message).toBe('Matchers must be added in a before function or a spec'); + expect(exception.message).toBe( + 'Matchers must be added in a before function or a spec' + ); done(); }); }); - it('throws an exception if you try to add a custom equality outside of a runnable', function (done) { - var obj = {fn: function () {}}, + it('throws an exception if you try to add a custom equality outside of a runnable', function(done) { + var obj = { fn: function() {} }, exception; - env.describe("a suite", function () { + env.describe('a suite', function() { try { - env.addCustomEqualityTester(function(first, second) {return true;}); - } catch(e) { + env.addCustomEqualityTester(function(first, second) { + return true; + }); + } catch (e) { exception = e; } }); env.execute(null, function() { - expect(exception.message).toBe('Custom Equalities must be added in a before function or a spec'); + expect(exception.message).toBe( + 'Custom Equalities must be added in a before function or a spec' + ); done(); }); }); it('reports test properties on specs', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['suiteDone', 'specDone']); + var env = new jasmineUnderTest.Env(), + reporter = jasmine.createSpyObj('reporter', ['suiteDone', 'specDone']); - reporter.specDone.and.callFake(function(e) { - expect(e.properties).toEqual({a: 'Bee'}); - }); + reporter.specDone.and.callFake(function(e) { + expect(e.properties).toEqual({ a: 'Bee' }); + }); - env.addReporter(reporter); - env.it('calls setSpecProperty', function() { - env.setSpecProperty('a', 'Bee') - }); - env.execute(null, function() { - expect(reporter.specDone).toHaveBeenCalled(); - done(); - }); + env.addReporter(reporter); + env.it('calls setSpecProperty', function() { + env.setSpecProperty('a', 'Bee'); + }); + env.execute(null, function() { + expect(reporter.specDone).toHaveBeenCalled(); + done(); + }); }); - it('throws an exception if you try to setSpecProperty outside of a spec', function (done) { + it('throws an exception if you try to setSpecProperty outside of a spec', function(done) { var env = new jasmineUnderTest.Env(), - exception; + exception; - env.describe("a suite", function () { + env.describe('a suite', function() { env.it('a spec'); try { env.setSpecProperty('a prop', 'val'); - } catch(e) { + } catch (e) { exception = e; } }); env.execute(null, function() { - expect(exception.message).toBe("'setSpecProperty' was used when there was no current spec"); + expect(exception.message).toBe( + "'setSpecProperty' was used when there was no current spec" + ); done(); }); }); it('reports test properties on suites', function(done) { - var env = new jasmineUnderTest.Env(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var env = new jasmineUnderTest.Env(), + reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); - reporter.suiteDone.and.callFake(function(e) { - expect(e.properties).toEqual({b: 'Sweet'}); - }); + reporter.suiteDone.and.callFake(function(e) { + expect(e.properties).toEqual({ b: 'Sweet' }); + }); - env.addReporter(reporter); - env.describe('calls setSuiteProperty', function() { - env.beforeEach(function() { - env.setSuiteProperty('b', 'Sweet'); - }); - env.it('a passing spec', function() { - expect.nothing(); - }); + env.addReporter(reporter); + env.describe('calls setSuiteProperty', function() { + env.beforeEach(function() { + env.setSuiteProperty('b', 'Sweet'); }); + env.it('a passing spec', function() { + expect.nothing(); + }); + }); - env.execute(null, function() { - expect(reporter.suiteDone).toHaveBeenCalled(); - done(); - }); + env.execute(null, function() { + expect(reporter.suiteDone).toHaveBeenCalled(); + done(); + }); }); - it('throws an exception if you try to setSuiteProperty outside of a suite', function (done) { + it('throws an exception if you try to setSuiteProperty outside of a suite', function(done) { var env = new jasmineUnderTest.Env(); try { env.setSuiteProperty('a', 'Bee'); - } catch(e) { - expect(e.message).toBe("'setSuiteProperty' was used when there was no current suite"); + } catch (e) { + expect(e.message).toBe( + "'setSuiteProperty' was used when there was no current suite" + ); done(); } }); - it("should associate errors thrown from async code with the correct runnable", function(done) { - var reporter = jasmine.createSpyObj('fakeReport', ['suiteDone','specDone']); + it('should associate errors thrown from async code with the correct runnable', function(done) { + var reporter = jasmine.createSpyObj('fakeReport', [ + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); env.describe('async suite', function() { env.afterAll(function(innerDone) { - setTimeout(function() { throw new Error('suite'); }, 1); + setTimeout(function() { + throw new Error('suite'); + }, 1); }, 10); env.it('spec', function() {}); }); env.describe('suite', function() { - env.it('async spec', function(innerDone) { - setTimeout(function() { throw new Error('spec'); }, 1); - }, 10); + env.it( + 'async spec', + function(innerDone) { + setTimeout(function() { + throw new Error('spec'); + }, 1); + }, + 10 + ); }); env.execute(null, function() { - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('async suite', [ - /^(((Uncaught )?(exception: )?Error: suite( thrown)?)|(suite thrown))$/ - ]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite async spec', [ - /^(((Uncaught )?(exception: )?Error: spec( thrown)?)|(spec thrown))$/ - ]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'async suite', + [ + /^(((Uncaught )?(exception: )?Error: suite( thrown)?)|(suite thrown))$/ + ] + ); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'suite async spec', + [/^(((Uncaught )?(exception: )?Error: spec( thrown)?)|(spec thrown))$/] + ); done(); }); }); - it('should throw on suites/specs/befores/afters nested in methods other than \'describe\'', function(done) { + it("should throw on suites/specs/befores/afters nested in methods other than 'describe'", function(done) { var reporter = jasmine.createSpyObj('reporter', ['suiteDone', 'specDone']); env.addReporter(reporter); env.describe('suite', function() { - env.it('describe', function() { env.describe('inner suite', function() {}); }); - env.it('xdescribe', function() { env.xdescribe('inner suite', function() {}); }); - env.it('fdescribe', function() { env.fdescribe('inner suite', function() {}); }); + env.it('describe', function() { + env.describe('inner suite', function() {}); + }); + env.it('xdescribe', function() { + env.xdescribe('inner suite', function() {}); + }); + env.it('fdescribe', function() { + env.fdescribe('inner suite', function() {}); + }); }); env.describe('spec', function() { - env.it('it', function() { env.it('inner spec', function() {}); }); - env.it('xit', function() { env.xit('inner spec', function() {}); }); - env.it('fit', function() { env.fit('inner spec', function() {}); }); + env.it('it', function() { + env.it('inner spec', function() {}); + }); + env.it('xit', function() { + env.xit('inner spec', function() {}); + }); + env.it('fit', function() { + env.fit('inner spec', function() {}); + }); }); env.describe('beforeAll', function() { - env.beforeAll(function() { env.beforeAll(function() {}); }); + env.beforeAll(function() { + env.beforeAll(function() {}); + }); env.it('spec', function() {}); }); env.describe('beforeEach', function() { - env.beforeEach(function() { env.beforeEach(function() {}); }); + env.beforeEach(function() { + env.beforeEach(function() {}); + }); env.it('spec', function() {}); }); env.describe('afterAll', function() { - env.afterAll(function() { env.afterAll(function() {}); }); + env.afterAll(function() { + env.afterAll(function() {}); + }); env.it('spec', function() {}); }); env.describe('afterEach', function() { - env.afterEach(function() { env.afterEach(function() {}); }); + env.afterEach(function() { + env.afterEach(function() {}); + }); env.it('spec', function() {}); }); env.execute(null, function() { var msg = /\'.*\' should only be used in \'describe\' function/; - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite describe', [msg]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite xdescribe', [msg]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('suite fdescribe', [msg]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'suite describe', + [msg] + ); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'suite xdescribe', + [msg] + ); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'suite fdescribe', + [msg] + ); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('spec it', [msg]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('spec xit', [msg]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('spec fit', [msg]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable('spec it', [ + msg + ]); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'spec xit', + [msg] + ); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'spec fit', + [msg] + ); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('beforeAll', [msg]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('beforeEach spec', [msg]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'beforeAll', + [msg] + ); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'beforeEach spec', + [msg] + ); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('afterAll', [msg]); - expect(reporter.specDone).toHaveFailedExpectationsForRunnable('afterEach spec', [msg]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'afterAll', + [msg] + ); + expect(reporter.specDone).toHaveFailedExpectationsForRunnable( + 'afterEach spec', + [msg] + ); done(); }); @@ -1997,18 +2236,32 @@ describe("Env integration", function() { it('reports errors that occur during loading', function(done) { var global = { - setTimeout: function(fn, delay) { setTimeout(fn, delay) }, - clearTimeout: function(fn, delay) { clearTimeout(fn, delay) }, + setTimeout: function(fn, delay) { + setTimeout(fn, delay); + }, + clearTimeout: function(fn, delay) { + clearTimeout(fn, delay); + }, onerror: function() {} }; spyOn(jasmineUnderTest, 'getGlobal').and.returnValue(global); env.cleanup_(); env = new jasmineUnderTest.Env(); - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); - global.onerror('Uncaught SyntaxError: Unexpected end of input', 'borkenSpec.js', 42, undefined, {stack: 'a stack'}); + global.onerror( + 'Uncaught SyntaxError: Unexpected end of input', + 'borkenSpec.js', + 42, + undefined, + { stack: 'a stack' } + ); global.onerror('Uncaught Error: ENOCHEESE'); env.execute(null, function() { @@ -2038,10 +2291,14 @@ describe("Env integration", function() { describe('If suppressLoadErrors: true was passed', function() { it('does not install a global error handler during loading', function(done) { - var originalOnerror = jasmine.createSpy('original onerror') + var originalOnerror = jasmine.createSpy('original onerror'); var global = { - setTimeout: function(fn, delay) { setTimeout(fn, delay) }, - clearTimeout: function(fn, delay) { clearTimeout(fn, delay) }, + setTimeout: function(fn, delay) { + setTimeout(fn, delay); + }, + clearTimeout: function(fn, delay) { + clearTimeout(fn, delay); + }, onerror: originalOnerror }; spyOn(jasmineUnderTest, 'getGlobal').and.returnValue(global); @@ -2051,8 +2308,12 @@ describe("Env integration", function() { spyOn(jasmineUnderTest, 'GlobalErrors').and.returnValue(globalErrors); env.cleanup_(); - env = new jasmineUnderTest.Env({suppressLoadErrors: true}); - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + env = new jasmineUnderTest.Env({ suppressLoadErrors: true }); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); global.onerror('Uncaught Error: ENOCHEESE'); @@ -2060,7 +2321,9 @@ describe("Env integration", function() { env.execute(null, function() { var e = reporter.jasmineDone.calls.argsFor(0)[0]; expect(e.failedExpectations).toEqual([]); - expect(originalOnerror).toHaveBeenCalledWith('Uncaught Error: ENOCHEESE'); + expect(originalOnerror).toHaveBeenCalledWith( + 'Uncaught Error: ENOCHEESE' + ); done(); }); }); @@ -2069,7 +2332,11 @@ describe("Env integration", function() { describe('Overall status in the jasmineDone event', function() { describe('When everything passes', function() { it('is "passed"', function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); env.it('passes', function() {}); @@ -2083,7 +2350,11 @@ describe("Env integration", function() { describe('When a spec fails', function() { it('is "failed"', function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); env.it('fails', function() { @@ -2093,7 +2364,7 @@ describe("Env integration", function() { var e = reporter.jasmineDone.calls.argsFor(0)[0]; expect(e.overallStatus).toEqual('failed'); done(); - }) + }); }); }); @@ -2101,13 +2372,16 @@ describe("Env integration", function() { var reporter; beforeEach(function() { - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); env.it('is a spec without any expectations', function() { // does nothing, just a mock spec without expectations }); - }); it('should report "failed" status if "failSpecWithNoExpectations" is enabled', function(done) { @@ -2131,7 +2405,11 @@ describe("Env integration", function() { describe('When a top-level beforeAll fails', function() { it('is "failed"', function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); env.beforeAll(function() { @@ -2148,7 +2426,11 @@ describe("Env integration", function() { describe('When a suite beforeAll fails', function() { it('is "failed"', function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); env.describe('something', function() { @@ -2167,7 +2449,11 @@ describe("Env integration", function() { describe('When a top-level afterAll fails', function() { it('is "failed"', function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); env.afterAll(function() { @@ -2184,7 +2470,11 @@ describe("Env integration", function() { describe('When a suite afterAll fails', function() { it('is "failed"', function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); env.describe('something', function() { @@ -2201,17 +2491,25 @@ describe("Env integration", function() { }); }); - describe("When there are load errors", function() { + describe('When there are load errors', function() { it('is "failed"', function(done) { var global = { - setTimeout: function(fn, delay) { setTimeout(fn, delay) }, - clearTimeout: function(fn, delay) { clearTimeout(fn, delay) }, + setTimeout: function(fn, delay) { + setTimeout(fn, delay); + }, + clearTimeout: function(fn, delay) { + clearTimeout(fn, delay); + } }; spyOn(jasmineUnderTest, 'getGlobal').and.returnValue(global); env.cleanup_(); env = new jasmineUnderTest.Env(); - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); reporter.jasmineDone.and.callFake(function(e) { expect(e.overallStatus).toEqual('failed'); @@ -2229,7 +2527,11 @@ describe("Env integration", function() { describe('When there are no specs', function() { it('is "incomplete"', function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); env.execute(null, function() { @@ -2243,7 +2545,11 @@ describe("Env integration", function() { describe('When a spec is focused', function() { it('is "incomplete"', function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); env.fit('is focused', function() {}); @@ -2258,7 +2564,11 @@ describe("Env integration", function() { describe('When a suite is focused', function() { it('is "incomplete"', function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); env.fdescribe('something focused', function() { @@ -2275,7 +2585,11 @@ describe("Env integration", function() { describe('When there are both failures and focused specs', function() { it('is "failed"', function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); env.addReporter(reporter); env.fit('is focused', function() { @@ -2292,10 +2606,14 @@ describe("Env integration", function() { }); it('should report deprecation warnings on the correct specs and suites', function(done) { - var reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']); + var reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]); // prevent deprecation from being displayed, as well as letting us observe calls - spyOn(console, "error"); + spyOn(console, 'error'); env.addReporter(reporter); @@ -2317,25 +2635,35 @@ describe("Env integration", function() { jasmine.objectContaining({ message: 'top level deprecation' }) ]); /* eslint-disable-next-line no-console */ - expect(console.error).toHaveBeenCalledWith('DEPRECATION: top level deprecation'); + expect(console.error).toHaveBeenCalledWith( + 'DEPRECATION: top level deprecation' + ); - expect(reporter.suiteDone).toHaveBeenCalledWith(jasmine.objectContaining({ - fullName: 'suite', - deprecationWarnings: [ - jasmine.objectContaining({ message: 'suite level deprecation' }) - ] - })); + expect(reporter.suiteDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + fullName: 'suite', + deprecationWarnings: [ + jasmine.objectContaining({ message: 'suite level deprecation' }) + ] + }) + ); /* eslint-disable-next-line no-console */ - expect(console.error).toHaveBeenCalledWith('DEPRECATION: suite level deprecation (in suite: suite)'); + expect(console.error).toHaveBeenCalledWith( + 'DEPRECATION: suite level deprecation (in suite: suite)' + ); - expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - fullName: 'suite spec', - deprecationWarnings: [ - jasmine.objectContaining({ message: 'spec level deprecation' }) - ] - })); + expect(reporter.specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + fullName: 'suite spec', + deprecationWarnings: [ + jasmine.objectContaining({ message: 'spec level deprecation' }) + ] + }) + ); /* eslint-disable-next-line no-console */ - expect(console.error).toHaveBeenCalledWith('DEPRECATION: spec level deprecation (in spec: suite spec)'); + expect(console.error).toHaveBeenCalledWith( + 'DEPRECATION: spec level deprecation (in spec: suite spec)' + ); done(); }); @@ -2343,15 +2671,33 @@ describe("Env integration", function() { it('should report deprecation stack with an error object', function(done) { var exceptionFormatter = new jasmineUnderTest.ExceptionFormatter(), - reporter = jasmine.createSpyObj('reporter', ['jasmineDone', 'suiteDone', 'specDone']), - topLevelError, suiteLevelError, specLevelError; + reporter = jasmine.createSpyObj('reporter', [ + 'jasmineDone', + 'suiteDone', + 'specDone' + ]), + topLevelError, + suiteLevelError, + specLevelError; - try { throw new Error('top level deprecation') } catch (err) { topLevelError = err; } - try { throw new Error('suite level deprecation') } catch (err) { suiteLevelError = err; } - try { throw new Error('spec level deprecation') } catch (err) { specLevelError = err; } + try { + throw new Error('top level deprecation'); + } catch (err) { + topLevelError = err; + } + try { + throw new Error('suite level deprecation'); + } catch (err) { + suiteLevelError = err; + } + try { + throw new Error('spec level deprecation'); + } catch (err) { + specLevelError = err; + } // prevent deprecation from being displayed - spyOn(console, "error"); + spyOn(console, 'error'); env.addReporter(reporter); @@ -2376,25 +2722,29 @@ describe("Env integration", function() { }) ]); - expect(reporter.suiteDone).toHaveBeenCalledWith(jasmine.objectContaining({ - fullName: 'suite', - deprecationWarnings: [ - jasmine.objectContaining({ - message: suiteLevelError.message, - stack: exceptionFormatter.stack(suiteLevelError) - }) - ] - })); + expect(reporter.suiteDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + fullName: 'suite', + deprecationWarnings: [ + jasmine.objectContaining({ + message: suiteLevelError.message, + stack: exceptionFormatter.stack(suiteLevelError) + }) + ] + }) + ); - expect(reporter.specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - fullName: 'suite spec', - deprecationWarnings: [ - jasmine.objectContaining({ - message: specLevelError.message, - stack: exceptionFormatter.stack(specLevelError) - }) - ] - })); + expect(reporter.specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + fullName: 'suite spec', + deprecationWarnings: [ + jasmine.objectContaining({ + message: specLevelError.message, + stack: exceptionFormatter.stack(specLevelError) + }) + ] + }) + ); done(); }); @@ -2404,8 +2754,8 @@ describe("Env integration", function() { jasmine.getEnv().requirePromises(); var specDone = jasmine.createSpy('specDone'), - suiteDone = jasmine.createSpy('suiteDone'), - jasmineDone = jasmine.createSpy('jasmineDone'); + suiteDone = jasmine.createSpy('suiteDone'), + jasmineDone = jasmine.createSpy('jasmineDone'); env.addReporter({ specDone: specDone, @@ -2415,8 +2765,14 @@ describe("Env integration", function() { function fail(innerDone) { var resolve; - var p = new Promise(function(res, rej) { resolve = res }); // eslint-disable-line compat/compat - env.expectAsync(p).toBeRejected().then(innerDone); + // eslint-disable-next-line compat/compat + var p = new Promise(function(res, rej) { + resolve = res; + }); + env + .expectAsync(p) + .toBeRejected() + .then(innerDone); resolve(); } @@ -2428,23 +2784,33 @@ describe("Env integration", function() { env.execute(null, function() { var result = jasmineDone.calls.argsFor(0)[0]; - expect(result.failedExpectations).toEqual([jasmine.objectContaining({ - message: 'Expected [object Promise] to be rejected.' - })]); - - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'has an async failure', - failedExpectations: [jasmine.objectContaining({ + expect(result.failedExpectations).toEqual([ + jasmine.objectContaining({ message: 'Expected [object Promise] to be rejected.' - })] - })); + }) + ]); - expect(suiteDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'a suite', - failedExpectations: [jasmine.objectContaining({ - message: 'Expected [object Promise] to be rejected.' - })] - })); + expect(specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: 'has an async failure', + failedExpectations: [ + jasmine.objectContaining({ + message: 'Expected [object Promise] to be rejected.' + }) + ] + }) + ); + + expect(suiteDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: 'a suite', + failedExpectations: [ + jasmine.objectContaining({ + message: 'Expected [object Promise] to be rejected.' + }) + ] + }) + ); done(); }); @@ -2455,19 +2821,23 @@ describe("Env integration", function() { var specDone = jasmine.createSpy('specDone'); - env.addReporter({specDone: specDone}); + env.addReporter({ specDone: specDone }); env.it('has an async failure', function() { - env.addCustomEqualityTester(function() { return true; }); + env.addCustomEqualityTester(function() { + return true; + }); var p = Promise.resolve('something'); // eslint-disable-line compat/compat return env.expectAsync(p).toBeResolvedTo('something else'); }); env.execute(null, function() { - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - description: 'has an async failure', - failedExpectations: [] - })); + expect(specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + description: 'has an async failure', + failedExpectations: [] + }) + ); done(); }); }); @@ -2477,20 +2847,26 @@ describe("Env integration", function() { var specDone = jasmine.createSpy('specDone'); - env.addReporter({specDone: specDone}); + env.addReporter({ specDone: specDone }); env.it('has an async failure', function() { - env.addCustomEqualityTester(function() { return true; }); + env.addCustomEqualityTester(function() { + return true; + }); var p = Promise.resolve(); // eslint-disable-line compat/compat return env.expectAsync(p).toBeRejected(); }); env.execute(null, function() { - expect(specDone).toHaveBeenCalledWith(jasmine.objectContaining({ - failedExpectations: [jasmine.objectContaining({ - stack: jasmine.stringMatching('EnvSpec.js') - })] - })); + expect(specDone).toHaveBeenCalledWith( + jasmine.objectContaining({ + failedExpectations: [ + jasmine.objectContaining({ + stack: jasmine.stringMatching('EnvSpec.js') + }) + ] + }) + ); done(); }); }); @@ -2500,7 +2876,10 @@ describe("Env integration", function() { var resolve, jasmineDone = jasmine.createSpy('jasmineDone'), - promise = new Promise(function(res) { resolve = res; }); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + promise = new Promise(function(res) { + resolve = res; + }); env.describe('a suite', function() { env.it('does not wait', function() { @@ -2518,13 +2897,14 @@ describe("Env integration", function() { jasmineDone: jasmineDone }); - env.execute(null, function () { + env.execute(null, function() { var result = jasmineDone.calls.argsFor(0)[0]; expect(result.failedExpectations).toEqual([ jasmine.objectContaining({ passed: false, globalErrorType: 'lateExpectation', - message: 'Spec "a suite does not wait" ran a "toBeResolved" expectation ' + + message: + 'Spec "a suite does not wait" ran a "toBeResolved" expectation ' + 'after it finished.\n' + 'Did you forget to return or await the result of expectAsync?', matcherName: 'toBeResolved' @@ -2532,9 +2912,10 @@ describe("Env integration", function() { jasmine.objectContaining({ passed: false, globalErrorType: 'lateExpectation', - message: 'Spec "a suite does not wait" ran a "toBeResolvedTo" expectation ' + + message: + 'Spec "a suite does not wait" ran a "toBeResolvedTo" expectation ' + 'after it finished.\n' + - 'Message: "Expected a promise to be resolved to \'something else\' ' + + "Message: \"Expected a promise to be resolved to 'something else' " + 'but it was resolved to undefined."\n' + 'Did you forget to return or await the result of expectAsync?', matcherName: 'toBeResolvedTo' @@ -2550,7 +2931,10 @@ describe("Env integration", function() { var resolve, jasmineDone = jasmine.createSpy('jasmineDone'), - promise = new Promise(function(res) { resolve = res; }); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + promise = new Promise(function(res) { + resolve = res; + }); env.describe('a suite', function() { env.afterAll(function() { @@ -2569,13 +2953,14 @@ describe("Env integration", function() { jasmineDone: jasmineDone }); - env.execute(null, function () { + env.execute(null, function() { var result = jasmineDone.calls.argsFor(0)[0]; expect(result.failedExpectations).toEqual([ jasmine.objectContaining({ passed: false, globalErrorType: 'lateExpectation', - message: 'Suite "a suite" ran a "toBeResolved" expectation ' + + message: + 'Suite "a suite" ran a "toBeResolved" expectation ' + 'after it finished.\n' + 'Did you forget to return or await the result of expectAsync?', matcherName: 'toBeResolved' @@ -2586,25 +2971,25 @@ describe("Env integration", function() { }); }); - it("supports asymmetric equality testers that take a matchersUtil", function(done) { + it('supports asymmetric equality testers that take a matchersUtil', function(done) { var env = new jasmineUnderTest.Env(); - env.it("spec using custom asymmetric equality tester", function() { + env.it('spec using custom asymmetric equality tester', function() { var customEqualityFn = function(a, b) { - if (a === 2 && b === "two") { + if (a === 2 && b === 'two') { return true; } }; var arrayWithFirstElement = function(sample) { return { - asymmetricMatch: function (actual, matchersUtil) { + asymmetricMatch: function(actual, matchersUtil) { return matchersUtil.equals(sample, actual[0]); } }; }; env.addCustomEqualityTester(customEqualityFn); - env.expect(["two"]).toEqual(arrayWithFirstElement(2)); + env.expect(['two']).toEqual(arrayWithFirstElement(2)); }); var specExpectations = function(result) { @@ -2625,13 +3010,14 @@ describe("Env integration", function() { }); it('is called after reporter events are dispatched', function(done) { - var reporter = jasmine.createSpyObj( - 'reporter', - ['specDone', 'suiteDone', 'jasmineDone'] - ); + var reporter = jasmine.createSpyObj('reporter', [ + 'specDone', + 'suiteDone', + 'jasmineDone' + ]); env.addReporter(reporter); - env.describe('suite', function () { + env.describe('suite', function() { env.it('spec', function() {}); }); @@ -2644,15 +3030,19 @@ describe("Env integration", function() { }); it('is called after the stack is cleared', function(done) { - var realClearStack = jasmineUnderTest.getClearStack(jasmineUnderTest.getGlobal()), - clearStackSpy = jasmine.createSpy('clearStack').and.callFake(realClearStack); + var realClearStack = jasmineUnderTest.getClearStack( + jasmineUnderTest.getGlobal() + ), + clearStackSpy = jasmine + .createSpy('clearStack') + .and.callFake(realClearStack); spyOn(jasmineUnderTest, 'getClearStack').and.returnValue(clearStackSpy); // Create a new env that has the clearStack defined above env.cleanup_(); env = new jasmineUnderTest.Env(); - env.describe('suite', function () { + env.describe('suite', function() { env.it('spec', function() {}); }); @@ -2667,24 +3057,32 @@ describe("Env integration", function() { }); it('is called after QueueRunner timeouts are cleared', function(done) { - var setTimeoutSpy = spyOn(jasmineUnderTest.getGlobal(), 'setTimeout') - .and.callThrough(); - var clearTimeoutSpy = spyOn(jasmineUnderTest.getGlobal(), 'clearTimeout') - .and.callThrough(); + var setTimeoutSpy = spyOn( + jasmineUnderTest.getGlobal(), + 'setTimeout' + ).and.callThrough(); + var clearTimeoutSpy = spyOn( + jasmineUnderTest.getGlobal(), + 'clearTimeout' + ).and.callThrough(); jasmineUnderTest.DEFAULT_TIMEOUT_INTERVAL = 123456; // a distinctive value env = new jasmineUnderTest.Env(); - env.describe('suite', function () { - env.it('spec', function () { - }); + env.describe('suite', function() { + env.it('spec', function() {}); }); - env.execute(null, function () { - var timeoutIds = setTimeoutSpy.calls.all() - .filter(function(call) { return call.args[1] === 123456; }) - .map(function(call) { return call.returnValue; }); + env.execute(null, function() { + var timeoutIds = setTimeoutSpy.calls + .all() + .filter(function(call) { + return call.args[1] === 123456; + }) + .map(function(call) { + return call.returnValue; + }); expect(timeoutIds.length).toBeGreaterThan(0); diff --git a/spec/core/integration/MatchersSpec.js b/spec/core/integration/MatchersSpec.js index 8174faf8..ac9f5e90 100644 --- a/spec/core/integration/MatchersSpec.js +++ b/spec/core/integration/MatchersSpec.js @@ -23,7 +23,9 @@ describe('Matchers (Integration)', function() { expect(result.failedExpectations.length) .withContext('Number of failed expectations') .toEqual(0); - expect(result.failedExpectations[0] && result.failedExpectations[0].message) + expect( + result.failedExpectations[0] && result.failedExpectations[0].message + ) .withContext('Failure message') .toBeUndefined(); }; @@ -45,12 +47,17 @@ describe('Matchers (Integration)', function() { .withContext('Number of failed expectations') .toEqual(1); expect(result.failedExpectations[0].message) - .withContext('Failed with a thrown error rather than a matcher failure') + .withContext( + 'Failed with a thrown error rather than a matcher failure' + ) .not.toMatch(/^Error: /); expect(result.failedExpectations[0].message) - .withContext('Failed with a thrown type error rather than a matcher failure') + .withContext( + 'Failed with a thrown type error rather than a matcher failure' + ) .not.toMatch(/^TypeError: /); - expect(result.failedExpectations[0].matcherName).withContext('Matcher name') + expect(result.failedExpectations[0].matcherName) + .withContext('Matcher name') .not.toEqual(''); }; @@ -61,18 +68,19 @@ describe('Matchers (Integration)', function() { function verifyFailsWithCustomObjectFormatters(config) { it('uses custom object formatters', function(done) { - env.it('a spec', function () { + env.it('a spec', function() { env.addCustomObjectFormatter(config.formatter); config.expectations(env); }); - var specExpectations = function (result) { + var specExpectations = function(result) { expect(result.status).toEqual('failed'); expect(result.failedExpectations.length) .withContext('Number of failed expectations') .toEqual(1); - expect(result.failedExpectations[0].message) - .toEqual(config.expectedMessage); + expect(result.failedExpectations[0].message).toEqual( + config.expectedMessage + ); }; env.addReporter({ specDone: specExpectations }); @@ -96,7 +104,9 @@ describe('Matchers (Integration)', function() { expect(result.failedExpectations.length) .withContext('Number of failed expectations') .toEqual(0); - expect(result.failedExpectations[0] && result.failedExpectations[0].message) + expect( + result.failedExpectations[0] && result.failedExpectations[0].message + ) .withContext('Failure message') .toBeUndefined(); }; @@ -120,9 +130,12 @@ describe('Matchers (Integration)', function() { .withContext('Number of failed expectations') .toEqual(1); expect(result.failedExpectations[0].message) - .withContext('Failed with a thrown error rather than a matcher failure') + .withContext( + 'Failed with a thrown error rather than a matcher failure' + ) .not.toMatch(/^Error: /); - expect(result.failedExpectations[0].matcherName).withContext('Matcher name') + expect(result.failedExpectations[0].matcherName) + .withContext('Matcher name') .not.toEqual(''); }; @@ -135,18 +148,19 @@ describe('Matchers (Integration)', function() { it('uses custom object formatters', function(done) { var env = new jasmineUnderTest.Env(); jasmine.getEnv().requirePromises(); - env.it('a spec', function () { + env.it('a spec', function() { env.addCustomObjectFormatter(config.formatter); return config.expectations(env); }); - var specExpectations = function (result) { + var specExpectations = function(result) { expect(result.status).toEqual('failed'); expect(result.failedExpectations.length) .withContext('Number of failed expectations') .toEqual(1); - expect(result.failedExpectations[0].message) - .toEqual(config.expectedMessage); + expect(result.failedExpectations[0].message).toEqual( + config.expectedMessage + ); }; env.addReporter({ specDone: specExpectations }); @@ -154,7 +168,6 @@ describe('Matchers (Integration)', function() { }); } - describe('nothing', function() { verifyPasses(function(env) { env.expect().nothing(); @@ -330,16 +343,18 @@ describe('Matchers (Integration)', function() { env.expect(1).toBePositiveInfinity(); }, expectedMessage: 'Expected |1| to be Infinity.' - }) + }); }); describe('toBeResolved', function() { verifyPassesAsync(function(env) { - return env.expectAsync(Promise.resolve()).toBeResolved(); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + return env.expectAsync(Promise.resolve()).toBeResolved(); }); verifyFailsAsync(function(env) { - return env.expectAsync(Promise.reject()).toBeResolved(); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + return env.expectAsync(Promise.reject()).toBeResolved(); }); }); @@ -348,11 +363,13 @@ describe('Matchers (Integration)', function() { env.addCustomEqualityTester(function(a, b) { return a.toString() === b.toString(); }); - return env.expectAsync(Promise.resolve('5')).toBeResolvedTo(5); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + return env.expectAsync(Promise.resolve('5')).toBeResolvedTo(5); }); verifyFailsAsync(function(env) { - return env.expectAsync(Promise.resolve('foo')).toBeResolvedTo('bar'); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + return env.expectAsync(Promise.resolve('foo')).toBeResolvedTo('bar'); }); verifyFailsWithCustomObjectFormattersAsync({ @@ -360,20 +377,24 @@ describe('Matchers (Integration)', function() { return '|' + val + '|'; }, expectations: function(env) { - return env.expectAsync(Promise.resolve('x')).toBeResolvedTo('y'); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + return env.expectAsync(Promise.resolve('x')).toBeResolvedTo('y'); }, - expectedMessage: 'Expected a promise to be resolved to |y| ' + + expectedMessage: + 'Expected a promise to be resolved to |y| ' + 'but it was resolved to |x|.' }); }); describe('toBeRejected', function() { verifyPassesAsync(function(env) { - return env.expectAsync(Promise.reject('nope')).toBeRejected(); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + return env.expectAsync(Promise.reject('nope')).toBeRejected(); }); verifyFailsAsync(function(env) { - return env.expectAsync(Promise.resolve()).toBeRejected(); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + return env.expectAsync(Promise.resolve()).toBeRejected(); }); }); @@ -382,11 +403,13 @@ describe('Matchers (Integration)', function() { env.addCustomEqualityTester(function(a, b) { return a.toString() === b.toString(); }); - return env.expectAsync(Promise.reject('5')).toBeRejectedWith(5); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + return env.expectAsync(Promise.reject('5')).toBeRejectedWith(5); }); verifyFailsAsync(function(env) { - return env.expectAsync(Promise.resolve()).toBeRejectedWith('nope'); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + return env.expectAsync(Promise.resolve()).toBeRejectedWith('nope'); }); verifyFailsWithCustomObjectFormattersAsync({ @@ -394,20 +417,28 @@ describe('Matchers (Integration)', function() { return '|' + val + '|'; }, expectations: function(env) { - return env.expectAsync(Promise.reject('x')).toBeRejectedWith('y'); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + return env.expectAsync(Promise.reject('x')).toBeRejectedWith('y'); }, - expectedMessage: 'Expected a promise to be rejected with |y| ' + + expectedMessage: + 'Expected a promise to be rejected with |y| ' + 'but it was rejected with |x|.' }); }); describe('toBeRejectedWithError', function() { verifyPassesAsync(function(env) { - return env.expectAsync(Promise.reject(new Error())).toBeRejectedWithError(Error); // eslint-disable-line compat/compat + return ( + env + // eslint-disable-next-line compat/compat + .expectAsync(Promise.reject(new Error())) + .toBeRejectedWithError(Error) + ); }); verifyFailsAsync(function(env) { - return env.expectAsync(Promise.resolve()).toBeRejectedWithError(Error); // eslint-disable-line compat/compat + // eslint-disable-next-line compat/compat + return env.expectAsync(Promise.resolve()).toBeRejectedWithError(Error); }); verifyFailsWithCustomObjectFormattersAsync({ @@ -415,9 +446,15 @@ describe('Matchers (Integration)', function() { return '|' + val + '|'; }, expectations: function(env) { - return env.expectAsync(Promise.reject('foo')).toBeRejectedWithError('foo'); // eslint-disable-line compat/compat + return ( + env + // eslint-disable-next-line compat/compat + .expectAsync(Promise.reject('foo')) + .toBeRejectedWithError('foo') + ); }, - expectedMessage: 'Expected a promise to be rejected with Error: |foo| ' + + expectedMessage: + 'Expected a promise to be rejected with Error: |foo| ' + 'but it was rejected with |foo|.' }); }); @@ -486,7 +523,7 @@ describe('Matchers (Integration)', function() { } }, expectations: function(env) { - env.expect([{foo: 4}]).toEqual([{foo: 5}]); + env.expect([{ foo: 4 }]).toEqual([{ foo: 5 }]); }, expectedMessage: 'Expected $[0].foo = four to equal five.' }); @@ -494,11 +531,11 @@ describe('Matchers (Integration)', function() { describe('toHaveSize', function() { verifyPasses(function(env) { - env.expect(['a','b']).toHaveSize(2); + env.expect(['a', 'b']).toHaveSize(2); }); verifyFails(function(env) { - env.expect(['a','b']).toHaveSize(1); + env.expect(['a', 'b']).toHaveSize(1); }); }); @@ -517,14 +554,16 @@ describe('Matchers (Integration)', function() { describe('toHaveBeenCalledBefore', function() { verifyPasses(function(env) { - var a = env.createSpy('a'), b = env.createSpy('b'); + var a = env.createSpy('a'), + b = env.createSpy('b'); a(); b(); env.expect(a).toHaveBeenCalledBefore(b); }); verifyFails(function(env) { - var a = env.createSpy('a'), b = env.createSpy('b'); + var a = env.createSpy('a'), + b = env.createSpy('b'); b(); a(); env.expect(a).toHaveBeenCalledBefore(b); @@ -567,7 +606,8 @@ describe('Matchers (Integration)', function() { var spy = env.createSpy('foo'); env.expect(spy).toHaveBeenCalledWith('x'); }, - expectedMessage: 'Expected spy foo to have been called with:\n' + + expectedMessage: + 'Expected spy foo to have been called with:\n' + ' |x|\n' + 'but it was never called.' }); @@ -622,7 +662,11 @@ describe('Matchers (Integration)', function() { env.addCustomEqualityTester(function(a, b) { return a.toString() === b.toString(); }); - env.expect(function() { throw '5'; }).toThrow(5); + env + .expect(function() { + throw '5'; + }) + .toThrow(5); }); verifyFails(function(env) { @@ -635,9 +679,11 @@ describe('Matchers (Integration)', function() { }, expectations: function(env) { var spy = env.createSpy('foo'); - env.expect(function() { - throw 'x' - }).not.toThrow(); + env + .expect(function() { + throw 'x'; + }) + .not.toThrow(); }, expectedMessage: 'Expected function not to throw, but it threw |x|.' }); @@ -645,11 +691,15 @@ describe('Matchers (Integration)', function() { describe('toThrowError', function() { verifyPasses(function(env) { - env.expect(function() { throw new Error(); }).toThrowError(); + env + .expect(function() { + throw new Error(); + }) + .toThrowError(); }); verifyFails(function(env) { - env.expect(function() { }).toThrowError(); + env.expect(function() {}).toThrowError(); }); verifyFailsWithCustomObjectFormatters({ @@ -658,9 +708,11 @@ describe('Matchers (Integration)', function() { }, expectations: function(env) { var spy = env.createSpy('foo'); - env.expect(function() { - throw 'x' - }).toThrowError(); + env + .expect(function() { + throw 'x'; + }) + .toThrowError(); }, expectedMessage: 'Expected function to throw an Error, but it threw |x|.' }); @@ -672,11 +724,15 @@ describe('Matchers (Integration)', function() { } verifyPasses(function(env) { - env.expect(throws).toThrowMatching(function() { return true; }); + env.expect(throws).toThrowMatching(function() { + return true; + }); }); verifyFails(function(env) { - env.expect(throws).toThrowMatching(function() { return false; }); + env.expect(throws).toThrowMatching(function() { + return false; + }); }); verifyFailsWithCustomObjectFormatters({ @@ -685,13 +741,16 @@ describe('Matchers (Integration)', function() { }, expectations: function(env) { var spy = env.createSpy('foo'); - env.expect(function() { - throw new Error('nope') - }).toThrowMatching(function() { - return false; - }); + env + .expect(function() { + throw new Error('nope'); + }) + .toThrowMatching(function() { + return false; + }); }, - expectedMessage: 'Expected function to throw an exception matching ' + + expectedMessage: + 'Expected function to throw an exception matching ' + 'a predicate, but it threw Error with message |nope|.' }); }); diff --git a/spec/core/integration/SpecRunningSpec.js b/spec/core/integration/SpecRunningSpec.js index 33459d02..d6e26104 100644 --- a/spec/core/integration/SpecRunningSpec.js +++ b/spec/core/integration/SpecRunningSpec.js @@ -1,10 +1,10 @@ -describe("spec running", function () { +describe('spec running', function() { var env; beforeEach(function() { jasmine.getEnv().registerIntegrationMatchers(); env = new jasmineUnderTest.Env(); - env.configure({random: false}); + env.configure({ random: false }); }); afterEach(function() { @@ -14,18 +14,13 @@ describe("spec running", function () { it('should assign spec ids sequentially', function() { var it0, it1, it2, it3, it4; env.describe('test suite', function() { - it0 = env.it('spec 0', function() { - }); - it1 = env.it('spec 1', function() { - }); - it2 = env.xit('spec 2', function() { - }); - it3 = env.it('spec 3', function() { - }); + it0 = env.it('spec 0', function() {}); + it1 = env.it('spec 1', function() {}); + it2 = env.xit('spec 2', function() {}); + it3 = env.it('spec 3', function() {}); }); env.describe('test suite 2', function() { - it4 = env.it('spec 4', function() { - }); + it4 = env.it('spec 4', function() {}); }); expect(it0.id).toEqual('spec0'); @@ -35,29 +30,28 @@ describe("spec running", function () { expect(it4.id).toEqual('spec4'); }); - it('nested suites', function (done) { - + it('nested suites', function(done) { var foo = 0; var bar = 0; var baz = 0; var quux = 0; - var nested = env.describe('suite', function () { - env.describe('nested', function () { - env.it('should run nested suites', function () { + var nested = env.describe('suite', function() { + env.describe('nested', function() { + env.it('should run nested suites', function() { foo++; }); - env.it('should run nested suites', function () { + env.it('should run nested suites', function() { bar++; }); }); - env.describe('nested 2', function () { - env.it('should run suites following nested suites', function () { + env.describe('nested 2', function() { + env.it('should run suites following nested suites', function() { baz++; }); }); - env.it('should run tests following nested suites', function () { + env.it('should run tests following nested suites', function() { quux++; }); }); @@ -76,14 +70,14 @@ describe("spec running", function () { }); }); - it("should permit nested describes", function(done) { + it('should permit nested describes', function(done) { var actions = []; - env.beforeEach(function () { + env.beforeEach(function() { actions.push('topSuite beforeEach'); }); - env.afterEach(function () { + env.afterEach(function() { actions.push('topSuite afterEach'); }); @@ -135,40 +129,40 @@ describe("spec running", function () { env.execute(null, function() { var expected = [ - "topSuite beforeEach", - "outer beforeEach", - "outer it 1", - "outer afterEach", - "topSuite afterEach", + 'topSuite beforeEach', + 'outer beforeEach', + 'outer it 1', + 'outer afterEach', + 'topSuite afterEach', - "topSuite beforeEach", - "outer beforeEach", - "inner 1 beforeEach", - "inner 1 it", - "inner 1 afterEach", - "outer afterEach", - "topSuite afterEach", + 'topSuite beforeEach', + 'outer beforeEach', + 'inner 1 beforeEach', + 'inner 1 it', + 'inner 1 afterEach', + 'outer afterEach', + 'topSuite afterEach', - "topSuite beforeEach", - "outer beforeEach", - "outer it 2", - "outer afterEach", - "topSuite afterEach", + 'topSuite beforeEach', + 'outer beforeEach', + 'outer it 2', + 'outer afterEach', + 'topSuite afterEach', - "topSuite beforeEach", - "outer beforeEach", - "inner 2 beforeEach", - "inner 2 it", - "inner 2 afterEach", - "outer afterEach", - "topSuite afterEach" + 'topSuite beforeEach', + 'outer beforeEach', + 'inner 2 beforeEach', + 'inner 2 it', + 'inner 2 afterEach', + 'outer afterEach', + 'topSuite afterEach' ]; expect(actions).toEqual(expected); done(); }); }); - it("should run multiple befores and afters ordered so functions declared later are treated as more specific", function(done) { + it('should run multiple befores and afters ordered so functions declared later are treated as more specific', function(done) { var actions = []; env.beforeAll(function() { @@ -187,19 +181,19 @@ describe("spec running", function () { actions.push('runner afterAll2'); }); - env.beforeEach(function () { + env.beforeEach(function() { actions.push('runner beforeEach1'); }); - env.afterEach(function () { + env.afterEach(function() { actions.push('runner afterEach1'); }); - env.beforeEach(function () { + env.beforeEach(function() { actions.push('runner beforeEach2'); }); - env.afterEach(function () { + env.afterEach(function() { actions.push('runner afterEach2'); }); @@ -227,19 +221,19 @@ describe("spec running", function () { env.execute(null, function() { var expected = [ - "runner beforeAll1", - "runner beforeAll2", - "runner beforeEach1", - "runner beforeEach2", - "beforeEach1", - "beforeEach2", - "outer it 1", - "afterEach2", - "afterEach1", - "runner afterEach2", - "runner afterEach1", - "runner afterAll2", - "runner afterAll1" + 'runner beforeAll1', + 'runner beforeAll2', + 'runner beforeEach1', + 'runner beforeEach2', + 'beforeEach1', + 'beforeEach2', + 'outer it 1', + 'afterEach2', + 'afterEach1', + 'runner afterEach2', + 'runner afterEach1', + 'runner afterAll2', + 'runner afterAll1' ]; expect(actions).toEqual(expected); done(); @@ -257,11 +251,11 @@ describe("spec running", function () { actions.push('runner afterAll'); }); - env.beforeEach(function () { + env.beforeEach(function() { actions.push('runner beforeEach'); }); - env.afterEach(function () { + env.afterEach(function() { actions.push('runner afterEach'); }); @@ -289,15 +283,15 @@ describe("spec running", function () { env.execute(null, function() { var expected = [ - "runner beforeAll", - "inner beforeAll", - "runner beforeEach", - "inner beforeEach", - "it", - "inner afterEach", - "runner afterEach", - "inner afterAll", - "runner afterAll" + 'runner beforeAll', + 'inner beforeAll', + 'runner beforeEach', + 'inner beforeEach', + 'it', + 'inner afterEach', + 'runner afterEach', + 'inner afterAll', + 'runner afterAll' ]; expect(actions).toEqual(expected); done(); @@ -317,11 +311,11 @@ describe("spec running", function () { actions.push('runner afterAll'); }); - env.beforeEach(function () { + env.beforeEach(function() { actions.push('runner beforeEach'); }); - env.afterEach(function () { + env.afterEach(function() { actions.push('runner afterEach'); }); @@ -353,38 +347,38 @@ describe("spec running", function () { env.execute([spec2.id, spec.id], function() { var expected = [ - "runner beforeAll", - "inner beforeAll", - "runner beforeEach", - "inner beforeEach", - "it2", - "inner afterEach", - "runner afterEach", + 'runner beforeAll', + 'inner beforeAll', + 'runner beforeEach', + 'inner beforeEach', + 'it2', + 'inner afterEach', + 'runner afterEach', - "runner beforeEach", - "inner beforeEach", - "it", - "inner afterEach", - "runner afterEach", - "inner afterAll", - "runner afterAll" + 'runner beforeEach', + 'inner beforeEach', + 'it', + 'inner afterEach', + 'runner afterEach', + 'inner afterAll', + 'runner afterAll' ]; expect(actions).toEqual(expected); done(); }); }); - it('only runs *Alls once in a focused suite', function(done){ + it('only runs *Alls once in a focused suite', function(done) { var actions = []; env.fdescribe('Suite', function() { - env.beforeAll(function(){ + env.beforeAll(function() { actions.push('beforeAll'); }); env.it('should run beforeAll once', function() { actions.push('spec'); }); - env.afterAll(function(){ + env.afterAll(function() { actions.push('afterAll'); }); }); @@ -398,20 +392,28 @@ describe("spec running", function () { describe('focused runnables', function() { it('runs the relevant alls and eachs for each runnable', function(done) { var actions = []; - env.beforeAll(function() {actions.push('beforeAll')}); - env.afterAll(function() {actions.push('afterAll')}); - env.beforeEach(function() {actions.push('beforeEach')}); - env.afterEach(function() {actions.push('afterEach')}); + env.beforeAll(function() { + actions.push('beforeAll'); + }); + env.afterAll(function() { + actions.push('afterAll'); + }); + env.beforeEach(function() { + actions.push('beforeEach'); + }); + env.afterEach(function() { + actions.push('afterEach'); + }); env.fdescribe('a focused suite', function() { env.it('is run', function() { - actions.push('spec in fdescribe') + actions.push('spec in fdescribe'); }); }); env.describe('an unfocused suite', function() { env.fit('has a focused spec', function() { - actions.push('focused spec') + actions.push('focused spec'); }); }); @@ -432,15 +434,15 @@ describe("spec running", function () { }); }); - it('focused specs in focused suites cause non-focused siblings to not run', function(done){ + it('focused specs in focused suites cause non-focused siblings to not run', function(done) { var actions = []; env.fdescribe('focused suite', function() { env.it('unfocused spec', function() { - actions.push('unfocused spec') + actions.push('unfocused spec'); }); env.fit('focused spec', function() { - actions.push('focused spec') + actions.push('focused spec'); }); }); @@ -451,12 +453,12 @@ describe("spec running", function () { }); }); - it('focused suites in focused suites cause non-focused siblings to not run', function(done){ + it('focused suites in focused suites cause non-focused siblings to not run', function(done) { var actions = []; env.fdescribe('focused suite', function() { env.it('unfocused spec', function() { - actions.push('unfocused spec') + actions.push('unfocused spec'); }); env.fdescribe('inner focused suite', function() { env.it('inner spec', function() { @@ -477,7 +479,7 @@ describe("spec running", function () { env.fdescribe('focused suite', function() { env.it('unfocused spec', function() { - actions.push('unfocused spec') + actions.push('unfocused spec'); }); env.describe('inner focused suite', function() { env.fit('focused spec', function() { @@ -495,12 +497,12 @@ describe("spec running", function () { }); it("shouldn't run disabled suites", function(done) { - var specInADisabledSuite = jasmine.createSpy("specInADisabledSuite"), - suite = env.describe('A Suite', function() { - env.xdescribe('with a disabled suite', function(){ - env.it('spec inside a disabled suite', specInADisabledSuite); + var specInADisabledSuite = jasmine.createSpy('specInADisabledSuite'), + suite = env.describe('A Suite', function() { + env.xdescribe('with a disabled suite', function() { + env.it('spec inside a disabled suite', specInADisabledSuite); + }); }); - }); env.execute(null, function() { expect(specInADisabledSuite).not.toHaveBeenCalled(); @@ -509,16 +511,16 @@ describe("spec running", function () { }); it("shouldn't run before/after functions in disabled suites", function(done) { - var shouldNotRun = jasmine.createSpy("shouldNotRun"), - suite = env.xdescribe('A disabled Suite', function() { - // None of the before/after functions should run. - env.beforeAll(shouldNotRun); - env.beforeEach(shouldNotRun); - env.afterEach(shouldNotRun); - env.afterAll(shouldNotRun); + var shouldNotRun = jasmine.createSpy('shouldNotRun'), + suite = env.xdescribe('A disabled Suite', function() { + // None of the before/after functions should run. + env.beforeAll(shouldNotRun); + env.beforeEach(shouldNotRun); + env.afterEach(shouldNotRun); + env.afterAll(shouldNotRun); - env.it('spec inside a disabled suite', shouldNotRun); - }); + env.it('spec inside a disabled suite', shouldNotRun); + }); env.execute(null, function() { expect(shouldNotRun).not.toHaveBeenCalled(); @@ -526,9 +528,9 @@ describe("spec running", function () { }); }); - it("should allow top level suites to be disabled", function(done) { - var specInADisabledSuite = jasmine.createSpy("specInADisabledSuite"), - otherSpec = jasmine.createSpy("otherSpec"); + it('should allow top level suites to be disabled', function(done) { + var specInADisabledSuite = jasmine.createSpy('specInADisabledSuite'), + otherSpec = jasmine.createSpy('otherSpec'); env.xdescribe('A disabled suite', function() { env.it('spec inside a disabled suite', specInADisabledSuite); @@ -544,19 +546,19 @@ describe("spec running", function () { }); }); - it("should set all pending specs to pending when a suite is run", function(done) { + it('should set all pending specs to pending when a suite is run', function(done) { var pendingSpec, suite = env.describe('default current suite', function() { - pendingSpec = env.it("I am a pending spec"); + pendingSpec = env.it('I am a pending spec'); }); env.execute(null, function() { - expect(pendingSpec.status()).toBe("pending"); + expect(pendingSpec.status()).toBe('pending'); done(); }); }); - it("should recover gracefully when there are errors in describe functions", function(done) { + it('should recover gracefully when there are errors in describe functions', function(done) { var specs = [], reporter = jasmine.createSpyObj(['specDone', 'suiteDone']); @@ -565,83 +567,95 @@ describe("spec running", function () { }); expect(function() { - env.describe("outer1", function() { - env.describe("inner1", function() { - env.it("should thingy", function() { + env.describe('outer1', function() { + env.describe('inner1', function() { + env.it('should thingy', function() { this.expect(true).toEqual(true); }); - throw new Error("inner error"); + throw new Error('inner error'); }); - env.describe("inner2", function() { - env.it("should other thingy", function() { + env.describe('inner2', function() { + env.it('should other thingy', function() { this.expect(true).toEqual(true); }); }); - throw new Error("outer error"); - + throw new Error('outer error'); }); }).not.toThrow(); - env.describe("outer2", function() { - env.it("should xxx", function() { + env.describe('outer2', function() { + env.it('should xxx', function() { this.expect(true).toEqual(true); }); }); env.addReporter(reporter); env.execute(null, function() { - expect(specs).toEqual(['outer1 inner1 should thingy', 'outer1 inner2 should other thingy', 'outer2 should xxx']); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('outer1 inner1', [/inner error/]); - expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('outer1', [/outer error/]); + expect(specs).toEqual([ + 'outer1 inner1 should thingy', + 'outer1 inner2 should other thingy', + 'outer2 should xxx' + ]); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable( + 'outer1 inner1', + [/inner error/] + ); + expect(reporter.suiteDone).toHaveFailedExpectationsForRunnable('outer1', [ + /outer error/ + ]); done(); }); }); - it("re-enters suites that have no *Alls", function(done) { + it('re-enters suites that have no *Alls', function(done) { var actions = [], - spec1, spec2, spec3; + spec1, + spec2, + spec3; - env.describe("top", function() { - spec1 = env.it("spec1", function() { - actions.push("spec1"); + env.describe('top', function() { + spec1 = env.it('spec1', function() { + actions.push('spec1'); }); - spec2 = env.it("spec2", function() { - actions.push("spec2"); + spec2 = env.it('spec2', function() { + actions.push('spec2'); }); }); - spec3 = env.it("spec3", function() { - actions.push("spec3"); + spec3 = env.it('spec3', function() { + actions.push('spec3'); }); env.execute([spec2.id, spec3.id, spec1.id], function() { - expect(actions).toEqual(["spec2", "spec3", "spec1"]); + expect(actions).toEqual(['spec2', 'spec3', 'spec1']); done(); }); }); - it("refuses to re-enter suites with a beforeAll", function() { + it('refuses to re-enter suites with a beforeAll', function() { var actions = [], - spec1, spec2, spec3; + spec1, + spec2, + spec3; - env.describe("top", function() { + env.describe('top', function() { env.beforeAll(function() {}); - spec1 = env.it("spec1", function() { - actions.push("spec1"); + spec1 = env.it('spec1', function() { + actions.push('spec1'); }); - spec2 = env.it("spec2", function() { - actions.push("spec2"); + spec2 = env.it('spec2', function() { + actions.push('spec2'); }); }); - spec3 = env.it("spec3", function() { - actions.push("spec3"); + spec3 = env.it('spec3', function() { + actions.push('spec3'); }); expect(function() { @@ -650,24 +664,26 @@ describe("spec running", function () { expect(actions).toEqual([]); }); - it("refuses to re-enter suites with a afterAll", function() { + it('refuses to re-enter suites with a afterAll', function() { var actions = [], - spec1, spec2, spec3; + spec1, + spec2, + spec3; - env.describe("top", function() { + env.describe('top', function() { env.afterAll(function() {}); - spec1 = env.it("spec1", function() { - actions.push("spec1"); + spec1 = env.it('spec1', function() { + actions.push('spec1'); }); - spec2 = env.it("spec2", function() { - actions.push("spec2"); + spec2 = env.it('spec2', function() { + actions.push('spec2'); }); }); - spec3 = env.it("spec3", function() { - actions.push("spec3"); + spec3 = env.it('spec3', function() { + actions.push('spec3'); }); expect(function() { @@ -676,15 +692,15 @@ describe("spec running", function () { expect(actions).toEqual([]); }); - it("should run the tests in a consistent order when a seed is supplied", function(done) { + it('should run the tests in a consistent order when a seed is supplied', function(done) { var actions = []; - env.configure({random: true, seed: '123456'}); + env.configure({ random: true, seed: '123456' }); - env.beforeEach(function () { + env.beforeEach(function() { actions.push('topSuite beforeEach'); }); - env.afterEach(function () { + env.afterEach(function() { actions.push('topSuite afterEach'); }); @@ -769,14 +785,14 @@ describe("spec running", function () { }); }); - describe("When throwOnExpectationFailure is set", function() { - it("skips to cleanup functions after an error", function(done) { + describe('When throwOnExpectationFailure is set', function() { + it('skips to cleanup functions after an error', function(done) { var actions = []; env.describe('Something', function() { env.beforeEach(function() { actions.push('outer beforeEach'); - throw new Error("error"); + throw new Error('error'); }); env.afterEach(function() { @@ -792,13 +808,13 @@ describe("spec running", function () { actions.push('inner afterEach'); }); - env.it('does it' , function() { + env.it('does it', function() { actions.push('inner it'); }); }); }); - env.configure({oneFailurePerSpec: true}); + env.configure({ oneFailurePerSpec: true }); env.execute(null, function() { expect(actions).toEqual([ @@ -810,7 +826,7 @@ describe("spec running", function () { }); }); - it("skips to cleanup functions after done.fail is called", function(done) { + it('skips to cleanup functions after done.fail is called', function(done) { var actions = []; env.describe('Something', function() { @@ -824,23 +840,20 @@ describe("spec running", function () { actions.push('afterEach'); }); - env.it('does it' , function() { + env.it('does it', function() { actions.push('it'); }); }); - env.configure({oneFailurePerSpec: true}); + env.configure({ oneFailurePerSpec: true }); env.execute(null, function() { - expect(actions).toEqual([ - 'beforeEach', - 'afterEach' - ]); + expect(actions).toEqual(['beforeEach', 'afterEach']); done(); }); }); - it("skips to cleanup functions when an async function times out", function(done) { + it('skips to cleanup functions when an async function times out', function(done) { var actions = []; env.describe('Something', function() { @@ -852,23 +865,20 @@ describe("spec running", function () { actions.push('afterEach'); }); - env.it('does it' , function() { + env.it('does it', function() { actions.push('it'); }); }); - env.configure({oneFailurePerSpec: true}); + env.configure({ oneFailurePerSpec: true }); env.execute(null, function() { - expect(actions).toEqual([ - 'beforeEach', - 'afterEach' - ]); + expect(actions).toEqual(['beforeEach', 'afterEach']); done(); }); }); - it("skips to cleanup functions after an error with deprecations", function(done) { + it('skips to cleanup functions after an error with deprecations', function(done) { var actions = []; spyOn(env, 'deprecated'); @@ -876,7 +886,7 @@ describe("spec running", function () { env.describe('Something', function() { env.beforeEach(function() { actions.push('outer beforeEach'); - throw new Error("error"); + throw new Error('error'); }); env.afterEach(function() { @@ -892,7 +902,7 @@ describe("spec running", function () { actions.push('inner afterEach'); }); - env.it('does it' , function() { + env.it('does it', function() { actions.push('inner it'); }); }); @@ -911,7 +921,7 @@ describe("spec running", function () { }); }); - it("skips to cleanup functions after done.fail is called with deprecations", function(done) { + it('skips to cleanup functions after done.fail is called with deprecations', function(done) { var actions = []; spyOn(env, 'deprecated'); @@ -927,7 +937,7 @@ describe("spec running", function () { actions.push('afterEach'); }); - env.it('does it' , function() { + env.it('does it', function() { actions.push('it'); }); }); @@ -935,16 +945,13 @@ describe("spec running", function () { env.throwOnExpectationFailure(true); env.execute(null, function() { - expect(actions).toEqual([ - 'beforeEach', - 'afterEach' - ]); + expect(actions).toEqual(['beforeEach', 'afterEach']); expect(env.deprecated).toHaveBeenCalled(); done(); }); }); - it("skips to cleanup functions when an async function times out with deprecations", function(done) { + it('skips to cleanup functions when an async function times out with deprecations', function(done) { var actions = []; spyOn(env, 'deprecated'); @@ -958,7 +965,7 @@ describe("spec running", function () { actions.push('afterEach'); }); - env.it('does it' , function() { + env.it('does it', function() { actions.push('it'); }); }); @@ -966,18 +973,15 @@ describe("spec running", function () { env.throwOnExpectationFailure(true); env.execute(null, function() { - expect(actions).toEqual([ - 'beforeEach', - 'afterEach' - ]); + expect(actions).toEqual(['beforeEach', 'afterEach']); expect(env.deprecated).toHaveBeenCalled(); done(); }); }); }); - describe("when stopOnSpecFailure is on", function() { - it("does not run further specs when one fails", function(done) { + describe('when stopOnSpecFailure is on', function() { + it('does not run further specs when one fails', function(done) { var actions = []; env.describe('wrapper', function() { @@ -993,7 +997,7 @@ describe("spec running", function () { }); }); - env.configure({random: false, failFast: true}); + env.configure({ random: false, failFast: true }); env.execute(null, function() { expect(actions).toEqual(['fails']); @@ -1001,7 +1005,7 @@ describe("spec running", function () { }); }); - it("does not run further specs when one fails when configured with deprecated option", function(done) { + it('does not run further specs when one fails when configured with deprecated option', function(done) { var actions = []; spyOn(env, 'deprecated'); @@ -1019,7 +1023,7 @@ describe("spec running", function () { }); }); - env.configure({random: false}); + env.configure({ random: false }); env.stopOnSpecFailure(true); env.execute(null, function() { diff --git a/spec/core/matchers/DiffBuilderSpec.js b/spec/core/matchers/DiffBuilderSpec.js index 01220ce0..d1a3d884 100644 --- a/spec/core/matchers/DiffBuilderSpec.js +++ b/spec/core/matchers/DiffBuilderSpec.js @@ -1,132 +1,159 @@ -describe("DiffBuilder", function () { - it("records the actual and expected objects", function () { +describe('DiffBuilder', function() { + it('records the actual and expected objects', function() { var diffBuilder = jasmineUnderTest.DiffBuilder(); - diffBuilder.setRoots({x: 'actual'}, {x: 'expected'}); + diffBuilder.setRoots({ x: 'actual' }, { x: 'expected' }); diffBuilder.recordMismatch(); - expect(diffBuilder.getMessage()).toEqual("Expected Object({ x: 'actual' }) to equal Object({ x: 'expected' })."); + expect(diffBuilder.getMessage()).toEqual( + "Expected Object({ x: 'actual' }) to equal Object({ x: 'expected' })." + ); }); - it("prints the path at which the difference was found", function () { + it('prints the path at which the difference was found', function() { var diffBuilder = jasmineUnderTest.DiffBuilder(); - diffBuilder.setRoots({foo: {x: 'actual'}}, {foo: {x: 'expected'}}); + diffBuilder.setRoots({ foo: { x: 'actual' } }, { foo: { x: 'expected' } }); - diffBuilder.withPath('foo', function () { + diffBuilder.withPath('foo', function() { diffBuilder.recordMismatch(); }); - expect(diffBuilder.getMessage()).toEqual("Expected $.foo = Object({ x: 'actual' }) to equal Object({ x: 'expected' })."); + expect(diffBuilder.getMessage()).toEqual( + "Expected $.foo = Object({ x: 'actual' }) to equal Object({ x: 'expected' })." + ); }); - it("prints multiple messages, separated by newlines", function () { + it('prints multiple messages, separated by newlines', function() { var diffBuilder = jasmineUnderTest.DiffBuilder(); - diffBuilder.setRoots({foo: 1, bar: 3}, {foo: 2, bar: 4}); + diffBuilder.setRoots({ foo: 1, bar: 3 }, { foo: 2, bar: 4 }); - diffBuilder.withPath('foo', function () { + diffBuilder.withPath('foo', function() { diffBuilder.recordMismatch(); }); - diffBuilder.withPath('bar', function () { + diffBuilder.withPath('bar', function() { diffBuilder.recordMismatch(); }); var message = - "Expected $.foo = 1 to equal 2.\n" + - "Expected $.bar = 3 to equal 4."; + 'Expected $.foo = 1 to equal 2.\n' + 'Expected $.bar = 3 to equal 4.'; expect(diffBuilder.getMessage()).toEqual(message); }); - it("allows customization of the message", function () { + it('allows customization of the message', function() { var diffBuilder = jasmineUnderTest.DiffBuilder(); - diffBuilder.setRoots({x: 'bar'}, {x: 'foo'}); + diffBuilder.setRoots({ x: 'bar' }, { x: 'foo' }); function darthVaderFormatter(actual, expected, path) { - return "I find your lack of " + expected + " disturbing. (was " + actual + ", at " + path + ")" + return ( + 'I find your lack of ' + + expected + + ' disturbing. (was ' + + actual + + ', at ' + + path + + ')' + ); } - diffBuilder.withPath('x', function () { + diffBuilder.withPath('x', function() { diffBuilder.recordMismatch(darthVaderFormatter); }); - expect(diffBuilder.getMessage()).toEqual("I find your lack of foo disturbing. (was bar, at $.x)"); + expect(diffBuilder.getMessage()).toEqual( + 'I find your lack of foo disturbing. (was bar, at $.x)' + ); }); - it("uses the injected pretty-printer", function () { - var prettyPrinter = function (val) { + it('uses the injected pretty-printer', function() { + var prettyPrinter = function(val) { return '|' + val + '|'; }, - diffBuilder = jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}); - prettyPrinter.customFormat_ = function () { - }; + diffBuilder = jasmineUnderTest.DiffBuilder({ + prettyPrinter: prettyPrinter + }); + prettyPrinter.customFormat_ = function() {}; - diffBuilder.setRoots({foo: 'actual'}, {foo: 'expected'}); - diffBuilder.withPath('foo', function () { + diffBuilder.setRoots({ foo: 'actual' }, { foo: 'expected' }); + diffBuilder.withPath('foo', function() { diffBuilder.recordMismatch(); }); - expect(diffBuilder.getMessage()).toEqual("Expected $.foo = |actual| to equal |expected|."); + expect(diffBuilder.getMessage()).toEqual( + 'Expected $.foo = |actual| to equal |expected|.' + ); }); - it("passes the injected pretty-printer to the diff formatter", function () { + it('passes the injected pretty-printer to the diff formatter', function() { var diffFormatter = jasmine.createSpy('diffFormatter'), - prettyPrinter = function () { - }, - diffBuilder = jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}); - prettyPrinter.customFormat_ = function () { - }; + prettyPrinter = function() {}, + diffBuilder = jasmineUnderTest.DiffBuilder({ + prettyPrinter: prettyPrinter + }); + prettyPrinter.customFormat_ = function() {}; - diffBuilder.setRoots({x: 'bar'}, {x: 'foo'}); - diffBuilder.withPath('x', function () { + diffBuilder.setRoots({ x: 'bar' }, { x: 'foo' }); + diffBuilder.withPath('x', function() { diffBuilder.recordMismatch(diffFormatter); }); diffBuilder.getMessage(); - expect(diffFormatter).toHaveBeenCalledWith('bar', 'foo', jasmine.anything(), prettyPrinter); + expect(diffFormatter).toHaveBeenCalledWith( + 'bar', + 'foo', + jasmine.anything(), + prettyPrinter + ); }); - it("uses custom object formatters on leaf nodes", function() { + it('uses custom object formatters on leaf nodes', function() { var formatter = function(x) { if (typeof x === 'number') { return '[number:' + x + ']'; } }; prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]); - var diffBuilder = new jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}); + var diffBuilder = new jasmineUnderTest.DiffBuilder({ + prettyPrinter: prettyPrinter + }); diffBuilder.setRoots(5, 4); diffBuilder.recordMismatch(); - expect(diffBuilder.getMessage()).toEqual('Expected [number:5] to equal [number:4].'); + expect(diffBuilder.getMessage()).toEqual( + 'Expected [number:5] to equal [number:4].' + ); }); - - it("uses custom object formatters on non leaf nodes", function () { - var formatter = function (x) { + it('uses custom object formatters on non leaf nodes', function() { + var formatter = function(x) { if (x.hasOwnProperty('a')) { return '[thing with a=' + x.a + ', b=' + JSON.stringify(x.b) + ']'; } }; prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]); - var diffBuilder = new jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}); - var expectedMsg = 'Expected $[0].foo = [thing with a=1, b={"x":42}] to equal [thing with a=1, b={"x":43}].\n' + + var diffBuilder = new jasmineUnderTest.DiffBuilder({ + prettyPrinter: prettyPrinter + }); + var expectedMsg = + 'Expected $[0].foo = [thing with a=1, b={"x":42}] to equal [thing with a=1, b={"x":43}].\n' + "Expected $[0].bar = 'yes' to equal 'no'."; diffBuilder.setRoots( - [{foo: {a: 1, b: {x: 42}}, bar: 'yes'}], - [{foo: {a: 1, b: {x: 43}}, bar: 'no'}] + [{ foo: { a: 1, b: { x: 42 } }, bar: 'yes' }], + [{ foo: { a: 1, b: { x: 43 } }, bar: 'no' }] ); - diffBuilder.withPath(0, function () { - diffBuilder.withPath('foo', function () { - diffBuilder.withPath('b', function () { - diffBuilder.withPath('x', function () { + diffBuilder.withPath(0, function() { + diffBuilder.withPath('foo', function() { + diffBuilder.withPath('b', function() { + diffBuilder.withPath('x', function() { diffBuilder.recordMismatch(); }); }); }); - diffBuilder.withPath('bar', function () { + diffBuilder.withPath('bar', function() { diffBuilder.recordMismatch(); }); }); @@ -136,14 +163,16 @@ describe("DiffBuilder", function () { it('builds diffs involving asymmetric equality testers that implement valuesForDiff_ at the root', function() { var prettyPrinter = jasmineUnderTest.makePrettyPrinter([]), - diffBuilder = new jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}), - expectedMsg = 'Expected $.foo = 1 to equal 2.\n' + - "Expected $.baz = undefined to equal 3."; - + diffBuilder = new jasmineUnderTest.DiffBuilder({ + prettyPrinter: prettyPrinter + }), + expectedMsg = + 'Expected $.foo = 1 to equal 2.\n' + + 'Expected $.baz = undefined to equal 3.'; diffBuilder.setRoots( - {foo: 1, bar: 2}, - jasmine.objectContaining({foo: 2, baz: 3}) + { foo: 1, bar: 2 }, + jasmine.objectContaining({ foo: 2, baz: 3 }) ); diffBuilder.withPath('foo', function() { @@ -158,21 +187,23 @@ describe("DiffBuilder", function () { it('builds diffs involving asymmetric equality testers that implement valuesForDiff_ below the root', function() { var prettyPrinter = jasmineUnderTest.makePrettyPrinter([]), - diffBuilder = new jasmineUnderTest.DiffBuilder({prettyPrinter: prettyPrinter}), - expectedMsg = 'Expected $.x.foo = 1 to equal 2.\n' + - "Expected $.x.baz = undefined to equal 3."; - + diffBuilder = new jasmineUnderTest.DiffBuilder({ + prettyPrinter: prettyPrinter + }), + expectedMsg = + 'Expected $.x.foo = 1 to equal 2.\n' + + 'Expected $.x.baz = undefined to equal 3.'; diffBuilder.setRoots( - {x: {foo: 1, bar: 2}}, - {x: jasmine.objectContaining({foo: 2, baz: 3})} + { x: { foo: 1, bar: 2 } }, + { x: jasmine.objectContaining({ foo: 2, baz: 3 }) } ); diffBuilder.withPath('x', function() { - diffBuilder.withPath('foo', function () { + diffBuilder.withPath('foo', function() { diffBuilder.recordMismatch(); }); - diffBuilder.withPath('baz', function () { + diffBuilder.withPath('baz', function() { diffBuilder.recordMismatch(); }); }); diff --git a/spec/core/matchers/MismatchTreeSpec.js b/spec/core/matchers/MismatchTreeSpec.js index ea053eb7..8a158df4 100644 --- a/spec/core/matchers/MismatchTreeSpec.js +++ b/spec/core/matchers/MismatchTreeSpec.js @@ -1,15 +1,15 @@ -describe('MismatchTree', function () { - describe('#add', function () { - describe('When the path is empty', function () { - it('flags the root node as mismatched', function () { +describe('MismatchTree', function() { + describe('#add', function() { + describe('When the path is empty', function() { + it('flags the root node as mismatched', function() { var tree = new jasmineUnderTest.MismatchTree(); tree.add(new jasmineUnderTest.ObjectPath([])); expect(tree.isMismatch).toBe(true); }); }); - describe('When the path is not empty', function () { - it('flags the node as mismatched', function () { + describe('When the path is not empty', function() { + it('flags the node as mismatched', function() { var tree = new jasmineUnderTest.MismatchTree(); tree.add(new jasmineUnderTest.ObjectPath(['a', 'b'])); @@ -17,7 +17,7 @@ describe('MismatchTree', function () { expect(tree.child('a').child('b').isMismatch).toBe(true); }); - it('does not flag ancestors as mismatched', function () { + it('does not flag ancestors as mismatched', function() { var tree = new jasmineUnderTest.MismatchTree(); tree.add(new jasmineUnderTest.ObjectPath(['a', 'b'])); @@ -27,7 +27,7 @@ describe('MismatchTree', function () { }); }); - it('stores the formatter on only the target node', function () { + it('stores the formatter on only the target node', function() { var tree = new jasmineUnderTest.MismatchTree(); tree.add(new jasmineUnderTest.ObjectPath(['a', 'b']), formatter); @@ -37,7 +37,7 @@ describe('MismatchTree', function () { expect(tree.child('a').child('b').formatter).toBe(formatter); }); - it('stores the path to the node', function () { + it('stores the path to the node', function() { var tree = new jasmineUnderTest.MismatchTree(); tree.add(new jasmineUnderTest.ObjectPath(['a', 'b']), formatter); @@ -46,8 +46,8 @@ describe('MismatchTree', function () { }); }); - describe('#traverse', function () { - it('calls the callback for all nodes that are or contain mismatches', function () { + describe('#traverse', function() { + it('calls the callback for all nodes that are or contain mismatches', function() { var tree = new jasmineUnderTest.MismatchTree(); tree.add(new jasmineUnderTest.ObjectPath(['a', 'b']), formatter); tree.add(new jasmineUnderTest.ObjectPath(['c'])); @@ -56,20 +56,28 @@ describe('MismatchTree', function () { tree.traverse(visit); expect(visit).toHaveBeenCalledWith( - new jasmineUnderTest.ObjectPath([]), false, undefined + new jasmineUnderTest.ObjectPath([]), + false, + undefined ); expect(visit).toHaveBeenCalledWith( - new jasmineUnderTest.ObjectPath(['a']), false, undefined + new jasmineUnderTest.ObjectPath(['a']), + false, + undefined ); expect(visit).toHaveBeenCalledWith( - new jasmineUnderTest.ObjectPath(['a', 'b']), true, formatter + new jasmineUnderTest.ObjectPath(['a', 'b']), + true, + formatter ); expect(visit).toHaveBeenCalledWith( - new jasmineUnderTest.ObjectPath(['c']), true, undefined + new jasmineUnderTest.ObjectPath(['c']), + true, + undefined ); }); - it('does not call the callback if there are no mismatches', function () { + it('does not call the callback if there are no mismatches', function() { var tree = new jasmineUnderTest.MismatchTree(); var visit = jasmine.createSpy('visit'); @@ -78,12 +86,12 @@ describe('MismatchTree', function () { expect(visit).not.toHaveBeenCalled(); }); - it('visits parents before children', function () { + it('visits parents before children', function() { var tree = new jasmineUnderTest.MismatchTree(); tree.add(new jasmineUnderTest.ObjectPath(['a', 'b'])); var visited = []; - tree.traverse(function (path) { + tree.traverse(function(path) { visited.push(path); return true; }); @@ -101,7 +109,7 @@ describe('MismatchTree', function () { tree.add(new jasmineUnderTest.ObjectPath([1])); var visited = []; - tree.traverse(function (path) { + tree.traverse(function(path) { visited.push(path); return true; }); @@ -118,7 +126,7 @@ describe('MismatchTree', function () { tree.add(new jasmineUnderTest.ObjectPath(['a', 'b'])); var visited = []; - tree.traverse(function (path) { + tree.traverse(function(path) { visited.push(path); return path.depth() === 0; }); @@ -130,7 +138,5 @@ describe('MismatchTree', function () { }); }); - function formatter() { - } - + function formatter() {} }); diff --git a/spec/core/matchers/NullDiffBuilderSpec.js b/spec/core/matchers/NullDiffBuilderSpec.js index 3333776b..fa9ed299 100644 --- a/spec/core/matchers/NullDiffBuilderSpec.js +++ b/spec/core/matchers/NullDiffBuilderSpec.js @@ -1,8 +1,7 @@ -describe('NullDiffBuilder', function () { - it('responds to withPath() by calling the passed function', function () { +describe('NullDiffBuilder', function() { + it('responds to withPath() by calling the passed function', function() { var spy = jasmine.createSpy('callback'); jasmineUnderTest.NullDiffBuilder().withPath('does not matter', spy); expect(spy).toHaveBeenCalled(); }); - }); diff --git a/spec/core/matchers/async/toBePendingSpec.js b/spec/core/matchers/async/toBePendingSpec.js index 285414f1..0b78d8cd 100644 --- a/spec/core/matchers/async/toBePendingSpec.js +++ b/spec/core/matchers/async/toBePendingSpec.js @@ -8,7 +8,7 @@ describe('toBePending', function() { actual = new Promise(function() {}); return matcher.compare(actual).then(function(result) { - expect(result).toEqual(jasmine.objectContaining({pass: true})); + expect(result).toEqual(jasmine.objectContaining({ pass: true })); }); }); @@ -20,7 +20,7 @@ describe('toBePending', function() { actual = Promise.resolve(); return matcher.compare(actual).then(function(result) { - expect(result).toEqual(jasmine.objectContaining({pass: false})); + expect(result).toEqual(jasmine.objectContaining({ pass: false })); }); }); @@ -32,21 +32,19 @@ describe('toBePending', function() { actual = Promise.reject(new Error('promise was rejected')); return matcher.compare(actual).then(function(result) { - expect(result).toEqual(jasmine.objectContaining({pass: false})); + expect(result).toEqual(jasmine.objectContaining({ pass: false })); }); }); it('fails if actual is not a promise', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(), - matcher = jasmineUnderTest.asyncMatchers.toBePending(matchersUtil), - actual = 'not a promise'; + matcher = jasmineUnderTest.asyncMatchers.toBePending(matchersUtil), + actual = 'not a promise'; function f() { return matcher.compare(actual); } - expect(f).toThrowError( - 'Expected toBePending to be called on a promise.' - ); + expect(f).toThrowError('Expected toBePending to be called on a promise.'); }); }); diff --git a/spec/core/matchers/async/toBeRejectedSpec.js b/spec/core/matchers/async/toBeRejectedSpec.js index 6ecf9ebc..c1ea377b 100644 --- a/spec/core/matchers/async/toBeRejectedSpec.js +++ b/spec/core/matchers/async/toBeRejectedSpec.js @@ -8,7 +8,7 @@ describe('toBeRejected', function() { actual = Promise.reject('AsyncExpectationSpec rejection'); return matcher.compare(actual).then(function(result) { - expect(result).toEqual(jasmine.objectContaining({pass: true})); + expect(result).toEqual(jasmine.objectContaining({ pass: true })); }); }); @@ -20,7 +20,7 @@ describe('toBeRejected', function() { actual = Promise.resolve(); return matcher.compare(actual).then(function(result) { - expect(result).toEqual(jasmine.objectContaining({pass: false})); + expect(result).toEqual(jasmine.objectContaining({ pass: false })); }); }); @@ -33,8 +33,6 @@ describe('toBeRejected', function() { return matcher.compare(actual); } - expect(f).toThrowError( - 'Expected toBeRejected to be called on a promise.' - ); + expect(f).toThrowError('Expected toBeRejected to be called on a promise.'); }); }); diff --git a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js index d09a05fd..d7d3f659 100644 --- a/spec/core/matchers/async/toBeRejectedWithErrorSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithErrorSpec.js @@ -1,174 +1,253 @@ /* eslint-disable compat/compat */ -describe('#toBeRejectedWithError', function () { - it('passes when Error type matches', function () { +describe('#toBeRejectedWithError', function() { + it('passes when Error type matches', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError( + matchersUtil + ), actual = Promise.reject(new TypeError('foo')); - return matcher.compare(actual, TypeError).then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: true, - message: 'Expected a promise not to be rejected with TypeError, but it was.' - })); + return matcher.compare(actual, TypeError).then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: true, + message: + 'Expected a promise not to be rejected with TypeError, but it was.' + }) + ); }); }); - it('passes when Error type and message matches', function () { + it('passes when Error type and message matches', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError( + matchersUtil + ), actual = Promise.reject(new TypeError('foo')); - return matcher.compare(actual, TypeError, 'foo').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: true, - message: 'Expected a promise not to be rejected with TypeError: \'foo\', but it was.' - })); + return matcher.compare(actual, TypeError, 'foo').then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: true, + message: + "Expected a promise not to be rejected with TypeError: 'foo', but it was." + }) + ); }); }); it('passes when Error matches and is exactly Error', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError( + matchersUtil + ), actual = Promise.reject(new Error()); - return matcher.compare(actual, Error).then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: true, - message: 'Expected a promise not to be rejected with Error, but it was.' - })); + return matcher.compare(actual, Error).then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: true, + message: + 'Expected a promise not to be rejected with Error, but it was.' + }) + ); }); - }); - it('passes when Error message matches a string', function () { + it('passes when Error message matches a string', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError( + matchersUtil + ), actual = Promise.reject(new Error('foo')); - return matcher.compare(actual, 'foo').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: true, - message: 'Expected a promise not to be rejected with Error: \'foo\', but it was.' - })); + return matcher.compare(actual, 'foo').then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: true, + message: + "Expected a promise not to be rejected with Error: 'foo', but it was." + }) + ); }); }); - it('passes when Error message matches a RegExp', function () { + it('passes when Error message matches a RegExp', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError( + matchersUtil + ), actual = Promise.reject(new Error('foo')); - return matcher.compare(actual, /foo/).then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: true, - message: 'Expected a promise not to be rejected with Error: /foo/, but it was.' - })); + return matcher.compare(actual, /foo/).then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: true, + message: + 'Expected a promise not to be rejected with Error: /foo/, but it was.' + }) + ); }); }); - it('passes when Error message is empty', function () { + it('passes when Error message is empty', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError( + matchersUtil + ), actual = Promise.reject(new Error()); - return matcher.compare(actual, '').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: true, - message: 'Expected a promise not to be rejected with Error: \'\', but it was.' - })); + return matcher.compare(actual, '').then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: true, + message: + "Expected a promise not to be rejected with Error: '', but it was." + }) + ); }); }); - it('passes when no arguments', function () { + it('passes when no arguments', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError( + matchersUtil + ), actual = Promise.reject(new Error()); - return matcher.compare(actual, void 0).then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: true, - message: 'Expected a promise not to be rejected with Error, but it was.' - })); + return matcher.compare(actual, void 0).then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: true, + message: + 'Expected a promise not to be rejected with Error, but it was.' + }) + ); }); }); - it('fails when resolved', function () { + it('fails when resolved', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError( + matchersUtil + ), actual = Promise.resolve(new Error('foo')); - return matcher.compare(actual, 'foo').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: false, - message: 'Expected a promise to be rejected but it was resolved.' - })); + return matcher.compare(actual, 'foo').then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: false, + message: 'Expected a promise to be rejected but it was resolved.' + }) + ); }); }); - it('fails when rejected with non Error type', function () { + it('fails when rejected with non Error type', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError( + matchersUtil + ), actual = Promise.reject('foo'); - return matcher.compare(actual, 'foo').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: false, - message: 'Expected a promise to be rejected with Error: \'foo\' but it was rejected with \'foo\'.' - })); + return matcher.compare(actual, 'foo').then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: false, + message: + "Expected a promise to be rejected with Error: 'foo' but it was rejected with 'foo'." + }) + ); }); }); - it('fails when Error type mismatches', function () { + it('fails when Error type mismatches', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError( + matchersUtil + ), actual = Promise.reject(new Error('foo')); - return matcher.compare(actual, TypeError, 'foo').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: false, - message: 'Expected a promise to be rejected with TypeError: \'foo\' but it was rejected with type Error.' - })); + return matcher.compare(actual, TypeError, 'foo').then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: false, + message: + "Expected a promise to be rejected with TypeError: 'foo' but it was rejected with type Error." + }) + ); }); }); - it('fails when Error message mismatches', function () { + it('fails when Error message mismatches', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError( + matchersUtil + ), actual = Promise.reject(new Error('foo')); - return matcher.compare(actual, 'bar').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: false, - message: 'Expected a promise to be rejected with Error: \'bar\' but it was rejected with Error: foo.' - })); + return matcher.compare(actual, 'bar').then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: false, + message: + "Expected a promise to be rejected with Error: 'bar' but it was rejected with Error: foo." + }) + ); }); }); it('fails if actual is not a promise', function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError(matchersUtil), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWithError( + matchersUtil + ), actual = 'not a promise'; function f() { diff --git a/spec/core/matchers/async/toBeRejectedWithSpec.js b/spec/core/matchers/async/toBeRejectedWithSpec.js index 69003c59..9c663930 100644 --- a/spec/core/matchers/async/toBeRejectedWithSpec.js +++ b/spec/core/matchers/async/toBeRejectedWithSpec.js @@ -1,74 +1,91 @@ /* eslint-disable compat/compat */ -describe('#toBeRejectedWith', function () { - it('should return true if the promise is rejected with the expected value', function () { +describe('#toBeRejectedWith', function() { + it('should return true if the promise is rejected with the expected value', function() { jasmine.getEnv().requirePromises(); var matchersUtil = new jasmineUnderTest.MatchersUtil(), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), - actual = Promise.reject({error: 'PEBCAK'}); + actual = Promise.reject({ error: 'PEBCAK' }); - return matcher.compare(actual, {error: 'PEBCAK'}).then(function (result) { + return matcher.compare(actual, { error: 'PEBCAK' }).then(function(result) { expect(result).toEqual(jasmine.objectContaining({ pass: true })); }); }); - it('should fail if the promise resolves', function () { + it('should fail if the promise resolves', function() { jasmine.getEnv().requirePromises(); var matchersUtil = new jasmineUnderTest.MatchersUtil(), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = Promise.resolve(); - return matcher.compare(actual, '').then(function (result) { + return matcher.compare(actual, '').then(function(result) { expect(result).toEqual(jasmine.objectContaining({ pass: false })); }); }); - it('should fail if the promise is rejected with a different value', function () { + it('should fail if the promise is rejected with a different value', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = Promise.reject('A Bad Apple'); - return matcher.compare(actual, 'Some Cool Thing').then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: false, - message: "Expected a promise to be rejected with 'Some Cool Thing' but it was rejected with 'A Bad Apple'.", - })); + return matcher.compare(actual, 'Some Cool Thing').then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: false, + message: + "Expected a promise to be rejected with 'Some Cool Thing' but it was rejected with 'A Bad Apple'." + }) + ); }); }); - it('should build its error correctly when negated', function () { + it('should build its error correctly when negated', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = Promise.reject(true); - return matcher.compare(actual, true).then(function (result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: true, - message: 'Expected a promise not to be rejected with true.' - })); + return matcher.compare(actual, true).then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: true, + message: 'Expected a promise not to be rejected with true.' + }) + ); }); }); - it('should support custom equality testers', function () { + it('should support custom equality testers', function() { jasmine.getEnv().requirePromises(); - var customEqualityTesters = [function() { return true; }], - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: customEqualityTesters}), + var customEqualityTesters = [ + function() { + return true; + } + ], + matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: customEqualityTesters + }), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = Promise.reject('actual'); return matcher.compare(actual, 'expected').then(function(result) { - expect(result).toEqual(jasmine.objectContaining({pass: true})); + expect(result).toEqual(jasmine.objectContaining({ pass: true })); }); }); it('fails if actual is not a promise', function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.asyncMatchers.toBeRejectedWith(matchersUtil), actual = 'not a promise'; diff --git a/spec/core/matchers/async/toBeResolvedSpec.js b/spec/core/matchers/async/toBeResolvedSpec.js index 8dbff1c9..668b1bb3 100644 --- a/spec/core/matchers/async/toBeResolvedSpec.js +++ b/spec/core/matchers/async/toBeResolvedSpec.js @@ -8,7 +8,7 @@ describe('toBeResolved', function() { actual = Promise.resolve(); return matcher.compare(actual).then(function(result) { - expect(result).toEqual(jasmine.objectContaining({pass: true})); + expect(result).toEqual(jasmine.objectContaining({ pass: true })); }); }); @@ -20,7 +20,7 @@ describe('toBeResolved', function() { actual = Promise.reject('AsyncExpectationSpec rejection'); return matcher.compare(actual).then(function(result) { - expect(result).toEqual(jasmine.objectContaining({pass: false})); + expect(result).toEqual(jasmine.objectContaining({ pass: false })); }); }); @@ -33,8 +33,6 @@ describe('toBeResolved', function() { return matcher.compare(actual); } - expect(f).toThrowError( - 'Expected toBeResolved to be called on a promise.' - ); + expect(f).toThrowError('Expected toBeResolved to be called on a promise.'); }); }); diff --git a/spec/core/matchers/async/toBeResolvedToSpec.js b/spec/core/matchers/async/toBeResolvedToSpec.js index ee57abe1..459e93ac 100644 --- a/spec/core/matchers/async/toBeResolvedToSpec.js +++ b/spec/core/matchers/async/toBeResolvedToSpec.js @@ -5,62 +5,80 @@ describe('#toBeResolvedTo', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), - actual = Promise.resolve({foo: 42}); + actual = Promise.resolve({ foo: 42 }); - return matcher.compare(actual, {foo: 42}).then(function(result) { - expect(result).toEqual(jasmine.objectContaining({pass: true})); + return matcher.compare(actual, { foo: 42 }).then(function(result) { + expect(result).toEqual(jasmine.objectContaining({ pass: true })); }); }); it('fails if the promise is rejected', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.reject('AsyncExpectationSpec error'); return matcher.compare(actual, '').then(function(result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: false, - message: "Expected a promise to be resolved to '' but it was rejected.", - })); + expect(result).toEqual( + jasmine.objectContaining({ + pass: false, + message: + "Expected a promise to be resolved to '' but it was rejected." + }) + ); }); }); it('fails if the promise is resolved to a different value', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), - actual = Promise.resolve({foo: 17}); + actual = Promise.resolve({ foo: 17 }); - return matcher.compare(actual, {foo: 42}).then(function(result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: false, - message: 'Expected a promise to be resolved to Object({ foo: 42 }) but it was resolved to Object({ foo: 17 }).', - })); + return matcher.compare(actual, { foo: 42 }).then(function(result) { + expect(result).toEqual( + jasmine.objectContaining({ + pass: false, + message: + 'Expected a promise to be resolved to Object({ foo: 42 }) but it was resolved to Object({ foo: 17 }).' + }) + ); }); }); it('builds its message correctly when negated', function() { jasmine.getEnv().requirePromises(); - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = Promise.resolve(true); return matcher.compare(actual, true).then(function(result) { - expect(result).toEqual(jasmine.objectContaining({ - pass: true, - message: 'Expected a promise not to be resolved to true.' - })); + expect(result).toEqual( + jasmine.objectContaining({ + pass: true, + message: 'Expected a promise not to be resolved to true.' + }) + ); }); }); it('supports custom equality testers', function() { jasmine.getEnv().requirePromises(); - var customEqualityTesters = [function() { return true; }], + var customEqualityTesters = [ + function() { + return true; + } + ], matchersUtil = new jasmineUnderTest.MatchersUtil({ customTesters: customEqualityTesters, pp: jasmineUnderTest.makePrettyPrinter() @@ -69,12 +87,14 @@ describe('#toBeResolvedTo', function() { actual = Promise.resolve('actual'); return matcher.compare(actual, 'expected').then(function(result) { - expect(result).toEqual(jasmine.objectContaining({pass: true})); + expect(result).toEqual(jasmine.objectContaining({ pass: true })); }); }); it('fails if actual is not a promise', function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.asyncMatchers.toBeResolvedTo(matchersUtil), actual = 'not a promise'; diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index 387aa3e2..ed03f38e 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -1,12 +1,12 @@ -describe("matchersUtil", function() { - it("exposes the injected pretty-printer as .pp", function() { +describe('matchersUtil', function() { + it('exposes the injected pretty-printer as .pp', function() { var pp = function() {}, - matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}); + matchersUtil = new jasmineUnderTest.MatchersUtil({ pp: pp }); expect(matchersUtil.pp).toBe(pp); }); - describe("equals", function() { + describe('equals', function() { describe('Properties', function() { var fc; @@ -79,79 +79,85 @@ describe("matchersUtil", function() { }); }); - it("passes for literals that are triple-equal", function() { + it('passes for literals that are triple-equal', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(null, null)).toBe(true); expect(matchersUtil.equals(void 0, void 0)).toBe(true); }); - it("fails for things that are not equivalent", function() { + it('fails for things that are not equivalent', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals({a: "foo"}, 1)).toBe(false); + expect(matchersUtil.equals({ a: 'foo' }, 1)).toBe(false); }); - it("passes for Strings that are equivalent", function() { + it('passes for Strings that are equivalent', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals("foo", "foo")).toBe(true); + expect(matchersUtil.equals('foo', 'foo')).toBe(true); }); - it("fails for Strings that are not equivalent", function() { + it('fails for Strings that are not equivalent', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals("foo", "bar")).toBe(false); + expect(matchersUtil.equals('foo', 'bar')).toBe(false); }); - it("passes for Numbers that are equivalent", function() { + it('passes for Numbers that are equivalent', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(123, 123)).toBe(true); }); - it("fails for Numbers that are not equivalent", function() { + it('fails for Numbers that are not equivalent', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(123, 456)).toBe(false); }); - it("fails for a Number and a String that have equivalent values", function() { + it('fails for a Number and a String that have equivalent values', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals(123, "123")).toBe(false); + expect(matchersUtil.equals(123, '123')).toBe(false); }); - it("passes for Dates that are equivalent", function() { + it('passes for Dates that are equivalent', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals(new Date("Jan 1, 1970"), new Date("Jan 1, 1970"))).toBe(true); + expect( + matchersUtil.equals(new Date('Jan 1, 1970'), new Date('Jan 1, 1970')) + ).toBe(true); }); - it("fails for Dates that are not equivalent", function() { + it('fails for Dates that are not equivalent', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals(new Date("Jan 1, 1970"), new Date("Feb 3, 1991"))).toBe(false); + expect( + matchersUtil.equals(new Date('Jan 1, 1970'), new Date('Feb 3, 1991')) + ).toBe(false); }); - it("passes for Booleans that are equivalent", function() { + it('passes for Booleans that are equivalent', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(true, true)).toBe(true); }); - it("fails for Booleans that are not equivalent", function() { + it('fails for Booleans that are not equivalent', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(true, false)).toBe(false); }); - it("passes for RegExps that are equivalent", function() { + it('passes for RegExps that are equivalent', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(/foo/, /foo/)).toBe(true); }); - it("fails for RegExps that are not equivalent", function() { + it('fails for RegExps that are not equivalent', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(/foo/, /bar/)).toBe(false); - expect(matchersUtil.equals(new RegExp("foo", "i"), new RegExp("foo"))).toBe(false); + expect( + matchersUtil.equals(new RegExp('foo', 'i'), new RegExp('foo')) + ).toBe(false); }); - it("passes for Arrays that are equivalent", function() { + it('passes for Arrays that are equivalent', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals([1, 2], [1, 2])).toBe(true); }); - it("passes for Arrays that are equivalent, with elements added by changing length", function() { + it('passes for Arrays that are equivalent, with elements added by changing length', function() { var foo = [], matchersUtil = new jasmineUnderTest.MatchersUtil(); foo.length = 1; @@ -159,19 +165,19 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(foo, [undefined])).toBe(true); }); - it("fails for Arrays that have different lengths", function() { + it('fails for Arrays that have different lengths', function() { matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals([1, 2], [1, 2, 3])).toBe(false); }); - it("fails for Arrays that have different elements", function() { + it('fails for Arrays that have different elements', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals([1, 2, 3], [1, 5, 3])).toBe(false); }); - it("fails for Arrays whose contents are equivalent, but have differing properties", function() { - var one = [1,2,3], - two = [1,2,3], + it('fails for Arrays whose contents are equivalent, but have differing properties', function() { + var one = [1, 2, 3], + two = [1, 2, 3], matchersUtil = new jasmineUnderTest.MatchersUtil(); one.foo = 'bar'; @@ -180,9 +186,9 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(one, two)).toBe(false); }); - it("passes for Arrays with equivalent contents and properties", function() { - var one = [1,2,3], - two = [1,2,3], + it('passes for Arrays with equivalent contents and properties', function() { + var one = [1, 2, 3], + two = [1, 2, 3], matchersUtil = new jasmineUnderTest.MatchersUtil(); one.foo = 'bar'; @@ -191,17 +197,21 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(one, two)).toBe(true); }); - it("passes for Errors that are the same type and have the same message", function() { + it('passes for Errors that are the same type and have the same message', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals(new Error("foo"), new Error("foo"))).toBe(true); + expect(matchersUtil.equals(new Error('foo'), new Error('foo'))).toBe( + true + ); }); - it("fails for Errors that are the same type and have different messages", function() { + it('fails for Errors that are the same type and have different messages', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals(new Error("foo"), new Error("bar"))).toBe(false); + expect(matchersUtil.equals(new Error('foo'), new Error('bar'))).toBe( + false + ); }); - it("fails for objects with different constructors", function() { + it('fails for objects with different constructors', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); function One() {} function Two() {} @@ -209,29 +219,39 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(new One(), new Two())).toBe(false); }); - it("passes for Objects that are equivalent (simple case)", function() { + it('passes for Objects that are equivalent (simple case)', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals({a: "foo"}, {a: "foo"})).toBe(true); + expect(matchersUtil.equals({ a: 'foo' }, { a: 'foo' })).toBe(true); }); - it("fails for Objects that are not equivalent (simple case)", function() { + it('fails for Objects that are not equivalent (simple case)', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals({a: "foo"}, {a: "bar"})).toBe(false); + expect(matchersUtil.equals({ a: 'foo' }, { a: 'bar' })).toBe(false); }); - it("passes for Objects that are equivalent (deep case)", function() { + it('passes for Objects that are equivalent (deep case)', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals({a: "foo", b: { c: "bar"}}, {a: "foo", b: { c: "bar"}})).toBe(true); + expect( + matchersUtil.equals( + { a: 'foo', b: { c: 'bar' } }, + { a: 'foo', b: { c: 'bar' } } + ) + ).toBe(true); }); - it("fails for Objects that are not equivalent (deep case)", function() { + it('fails for Objects that are not equivalent (deep case)', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals({a: "foo", b: { c: "baz"}}, {a: "foo", b: { c: "bar"}})).toBe(false); + expect( + matchersUtil.equals( + { a: 'foo', b: { c: 'baz' } }, + { a: 'foo', b: { c: 'bar' } } + ) + ).toBe(false); }); - it("passes for Objects that are equivalent (with cycles)", function() { - var actual = { a: "foo" }, - expected = { a: "foo" }, + it('passes for Objects that are equivalent (with cycles)', function() { + var actual = { a: 'foo' }, + expected = { a: 'foo' }, matchersUtil = new jasmineUnderTest.MatchersUtil(); actual.b = actual; @@ -240,9 +260,9 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(actual, expected)).toBe(true); }); - it("fails for Objects that are not equivalent (with cycles)", function() { - var actual = { a: "foo" }, - expected = { a: "bar" }, + it('fails for Objects that are not equivalent (with cycles)', function() { + var actual = { a: 'foo' }, + expected = { a: 'bar' }, matchersUtil = new jasmineUnderTest.MatchersUtil(); actual.b = actual; @@ -251,7 +271,7 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(actual, expected)).toBe(false); }); - it("fails for Objects that have the same number of keys, but different keys/values", function () { + it('fails for Objects that have the same number of keys, but different keys/values', function() { var expected = { a: undefined }, actual = { b: 1 }, matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -259,61 +279,62 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(actual, expected)).toBe(false); }); - it("fails when comparing an empty object to an empty array (issue #114)", function() { + it('fails when comparing an empty object to an empty array (issue #114)', function() { var emptyObject = {}, emptyArray = [], matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals(emptyObject, emptyArray)).toBe(false); expect(matchersUtil.equals(emptyArray, emptyObject)).toBe(false); }); - it("passes for equivalent frozen objects (GitHub issue #266)", function() { + it('passes for equivalent frozen objects (GitHub issue #266)', function() { var a = { foo: 1 }, - b = {foo: 1 }, + b = { foo: 1 }, matchersUtil = new jasmineUnderTest.MatchersUtil(); Object.freeze(a); Object.freeze(b); - expect(matchersUtil.equals(a,b)).toBe(true); + expect(matchersUtil.equals(a, b)).toBe(true); }); - it("passes for equivalent Promises (GitHub issue #1314)", function() { - if (typeof Promise === 'undefined') { return; } + it('passes for equivalent Promises (GitHub issue #1314)', function() { + if (typeof Promise === 'undefined') { + return; + } - var p1 = new Promise(function () {}), // eslint-disable-line compat/compat - p2 = new Promise(function () {}), // eslint-disable-line compat/compat + var p1 = new Promise(function() {}), // eslint-disable-line compat/compat + p2 = new Promise(function() {}), // eslint-disable-line compat/compat matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(p1, p1)).toBe(true); expect(matchersUtil.equals(p1, p2)).toBe(false); }); - describe("when running in a browser", function() { + describe('when running in a browser', function() { function isNotRunningInBrowser() { - return typeof document === 'undefined' + return typeof document === 'undefined'; } - it("passes for equivalent DOM nodes", function() { + it('passes for equivalent DOM nodes', function() { if (isNotRunningInBrowser()) { return; } - var a = document.createElement("div"); + var a = document.createElement('div'); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - a.setAttribute("test-attr", "attr-value"); + a.setAttribute('test-attr', 'attr-value'); a.appendChild(document.createTextNode('test')); - var b = document.createElement("div"); - b.setAttribute("test-attr", "attr-value"); + var b = document.createElement('div'); + b.setAttribute('test-attr', 'attr-value'); b.appendChild(document.createTextNode('test')); - expect(matchersUtil.equals(a,b)).toBe(true); + expect(matchersUtil.equals(a, b)).toBe(true); }); - it("passes for equivalent objects from different frames", function() { + it('passes for equivalent objects from different frames', function() { if (isNotRunningInBrowser()) { return; } @@ -321,42 +342,44 @@ describe("matchersUtil", function() { var iframe = document.createElement('iframe'); document.body.appendChild(iframe); iframe.contentWindow.eval('window.testObject = {}'); - expect(matchersUtil.equals({}, iframe.contentWindow.testObject)).toBe(true); + expect(matchersUtil.equals({}, iframe.contentWindow.testObject)).toBe( + true + ); document.body.removeChild(iframe); }); - it("fails for DOM nodes with different attributes or child nodes", function() { + it('fails for DOM nodes with different attributes or child nodes', function() { if (isNotRunningInBrowser()) { return; } var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var a = document.createElement("div"); - a.setAttribute("test-attr", "attr-value"); + var a = document.createElement('div'); + a.setAttribute('test-attr', 'attr-value'); a.appendChild(document.createTextNode('test')); - var b = document.createElement("div"); - b.setAttribute("test-attr", "attr-value2"); + var b = document.createElement('div'); + b.setAttribute('test-attr', 'attr-value2'); b.appendChild(document.createTextNode('test')); - expect(matchersUtil.equals(a,b)).toBe(false); + expect(matchersUtil.equals(a, b)).toBe(false); - b.setAttribute("test-attr", "attr-value"); - expect(matchersUtil.equals(a,b)).toBe(true); + b.setAttribute('test-attr', 'attr-value'); + expect(matchersUtil.equals(a, b)).toBe(true); b.appendChild(document.createTextNode('2')); - expect(matchersUtil.equals(a,b)).toBe(false); + expect(matchersUtil.equals(a, b)).toBe(false); a.appendChild(document.createTextNode('2')); - expect(matchersUtil.equals(a,b)).toBe(true); + expect(matchersUtil.equals(a, b)).toBe(true); }); }); - describe("when running in Node", function() { + describe('when running in Node', function() { function isNotRunningInNode() { - return typeof require !== 'function' + return typeof require !== 'function'; } - it("passes for equivalent objects from different vm contexts", function() { + it('passes for equivalent objects from different vm contexts', function() { if (isNotRunningInNode()) { return; } @@ -367,10 +390,10 @@ describe("matchersUtil", function() { }; vm.runInNewContext('obj = {a: 1, b: 2}', sandbox); - expect(matchersUtil.equals(sandbox.obj, {a: 1, b: 2})).toBe(true); + expect(matchersUtil.equals(sandbox.obj, { a: 1, b: 2 })).toBe(true); }); - it("passes for equivalent arrays from different vm contexts", function() { + it('passes for equivalent arrays from different vm contexts', function() { if (isNotRunningInNode()) { return; } @@ -385,7 +408,7 @@ describe("matchersUtil", function() { }); }); - it("passes when Any is used", function() { + it('passes when Any is used', function() { var number = 3, anyNumber = new jasmineUnderTest.Any(Number), matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -394,7 +417,7 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(anyNumber, number)).toBe(true); }); - it("fails when Any is compared to something unexpected", function() { + it('fails when Any is compared to something unexpected', function() { var number = 3, anyString = new jasmineUnderTest.Any(String), matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -403,19 +426,19 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(anyString, number)).toBe(false); }); - it("passes when ObjectContaining is used", function() { + it('passes when ObjectContaining is used', function() { var obj = { - foo: 3, - bar: 7 - }, - containing = new jasmineUnderTest.ObjectContaining({foo: 3}), + foo: 3, + bar: 7 + }, + containing = new jasmineUnderTest.ObjectContaining({ foo: 3 }), matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(obj, containing)).toBe(true); expect(matchersUtil.equals(containing, obj)).toBe(true); }); - it("passes when MapContaining is used", function() { + it('passes when MapContaining is used', function() { jasmine.getEnv().requireFunctioningMaps(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -429,7 +452,7 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(containing, obj)).toBe(true); }); - it("passes when SetContaining is used", function() { + it('passes when SetContaining is used', function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -443,107 +466,159 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(containing, obj)).toBe(true); }); - it("passes when an asymmetric equality tester returns true", function() { - var tester = { asymmetricMatch: function(other) { return true; } }, + it('passes when an asymmetric equality tester returns true', function() { + var tester = { + asymmetricMatch: function(other) { + return true; + } + }, matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(false, tester)).toBe(true); expect(matchersUtil.equals(tester, false)).toBe(true); }); - it("fails when an asymmetric equality tester returns false", function() { - var tester = { asymmetricMatch: function(other) { return false; } }, + it('fails when an asymmetric equality tester returns false', function() { + var tester = { + asymmetricMatch: function(other) { + return false; + } + }, matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(true, tester)).toBe(false); expect(matchersUtil.equals(tester, true)).toBe(false); }); - it("passes when ArrayContaining is used", function() { - var arr = ["foo", "bar"], + it('passes when ArrayContaining is used', function() { + var arr = ['foo', 'bar'], matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals(arr, new jasmineUnderTest.ArrayContaining(["bar"]))).toBe(true); + expect( + matchersUtil.equals(arr, new jasmineUnderTest.ArrayContaining(['bar'])) + ).toBe(true); }); - it("passes when a custom equality matcher passed to equals returns true", function() { + it('passes when a custom equality matcher passed to equals returns true', function() { // TODO: remove this in the next major release. - var tester = function(a, b) { return true; }, + var tester = function(a, b) { + return true; + }, matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(1, 2, [tester])).toBe(true); }); - it("passes when a custom equality matcher passed to the constructor returns true", function() { - var tester = function(a, b) { return true; }, - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester], pp: function() {}}); + it('passes when a custom equality matcher passed to the constructor returns true', function() { + var tester = function(a, b) { + return true; + }, + matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [tester], + pp: function() {} + }); expect(matchersUtil.equals(1, 2)).toBe(true); }); - it("passes for two empty Objects", function () { + it('passes for two empty Objects', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals({}, {})).toBe(true); }); - describe("when a custom equality matcher is passed to equals that returns 'undefined'", function () { + describe("when a custom equality matcher is passed to equals that returns 'undefined'", function() { // TODO: remove this in the next major release. - var tester = function(a, b) { return jasmine.undefined; }; + var tester = function(a, b) { + return jasmine.undefined; + }; - it("passes for two empty Objects", function () { + it('passes for two empty Objects', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals({}, {}, [tester])).toBe(true); }); }); - describe("when a custom equality matcher is passed to the constructor that returns 'undefined'", function () { - var tester = function(a, b) { return jasmine.undefined; }; + describe("when a custom equality matcher is passed to the constructor that returns 'undefined'", function() { + var tester = function(a, b) { + return jasmine.undefined; + }; - it("passes for two empty Objects", function () { - var matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester], pp: function() {}}); + it('passes for two empty Objects', function() { + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [tester], + pp: function() {} + }); expect(matchersUtil.equals({}, {})).toBe(true); }); }); - it("fails for equivalents when a custom equality matcher passed to equals returns false", function() { + it('fails for equivalents when a custom equality matcher passed to equals returns false', function() { // TODO: remove this in the next major release. - var tester = function(a, b) { return false; }, + var tester = function(a, b) { + return false; + }, matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(1, 1, [tester])).toBe(false); }); - it("fails for equivalents when a custom equality matcher passed to the constructor returns false", function() { - var tester = function(a, b) { return false; }, - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester], pp: function() {}}); + it('fails for equivalents when a custom equality matcher passed to the constructor returns false', function() { + var tester = function(a, b) { + return false; + }, + matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [tester], + pp: function() {} + }); expect(matchersUtil.equals(1, 1)).toBe(false); }); - it("passes for an asymmetric equality tester that returns true when a custom equality tester passed to equals return false", function() { + it('passes for an asymmetric equality tester that returns true when a custom equality tester passed to equals return false', function() { // TODO: remove this in the next major release. - var asymmetricTester = { asymmetricMatch: function(other) { return true; } }, - symmetricTester = function(a, b) { return false; }, + var asymmetricTester = { + asymmetricMatch: function(other) { + return true; + } + }, + symmetricTester = function(a, b) { + return false; + }, matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.equals(asymmetricTester, true, [symmetricTester])).toBe(true); - expect(matchersUtil.equals(true, asymmetricTester, [symmetricTester])).toBe(true); + expect( + matchersUtil.equals(asymmetricTester, true, [symmetricTester]) + ).toBe(true); + expect( + matchersUtil.equals(true, asymmetricTester, [symmetricTester]) + ).toBe(true); }); - it("passes for an asymmetric equality tester that returns true when a custom equality tester passed to the constructor return false", function() { - var asymmetricTester = { asymmetricMatch: function(other) { return true; } }, - symmetricTester = function(a, b) { return false; }, - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [symmetricTester()], pp: function() {}}); + it('passes for an asymmetric equality tester that returns true when a custom equality tester passed to the constructor return false', function() { + var asymmetricTester = { + asymmetricMatch: function(other) { + return true; + } + }, + symmetricTester = function(a, b) { + return false; + }, + matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [symmetricTester()], + pp: function() {} + }); expect(matchersUtil.equals(asymmetricTester, true)).toBe(true); expect(matchersUtil.equals(true, asymmetricTester)).toBe(true); }); - describe("The compatibility shim passed to asymmetric equality testers", function() { - describe("When equals is called with custom equality testers", function() { - it("is both a matchersUtil and the custom equality testers passed to equals", function() { - var asymmetricTester = jasmine.createSpyObj('tester', ['asymmetricMatch']), - symmetricTester = function() { } , + describe('The compatibility shim passed to asymmetric equality testers', function() { + describe('When equals is called with custom equality testers', function() { + it('is both a matchersUtil and the custom equality testers passed to equals', function() { + var asymmetricTester = jasmine.createSpyObj('tester', [ + 'asymmetricMatch' + ]), + symmetricTester = function() {}, matchersUtil = new jasmineUnderTest.MatchersUtil(), shim; @@ -555,11 +630,16 @@ describe("matchersUtil", function() { }); }); - describe("When equals is called with custom equality testers", function() { - it("is both a matchersUtil and the custom equality testers passed to the constructor", function() { - var asymmetricTester = jasmine.createSpyObj('tester', ['asymmetricMatch']), - symmetricTester = function() { } , - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [symmetricTester], pp: function() {}}), + describe('When equals is called with custom equality testers', function() { + it('is both a matchersUtil and the custom equality testers passed to the constructor', function() { + var asymmetricTester = jasmine.createSpyObj('tester', [ + 'asymmetricMatch' + ]), + symmetricTester = function() {}, + matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [symmetricTester], + pp: function() {} + }), shim; matchersUtil.equals(true, asymmetricTester); @@ -571,7 +651,7 @@ describe("matchersUtil", function() { }); }); - it("passes when an Any is compared to an Any that checks for the same type", function() { + it('passes when an Any is compared to an Any that checks for the same type', function() { var any1 = new jasmineUnderTest.Any(Function), any2 = new jasmineUnderTest.Any(Function), matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -579,7 +659,7 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(any1, any2)).toBe(true); }); - it("passes for null prototype objects with same properties", function () { + it('passes for null prototype objects with same properties', function() { var objA = Object.create(null), objB = Object.create(null), matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -590,7 +670,7 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(objA, objB)).toBe(true); }); - it("fails for null prototype objects with different properties", function () { + it('fails for null prototype objects with different properties', function() { var objA = Object.create(null), objB = Object.create(null), matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -601,13 +681,13 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(objA, objB)).toBe(false); }); - it("passes when comparing two empty sets", function() { + it('passes when comparing two empty sets', function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(new Set(), new Set())).toBe(true); // eslint-disable-line compat/compat }); - it("passes when comparing identical sets", function() { + it('passes when comparing identical sets', function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -621,7 +701,7 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(setA, setB)).toBe(true); }); - it("passes when comparing identical sets with different insertion order and simple elements", function() { + it('passes when comparing identical sets with different insertion order and simple elements', function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); @@ -635,26 +715,26 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(setA, setB)).toBe(true); }); - it("passes when comparing identical sets with different insertion order and complex elements 1", function() { + it('passes when comparing identical sets with different insertion order and complex elements 1', function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); var setA1 = new Set(); // eslint-disable-line compat/compat - setA1.add(['a',3]); - setA1.add([6,1]); + setA1.add(['a', 3]); + setA1.add([6, 1]); var setA2 = new Set(); // eslint-disable-line compat/compat - setA1.add(['y',3]); - setA1.add([6,1]); + setA1.add(['y', 3]); + setA1.add([6, 1]); var setA = new Set(); // eslint-disable-line compat/compat setA.add(setA1); setA.add(setA2); var setB1 = new Set(); // eslint-disable-line compat/compat - setB1.add([6,1]); - setB1.add(['a',3]); + setB1.add([6, 1]); + setB1.add(['a', 3]); var setB2 = new Set(); // eslint-disable-line compat/compat - setB1.add([6,1]); - setB1.add(['y',3]); + setB1.add([6, 1]); + setB1.add(['y', 3]); var setB = new Set(); // eslint-disable-line compat/compat setB.add(setB1); setB.add(setB2); @@ -662,21 +742,21 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(setA, setB)).toBe(true); }); - it("passes when comparing identical sets with different insertion order and complex elements 2", function() { + it('passes when comparing identical sets with different insertion order and complex elements 2', function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); var setA = new Set(); // eslint-disable-line compat/compat - setA.add([[1,2], [3,4]]); - setA.add([[5,6], [7,8]]); + setA.add([[1, 2], [3, 4]]); + setA.add([[5, 6], [7, 8]]); var setB = new Set(); // eslint-disable-line compat/compat - setB.add([[5,6], [7,8]]); - setB.add([[1,2], [3,4]]); + setB.add([[5, 6], [7, 8]]); + setB.add([[1, 2], [3, 4]]); expect(matchersUtil.equals(setA, setB)).toBe(true); }); - it("fails for sets with different elements", function() { + it('fails for sets with different elements', function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); var setA = new Set(); // eslint-disable-line compat/compat @@ -691,7 +771,7 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(setA, setB)).toBe(false); }); - it("fails for sets of different size", function() { + it('fails for sets of different size', function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); var setA = new Set(); // eslint-disable-line compat/compat @@ -705,13 +785,13 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(setA, setB)).toBe(false); }); - it("passes when comparing two empty maps", function() { + it('passes when comparing two empty maps', function() { jasmine.getEnv().requireFunctioningMaps(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.equals(new Map(), new Map())).toBe(true); // eslint-disable-line compat/compat }); - it("passes when comparing identical maps", function() { + it('passes when comparing identical maps', function() { jasmine.getEnv().requireFunctioningMaps(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); var mapA = new Map(); // eslint-disable-line compat/compat @@ -721,19 +801,19 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(mapA, mapB)).toBe(true); }); - it("passes when comparing identical maps with different insertion order", function() { + it('passes when comparing identical maps with different insertion order', function() { jasmine.getEnv().requireFunctioningMaps(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); var mapA = new Map(); // eslint-disable-line compat/compat - mapA.set("a", 3); + mapA.set('a', 3); mapA.set(6, 1); var mapB = new Map(); // eslint-disable-line compat/compat mapB.set(6, 1); - mapB.set("a", 3); + mapB.set('a', 3); expect(matchersUtil.equals(mapA, mapB)).toBe(true); }); - it("fails for maps with different elements", function() { + it('fails for maps with different elements', function() { jasmine.getEnv().requireFunctioningMaps(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); var mapA = new Map(); // eslint-disable-line compat/compat @@ -746,7 +826,7 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(mapA, mapB)).toBe(false); }); - it("fails for maps of different size", function() { + it('fails for maps of different size', function() { jasmine.getEnv().requireFunctioningMaps(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); var mapA = new Map(); // eslint-disable-line compat/compat @@ -757,8 +837,11 @@ describe("matchersUtil", function() { expect(matchersUtil.equals(mapA, mapB)).toBe(false); }); - describe("when running in an environment with array polyfills", function() { - var findIndexDescriptor = Object.getOwnPropertyDescriptor(Array.prototype, 'findIndex'); + describe('when running in an environment with array polyfills', function() { + var findIndexDescriptor = Object.getOwnPropertyDescriptor( + Array.prototype, + 'findIndex' + ); if (!findIndexDescriptor) { return; } @@ -766,9 +849,11 @@ describe("matchersUtil", function() { beforeEach(function() { Object.defineProperty(Array.prototype, 'findIndex', { enumerable: true, - value: function (predicate) { + value: function(predicate) { if (this === null) { - throw new TypeError('Array.prototype.findIndex called on null or undefined'); + throw new TypeError( + 'Array.prototype.findIndex called on null or undefined' + ); } if (typeof predicate !== 'function') { @@ -793,7 +878,11 @@ describe("matchersUtil", function() { }); afterEach(function() { - Object.defineProperty(Array.prototype, 'findIndex', findIndexDescriptor); + Object.defineProperty( + Array.prototype, + 'findIndex', + findIndexDescriptor + ); }); it("passes when there's an array polyfill", function() { @@ -801,10 +890,12 @@ describe("matchersUtil", function() { }); }); - describe("Building diffs for asymmetric equality testers", function() { - it("diffs the values returned by valuesForDiff_", function() { + describe('Building diffs for asymmetric equality testers', function() { + it('diffs the values returned by valuesForDiff_', function() { var tester = { - asymmetricMatch: function() { return false; }, + asymmetricMatch: function() { + return false; + }, valuesForDiff_: function() { return { self: 'asymmetric tester value', @@ -812,30 +903,50 @@ describe("matchersUtil", function() { }; } }, - actual = {x: 42}, - expected = {x: tester}, - diffBuilder = jasmine.createSpyObj('diffBuilder', ['recordMismatch', 'withPath', 'setRoots']); + actual = { x: 42 }, + expected = { x: tester }, + diffBuilder = jasmine.createSpyObj('diffBuilder', [ + 'recordMismatch', + 'withPath', + 'setRoots' + ]); - diffBuilder.withPath.and.callFake(function(p, block) { block(); }); + diffBuilder.withPath.and.callFake(function(p, block) { + block(); + }); jasmineUnderTest.matchersUtil.equals(actual, expected, [], diffBuilder); expect(diffBuilder.setRoots).toHaveBeenCalledWith(actual, expected); - expect(diffBuilder.withPath).toHaveBeenCalledWith('x', jasmine.any(Function)); + expect(diffBuilder.withPath).toHaveBeenCalledWith( + 'x', + jasmine.any(Function) + ); expect(diffBuilder.recordMismatch).toHaveBeenCalledWith(); }); - it("records both objects when the tester does not implement valuesForDiff", function() { + it('records both objects when the tester does not implement valuesForDiff', function() { var tester = { - asymmetricMatch: function() { return false; }, + asymmetricMatch: function() { + return false; + } }, - actual = {x: 42}, - expected = {x: tester}, - diffBuilder = jasmine.createSpyObj('diffBuilder', ['recordMismatch', 'withPath', 'setRoots']); - diffBuilder.withPath.and.callFake(function(p, block) { block(); }); + actual = { x: 42 }, + expected = { x: tester }, + diffBuilder = jasmine.createSpyObj('diffBuilder', [ + 'recordMismatch', + 'withPath', + 'setRoots' + ]); + diffBuilder.withPath.and.callFake(function(p, block) { + block(); + }); jasmineUnderTest.matchersUtil.equals(actual, expected, [], diffBuilder); expect(diffBuilder.setRoots).toHaveBeenCalledWith(actual, expected); - expect(diffBuilder.withPath).toHaveBeenCalledWith('x', jasmine.any(Function)); + expect(diffBuilder.withPath).toHaveBeenCalledWith( + 'x', + jasmine.any(Function) + ); expect(diffBuilder.recordMismatch).toHaveBeenCalledWith(); }); }); @@ -849,8 +960,14 @@ describe("matchersUtil", function() { spyOn(diffBuilder, 'withPath').and.callThrough(); matchersUtil.equals([1], [2], [], diffBuilder); - expect(diffBuilder.withPath).toHaveBeenCalledWith('length', jasmine.any(Function)); - expect(diffBuilder.withPath).toHaveBeenCalledWith(0, jasmine.any(Function)); + expect(diffBuilder.withPath).toHaveBeenCalledWith( + 'length', + jasmine.any(Function) + ); + expect(diffBuilder.withPath).toHaveBeenCalledWith( + 0, + jasmine.any(Function) + ); expect(diffBuilder.recordMismatch).toHaveBeenCalledWith(); }); @@ -862,69 +979,84 @@ describe("matchersUtil", function() { spyOn(diffBuilder, 'withPath').and.callThrough(); matchersUtil.equals([1], [2], diffBuilder); - expect(diffBuilder.withPath).toHaveBeenCalledWith('length', jasmine.any(Function)); - expect(diffBuilder.withPath).toHaveBeenCalledWith(0, jasmine.any(Function)); + expect(diffBuilder.withPath).toHaveBeenCalledWith( + 'length', + jasmine.any(Function) + ); + expect(diffBuilder.withPath).toHaveBeenCalledWith( + 0, + jasmine.any(Function) + ); expect(diffBuilder.recordMismatch).toHaveBeenCalled(); }); }); - describe("contains", function() { - it("passes when expected is a substring of actual", function() { + describe('contains', function() { + it('passes when expected is a substring of actual', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.contains("ABC", "BC")).toBe(true); + expect(matchersUtil.contains('ABC', 'BC')).toBe(true); }); - it("fails when expected is a not substring of actual", function() { + it('fails when expected is a not substring of actual', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.contains("ABC", "X")).toBe(false); + expect(matchersUtil.contains('ABC', 'X')).toBe(false); }); - it("passes when expected is an element in an actual array", function() { + it('passes when expected is an element in an actual array', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.contains(['foo', 'bar'], 'foo')).toBe(true); }); - it("fails when expected is not an element in an actual array", function() { + it('fails when expected is not an element in an actual array', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.contains(['foo', 'bar'], 'baz')).toBe(false); }); - it("passes with mixed-element arrays", function() { + it('passes with mixed-element arrays', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.contains(["foo", {some: "bar"}], "foo")).toBe(true); - expect(matchersUtil.contains(["foo", {some: "bar"}], {some: "bar"})).toBe(true); + expect(matchersUtil.contains(['foo', { some: 'bar' }], 'foo')).toBe(true); + expect( + matchersUtil.contains(['foo', { some: 'bar' }], { some: 'bar' }) + ).toBe(true); }); - it("uses custom equality testers if passed to contains and actual is an Array", function() { + it('uses custom equality testers if passed to contains and actual is an Array', function() { // TODO: remove this in the next major release. - var customTester = function(a, b) {return true;}, + var customTester = function(a, b) { + return true; + }, matchersUtil = new jasmineUnderTest.MatchersUtil(); - expect(matchersUtil.contains([1, 2], 3, [customTester])).toBe(true); + expect(matchersUtil.contains([1, 2], 3, [customTester])).toBe(true); }); - it("uses custom equality testers if passed to the constructor and actual is an Array", function() { - var customTester = function(a, b) {return true;}, - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [customTester], pp: function() {}}); + it('uses custom equality testers if passed to the constructor and actual is an Array', function() { + var customTester = function(a, b) { + return true; + }, + matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [customTester], + pp: function() {} + }); expect(matchersUtil.contains([1, 2], 3)).toBe(true); }); - it("fails when actual is undefined", function() { + it('fails when actual is undefined', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.contains(undefined, 'A')).toBe(false); }); - it("fails when actual is null", function() { + it('fails when actual is null', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(); expect(matchersUtil.contains(null, 'A')).toBe(false); }); - it("passes with array-like objects", function() { + it('passes with array-like objects', function() { var capturedArgs = null, matchersUtil = new jasmineUnderTest.MatchersUtil(); - function testFunction(){ + function testFunction() { capturedArgs = arguments; } @@ -932,11 +1064,11 @@ describe("matchersUtil", function() { expect(matchersUtil.contains(capturedArgs, 'bar')).toBe(true); }); - it("passes for set members", function() { + it('passes for set members', function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); - var setItem = {'foo': 'bar'}; + var setItem = { foo: 'bar' }; var set = new Set(); // eslint-disable-line compat/compat set.add(setItem); @@ -944,61 +1076,78 @@ describe("matchersUtil", function() { }); // documenting current behavior - it("fails (!) for objects that equal to a set member", function() { + it('fails (!) for objects that equal to a set member', function() { jasmine.getEnv().requireFunctioningSets(); var matchersUtil = new jasmineUnderTest.MatchersUtil(); var set = new Set(); // eslint-disable-line compat/compat - set.add({'foo': 'bar'}); + set.add({ foo: 'bar' }); - expect(matchersUtil.contains(set, {'foo': 'bar'})).toBe(false); + expect(matchersUtil.contains(set, { foo: 'bar' })).toBe(false); }); }); - describe("buildFailureMessage", function() { - - it("builds an English sentence for a failure case", function() { - var actual = "foo", - name = "toBar", + describe('buildFailureMessage', function() { + it('builds an English sentence for a failure case', function() { + var actual = 'foo', + name = 'toBar', pp = jasmineUnderTest.makePrettyPrinter(), - matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), + matchersUtil = new jasmineUnderTest.MatchersUtil({ pp: pp }), message = matchersUtil.buildFailureMessage(name, false, actual); expect(message).toEqual("Expected 'foo' to bar."); }); it("builds an English sentence for a 'not' failure case", function() { - var actual = "foo", - name = "toBar", + var actual = 'foo', + name = 'toBar', isNot = true, pp = jasmineUnderTest.makePrettyPrinter(), - matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), - message = message = matchersUtil.buildFailureMessage(name, isNot, actual); + matchersUtil = new jasmineUnderTest.MatchersUtil({ pp: pp }), + message = (message = matchersUtil.buildFailureMessage( + name, + isNot, + actual + )); expect(message).toEqual("Expected 'foo' not to bar."); }); - it("builds an English sentence for an arbitrary array of expected arguments", function() { - var actual = "foo", - name = "toBar", + it('builds an English sentence for an arbitrary array of expected arguments', function() { + var actual = 'foo', + name = 'toBar', pp = jasmineUnderTest.makePrettyPrinter(), - matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), - message = matchersUtil.buildFailureMessage(name, false, actual, "quux", "corge"); + matchersUtil = new jasmineUnderTest.MatchersUtil({ pp: pp }), + message = matchersUtil.buildFailureMessage( + name, + false, + actual, + 'quux', + 'corge' + ); expect(message).toEqual("Expected 'foo' to bar 'quux', 'corge'."); }); - it("uses the injected pretty-printer to format the expecteds and actual", function() { - var actual = "foo", - expected1 = "qux", - expected2 = "grault", - name = "toBar", + it('uses the injected pretty-printer to format the expecteds and actual', function() { + var actual = 'foo', + expected1 = 'qux', + expected2 = 'grault', + name = 'toBar', isNot = false, - pp = function(value) { return '<' + value + '>'; }, - matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), - message = message = matchersUtil.buildFailureMessage(name, isNot, actual, expected1, expected2); + pp = function(value) { + return '<' + value + '>'; + }, + matchersUtil = new jasmineUnderTest.MatchersUtil({ pp: pp }), + message = (message = matchersUtil.buildFailureMessage( + name, + isNot, + actual, + expected1, + expected2 + )); - expect(message).toEqual("Expected to bar , ."); + expect(message).toEqual('Expected to bar , .'); }); }); }); diff --git a/spec/core/matchers/toBeCloseToSpec.js b/spec/core/matchers/toBeCloseToSpec.js index 402ce88e..2594e9ef 100644 --- a/spec/core/matchers/toBeCloseToSpec.js +++ b/spec/core/matchers/toBeCloseToSpec.js @@ -1,5 +1,5 @@ -describe("toBeCloseTo", function() { - it("passes when within two decimal places by default", function() { +describe('toBeCloseTo', function() { + it('passes when within two decimal places by default', function() { var matcher = jasmineUnderTest.matchers.toBeCloseTo(), result; @@ -13,7 +13,7 @@ describe("toBeCloseTo", function() { expect(result.pass).toBe(true); }); - it("fails when not within two decimal places by default", function() { + it('fails when not within two decimal places by default', function() { var matcher = jasmineUnderTest.matchers.toBeCloseTo(), result; @@ -24,7 +24,7 @@ describe("toBeCloseTo", function() { expect(result.pass).toBe(false); }); - it("accepts an optional precision argument", function() { + it('accepts an optional precision argument', function() { var matcher = jasmineUnderTest.matchers.toBeCloseTo(), result; @@ -47,23 +47,29 @@ describe("toBeCloseTo", function() { expect(result.pass).toBe(true); }); - it("fails when one of the arguments is null", function() { + it('fails when one of the arguments is null', function() { var matcher = jasmineUnderTest.matchers.toBeCloseTo(); expect(function() { matcher.compare(null, null); - }).toThrowError('Cannot use toBeCloseTo with null. Arguments evaluated to: expect(null).toBeCloseTo(null).'); + }).toThrowError( + 'Cannot use toBeCloseTo with null. Arguments evaluated to: expect(null).toBeCloseTo(null).' + ); expect(function() { matcher.compare(0, null); - }).toThrowError('Cannot use toBeCloseTo with null. Arguments evaluated to: expect(0).toBeCloseTo(null).'); + }).toThrowError( + 'Cannot use toBeCloseTo with null. Arguments evaluated to: expect(0).toBeCloseTo(null).' + ); expect(function() { matcher.compare(null, 0); - }).toThrowError('Cannot use toBeCloseTo with null. Arguments evaluated to: expect(null).toBeCloseTo(0).'); + }).toThrowError( + 'Cannot use toBeCloseTo with null. Arguments evaluated to: expect(null).toBeCloseTo(0).' + ); }); - it("rounds expected values", function() { + it('rounds expected values', function() { var matcher = jasmineUnderTest.matchers.toBeCloseTo(), result; @@ -91,15 +97,15 @@ describe("toBeCloseTo", function() { expect(result.pass).toBe(true); }); - it("handles edge cases with rounding", function () { + it('handles edge cases with rounding', function() { var matcher = jasmineUnderTest.matchers.toBeCloseTo(), result; - // these cases resulted in false negatives in version of V8 + // these cases resulted in false negatives in version of V8 // included in Node.js 12 and Chrome 74 (and Edge Chromium) result = matcher.compare(4.030904708957288, 4.0309, 5); expect(result.pass).toBe(true); - result = matcher.compare(4.82665525779431,4.82666, 5); + result = matcher.compare(4.82665525779431, 4.82666, 5); expect(result.pass).toBe(true); result = matcher.compare(-2.82665525779431, -2.82666, 5); expect(result.pass).toBe(true); diff --git a/spec/core/matchers/toBeDefinedSpec.js b/spec/core/matchers/toBeDefinedSpec.js index 5649f423..4b89c9ac 100644 --- a/spec/core/matchers/toBeDefinedSpec.js +++ b/spec/core/matchers/toBeDefinedSpec.js @@ -1,18 +1,17 @@ -describe("toBeDefined", function() { - it("matches for defined values", function() { +describe('toBeDefined', function() { + it('matches for defined values', function() { var matcher = jasmineUnderTest.matchers.toBeDefined(), result; - result = matcher.compare('foo'); expect(result.pass).toBe(true); }); - it("fails when matching undefined values", function() { + it('fails when matching undefined values', function() { var matcher = jasmineUnderTest.matchers.toBeDefined(), result; result = matcher.compare(void 0); expect(result.pass).toBe(false); - }) + }); }); diff --git a/spec/core/matchers/toBeFalseSpec.js b/spec/core/matchers/toBeFalseSpec.js index 7c0900e6..47e2b389 100644 --- a/spec/core/matchers/toBeFalseSpec.js +++ b/spec/core/matchers/toBeFalseSpec.js @@ -1,5 +1,5 @@ -describe("toBeFalse", function() { - it("passes for false", function() { +describe('toBeFalse', function() { + it('passes for false', function() { var matcher = jasmineUnderTest.matchers.toBeFalse(), result; @@ -7,7 +7,7 @@ describe("toBeFalse", function() { expect(result.pass).toBe(true); }); - it("fails for non-false", function() { + it('fails for non-false', function() { var matcher = jasmineUnderTest.matchers.toBeFalse(), result; @@ -15,7 +15,7 @@ describe("toBeFalse", function() { expect(result.pass).toBe(false); }); - it("fails for falsy", function() { + it('fails for falsy', function() { var matcher = jasmineUnderTest.matchers.toBeFalse(), result; diff --git a/spec/core/matchers/toBeFalsySpec.js b/spec/core/matchers/toBeFalsySpec.js index 2099234f..ec4a98e4 100644 --- a/spec/core/matchers/toBeFalsySpec.js +++ b/spec/core/matchers/toBeFalsySpec.js @@ -1,4 +1,4 @@ -describe("toBeFalsy", function() { +describe('toBeFalsy', function() { it("passes for 'falsy' values", function() { var matcher = jasmineUnderTest.matchers.toBeFalsy(), result; @@ -29,7 +29,7 @@ describe("toBeFalsy", function() { result = matcher.compare(1); expect(result.pass).toBe(false); - result = matcher.compare("foo"); + result = matcher.compare('foo'); expect(result.pass).toBe(false); result = matcher.compare({}); diff --git a/spec/core/matchers/toBeGreaterThanOrEqualSpec.js b/spec/core/matchers/toBeGreaterThanOrEqualSpec.js index 81817c15..444cd317 100644 --- a/spec/core/matchers/toBeGreaterThanOrEqualSpec.js +++ b/spec/core/matchers/toBeGreaterThanOrEqualSpec.js @@ -1,5 +1,5 @@ -describe("toBeGreaterThanOrEqual", function() { - it("passes when actual >= expected", function() { +describe('toBeGreaterThanOrEqual', function() { + it('passes when actual >= expected', function() { var matcher = jasmineUnderTest.matchers.toBeGreaterThanOrEqual(), result; @@ -16,7 +16,7 @@ describe("toBeGreaterThanOrEqual", function() { expect(result.pass).toBe(true); }); - it("fails when actual < expected", function() { + it('fails when actual < expected', function() { var matcher = jasmineUnderTest.matchers.toBeGreaterThanOrEqual(), result; @@ -25,5 +25,5 @@ describe("toBeGreaterThanOrEqual", function() { result = matcher.compare(1, 1.0000001); expect(result.pass).toBe(false); - }) + }); }); diff --git a/spec/core/matchers/toBeGreaterThanSpec.js b/spec/core/matchers/toBeGreaterThanSpec.js index 75b92824..f157e524 100644 --- a/spec/core/matchers/toBeGreaterThanSpec.js +++ b/spec/core/matchers/toBeGreaterThanSpec.js @@ -1,5 +1,5 @@ -describe("toBeGreaterThan", function() { - it("passes when actual > expected", function() { +describe('toBeGreaterThan', function() { + it('passes when actual > expected', function() { var matcher = jasmineUnderTest.matchers.toBeGreaterThan(), result; @@ -7,7 +7,7 @@ describe("toBeGreaterThan", function() { expect(result.pass).toBe(true); }); - it("fails when actual <= expected", function() { + it('fails when actual <= expected', function() { var matcher = jasmineUnderTest.matchers.toBeGreaterThan(), result; diff --git a/spec/core/matchers/toBeInstanceOfSpec.js b/spec/core/matchers/toBeInstanceOfSpec.js index d8355af7..f63ec842 100644 --- a/spec/core/matchers/toBeInstanceOfSpec.js +++ b/spec/core/matchers/toBeInstanceOfSpec.js @@ -92,13 +92,14 @@ describe('toBeInstanceOf', function() { describe('when expecting Function', function() { it('passes for a function', function() { - var fn = function() { }; + var fn = function() {}; var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); var result = matcher.compare(fn, Function); expect(result).toEqual({ pass: true, - message: 'Expected instance of Function not to be an instance of Function' + message: + 'Expected instance of Function not to be an instance of Function' }); }); @@ -111,13 +112,14 @@ describe('toBeInstanceOf', function() { var result = matcher.compare(fn, Function); expect(result).toEqual({ pass: true, - message: 'Expected instance of AsyncFunction not to be an instance of Function' + message: + 'Expected instance of AsyncFunction not to be an instance of Function' }); }); }); describe('when expecting Object', function() { - function Animal() { } + function Animal() {} it('passes for any object', function() { var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); @@ -164,14 +166,15 @@ describe('toBeInstanceOf', function() { var result = matcher.compare(object, Object); expect(result).toEqual({ pass: true, - message: 'Expected instance of null({ }) not to be an instance of Object' + message: + 'Expected instance of null({ }) not to be an instance of Object' }); }); }); describe('when expecting a user-defined class', function() { // Base class - function Animal() { } + function Animal() {} // Subclasses, defined using syntax that is as old as possible function Dog() { @@ -218,8 +221,10 @@ describe('toBeInstanceOf', function() { var matcher = jasmineUnderTest.matchers.toBeInstanceOf(); expect(function() { matcher.compare({}, 'Error'); - }).toThrowError(' : Expected value is not a constructor function\n' + - 'Usage: expect(value).toBeInstanceOf()'); + }).toThrowError( + ' : Expected value is not a constructor function\n' + + 'Usage: expect(value).toBeInstanceOf()' + ); }); it('raises an error if missing an expected value', function() { @@ -228,7 +233,9 @@ describe('toBeInstanceOf', function() { }); expect(function() { matcher.compare({}, undefined); - }).toThrowError(' : Expected value is not a constructor function\n' + - 'Usage: expect(value).toBeInstanceOf()'); + }).toThrowError( + ' : Expected value is not a constructor function\n' + + 'Usage: expect(value).toBeInstanceOf()' + ); }); }); diff --git a/spec/core/matchers/toBeLessThanOrEqualSpec.js b/spec/core/matchers/toBeLessThanOrEqualSpec.js index 20d36e89..0aa7940b 100644 --- a/spec/core/matchers/toBeLessThanOrEqualSpec.js +++ b/spec/core/matchers/toBeLessThanOrEqualSpec.js @@ -1,5 +1,5 @@ -describe("toBeLessThanOrEqual", function() { - it("passes when actual <= expected", function() { +describe('toBeLessThanOrEqual', function() { + it('passes when actual <= expected', function() { var matcher = jasmineUnderTest.matchers.toBeLessThanOrEqual(), result; @@ -11,12 +11,12 @@ describe("toBeLessThanOrEqual", function() { result = matcher.compare(1, 1.0000001); expect(result.pass).toBe(true); - + result = matcher.compare(1.0, 1.0); expect(result.pass).toBe(true); }); - it("fails when actual < expected", function() { + it('fails when actual < expected', function() { var matcher = jasmineUnderTest.matchers.toBeLessThanOrEqual(), result; diff --git a/spec/core/matchers/toBeLessThanSpec.js b/spec/core/matchers/toBeLessThanSpec.js index 55868ec5..24a1d9af 100644 --- a/spec/core/matchers/toBeLessThanSpec.js +++ b/spec/core/matchers/toBeLessThanSpec.js @@ -1,5 +1,5 @@ -describe("toBeLessThan", function() { - it("passes when actual < expected", function() { +describe('toBeLessThan', function() { + it('passes when actual < expected', function() { var matcher = jasmineUnderTest.matchers.toBeLessThan(), result; @@ -7,7 +7,7 @@ describe("toBeLessThan", function() { expect(result.pass).toBe(true); }); - it("fails when actual <= expected", function() { + it('fails when actual <= expected', function() { var matcher = jasmineUnderTest.matchers.toBeLessThan(), result; diff --git a/spec/core/matchers/toBeNaNSpec.js b/spec/core/matchers/toBeNaNSpec.js index e859f64f..d38ffed7 100644 --- a/spec/core/matchers/toBeNaNSpec.js +++ b/spec/core/matchers/toBeNaNSpec.js @@ -1,14 +1,14 @@ -describe("toBeNaN", function() { - it("passes for NaN with a custom .not fail", function() { +describe('toBeNaN', function() { + it('passes for NaN with a custom .not fail', function() { var matcher = jasmineUnderTest.matchers.toBeNaN(), result; result = matcher.compare(Number.NaN); expect(result.pass).toBe(true); - expect(result.message).toEqual("Expected actual not to be NaN."); + expect(result.message).toEqual('Expected actual not to be NaN.'); }); - it("fails for anything not a NaN", function() { + it('fails for anything not a NaN', function() { var matcher = jasmineUnderTest.matchers.toBeNaN(), result; @@ -28,12 +28,12 @@ describe("toBeNaN", function() { expect(result.pass).toBe(false); }); - it("has a custom message on failure", function() { + it('has a custom message on failure', function() { var matcher = jasmineUnderTest.matchers.toBeNaN({ pp: jasmineUnderTest.makePrettyPrinter() }), result = matcher.compare(0); - expect(result.message()).toEqual("Expected 0 to be NaN."); + expect(result.message()).toEqual('Expected 0 to be NaN.'); }); }); diff --git a/spec/core/matchers/toBeNegativeInfinitySpec.js b/spec/core/matchers/toBeNegativeInfinitySpec.js index 876bf209..d771378f 100644 --- a/spec/core/matchers/toBeNegativeInfinitySpec.js +++ b/spec/core/matchers/toBeNegativeInfinitySpec.js @@ -1,4 +1,4 @@ -describe("toBeNegativeInfinity", function() { +describe('toBeNegativeInfinity', function() { it("fails for anything that isn't -Infinity", function() { var matcher = jasmineUnderTest.matchers.toBeNegativeInfinity(), result; @@ -13,21 +13,20 @@ describe("toBeNegativeInfinity", function() { expect(result.pass).toBe(false); }); - it("has a custom message on failure", function() { + it('has a custom message on failure', function() { var matcher = jasmineUnderTest.matchers.toBeNegativeInfinity({ pp: jasmineUnderTest.makePrettyPrinter() }), result = matcher.compare(0); - expect(result.message()).toEqual("Expected 0 to be -Infinity.") + expect(result.message()).toEqual('Expected 0 to be -Infinity.'); }); - it("succeeds for -Infinity", function() { + it('succeeds for -Infinity', function() { var matcher = jasmineUnderTest.matchers.toBeNegativeInfinity(), result = matcher.compare(Number.NEGATIVE_INFINITY); expect(result.pass).toBe(true); - expect(result.message).toEqual("Expected actual not to be -Infinity.") + expect(result.message).toEqual('Expected actual not to be -Infinity.'); }); - }); diff --git a/spec/core/matchers/toBeNullSpec.js b/spec/core/matchers/toBeNullSpec.js index 35dfe8d1..da5c2856 100644 --- a/spec/core/matchers/toBeNullSpec.js +++ b/spec/core/matchers/toBeNullSpec.js @@ -1,5 +1,5 @@ -describe("toBeNull", function() { - it("passes for null", function() { +describe('toBeNull', function() { + it('passes for null', function() { var matcher = jasmineUnderTest.matchers.toBeNull(), result; @@ -7,7 +7,7 @@ describe("toBeNull", function() { expect(result.pass).toBe(true); }); - it("fails for non-null", function() { + it('fails for non-null', function() { var matcher = jasmineUnderTest.matchers.toBeNull(), result; diff --git a/spec/core/matchers/toBePositiveInfinitySpec.js b/spec/core/matchers/toBePositiveInfinitySpec.js index 6fc91b65..3673fb69 100644 --- a/spec/core/matchers/toBePositiveInfinitySpec.js +++ b/spec/core/matchers/toBePositiveInfinitySpec.js @@ -1,4 +1,4 @@ -describe("toBePositiveInfinity", function() { +describe('toBePositiveInfinity', function() { it("fails for anything that isn't Infinity", function() { var matcher = jasmineUnderTest.matchers.toBePositiveInfinity(), result; @@ -13,21 +13,20 @@ describe("toBePositiveInfinity", function() { expect(result.pass).toBe(false); }); - it("has a custom message on failure", function() { + it('has a custom message on failure', function() { var matcher = jasmineUnderTest.matchers.toBePositiveInfinity({ pp: jasmineUnderTest.makePrettyPrinter() }), result = matcher.compare(0); - expect(result.message()).toEqual("Expected 0 to be Infinity.") + expect(result.message()).toEqual('Expected 0 to be Infinity.'); }); - it("succeeds for Infinity", function() { + it('succeeds for Infinity', function() { var matcher = jasmineUnderTest.matchers.toBePositiveInfinity(), result = matcher.compare(Number.POSITIVE_INFINITY); expect(result.pass).toBe(true); - expect(result.message).toEqual("Expected actual not to be Infinity.") + expect(result.message).toEqual('Expected actual not to be Infinity.'); }); - }); diff --git a/spec/core/matchers/toBeSpec.js b/spec/core/matchers/toBeSpec.js index 4d74a6de..b577b0da 100644 --- a/spec/core/matchers/toBeSpec.js +++ b/spec/core/matchers/toBeSpec.js @@ -1,5 +1,5 @@ -describe("toBe", function() { - it("passes with no message when actual === expected", function() { +describe('toBe', function() { + it('passes with no message when actual === expected', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(), matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result; @@ -8,29 +8,37 @@ describe("toBe", function() { expect(result.pass).toBe(true); }); - it("passes with a custom message when expected is an array", function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + it('passes with a custom message when expected is an array', function() { + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result, array = [1]; result = matcher.compare(array, array); expect(result.pass).toBe(true); - expect(result.message).toBe("Expected [ 1 ] not to be [ 1 ]. Tip: To check for deep equality, use .toEqual() instead of .toBe().") + expect(result.message).toBe( + 'Expected [ 1 ] not to be [ 1 ]. Tip: To check for deep equality, use .toEqual() instead of .toBe().' + ); }); - it("passes with a custom message when expected is an object", function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + it('passes with a custom message when expected is an object', function() { + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result, - obj = {foo: "bar"}; + obj = { foo: 'bar' }; result = matcher.compare(obj, obj); expect(result.pass).toBe(true); - expect(result.message).toBe("Expected Object({ foo: 'bar' }) not to be Object({ foo: 'bar' }). Tip: To check for deep equality, use .toEqual() instead of .toBe().") + expect(result.message).toBe( + "Expected Object({ foo: 'bar' }) not to be Object({ foo: 'bar' }). Tip: To check for deep equality, use .toEqual() instead of .toBe()." + ); }); - it("fails with no message when actual !== expected", function() { + it('fails with no message when actual !== expected', function() { var matchersUtil = new jasmineUnderTest.MatchersUtil(), matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result; @@ -40,35 +48,47 @@ describe("toBe", function() { expect(result.message).toBeUndefined(); }); - it("fails with a custom message when expected is an array", function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + it('fails with a custom message when expected is an array', function() { + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result; result = matcher.compare([1], [1]); expect(result.pass).toBe(false); - expect(result.message).toBe("Expected [ 1 ] to be [ 1 ]. Tip: To check for deep equality, use .toEqual() instead of .toBe().") + expect(result.message).toBe( + 'Expected [ 1 ] to be [ 1 ]. Tip: To check for deep equality, use .toEqual() instead of .toBe().' + ); }); - it("fails with a custom message when expected is an object", function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), + it('fails with a custom message when expected is an object', function() { + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result; - result = matcher.compare({foo: "bar"}, {foo: "bar"}); + result = matcher.compare({ foo: 'bar' }, { foo: 'bar' }); expect(result.pass).toBe(false); - expect(result.message).toBe("Expected Object({ foo: 'bar' }) to be Object({ foo: 'bar' }). Tip: To check for deep equality, use .toEqual() instead of .toBe().") + expect(result.message).toBe( + "Expected Object({ foo: 'bar' }) to be Object({ foo: 'bar' }). Tip: To check for deep equality, use .toEqual() instead of .toBe()." + ); }); - it("works with custom object formatters when expected is an object", function() { - var formatter = function(x) { return '<' + x.foo + '>'; }, + it('works with custom object formatters when expected is an object', function() { + var formatter = function(x) { + return '<' + x.foo + '>'; + }, prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]), - matchersUtil = new jasmineUnderTest.MatchersUtil({pp: prettyPrinter}), + matchersUtil = new jasmineUnderTest.MatchersUtil({ pp: prettyPrinter }), matcher = jasmineUnderTest.matchers.toBe(matchersUtil), result; - result = matcher.compare({foo: "bar"}, {foo: "bar"}); + result = matcher.compare({ foo: 'bar' }, { foo: 'bar' }); expect(result.pass).toBe(false); - expect(result.message).toBe("Expected to be . Tip: To check for deep equality, use .toEqual() instead of .toBe().") + expect(result.message).toBe( + 'Expected to be . Tip: To check for deep equality, use .toEqual() instead of .toBe().' + ); }); }); diff --git a/spec/core/matchers/toBeTrueSpec.js b/spec/core/matchers/toBeTrueSpec.js index ceac2074..d444d206 100644 --- a/spec/core/matchers/toBeTrueSpec.js +++ b/spec/core/matchers/toBeTrueSpec.js @@ -1,5 +1,5 @@ -describe("toBeTrue", function() { - it("passes for true", function() { +describe('toBeTrue', function() { + it('passes for true', function() { var matcher = jasmineUnderTest.matchers.toBeTrue(), result; @@ -7,7 +7,7 @@ describe("toBeTrue", function() { expect(result.pass).toBe(true); }); - it("fails for non-true", function() { + it('fails for non-true', function() { var matcher = jasmineUnderTest.matchers.toBeTrue(), result; diff --git a/spec/core/matchers/toBeTruthySpec.js b/spec/core/matchers/toBeTruthySpec.js index 7d5f284c..f7bb258b 100644 --- a/spec/core/matchers/toBeTruthySpec.js +++ b/spec/core/matchers/toBeTruthySpec.js @@ -1,4 +1,4 @@ -describe("toBeTruthy", function() { +describe('toBeTruthy', function() { it("passes for 'truthy' values", function() { var matcher = jasmineUnderTest.matchers.toBeTruthy(), result; @@ -9,7 +9,7 @@ describe("toBeTruthy", function() { result = matcher.compare(1); expect(result.pass).toBe(true); - result = matcher.compare("foo"); + result = matcher.compare('foo'); expect(result.pass).toBe(true); result = matcher.compare({}); diff --git a/spec/core/matchers/toBeUndefinedSpec.js b/spec/core/matchers/toBeUndefinedSpec.js index c3588e34..f4c090fe 100644 --- a/spec/core/matchers/toBeUndefinedSpec.js +++ b/spec/core/matchers/toBeUndefinedSpec.js @@ -1,18 +1,17 @@ -describe("toBeUndefined", function() { - it("passes for undefined values", function() { +describe('toBeUndefined', function() { + it('passes for undefined values', function() { var matcher = jasmineUnderTest.matchers.toBeUndefined(), result; result = matcher.compare(void 0); expect(result.pass).toBe(true); - }); - it("fails when matching defined values", function() { + it('fails when matching defined values', function() { var matcher = jasmineUnderTest.matchers.toBeUndefined(), result; result = matcher.compare('foo'); expect(result.pass).toBe(false); - }) + }); }); diff --git a/spec/core/matchers/toContainSpec.js b/spec/core/matchers/toContainSpec.js index 5fd1c8f8..1feab6b4 100644 --- a/spec/core/matchers/toContainSpec.js +++ b/spec/core/matchers/toContainSpec.js @@ -1,21 +1,23 @@ -describe("toContain", function() { - it("delegates to jasmineUnderTest.matchersUtil.contains", function() { +describe('toContain', function() { + it('delegates to jasmineUnderTest.matchersUtil.contains', function() { var matchersUtil = { contains: jasmine.createSpy('delegated-contains').and.returnValue(true) }, matcher = jasmineUnderTest.matchers.toContain(matchersUtil), result; - result = matcher.compare("ABC", "B"); - expect(matchersUtil.contains).toHaveBeenCalledWith("ABC", "B"); + result = matcher.compare('ABC', 'B'); + expect(matchersUtil.contains).toHaveBeenCalledWith('ABC', 'B'); expect(result.pass).toBe(true); }); - it("works with custom equality testers", function() { - var tester = function (a, b) { + it('works with custom equality testers', function() { + var tester = function(a, b) { return a.toString() === b.toString(); }, - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}), + matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [tester] + }), matcher = jasmineUnderTest.matchers.toContain(matchersUtil), result; diff --git a/spec/core/matchers/toEqualSpec.js b/spec/core/matchers/toEqualSpec.js index db7f3ffb..b2fb9f9c 100644 --- a/spec/core/matchers/toEqualSpec.js +++ b/spec/core/matchers/toEqualSpec.js @@ -1,5 +1,5 @@ -describe("toEqual", function() { - "use strict"; +describe('toEqual', function() { + 'use strict'; function compareEquals(actual, expected) { var matchersUtil = new jasmineUnderTest.MatchersUtil({ @@ -12,7 +12,7 @@ describe("toEqual", function() { return result; } - it("delegates to equals function", function() { + it('delegates to equals function', function() { var matchersUtil = { equals: jasmine.createSpy('delegated-equals').and.returnValue(true), buildFailureMessage: function() { @@ -29,11 +29,13 @@ describe("toEqual", function() { expect(result.pass).toBe(true); }); - it("works with custom equality testers", function() { - var tester = function (a, b) { + it('works with custom equality testers', function() { + var tester = function(a, b) { return a.toString() === b.toString(); }, - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: [tester]}), + matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: [tester] + }), matcher = jasmineUnderTest.matchers.toEqual(matchersUtil), result; @@ -42,300 +44,297 @@ describe("toEqual", function() { expect(result.pass).toBe(true); }); - it("reports the difference between objects that are not equal", function() { - var actual = {x: 1, y: 3}, - expected = {x: 2, y: 3}, - message = "Expected $.x = 1 to equal 2."; + it('reports the difference between objects that are not equal', function() { + var actual = { x: 1, y: 3 }, + expected = { x: 2, y: 3 }, + message = 'Expected $.x = 1 to equal 2.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports the difference between nested objects that are not equal", function() { - var actual = {x: {y: 1}}, - expected = {x: {y: 2}}, - message = "Expected $.x.y = 1 to equal 2."; + it('reports the difference between nested objects that are not equal', function() { + var actual = { x: { y: 1 } }, + expected = { x: { y: 2 } }, + message = 'Expected $.x.y = 1 to equal 2.'; expect(compareEquals(actual, expected).message).toEqual(message); }); it("formats property access so that it's valid JavaScript", function() { - var actual = {'my prop': 1}, - expected = {'my prop': 2}, + var actual = { 'my prop': 1 }, + expected = { 'my prop': 2 }, message = "Expected $['my prop'] = 1 to equal 2."; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports missing properties", function() { - var actual = {x: {}}, - expected = {x: {y: 1}}, - message = - "Expected $.x to have properties\n" + - " y: 1"; + it('reports missing properties', function() { + var actual = { x: {} }, + expected = { x: { y: 1 } }, + message = 'Expected $.x to have properties\n' + ' y: 1'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports extra properties", function() { - var actual = {x: {y: 1, z: 2}}, - expected = {x: {}}, + it('reports extra properties', function() { + var actual = { x: { y: 1, z: 2 } }, + expected = { x: {} }, message = - "Expected $.x not to have properties\n" + - " y: 1\n" + - " z: 2"; + 'Expected $.x not to have properties\n' + ' y: 1\n' + ' z: 2'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("pretty-prints properties", function() { - var actual = {x: {y: 'foo bar'}}, - expected = {x: {}}, - message = - "Expected $.x not to have properties\n" + - " y: 'foo bar'"; + it('pretty-prints properties', function() { + var actual = { x: { y: 'foo bar' } }, + expected = { x: {} }, + message = 'Expected $.x not to have properties\n' + " y: 'foo bar'"; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("uses custom object formatters to pretty-print simple properties", function() { + it('uses custom object formatters to pretty-print simple properties', function() { function formatter(x) { if (typeof x === 'number') { return '|' + x + '|'; } } - var actual = {x: {y: 1, z: 2, f: 4}}, - expected = {x: {y: 1, z: 2, g: 3}}, + var actual = { x: { y: 1, z: 2, f: 4 } }, + expected = { x: { y: 1, z: 2, g: 3 } }, pp = jasmineUnderTest.makePrettyPrinter([formatter]), - matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), + matchersUtil = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toEqual(matchersUtil), message = - "Expected $.x to have properties\n" + - " g: |3|\n" + - "Expected $.x not to have properties\n" + - " f: |4|"; + 'Expected $.x to have properties\n' + + ' g: |3|\n' + + 'Expected $.x not to have properties\n' + + ' f: |4|'; expect(matcher.compare(actual, expected).message).toEqual(message); }); - it("uses custom object formatters to show simple values in diffs", function() { + it('uses custom object formatters to show simple values in diffs', function() { function formatter(x) { if (typeof x === 'number') { return '|' + x + '|'; } } - var actual = [{foo: 4}], - expected = [{foo: 5}], + var actual = [{ foo: 4 }], + expected = [{ foo: 5 }], prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]), - matchersUtil = new jasmineUnderTest.MatchersUtil({pp: prettyPrinter}), + matchersUtil = new jasmineUnderTest.MatchersUtil({ pp: prettyPrinter }), matcher = jasmineUnderTest.matchers.toEqual(matchersUtil), - message = "Expected $[0].foo = |4| to equal |5|."; + message = 'Expected $[0].foo = |4| to equal |5|.'; expect(matcher.compare(actual, expected).message).toEqual(message); }); - it("uses custom object formatters to show more complex objects diffs", function() { + it('uses custom object formatters to show more complex objects diffs', function() { function formatter(x) { if (x.hasOwnProperty('a')) { return '[thing with a=' + x.a + ', b=' + x.b + ']'; } } - var actual = [{ - foo: {a: 1, b: 2}, - bar: 'should not be pretty printed' - }], - expected = [{ - foo: {a: 5, b: 2}, - bar: "shouldn't be pretty printed" - }], + var actual = [ + { + foo: { a: 1, b: 2 }, + bar: 'should not be pretty printed' + } + ], + expected = [ + { + foo: { a: 5, b: 2 }, + bar: "shouldn't be pretty printed" + } + ], prettyPrinter = jasmineUnderTest.makePrettyPrinter([formatter]), - matchersUtil = new jasmineUnderTest.MatchersUtil({pp: prettyPrinter}), + matchersUtil = new jasmineUnderTest.MatchersUtil({ pp: prettyPrinter }), matcher = jasmineUnderTest.matchers.toEqual(matchersUtil), - message = "Expected $[0].foo = [thing with a=1, b=2] to equal [thing with a=5, b=2].\n" + + message = + 'Expected $[0].foo = [thing with a=1, b=2] to equal [thing with a=5, b=2].\n' + "Expected $[0].bar = 'should not be pretty printed' to equal 'shouldn't be pretty printed'."; expect(matcher.compare(actual, expected).message).toEqual(message); }); - it("reports extra and missing properties of the root-level object", function() { - var actual = {x: 1}, - expected = {a: 1}, + it('reports extra and missing properties of the root-level object', function() { + var actual = { x: 1 }, + expected = { a: 1 }, message = - "Expected object to have properties\n" + - " a: 1\n" + - "Expected object not to have properties\n" + - " x: 1"; + 'Expected object to have properties\n' + + ' a: 1\n' + + 'Expected object not to have properties\n' + + ' x: 1'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports multiple incorrect values", function() { - var actual = {x: 1, y: 2}, - expected = {x: 3, y: 4}, + it('reports multiple incorrect values', function() { + var actual = { x: 1, y: 2 }, + expected = { x: 3, y: 4 }, message = - "Expected $.x = 1 to equal 3.\n" + - "Expected $.y = 2 to equal 4."; + 'Expected $.x = 1 to equal 3.\n' + 'Expected $.y = 2 to equal 4.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatch between actual child object and expected child number", function() { - var actual = {x: {y: 2}}, - expected = {x: 1}, - message = "Expected $.x = Object({ y: 2 }) to equal 1."; + it('reports mismatch between actual child object and expected child number', function() { + var actual = { x: { y: 2 } }, + expected = { x: 1 }, + message = 'Expected $.x = Object({ y: 2 }) to equal 1.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("uses the default failure message if actual is not an object", function() { + it('uses the default failure message if actual is not an object', function() { var actual = 1, - expected = {x: {}}, - message = "Expected 1 to equal Object({ x: Object({ }) })."; + expected = { x: {} }, + message = 'Expected 1 to equal Object({ x: Object({ }) }).'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("uses the default failure message if expected is not an object", function() { - var actual = {x: {}}, + it('uses the default failure message if expected is not an object', function() { + var actual = { x: {} }, expected = 1, - message = "Expected Object({ x: Object({ }) }) to equal 1."; + message = 'Expected Object({ x: Object({ }) }) to equal 1.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("uses the default failure message given arrays with different lengths", function() { + it('uses the default failure message given arrays with different lengths', function() { var actual = [1, 2], expected = [1, 2, 3], - message = 'Expected $.length = 2 to equal 3.\n' + + message = + 'Expected $.length = 2 to equal 3.\n' + 'Expected $[2] = undefined to equal 3.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports a mismatch between elements of equal-length arrays", function() { + it('reports a mismatch between elements of equal-length arrays', function() { var actual = [1, 2, 5], expected = [1, 2, 3], - message = "Expected $[2] = 5 to equal 3."; + message = 'Expected $[2] = 5 to equal 3.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports a mismatch between multiple array elements", function() { + it('reports a mismatch between multiple array elements', function() { var actual = [2, 2, 5], expected = [1, 2, 3], message = - "Expected $[0] = 2 to equal 1.\n" + - "Expected $[2] = 5 to equal 3."; + 'Expected $[0] = 2 to equal 1.\n' + 'Expected $[2] = 5 to equal 3.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports a mismatch between properties of objects in arrays", function() { - var actual = [{x: 1}], - expected = [{x: 2}], - message = "Expected $[0].x = 1 to equal 2."; + it('reports a mismatch between properties of objects in arrays', function() { + var actual = [{ x: 1 }], + expected = [{ x: 2 }], + message = 'Expected $[0].x = 1 to equal 2.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports a mismatch between arrays in objects", function() { - var actual = {x: [1]}, - expected = {x: [2]}, - message = - "Expected $.x[0] = 1 to equal 2."; + it('reports a mismatch between arrays in objects', function() { + var actual = { x: [1] }, + expected = { x: [2] }, + message = 'Expected $.x[0] = 1 to equal 2.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between nested arrays", function() { + it('reports mismatches between nested arrays', function() { var actual = [[1]], expected = [[2]], - message = - "Expected $[0][0] = 1 to equal 2."; + message = 'Expected $[0][0] = 1 to equal 2.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between arrays of different types", function() { + it('reports mismatches between arrays of different types', function() { jasmine.getEnv().requireFunctioningTypedArrays(); var actual = new Uint32Array([1, 2, 3]), // eslint-disable-line compat/compat expected = new Uint16Array([1, 2, 3]), // eslint-disable-line compat/compat - message = "Expected Uint32Array [ 1, 2, 3 ] to equal Uint16Array [ 1, 2, 3 ]."; + message = + 'Expected Uint32Array [ 1, 2, 3 ] to equal Uint16Array [ 1, 2, 3 ].'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches involving NaN", function() { - var actual = {x: 0}, - expected = {x: 0/0}, - message = "Expected $.x = 0 to equal NaN."; + it('reports mismatches involving NaN', function() { + var actual = { x: 0 }, + expected = { x: 0 / 0 }, + message = 'Expected $.x = 0 to equal NaN.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches involving regular expressions", function() { - var actual = {x: '1'}, - expected = {x: /1/}, + it('reports mismatches involving regular expressions', function() { + var actual = { x: '1' }, + expected = { x: /1/ }, message = "Expected $.x = '1' to equal /1/."; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches involving infinities", function() { - var actual = {x: 0}, - expected = {x: 1/0}, - message = "Expected $.x = 0 to equal Infinity."; + it('reports mismatches involving infinities', function() { + var actual = { x: 0 }, + expected = { x: 1 / 0 }, + message = 'Expected $.x = 0 to equal Infinity.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches involving booleans", function() { - var actual = {x: false}, - expected = {x: true}, - message = "Expected $.x = false to equal true."; + it('reports mismatches involving booleans', function() { + var actual = { x: false }, + expected = { x: true }, + message = 'Expected $.x = false to equal true.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches involving strings", function() { - var actual = {x: 'foo'}, - expected = {x: 'bar'}, + it('reports mismatches involving strings', function() { + var actual = { x: 'foo' }, + expected = { x: 'bar' }, message = "Expected $.x = 'foo' to equal 'bar'."; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches involving undefined", function() { - var actual = {x: void 0}, - expected = {x: 0}, - message = "Expected $.x = undefined to equal 0."; + it('reports mismatches involving undefined', function() { + var actual = { x: void 0 }, + expected = { x: 0 }, + message = 'Expected $.x = undefined to equal 0.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches involving null", function() { - var actual = {x: null}, - expected = {x: 0}, - message = "Expected $.x = null to equal 0."; + it('reports mismatches involving null', function() { + var actual = { x: null }, + expected = { x: 0 }, + message = 'Expected $.x = null to equal 0.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between objects with different constructors", function () { + it('reports mismatches between objects with different constructors', function() { function Foo() {} function Bar() {} - var actual = {x: new Foo()}, - expected = {x: new Bar()}, - message = "Expected $.x to be a kind of Bar, but was Foo({ })."; + var actual = { x: new Foo() }, + expected = { x: new Bar() }, + message = 'Expected $.x to be a kind of Bar, but was Foo({ }).'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("uses custom object formatters for the value but not the type when reporting objects with different constructors", function () { + it('uses custom object formatters for the value but not the type when reporting objects with different constructors', function() { function Foo() {} function Bar() {} function formatter(x) { @@ -344,52 +343,50 @@ describe("toEqual", function() { } } - var actual = {x: new Foo()}, - expected = {x: new Bar()}, - message = "Expected $.x to be a kind of Bar, but was |[object Object]|.", + var actual = { x: new Foo() }, + expected = { x: new Bar() }, + message = 'Expected $.x to be a kind of Bar, but was |[object Object]|.', pp = jasmineUnderTest.makePrettyPrinter([formatter]), - matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), + matchersUtil = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toEqual(matchersUtil); expect(matcher.compare(actual, expected).message).toEqual(message); }); - it("reports type mismatches at the root level", function () { + it('reports type mismatches at the root level', function() { function Foo() {} function Bar() {} var actual = new Foo(), expected = new Bar(), - message = "Expected object to be a kind of Bar, but was Foo({ })."; + message = 'Expected object to be a kind of Bar, but was Foo({ }).'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports value mismatches at the root level", function() { - expect(compareEquals(1, 2).message).toEqual("Expected 1 to equal 2."); + it('reports value mismatches at the root level', function() { + expect(compareEquals(1, 2).message).toEqual('Expected 1 to equal 2.'); }); - - it("reports mismatches between objects with their own constructor property", function () { + it('reports mismatches between objects with their own constructor property', function() { function Foo() {} function Bar() {} - var actual = {x: {constructor: 'blerf'}}, - expected = {x: {constructor: 'ftarrh'}}, - message = "Expected $.x.constructor = 'blerf' to equal 'ftarrh'."; + var actual = { x: { constructor: 'blerf' } }, + expected = { x: { constructor: 'ftarrh' } }, + message = "Expected $.x.constructor = 'blerf' to equal 'ftarrh'."; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between an object with a real constructor and one with its own constructor property", function () { + it('reports mismatches between an object with a real constructor and one with its own constructor property', function() { function Foo() {} function Bar() {} - var actual = {x: {}}, - expected = {x: {constructor: 'ftarrh'}}, + var actual = { x: {} }, + expected = { x: { constructor: 'ftarrh' } }, message = - "Expected $.x to have properties\n" + - " constructor: 'ftarrh'"; + 'Expected $.x to have properties\n' + " constructor: 'ftarrh'"; expect(compareEquals(actual, expected).message).toEqual(message); expect(compareEquals(expected, actual).message).toEqual( @@ -397,68 +394,74 @@ describe("toEqual", function() { ); }); - it("reports mismatches between 0 and -0", function() { - var actual = {x: 0}, - expected = {x: -0}, - message = "Expected $.x = 0 to equal -0."; + it('reports mismatches between 0 and -0', function() { + var actual = { x: 0 }, + expected = { x: -0 }, + message = 'Expected $.x = 0 to equal -0.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between 0 and Number.MIN_VALUE", function() { - var actual = {x: 0}, - expected = {x: Number.MIN_VALUE}, - message = "Expected $.x = 0 to equal 5e-324."; + it('reports mismatches between 0 and Number.MIN_VALUE', function() { + var actual = { x: 0 }, + expected = { x: Number.MIN_VALUE }, + message = 'Expected $.x = 0 to equal 5e-324.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between Errors", function() { - var actual = {x: new Error("the error you got")}, - expected = {x: new Error("the error you want")}, - message = "Expected $.x = Error: the error you got to equal Error: the error you want."; + it('reports mismatches between Errors', function() { + var actual = { x: new Error('the error you got') }, + expected = { x: new Error('the error you want') }, + message = + 'Expected $.x = Error: the error you got to equal Error: the error you want.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between Functions", function() { - var actual = {x: function() {}}, - expected = {x: function() {}}, - message = "Expected $.x = Function to equal Function."; + it('reports mismatches between Functions', function() { + var actual = { x: function() {} }, + expected = { x: function() {} }, + message = 'Expected $.x = Function to equal Function.'; expect(compareEquals(actual, expected).message).toEqual(message); }); it('reports mismatches between an object and objectContaining', function() { - var actual = {a: 1, b: 4, c: 3, extra: 'ignored'}; - var expected = jasmineUnderTest.objectContaining({a: 1, b: 2, c: 3, d: 4}); - expect(compareEquals(actual, expected).message) - .toEqual( - 'Expected $.b = 4 to equal 2.\n' + - 'Expected $.d = undefined to equal 4.' - ); + var actual = { a: 1, b: 4, c: 3, extra: 'ignored' }; + var expected = jasmineUnderTest.objectContaining({ + a: 1, + b: 2, + c: 3, + d: 4 + }); + expect(compareEquals(actual, expected).message).toEqual( + 'Expected $.b = 4 to equal 2.\n' + 'Expected $.d = undefined to equal 4.' + ); }); - it("reports mismatches between a non-object and objectContaining", function() { + it('reports mismatches between a non-object and objectContaining', function() { var actual = 1; - var expected = jasmineUnderTest.objectContaining({a: 1}); + var expected = jasmineUnderTest.objectContaining({ a: 1 }); expect(compareEquals(actual, expected).message).toEqual( "Expected 1 to equal ''." ); }); - it("reports mismatches involving a nested objectContaining", function() { - var actual = {x: {a: 1, b: 4, c: 3, extra: 'ignored'}}; - var expected = {x: jasmineUnderTest.objectContaining({a: 1, b: 2, c: 3, d: 4})}; + it('reports mismatches involving a nested objectContaining', function() { + var actual = { x: { a: 1, b: 4, c: 3, extra: 'ignored' } }; + var expected = { + x: jasmineUnderTest.objectContaining({ a: 1, b: 2, c: 3, d: 4 }) + }; expect(compareEquals(actual, expected).message).toEqual( 'Expected $.x.b = 4 to equal 2.\n' + - 'Expected $.x.d = undefined to equal 4.' + 'Expected $.x.d = undefined to equal 4.' ); }); // == Sets == - it("reports mismatches between Sets", function() { + it('reports mismatches between Sets', function() { jasmine.getEnv().requireFunctioningSets(); var actual = new Set(); // eslint-disable-line compat/compat @@ -470,19 +473,20 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports deep mismatches within Sets", function() { + it('reports deep mismatches within Sets', function() { jasmine.getEnv().requireFunctioningSets(); var actual = new Set(); // eslint-disable-line compat/compat - actual.add({x: 1}); + actual.add({ x: 1 }); var expected = new Set(); // eslint-disable-line compat/compat - expected.add({x: 2}); - var message = 'Expected Set( Object({ x: 1 }) ) to equal Set( Object({ x: 2 }) ).'; + expected.add({ x: 2 }); + var message = + 'Expected Set( Object({ x: 1 }) ) to equal Set( Object({ x: 2 }) ).'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between Sets nested in objects", function() { + it('reports mismatches between Sets nested in objects', function() { jasmine.getEnv().requireFunctioningSets(); var actualSet = new Set(); // eslint-disable-line compat/compat @@ -492,12 +496,12 @@ describe("toEqual", function() { var actual = { sets: [actualSet] }; var expected = { sets: [expectedSet] }; - var message = "Expected $.sets[0] = Set( 1 ) to equal Set( 2 )."; + var message = 'Expected $.sets[0] = Set( 1 ) to equal Set( 2 ).'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between Sets of different lengths", function() { + it('reports mismatches between Sets of different lengths', function() { jasmine.getEnv().requireFunctioningSets(); var actual = new Set(); // eslint-disable-line compat/compat @@ -510,175 +514,182 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between Sets where actual is missing a value from expected", function() { + it('reports mismatches between Sets where actual is missing a value from expected', function() { jasmine.getEnv().requireFunctioningSets(); // Use 'duplicate' object in actual so sizes match var actual = new Set(); // eslint-disable-line compat/compat - actual.add({x: 1}); - actual.add({x: 1}); + actual.add({ x: 1 }); + actual.add({ x: 1 }); var expected = new Set(); // eslint-disable-line compat/compat - expected.add({x: 1}); - expected.add({x: 2}); - var message = 'Expected Set( Object({ x: 1 }), Object({ x: 1 }) ) to equal Set( Object({ x: 1 }), Object({ x: 2 }) ).'; + expected.add({ x: 1 }); + expected.add({ x: 2 }); + var message = + 'Expected Set( Object({ x: 1 }), Object({ x: 1 }) ) to equal Set( Object({ x: 1 }), Object({ x: 2 }) ).'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between Sets where actual has a value missing from expected", function() { + it('reports mismatches between Sets where actual has a value missing from expected', function() { jasmine.getEnv().requireFunctioningSets(); // Use 'duplicate' object in expected so sizes match var actual = new Set(); // eslint-disable-line compat/compat - actual.add({x: 1}); - actual.add({x: 2}); + actual.add({ x: 1 }); + actual.add({ x: 2 }); var expected = new Set(); // eslint-disable-line compat/compat - expected.add({x: 1}); - expected.add({x: 1}); - var message = 'Expected Set( Object({ x: 1 }), Object({ x: 2 }) ) to equal Set( Object({ x: 1 }), Object({ x: 1 }) ).'; + expected.add({ x: 1 }); + expected.add({ x: 1 }); + var message = + 'Expected Set( Object({ x: 1 }), Object({ x: 2 }) ) to equal Set( Object({ x: 1 }), Object({ x: 1 }) ).'; expect(compareEquals(actual, expected).message).toEqual(message); }); // == Maps == - it("does not report mismatches between deep equal Maps", function() { + it('does not report mismatches between deep equal Maps', function() { jasmine.getEnv().requireFunctioningMaps(); // values are the same but with different object identity var actual = new Map(); // eslint-disable-line compat/compat - actual.set('a',{x:1}); + actual.set('a', { x: 1 }); var expected = new Map(); // eslint-disable-line compat/compat - expected.set('a',{x:1}); + expected.set('a', { x: 1 }); expect(compareEquals(actual, expected).pass).toBe(true); }); - it("reports deep mismatches within Maps", function() { + it('reports deep mismatches within Maps', function() { jasmine.getEnv().requireFunctioningMaps(); var actual = new Map(); // eslint-disable-line compat/compat - actual.set('a',{x:1}); + actual.set('a', { x: 1 }); var expected = new Map(); // eslint-disable-line compat/compat - expected.set('a',{x:2}); - var message = "Expected Map( [ 'a', Object({ x: 1 }) ] ) to equal Map( [ 'a', Object({ x: 2 }) ] )."; + expected.set('a', { x: 2 }); + var message = + "Expected Map( [ 'a', Object({ x: 1 }) ] ) to equal Map( [ 'a', Object({ x: 2 }) ] )."; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between Maps nested in objects", function() { + it('reports mismatches between Maps nested in objects', function() { jasmine.getEnv().requireFunctioningMaps(); - var actual = {Maps:[new Map()]}; // eslint-disable-line compat/compat - actual.Maps[0].set('a',1); - var expected = {Maps:[new Map()]}; // eslint-disable-line compat/compat - expected.Maps[0].set('a',2); + var actual = { Maps: [new Map()] }; // eslint-disable-line compat/compat + actual.Maps[0].set('a', 1); + var expected = { Maps: [new Map()] }; // eslint-disable-line compat/compat + expected.Maps[0].set('a', 2); - var message = "Expected $.Maps[0] = Map( [ 'a', 1 ] ) to equal Map( [ 'a', 2 ] )."; + var message = + "Expected $.Maps[0] = Map( [ 'a', 1 ] ) to equal Map( [ 'a', 2 ] )."; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between Maps of different lengths", function() { + it('reports mismatches between Maps of different lengths', function() { jasmine.getEnv().requireFunctioningMaps(); var actual = new Map(); // eslint-disable-line compat/compat - actual.set('a',1); + actual.set('a', 1); var expected = new Map(); // eslint-disable-line compat/compat - expected.set('a',2); - expected.set('b',1); - var message = "Expected Map( [ 'a', 1 ] ) to equal Map( [ 'a', 2 ], [ 'b', 1 ] )."; + expected.set('a', 2); + expected.set('b', 1); + var message = + "Expected Map( [ 'a', 1 ] ) to equal Map( [ 'a', 2 ], [ 'b', 1 ] )."; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between Maps with equal values but differing keys", function() { + it('reports mismatches between Maps with equal values but differing keys', function() { jasmine.getEnv().requireFunctioningMaps(); var actual = new Map(); // eslint-disable-line compat/compat - actual.set('a',1); + actual.set('a', 1); var expected = new Map(); // eslint-disable-line compat/compat - expected.set('b',1); + expected.set('b', 1); var message = "Expected Map( [ 'a', 1 ] ) to equal Map( [ 'b', 1 ] )."; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("does not report mismatches between Maps with keys with same object identity", function() { + it('does not report mismatches between Maps with keys with same object identity', function() { jasmine.getEnv().requireFunctioningMaps(); - var key = {x: 1}; + var key = { x: 1 }; var actual = new Map(); // eslint-disable-line compat/compat - actual.set(key,2); + actual.set(key, 2); var expected = new Map(); // eslint-disable-line compat/compat - expected.set(key,2); + expected.set(key, 2); expect(compareEquals(actual, expected).pass).toBe(true); }); - it("reports mismatches between Maps with identical keys with different object identity", function() { + it('reports mismatches between Maps with identical keys with different object identity', function() { jasmine.getEnv().requireFunctioningMaps(); var actual = new Map(); // eslint-disable-line compat/compat - actual.set({x:1},2); + actual.set({ x: 1 }, 2); var expected = new Map(); // eslint-disable-line compat/compat - expected.set({x:1},2); - var message = "Expected Map( [ Object({ x: 1 }), 2 ] ) to equal Map( [ Object({ x: 1 }), 2 ] )."; + expected.set({ x: 1 }, 2); + var message = + 'Expected Map( [ Object({ x: 1 }), 2 ] ) to equal Map( [ Object({ x: 1 }), 2 ] ).'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("does not report mismatches when comparing Map key to jasmine.anything()", function() { + it('does not report mismatches when comparing Map key to jasmine.anything()', function() { jasmine.getEnv().requireFunctioningMaps(); var actual = new Map(); // eslint-disable-line compat/compat - actual.set('a',1); + actual.set('a', 1); var expected = new Map(); // eslint-disable-line compat/compat - expected.set(jasmineUnderTest.anything(),1); + expected.set(jasmineUnderTest.anything(), 1); expect(compareEquals(actual, expected).pass).toBe(true); }); - it("does not report mismatches when comparing Maps with the same symbol keys", function() { + it('does not report mismatches when comparing Maps with the same symbol keys', function() { jasmine.getEnv().requireFunctioningMaps(); jasmine.getEnv().requireFunctioningSymbols(); var key = Symbol(); // eslint-disable-line compat/compat var actual = new Map(); // eslint-disable-line compat/compat - actual.set(key,1); + actual.set(key, 1); var expected = new Map(); // eslint-disable-line compat/compat - expected.set(key,1); + expected.set(key, 1); expect(compareEquals(actual, expected).pass).toBe(true); }); - it("reports mismatches between Maps with different symbol keys", function() { + it('reports mismatches between Maps with different symbol keys', function() { jasmine.getEnv().requireFunctioningMaps(); jasmine.getEnv().requireFunctioningSymbols(); var actual = new Map(); // eslint-disable-line compat/compat - actual.set(Symbol(),1); // eslint-disable-line compat/compat + actual.set(Symbol(), 1); // eslint-disable-line compat/compat var expected = new Map(); // eslint-disable-line compat/compat - expected.set(Symbol(),1); // eslint-disable-line compat/compat - var message = "Expected Map( [ Symbol(), 1 ] ) to equal Map( [ Symbol(), 1 ] )."; + expected.set(Symbol(), 1); // eslint-disable-line compat/compat + var message = + 'Expected Map( [ Symbol(), 1 ] ) to equal Map( [ Symbol(), 1 ] ).'; expect(compareEquals(actual, expected).message).toBe(message); }); - it("does not report mismatches when comparing Map symbol key to jasmine.anything()", function() { + it('does not report mismatches when comparing Map symbol key to jasmine.anything()', function() { jasmine.getEnv().requireFunctioningMaps(); jasmine.getEnv().requireFunctioningSymbols(); var actual = new Map(); // eslint-disable-line compat/compat - actual.set(Symbol(),1); // eslint-disable-line compat/compat + actual.set(Symbol(), 1); // eslint-disable-line compat/compat var expected = new Map(); // eslint-disable-line compat/compat - expected.set(jasmineUnderTest.anything(),1); + expected.set(jasmineUnderTest.anything(), 1); expect(compareEquals(actual, expected).pass).toBe(true); }); describe('DOM nodes', function() { function isNotRunningInBrowser() { - return typeof document === 'undefined' + return typeof document === 'undefined'; } beforeEach(function() { @@ -699,30 +710,31 @@ describe("toEqual", function() { } }); - it("reports mismatches between DOM nodes with different tags", function() { - var actual = {a: this.doc.createElement('div')}, - expected = {a: this.doc.createElement('p')}, - message = 'Expected $.a =
to equal

.'; + it('reports mismatches between DOM nodes with different tags', function() { + var actual = { a: this.doc.createElement('div') }, + expected = { a: this.doc.createElement('p') }, + message = 'Expected $.a =

to equal

.'; expect(compareEquals(actual, expected).message).toEqual(message); }); it('reports mismatches between DOM nodes with different content', function() { var nodeA = this.doc.createElement('div'), - nodeB = this.doc.createElement('div'); + nodeB = this.doc.createElement('div'); nodeA.setAttribute('thing', 'foo'); nodeB.setAttribute('thing', 'bar'); expect(nodeA.isEqualNode(nodeB)).toBe(false); - var actual = {a: nodeA}, - expected = {a: nodeB}, - message = 'Expected $.a =

to equal
.'; + var actual = { a: nodeA }, + expected = { a: nodeB }, + message = + 'Expected $.a =
to equal
.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between SVG nodes", function () { + it('reports mismatches between SVG nodes', function() { var nodeA = this.doc.createElementNS('http://www.w3.org/2000/svg', 'svg'), nodeB = this.doc.createElementNS('http://www.w3.org/2000/svg', 'svg'); @@ -734,14 +746,15 @@ describe("toEqual", function() { nodeA.appendChild(rect); expect(nodeA.isEqualNode(nodeB)).toBe(false); - var actual = {a: nodeA}, - expected = {a: nodeB}, - message = 'Expected $.a = ... to equal .'; + var actual = { a: nodeA }, + expected = { a: nodeB }, + message = + 'Expected $.a = ... to equal .'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports whole DOM node when attribute contains > character", function () { + it('reports whole DOM node when attribute contains > character', function() { var nodeA = this.doc.createElement('div'), nodeB = this.doc.createElement('div'); @@ -749,14 +762,15 @@ describe("toEqual", function() { nodeB.setAttribute('thing', 'bar'); expect(nodeA.isEqualNode(nodeB)).toBe(false); - var actual = {a: nodeA}, - expected = {a: nodeB}, - message = 'Expected $.a =
to equal
.'; + var actual = { a: nodeA }, + expected = { a: nodeB }, + message = + 'Expected $.a =
to equal
.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it('reports no content when DOM node has multiple empty text nodes', function () { + it('reports no content when DOM node has multiple empty text nodes', function() { var nodeA = this.doc.createElement('div'), nodeB = this.doc.createElement('div'); @@ -766,103 +780,98 @@ describe("toEqual", function() { nodeA.appendChild(this.doc.createTextNode('')); expect(nodeA.isEqualNode(nodeB)).toBe(false); - var actual = {a: nodeA}, - expected = {a: nodeB}, + var actual = { a: nodeA }, + expected = { a: nodeB }, message = 'Expected $.a =
to equal
.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it('reports content when DOM node has non empty text node', function () { + it('reports content when DOM node has non empty text node', function() { var nodeA = this.doc.createElement('div'), nodeB = this.doc.createElement('div'); nodeA.appendChild(this.doc.createTextNode('Hello Jasmine!')); expect(nodeA.isEqualNode(nodeB)).toBe(false); - var actual = {a: nodeA}, - expected = {a: nodeB}, + var actual = { a: nodeA }, + expected = { a: nodeB }, message = 'Expected $.a =
...
to equal
.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it('reports empty DOM attributes', function () { + it('reports empty DOM attributes', function() { var nodeA = this.doc.createElement('div'), nodeB = this.doc.createElement('div'); nodeA.setAttribute('contenteditable', ''); expect(nodeA.isEqualNode(nodeB)).toBe(false); - var actual = {a: nodeA}, - expected = {a: nodeB}, + var actual = { a: nodeA }, + expected = { a: nodeB }, message = 'Expected $.a =
to equal
.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it('reports 0 attr value as non empty DOM attribute', function () { + it('reports 0 attr value as non empty DOM attribute', function() { var nodeA = this.doc.createElement('div'), nodeB = this.doc.createElement('div'); nodeA.setAttribute('contenteditable', 0); expect(nodeA.isEqualNode(nodeB)).toBe(false); - var actual = {a: nodeA}, - expected = {a: nodeB}, + var actual = { a: nodeA }, + expected = { a: nodeB }, message = 'Expected $.a =
to equal
.'; expect(compareEquals(actual, expected).message).toEqual(message); }); - it("reports mismatches between a DOM node and a bare Object", function() { - var actual = {a: this.doc.createElement('div')}, - expected = {a: {}}, - message = 'Expected $.a =
to equal Object({ }).'; + it('reports mismatches between a DOM node and a bare Object', function() { + var actual = { a: this.doc.createElement('div') }, + expected = { a: {} }, + message = 'Expected $.a =
to equal Object({ }).'; expect(compareEquals(actual, expected).message).toEqual(message); }); }); - it("reports asymmetric mismatches", function() { - var actual = {a: 1}, - expected = {a: jasmineUnderTest.any(String)}, + it('reports asymmetric mismatches', function() { + var actual = { a: 1 }, + expected = { a: jasmineUnderTest.any(String) }, message = 'Expected $.a = 1 to equal .'; expect(compareEquals(actual, expected).message).toEqual(message); - expect(compareEquals(actual, expected).pass).toBe(false) + expect(compareEquals(actual, expected).pass).toBe(false); }); - it("reports asymmetric mismatches when the asymmetric comparand is the actual value", function() { - var actual = {a: jasmineUnderTest.any(String)}, - expected = {a: 1}, + it('reports asymmetric mismatches when the asymmetric comparand is the actual value', function() { + var actual = { a: jasmineUnderTest.any(String) }, + expected = { a: 1 }, message = 'Expected $.a = to equal 1.'; expect(compareEquals(actual, expected).message).toEqual(message); - expect(compareEquals(actual, expected).pass).toBe(false) + expect(compareEquals(actual, expected).pass).toBe(false); }); - it("does not report a mismatch when asymmetric matchers are satisfied", function() { - var actual = {a: 'a'}, - expected = {a: jasmineUnderTest.any(String)}; + it('does not report a mismatch when asymmetric matchers are satisfied', function() { + var actual = { a: 'a' }, + expected = { a: jasmineUnderTest.any(String) }; expect(compareEquals(actual, expected).message).toEqual(''); - expect(compareEquals(actual, expected).pass).toBe(true) + expect(compareEquals(actual, expected).pass).toBe(true); }); - it("works on big complex stuff", function() { + it('works on big complex stuff', function() { var actual = { - foo: [ - {bar: 1, things: ['a', 'b']}, - {bar: 2, things: ['a', 'b']} - ], - baz: [ - {a: {b: 1}} - ], + foo: [{ bar: 1, things: ['a', 'b'] }, { bar: 2, things: ['a', 'b'] }], + baz: [{ a: { b: 1 } }], quux: 1, nan: 0, aRegexp: 'hi', - inf: -1/0, + inf: -1 / 0, boolean: false, notDefined: 0, aNull: void 0 @@ -870,16 +879,14 @@ describe("toEqual", function() { var expected = { foo: [ - {bar: 2, things: ['a', 'b', 'c']}, - {bar: 2, things: ['a', 'd']} - ], - baz: [ - {a: {b: 1, c: 1}} + { bar: 2, things: ['a', 'b', 'c'] }, + { bar: 2, things: ['a', 'd'] } ], + baz: [{ a: { b: 1, c: 1 } }], quux: [], - nan: 0/0, + nan: 0 / 0, aRegexp: /hi/, - inf: 1/0, + inf: 1 / 0, boolean: true, notDefined: void 0, aNull: null @@ -903,18 +910,19 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - describe("different length arrays", function() { - it("actual array is longer", function() { + describe('different length arrays', function() { + it('actual array is longer', function() { var actual = [1, 1, 2, 3, 5], expected = [1, 1, 2, 3], - message = 'Expected $.length = 5 to equal 4.\n' + + message = + 'Expected $.length = 5 to equal 4.\n' + 'Unexpected $[4] = 5 in array.'; expect(compareEquals(actual, expected).pass).toBe(false); expect(compareEquals(actual, expected).message).toEqual(message); }); - it("uses custom object formatters when the actual array is longer", function() { + it('uses custom object formatters when the actual array is longer', function() { function formatter(x) { if (typeof x === 'number') { return '|' + x + '|'; @@ -924,25 +932,27 @@ describe("toEqual", function() { var actual = [1, 1, 2, 3, 5], expected = [1, 1, 2, 3], pp = jasmineUnderTest.makePrettyPrinter([formatter]), - matchersUtil = new jasmineUnderTest.MatchersUtil({pp: pp}), + matchersUtil = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toEqual(matchersUtil), - message = 'Expected $.length = |5| to equal |4|.\n' + + message = + 'Expected $.length = |5| to equal |4|.\n' + 'Unexpected $[4] = |5| in array.'; expect(matcher.compare(actual, expected).message).toEqual(message); }); - it("expected array is longer", function() { + it('expected array is longer', function() { var actual = [1, 1, 2, 3], expected = [1, 1, 2, 3, 5], - message = 'Expected $.length = 4 to equal 5.\n' + + message = + 'Expected $.length = 4 to equal 5.\n' + 'Expected $[4] = undefined to equal 5.'; expect(compareEquals(actual, expected).pass).toBe(false); expect(compareEquals(actual, expected).message).toEqual(message); }); - it("undefined in middle of actual array", function() { + it('undefined in middle of actual array', function() { var actual = [1, void 0, 3], expected = [1, 2, 3], message = 'Expected $[1] = undefined to equal 2.'; @@ -951,7 +961,7 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("undefined in middle of expected array", function() { + it('undefined in middle of expected array', function() { var actual = [1, 2, 3], expected = [1, void 0, 3], message = 'Expected $[1] = 2 to equal undefined.'; @@ -960,10 +970,11 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("actual array is longer by 4 elements", function() { + it('actual array is longer by 4 elements', function() { var actual = [1, 1, 2, 3, 5, 8, 13], expected = [1, 1, 2], - message = 'Expected $.length = 7 to equal 3.\n' + + message = + 'Expected $.length = 7 to equal 3.\n' + 'Unexpected $[3] = 3 in array.\n' + 'Unexpected $[4] = 5 in array.\n' + 'Unexpected $[5] = 8 in array.\n' + @@ -973,10 +984,11 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("expected array is longer by 4 elements", function() { + it('expected array is longer by 4 elements', function() { var actual = [1, 1, 2], expected = [1, 1, 2, 3, 5, 8, 13], - message = 'Expected $.length = 3 to equal 7.\n' + + message = + 'Expected $.length = 3 to equal 7.\n' + 'Expected $[3] = undefined to equal 3.\n' + 'Expected $[4] = undefined to equal 5.\n' + 'Expected $[5] = undefined to equal 8.\n' + @@ -986,10 +998,11 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("different length and different elements", function() { + it('different length and different elements', function() { var actual = [1], expected = [2, 3], - message = 'Expected $.length = 1 to equal 2.\n' + + message = + 'Expected $.length = 1 to equal 2.\n' + 'Expected $[0] = 1 to equal 2.\n' + 'Expected $[1] = undefined to equal 3.'; @@ -997,50 +1010,55 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("object with nested array (actual longer than expected)", function() { + it('object with nested array (actual longer than expected)', function() { var actual = { values: [1, 1, 2, 3] }, expected = { values: [1, 1, 2] }, - message = 'Expected $.values.length = 4 to equal 3.\n' + + message = + 'Expected $.values.length = 4 to equal 3.\n' + 'Unexpected $.values[3] = 3 in array.'; expect(compareEquals(actual, expected).pass).toBe(false); expect(compareEquals(actual, expected).message).toEqual(message); }); - it("object with nested array (expected longer than actual)", function() { + it('object with nested array (expected longer than actual)', function() { var actual = { values: [1, 1, 2] }, expected = { values: [1, 1, 2, 3] }, - message = 'Expected $.values.length = 3 to equal 4.\n' + + message = + 'Expected $.values.length = 3 to equal 4.\n' + 'Expected $.values[3] = undefined to equal 3.'; expect(compareEquals(actual, expected).pass).toBe(false); expect(compareEquals(actual, expected).message).toEqual(message); }); - it("array with unexpected nested object", function() { + it('array with unexpected nested object', function() { var actual = [1, 1, 2, { value: 3 }], expected = [1, 1, 2], - message = 'Expected $.length = 4 to equal 3.\n' + + message = + 'Expected $.length = 4 to equal 3.\n' + 'Unexpected $[3] = Object({ value: 3 }) in array.'; expect(compareEquals(actual, expected).pass).toBe(false); expect(compareEquals(actual, expected).message).toEqual(message); }); - it("array with missing nested object", function() { + it('array with missing nested object', function() { var actual = [1, 1, 2], expected = [1, 1, 2, { value: 3 }], - message = 'Expected $.length = 3 to equal 4.\n' + + message = + 'Expected $.length = 3 to equal 4.\n' + 'Expected $[3] = undefined to equal Object({ value: 3 }).'; expect(compareEquals(actual, expected).pass).toBe(false); expect(compareEquals(actual, expected).message).toEqual(message); }); - it("array with nested different length array", function() { + it('array with nested different length array', function() { var actual = [[1], [1, 2]], expected = [[1, 1], [2]], - message = 'Expected $[0].length = 1 to equal 2.\n' + + message = + 'Expected $[0].length = 1 to equal 2.\n' + 'Expected $[0][1] = undefined to equal 1.\n' + 'Expected $[1].length = 2 to equal 1.\n' + 'Expected $[1][0] = 1 to equal 2.\n' + @@ -1050,7 +1068,7 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).message).toEqual(message); }); - it("last element of longer array is undefined", function() { + it('last element of longer array is undefined', function() { var actual = [1, 2], expected = [1, 2, void 0], message = 'Expected $.length = 2 to equal 3.'; @@ -1058,5 +1076,5 @@ describe("toEqual", function() { expect(compareEquals(actual, expected).pass).toBe(false); expect(compareEquals(actual, expected).message).toEqual(message); }); - }) + }); }); diff --git a/spec/core/matchers/toHaveBeenCalledBeforeSpec.js b/spec/core/matchers/toHaveBeenCalledBeforeSpec.js index 266758fe..2bf316e3 100644 --- a/spec/core/matchers/toHaveBeenCalledBeforeSpec.js +++ b/spec/core/matchers/toHaveBeenCalledBeforeSpec.js @@ -1,29 +1,29 @@ -describe("toHaveBeenCalledBefore", function() { - it("throws an exception when the actual is not a spy", function() { +describe('toHaveBeenCalledBefore', function() { + it('throws an exception when the actual is not a spy', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore({ - pp: jasmineUnderTest.makePrettyPrinter() - }), - fn = function() {}, - spy = new jasmineUnderTest.Env().createSpy('a spy'); + pp: jasmineUnderTest.makePrettyPrinter() + }), + fn = function() {}, + spy = new jasmineUnderTest.Env().createSpy('a spy'); - expect(function () { + expect(function() { matcher.compare(fn, spy); }).toThrowError(Error, /Expected a spy, but got Function./); }); - it("throws an exception when the expected is not a spy", function() { + it('throws an exception when the expected is not a spy', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore({ - pp: jasmineUnderTest.makePrettyPrinter() - }), - spy = new jasmineUnderTest.Env().createSpy('a spy'), - fn = function() {}; + pp: jasmineUnderTest.makePrettyPrinter() + }), + spy = new jasmineUnderTest.Env().createSpy('a spy'), + fn = function() {}; - expect(function () { + expect(function() { matcher.compare(spy, fn); }).toThrowError(Error, /Expected a spy, but got Function./); }); - it("fails when the actual was not called", function () { + it('fails when the actual was not called', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), firstSpy = new jasmineUnderTest.Spy('first spy'), secondSpy = new jasmineUnderTest.Spy('second spy'); @@ -32,10 +32,12 @@ describe("toHaveBeenCalledBefore", function() { result = matcher.compare(firstSpy, secondSpy); expect(result.pass).toBe(false); - expect(result.message).toMatch(/Expected spy first spy to have been called./); + expect(result.message).toMatch( + /Expected spy first spy to have been called./ + ); }); - it("fails when the expected was not called", function () { + it('fails when the expected was not called', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), firstSpy = new jasmineUnderTest.Spy('first spy'), secondSpy = new jasmineUnderTest.Spy('second spy'); @@ -44,10 +46,12 @@ describe("toHaveBeenCalledBefore", function() { result = matcher.compare(firstSpy, secondSpy); expect(result.pass).toBe(false); - expect(result.message).toMatch(/Expected spy second spy to have been called./); + expect(result.message).toMatch( + /Expected spy second spy to have been called./ + ); }); - it("fails when the actual is called after the expected", function () { + it('fails when the actual is called after the expected', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), firstSpy = new jasmineUnderTest.Spy('first spy'), secondSpy = new jasmineUnderTest.Spy('second spy'), @@ -58,10 +62,12 @@ describe("toHaveBeenCalledBefore", function() { result = matcher.compare(firstSpy, secondSpy); expect(result.pass).toBe(false); - expect(result.message).toEqual('Expected spy first spy to have been called before spy second spy'); + expect(result.message).toEqual( + 'Expected spy first spy to have been called before spy second spy' + ); }); - it("fails when the actual is called before and after the expected", function () { + it('fails when the actual is called before and after the expected', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), firstSpy = new jasmineUnderTest.Spy('first spy'), secondSpy = new jasmineUnderTest.Spy('second spy'), @@ -73,10 +79,12 @@ describe("toHaveBeenCalledBefore", function() { result = matcher.compare(firstSpy, secondSpy); expect(result.pass).toBe(false); - expect(result.message).toEqual('Expected latest call to spy first spy to have been called before first call to spy second spy (no interleaved calls)'); + expect(result.message).toEqual( + 'Expected latest call to spy first spy to have been called before first call to spy second spy (no interleaved calls)' + ); }); - it("fails when the expected is called before and after the actual", function () { + it('fails when the expected is called before and after the actual', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), firstSpy = new jasmineUnderTest.Spy('first spy'), secondSpy = new jasmineUnderTest.Spy('second spy'), @@ -88,10 +96,12 @@ describe("toHaveBeenCalledBefore", function() { result = matcher.compare(firstSpy, secondSpy); expect(result.pass).toBe(false); - expect(result.message).toEqual('Expected first call to spy second spy to have been called after latest call to spy first spy (no interleaved calls)'); + expect(result.message).toEqual( + 'Expected first call to spy second spy to have been called after latest call to spy first spy (no interleaved calls)' + ); }); - it("passes when the actual is called before the expected", function () { + it('passes when the actual is called before the expected', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledBefore(), firstSpy = new jasmineUnderTest.Spy('first spy'), secondSpy = new jasmineUnderTest.Spy('second spy'), @@ -102,6 +112,8 @@ describe("toHaveBeenCalledBefore", function() { result = matcher.compare(firstSpy, secondSpy); expect(result.pass).toBe(true); - expect(result.message).toEqual('Expected spy first spy to not have been called before spy second spy, but it was'); + expect(result.message).toEqual( + 'Expected spy first spy to not have been called before spy second spy, but it was' + ); }); }); diff --git a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js index d79711a5..ff2975c9 100644 --- a/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledOnceWithSpec.js @@ -1,6 +1,5 @@ -describe("toHaveBeenCalledOnceWith", function () { - - it("passes when the actual was called only once and with matching parameters", function () { +describe('toHaveBeenCalledOnceWith', function() { + it('passes when the actual was called only once and with matching parameters', function() { var pp = jasmineUnderTest.makePrettyPrinter(), util = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), @@ -11,13 +10,23 @@ describe("toHaveBeenCalledOnceWith", function () { result = matcher.compare(calledSpy, 'a', 'b'); expect(result.pass).toBe(true); - expect(result.message).toEqual("Expected spy called-spy to have been called 0 times, multiple times, or once, but with arguments different from:\n [ 'a', 'b' ]\nBut the actual call was:\n [ 'a', 'b' ].\n\n"); + expect(result.message).toEqual( + "Expected spy called-spy to have been called 0 times, multiple times, or once, but with arguments different from:\n [ 'a', 'b' ]\nBut the actual call was:\n [ 'a', 'b' ].\n\n" + ); }); - it("supports custom equality testers", function () { - var customEqualityTesters = [function() { return true; }], - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: customEqualityTesters}), - matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(matchersUtil), + it('supports custom equality testers', function() { + var customEqualityTesters = [ + function() { + return true; + } + ], + matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: customEqualityTesters + }), + matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith( + matchersUtil + ), calledSpy = new jasmineUnderTest.Spy('called-spy'), result; @@ -27,7 +36,7 @@ describe("toHaveBeenCalledOnceWith", function () { expect(result.pass).toBe(true); }); - it("fails when the actual was never called", function () { + it('fails when the actual was never called', function() { var pp = jasmineUnderTest.makePrettyPrinter(), util = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), @@ -37,10 +46,12 @@ describe("toHaveBeenCalledOnceWith", function () { result = matcher.compare(calledSpy, 'a', 'b'); expect(result.pass).toBe(false); - expect(result.message).toEqual("Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut it was never called.\n\n"); + expect(result.message).toEqual( + "Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut it was never called.\n\n" + ); }); - it("fails when the actual was called once with different parameters", function () { + it('fails when the actual was called once with different parameters', function() { var pp = jasmineUnderTest.makePrettyPrinter(), util = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), @@ -51,10 +62,12 @@ describe("toHaveBeenCalledOnceWith", function () { result = matcher.compare(calledSpy, 'a', 'b'); expect(result.pass).toBe(false); - expect(result.message).toEqual("Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut the actual call was:\n [ 'a', 'c' ].\nExpected $[1] = 'c' to equal 'b'.\n\n"); + expect(result.message).toEqual( + "Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut the actual call was:\n [ 'a', 'c' ].\nExpected $[1] = 'c' to equal 'b'.\n\n" + ); }); - it("fails when the actual was called multiple times with expected parameters", function () { + it('fails when the actual was called multiple times with expected parameters', function() { var pp = jasmineUnderTest.makePrettyPrinter(), util = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), @@ -66,10 +79,12 @@ describe("toHaveBeenCalledOnceWith", function () { result = matcher.compare(calledSpy, 'a', 'b'); expect(result.pass).toBe(false); - expect(result.message).toEqual("Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut the actual calls were:\n [ 'a', 'b' ],\n [ 'a', 'b' ].\n\n"); + expect(result.message).toEqual( + "Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut the actual calls were:\n [ 'a', 'b' ],\n [ 'a', 'b' ].\n\n" + ); }); - it("fails when the actual was called multiple times (one of them - with expected parameters)", function () { + it('fails when the actual was called multiple times (one of them - with expected parameters)', function() { var pp = jasmineUnderTest.makePrettyPrinter(), util = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), @@ -81,15 +96,19 @@ describe("toHaveBeenCalledOnceWith", function () { result = matcher.compare(calledSpy, 'a', 'b'); expect(result.pass).toBe(false); - expect(result.message).toEqual("Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut the actual calls were:\n [ 'a', 'b' ],\n [ 'a', 'c' ].\n\n"); + expect(result.message).toEqual( + "Expected spy called-spy to have been called only once, and with given args:\n [ 'a', 'b' ]\nBut the actual calls were:\n [ 'a', 'b' ],\n [ 'a', 'c' ].\n\n" + ); }); - it("throws an exception when the actual is not a spy", function () { + it('throws an exception when the actual is not a spy', function() { var pp = jasmineUnderTest.makePrettyPrinter(), util = new jasmineUnderTest.MatchersUtil({ pp: pp }), matcher = jasmineUnderTest.matchers.toHaveBeenCalledOnceWith(util), - fn = function () { }; + fn = function() {}; - expect(function () { matcher.compare(fn) }).toThrowError(/Expected a spy, but got Function./); + expect(function() { + matcher.compare(fn); + }).toThrowError(/Expected a spy, but got Function./); }); }); diff --git a/spec/core/matchers/toHaveBeenCalledSpec.js b/spec/core/matchers/toHaveBeenCalledSpec.js index 65106cf5..ebc9a9cb 100644 --- a/spec/core/matchers/toHaveBeenCalledSpec.js +++ b/spec/core/matchers/toHaveBeenCalledSpec.js @@ -1,5 +1,5 @@ -describe("toHaveBeenCalled", function() { - it("passes when the actual was called, with a custom .not fail message", function() { +describe('toHaveBeenCalled', function() { + it('passes when the actual was called, with a custom .not fail message', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalled(), calledSpy = new jasmineUnderTest.Spy('called-spy'), result; @@ -8,10 +8,12 @@ describe("toHaveBeenCalled", function() { result = matcher.compare(calledSpy); expect(result.pass).toBe(true); - expect(result.message).toEqual("Expected spy called-spy not to have been called."); + expect(result.message).toEqual( + 'Expected spy called-spy not to have been called.' + ); }); - it("fails when the actual was not called", function() { + it('fails when the actual was not called', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalled(), uncalledSpy = new jasmineUnderTest.Spy('uncalled spy'), result; @@ -20,30 +22,35 @@ describe("toHaveBeenCalled", function() { expect(result.pass).toBe(false); }); - it("throws an exception when the actual is not a spy", function() { + it('throws an exception when the actual is not a spy', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalled({ pp: jasmineUnderTest.makePrettyPrinter() }), fn = function() {}; - expect(function() { matcher.compare(fn) }).toThrowError(Error, /Expected a spy, but got Function./); + expect(function() { + matcher.compare(fn); + }).toThrowError(Error, /Expected a spy, but got Function./); }); - it("throws an exception when invoked with any arguments", function() { + it('throws an exception when invoked with any arguments', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalled(), spy = new jasmineUnderTest.Spy('sample spy'); - expect(function() { matcher.compare(spy, 'foo') }).toThrowError(Error, /Does not take arguments, use toHaveBeenCalledWith/); + expect(function() { + matcher.compare(spy, 'foo'); + }).toThrowError(Error, /Does not take arguments, use toHaveBeenCalledWith/); }); - it("has a custom message on failure", function() { + it('has a custom message on failure', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalled(), spy = new jasmineUnderTest.Spy('sample-spy'), result; result = matcher.compare(spy); - expect(result.message).toEqual("Expected spy sample-spy to have been called."); + expect(result.message).toEqual( + 'Expected spy sample-spy to have been called.' + ); }); }); - diff --git a/spec/core/matchers/toHaveBeenCalledTimesSpec.js b/spec/core/matchers/toHaveBeenCalledTimesSpec.js index e2c0c0ed..12075ad8 100644 --- a/spec/core/matchers/toHaveBeenCalledTimesSpec.js +++ b/spec/core/matchers/toHaveBeenCalledTimesSpec.js @@ -1,12 +1,12 @@ -describe("toHaveBeenCalledTimes", function() { - it("passes when the actual 0 matches the expected 0 ", function () { +describe('toHaveBeenCalledTimes', function() { + it('passes when the actual 0 matches the expected 0 ', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), - calledSpy = new jasmineUnderTest.Spy('called-spy'), - result; + calledSpy = new jasmineUnderTest.Spy('called-spy'), + result; result = matcher.compare(calledSpy, 0); expect(result.pass).toBeTruthy(); }); - it("passes when the actual matches the expected", function() { + it('passes when the actual matches the expected', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), calledSpy = new jasmineUnderTest.Spy('called-spy'), result; @@ -16,18 +16,20 @@ describe("toHaveBeenCalledTimes", function() { expect(result.pass).toBe(true); }); - it("fails when expected numbers is not supplied", function(){ - var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), + it('fails when expected numbers is not supplied', function() { + var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), spy = new jasmineUnderTest.Spy('spy'), result; spy(); - expect(function() { - matcher.compare(spy); - }).toThrowError(/The expected times failed is a required argument and must be a number./); + expect(function() { + matcher.compare(spy); + }).toThrowError( + /The expected times failed is a required argument and must be a number./ + ); }); - it("fails when the actual was called less than the expected", function() { + it('fails when the actual was called less than the expected', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), uncalledSpy = new jasmineUnderTest.Spy('uncalled spy'), result; @@ -36,7 +38,7 @@ describe("toHaveBeenCalledTimes", function() { expect(result.pass).toBe(false); }); - it("fails when the actual was called more than expected", function() { + it('fails when the actual was called more than expected', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), uncalledSpy = new jasmineUnderTest.Spy('uncalled spy'), result; @@ -48,7 +50,7 @@ describe("toHaveBeenCalledTimes", function() { expect(result.pass).toBe(false); }); - it("throws an exception when the actual is not a spy", function() { + it('throws an exception when the actual is not a spy', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes({ pp: jasmineUnderTest.makePrettyPrinter() }), @@ -59,7 +61,7 @@ describe("toHaveBeenCalledTimes", function() { }).toThrowError(/Expected a spy, but got Function./); }); - it("has a custom message on failure that tells it was called only once", function() { + it('has a custom message on failure that tells it was called only once', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), spy = new jasmineUnderTest.Spy('sample-spy'), result; @@ -69,10 +71,14 @@ describe("toHaveBeenCalledTimes", function() { spy(); result = matcher.compare(spy, 1); - expect(result.message).toEqual('Expected spy sample-spy to have been called once. It was called ' + 4 + ' times.'); + expect(result.message).toEqual( + 'Expected spy sample-spy to have been called once. It was called ' + + 4 + + ' times.' + ); }); - it("has a custom message on failure that tells how many times it was called", function() { + it('has a custom message on failure that tells how many times it was called', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledTimes(), spy = new jasmineUnderTest.Spy('sample-spy'), result; @@ -82,7 +88,10 @@ describe("toHaveBeenCalledTimes", function() { spy(); result = matcher.compare(spy, 2); - expect(result.message).toEqual('Expected spy sample-spy to have been called 2 times. It was called ' + 4 + ' times.'); + expect(result.message).toEqual( + 'Expected spy sample-spy to have been called 2 times. It was called ' + + 4 + + ' times.' + ); }); }); - diff --git a/spec/core/matchers/toHaveBeenCalledWithSpec.js b/spec/core/matchers/toHaveBeenCalledWithSpec.js index 5f391d6c..a0f869a4 100644 --- a/spec/core/matchers/toHaveBeenCalledWithSpec.js +++ b/spec/core/matchers/toHaveBeenCalledWithSpec.js @@ -1,24 +1,31 @@ -describe("toHaveBeenCalledWith", function() { - - it("passes when the actual was called with matching parameters", function() { +describe('toHaveBeenCalledWith', function() { + it('passes when the actual was called with matching parameters', function() { var matchersUtil = { - contains: jasmine.createSpy('delegated-contains').and.returnValue(true), - pp: jasmineUnderTest.makePrettyPrinter() - }, - matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(matchersUtil), - calledSpy = new jasmineUnderTest.Spy('called-spy'), - result; + contains: jasmine.createSpy('delegated-contains').and.returnValue(true), + pp: jasmineUnderTest.makePrettyPrinter() + }, + matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(matchersUtil), + calledSpy = new jasmineUnderTest.Spy('called-spy'), + result; calledSpy('a', 'b'); result = matcher.compare(calledSpy, 'a', 'b'); expect(result.pass).toBe(true); - expect(result.message()).toEqual("Expected spy called-spy not to have been called with:\n [ 'a', 'b' ]\nbut it was."); + expect(result.message()).toEqual( + "Expected spy called-spy not to have been called with:\n [ 'a', 'b' ]\nbut it was." + ); }); - it("supports custom equality testers", function() { - var customEqualityTesters = [function() { return true; }], - matchersUtil = new jasmineUnderTest.MatchersUtil({customTesters: customEqualityTesters}), + it('supports custom equality testers', function() { + var customEqualityTesters = [ + function() { + return true; + } + ], + matchersUtil = new jasmineUnderTest.MatchersUtil({ + customTesters: customEqualityTesters + }), matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(matchersUtil), calledSpy = new jasmineUnderTest.Spy('called-spy'), result; @@ -28,25 +35,31 @@ describe("toHaveBeenCalledWith", function() { expect(result.pass).toBe(true); }); - it("fails when the actual was not called", function() { + it('fails when the actual was not called', function() { var matchersUtil = { - contains: jasmine.createSpy('delegated-contains').and.returnValue(false), - pp: jasmineUnderTest.makePrettyPrinter() - }, - matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(matchersUtil), - uncalledSpy = new jasmineUnderTest.Spy('uncalled spy'), - result; + contains: jasmine + .createSpy('delegated-contains') + .and.returnValue(false), + pp: jasmineUnderTest.makePrettyPrinter() + }, + matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(matchersUtil), + uncalledSpy = new jasmineUnderTest.Spy('uncalled spy'), + result; result = matcher.compare(uncalledSpy); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected spy uncalled spy to have been called with:\n [ ]\nbut it was never called."); + expect(result.message()).toEqual( + 'Expected spy uncalled spy to have been called with:\n [ ]\nbut it was never called.' + ); }); - it("fails when the actual was called with different parameters", function() { - var matchersUtil = new jasmineUnderTest.MatchersUtil({pp: jasmineUnderTest.makePrettyPrinter()}), - matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(matchersUtil), - calledSpy = new jasmineUnderTest.Spy('called spy'), - result; + it('fails when the actual was called with different parameters', function() { + var matchersUtil = new jasmineUnderTest.MatchersUtil({ + pp: jasmineUnderTest.makePrettyPrinter() + }), + matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith(matchersUtil), + calledSpy = new jasmineUnderTest.Spy('called spy'), + result; calledSpy('a'); calledSpy('c', 'd'); @@ -55,30 +68,32 @@ describe("toHaveBeenCalledWith", function() { expect(result.pass).toBe(false); expect(result.message()).toEqual( - "Expected spy called spy to have been called with:\n" + - " [ 'a', 'b' ]\n" + - "but actual calls were:\n" + - " [ 'a' ],\n" + - " [ 'c', 'd' ],\n" + - " [ 'a', 'b', 'c' ].\n\n" + - "Call 0:\n" + - " Expected $.length = 1 to equal 2.\n" + - " Expected $[1] = undefined to equal 'b'.\n" + - "Call 1:\n" + - " Expected $[0] = 'c' to equal 'a'.\n" + - " Expected $[1] = 'd' to equal 'b'.\n" + - "Call 2:\n" + - " Expected $.length = 3 to equal 2.\n" + - " Unexpected $[2] = 'c' in array."); + 'Expected spy called spy to have been called with:\n' + + " [ 'a', 'b' ]\n" + + 'but actual calls were:\n' + + " [ 'a' ],\n" + + " [ 'c', 'd' ],\n" + + " [ 'a', 'b', 'c' ].\n\n" + + 'Call 0:\n' + + ' Expected $.length = 1 to equal 2.\n' + + " Expected $[1] = undefined to equal 'b'.\n" + + 'Call 1:\n' + + " Expected $[0] = 'c' to equal 'a'.\n" + + " Expected $[1] = 'd' to equal 'b'.\n" + + 'Call 2:\n' + + ' Expected $.length = 3 to equal 2.\n' + + " Unexpected $[2] = 'c' in array." + ); }); - it("throws an exception when the actual is not a spy", function() { + it('throws an exception when the actual is not a spy', function() { var matcher = jasmineUnderTest.matchers.toHaveBeenCalledWith({ pp: jasmineUnderTest.makePrettyPrinter() }), - fn = function () { - }; + fn = function() {}; - expect(function() { matcher.compare(fn) }).toThrowError(/Expected a spy, but got Function./); + expect(function() { + matcher.compare(fn); + }).toThrowError(/Expected a spy, but got Function./); }); }); diff --git a/spec/core/matchers/toHaveClassSpec.js b/spec/core/matchers/toHaveClassSpec.js index 5f593abc..d56a0a16 100644 --- a/spec/core/matchers/toHaveClassSpec.js +++ b/spec/core/matchers/toHaveClassSpec.js @@ -5,7 +5,10 @@ describe('toHaveClass', function() { it('fails for a DOM element that lacks the expected class', function() { var matcher = jasmineUnderTest.matchers.toHaveClass(), - result = matcher.compare(this.domHelpers.createElementWithClassName(''), 'foo'); + result = matcher.compare( + this.domHelpers.createElementWithClassName(''), + 'foo' + ); expect(result.pass).toBe(false); }); @@ -41,11 +44,11 @@ describe('toHaveClass', function() { var textNode = this.domHelpers.document.createTextNode(''); expect(function() { - matcher.compare(textNode, 'foo') + matcher.compare(textNode, 'foo'); }).toThrowError('HTMLNode is not a DOM element'); expect(function() { - matcher.compare({classList: ''}, 'foo'); + matcher.compare({ classList: '' }, 'foo'); }).toThrowError("Object({ classList: '' }) is not a DOM element"); }); }); diff --git a/spec/core/matchers/toHaveSizeSpec.js b/spec/core/matchers/toHaveSizeSpec.js index d25e39e7..fc5baf91 100644 --- a/spec/core/matchers/toHaveSizeSpec.js +++ b/spec/core/matchers/toHaveSizeSpec.js @@ -18,28 +18,28 @@ describe('toHaveSize', function() { it('passes for an object with the proper number of keys', function() { var matcher = jasmineUnderTest.matchers.toHaveSize(), - result = matcher.compare({a: 1, b: 2}, 2); + result = matcher.compare({ a: 1, b: 2 }, 2); expect(result.pass).toBe(true); }); it('fails for an object with a different number of keys', function() { var matcher = jasmineUnderTest.matchers.toHaveSize(), - result = matcher.compare({a: 1, b: 2}, 1); + result = matcher.compare({ a: 1, b: 2 }, 1); expect(result.pass).toBe(false); }); it('passes for an object with an explicit `length` property that matches', function() { var matcher = jasmineUnderTest.matchers.toHaveSize(), - result = matcher.compare({a: 1, b: 2, length: 5}, 5); + result = matcher.compare({ a: 1, b: 2, length: 5 }, 5); expect(result.pass).toBe(true); }); it('fails for an object with an explicit `length` property that does not match', function() { var matcher = jasmineUnderTest.matchers.toHaveSize(), - result = matcher.compare({a: 1, b: 2, length: 5}, 1); + result = matcher.compare({ a: 1, b: 2, length: 5 }, 1); expect(result.pass).toBe(false); }); @@ -62,8 +62,8 @@ describe('toHaveSize', function() { jasmine.getEnv().requireFunctioningMaps(); var map = new Map(); - map.set('a',1); - map.set('b',2); + map.set('a', 1); + map.set('b', 2); var matcher = jasmineUnderTest.matchers.toHaveSize(), result = matcher.compare(map, 2); @@ -75,8 +75,8 @@ describe('toHaveSize', function() { jasmine.getEnv().requireFunctioningMaps(); var map = new Map(); - map.set('a',1); - map.set('b',2); + map.set('a', 1); + map.set('b', 2); var matcher = jasmineUnderTest.matchers.toHaveSize(), result = matcher.compare(map, 1); diff --git a/spec/core/matchers/toMatchSpec.js b/spec/core/matchers/toMatchSpec.js index b245e34d..aa4d6c54 100644 --- a/spec/core/matchers/toMatchSpec.js +++ b/spec/core/matchers/toMatchSpec.js @@ -1,6 +1,5 @@ -describe("toMatch", function() { - - it("passes when RegExps are equivalent", function() { +describe('toMatch', function() { + it('passes when RegExps are equivalent', function() { var matcher = jasmineUnderTest.matchers.toMatch(), result; @@ -8,7 +7,7 @@ describe("toMatch", function() { expect(result.pass).toBe(true); }); - it("fails when RegExps are not equivalent", function() { + it('fails when RegExps are not equivalent', function() { var matcher = jasmineUnderTest.matchers.toMatch(), result; @@ -16,7 +15,7 @@ describe("toMatch", function() { expect(result.pass).toBe(false); }); - it("passes when the actual matches the expected string as a pattern", function() { + it('passes when the actual matches the expected string as a pattern', function() { var matcher = jasmineUnderTest.matchers.toMatch(), result; @@ -24,7 +23,7 @@ describe("toMatch", function() { expect(result.pass).toBe(true); }); - it("fails when the actual matches the expected string as a pattern", function() { + it('fails when the actual matches the expected string as a pattern', function() { var matcher = jasmineUnderTest.matchers.toMatch(), result; @@ -32,7 +31,7 @@ describe("toMatch", function() { expect(result.pass).toBe(false); }); - it("throws an Error when the expected is not a String or RegExp", function() { + it('throws an Error when the expected is not a String or RegExp', function() { var matcher = jasmineUnderTest.matchers.toMatch(); expect(function() { @@ -40,4 +39,3 @@ describe("toMatch", function() { }).toThrowError(/Expected is not a String or a RegExp/); }); }); - diff --git a/spec/core/matchers/toThrowErrorSpec.js b/spec/core/matchers/toThrowErrorSpec.js index 68fdf8be..c8532276 100644 --- a/spec/core/matchers/toThrowErrorSpec.js +++ b/spec/core/matchers/toThrowErrorSpec.js @@ -1,5 +1,5 @@ -describe("toThrowError", function() { - it("throws an error when the actual is not a function", function() { +describe('toThrowError', function() { + it('throws an error when the actual is not a function', function() { var matcher = jasmineUnderTest.matchers.toThrowError(); expect(function() { @@ -7,10 +7,10 @@ describe("toThrowError", function() { }).toThrowError(/Actual is not a Function/); }); - it("throws an error when the expected is not an Error, string, or RegExp", function() { + it('throws an error when the expected is not an Error, string, or RegExp', function() { var matcher = jasmineUnderTest.matchers.toThrowError(), fn = function() { - throw new Error("foo"); + throw new Error('foo'); }; expect(function() { @@ -18,21 +18,21 @@ describe("toThrowError", function() { }).toThrowError(/Expected is not an Error, string, or RegExp./); }); - it("throws an error when the expected error type is not an Error", function() { + it('throws an error when the expected error type is not an Error', function() { var matcher = jasmineUnderTest.matchers.toThrowError(), fn = function() { - throw new Error("foo"); + throw new Error('foo'); }; expect(function() { - matcher.compare(fn, void 0, "foo"); + matcher.compare(fn, void 0, 'foo'); }).toThrowError(/Expected error type is not an Error./); }); - it("throws an error when the expected error message is not a string or RegExp", function() { + it('throws an error when the expected error message is not a string or RegExp', function() { var matcher = jasmineUnderTest.matchers.toThrowError(), fn = function() { - throw new Error("foo"); + throw new Error('foo'); }; expect(function() { @@ -40,7 +40,7 @@ describe("toThrowError", function() { }).toThrowError(/Expected error message is not a string or RegExp./); }); - it("fails if actual does not throw at all", function() { + it('fails if actual does not throw at all', function() { var matcher = jasmineUnderTest.matchers.toThrowError(), fn = function() { return true; @@ -50,10 +50,10 @@ describe("toThrowError", function() { result = matcher.compare(fn); expect(result.pass).toBe(false); - expect(result.message).toEqual("Expected function to throw an Error."); + expect(result.message).toEqual('Expected function to throw an Error.'); }); - it("fails if thrown is not an instanceof Error", function() { + it('fails if thrown is not an instanceof Error', function() { var matcher = jasmineUnderTest.matchers.toThrowError({ pp: jasmineUnderTest.makePrettyPrinter() }), @@ -64,12 +64,14 @@ describe("toThrowError", function() { result = matcher.compare(fn); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected function to throw an Error, but it threw 4."); + expect(result.message()).toEqual( + 'Expected function to throw an Error, but it threw 4.' + ); }); - describe("when error is from another frame", function() { + describe('when error is from another frame', function() { function isNotRunningInBrowser() { - return typeof document === 'undefined' + return typeof document === 'undefined'; } var iframe = null; @@ -80,31 +82,36 @@ describe("toThrowError", function() { } }); - it("passes if thrown is an instanceof Error regardless of global that contains its constructor", function() { + it('passes if thrown is an instanceof Error regardless of global that contains its constructor', function() { if (isNotRunningInBrowser()) { return; } var matcher = jasmineUnderTest.matchers.toThrowError(); - iframe = document.body.appendChild(document.createElement("iframe")); - iframe.src = "about:blank"; + iframe = document.body.appendChild(document.createElement('iframe')); + iframe.src = 'about:blank'; var iframeDocument = iframe.contentWindow.document; if (iframeDocument.body) { - iframeDocument.body.appendChild(iframeDocument.createElement("script")) - .textContent = "function method() { throw new Error('foo'); }"; + iframeDocument.body.appendChild( + iframeDocument.createElement('script') + ).textContent = "function method() { throw new Error('foo'); }"; } else { // IE 10 and older - iframeDocument.write(""); + iframeDocument.write( + "" + ); } var result = matcher.compare(iframe.contentWindow.method); expect(result.pass).toBe(true); - expect(result.message).toEqual("Expected function not to throw an Error, but it threw Error."); + expect(result.message).toEqual( + 'Expected function not to throw an Error, but it threw Error.' + ); }); }); - it("fails with the correct message if thrown is a falsy value", function() { + it('fails with the correct message if thrown is a falsy value', function() { var matcher = jasmineUnderTest.matchers.toThrowError({ pp: jasmineUnderTest.makePrettyPrinter() }), @@ -115,10 +122,12 @@ describe("toThrowError", function() { result = matcher.compare(fn); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected function to throw an Error, but it threw undefined."); + expect(result.message()).toEqual( + 'Expected function to throw an Error, but it threw undefined.' + ); }); - it("passes if thrown is a type of Error, but there is no expected error", function() { + it('passes if thrown is a type of Error, but there is no expected error', function() { var matcher = jasmineUnderTest.matchers.toThrowError(), fn = function() { throw new TypeError(); @@ -128,70 +137,80 @@ describe("toThrowError", function() { result = matcher.compare(fn); expect(result.pass).toBe(true); - expect(result.message).toEqual("Expected function not to throw an Error, but it threw TypeError."); + expect(result.message).toEqual( + 'Expected function not to throw an Error, but it threw TypeError.' + ); }); - it("passes if thrown is an Error and the expected is the same message", function() { + it('passes if thrown is an Error and the expected is the same message', function() { var matcher = jasmineUnderTest.matchers.toThrowError({ pp: jasmineUnderTest.makePrettyPrinter() }), fn = function() { - throw new Error("foo"); + throw new Error('foo'); }, result; - result = matcher.compare(fn, "foo"); + result = matcher.compare(fn, 'foo'); expect(result.pass).toBe(true); - expect(result.message()).toEqual("Expected function not to throw an exception with message 'foo'."); + expect(result.message()).toEqual( + "Expected function not to throw an exception with message 'foo'." + ); }); - it("fails if thrown is an Error and the expected is not the same message", function() { + it('fails if thrown is an Error and the expected is not the same message', function() { var matcher = jasmineUnderTest.matchers.toThrowError({ pp: jasmineUnderTest.makePrettyPrinter() }), fn = function() { - throw new Error("foo"); + throw new Error('foo'); }, result; - result = matcher.compare(fn, "bar"); + result = matcher.compare(fn, 'bar'); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected function to throw an exception with message 'bar', but it threw an exception with message 'foo'."); + expect(result.message()).toEqual( + "Expected function to throw an exception with message 'bar', but it threw an exception with message 'foo'." + ); }); - it("passes if thrown is an Error and the expected is a RegExp that matches the message", function() { + it('passes if thrown is an Error and the expected is a RegExp that matches the message', function() { var matcher = jasmineUnderTest.matchers.toThrowError({ pp: jasmineUnderTest.makePrettyPrinter() }), fn = function() { - throw new Error("a long message"); + throw new Error('a long message'); }, result; result = matcher.compare(fn, /long/); expect(result.pass).toBe(true); - expect(result.message()).toEqual("Expected function not to throw an exception with a message matching /long/."); + expect(result.message()).toEqual( + 'Expected function not to throw an exception with a message matching /long/.' + ); }); - it("fails if thrown is an Error and the expected is a RegExp that does not match the message", function() { + it('fails if thrown is an Error and the expected is a RegExp that does not match the message', function() { var matcher = jasmineUnderTest.matchers.toThrowError({ pp: jasmineUnderTest.makePrettyPrinter() }), fn = function() { - throw new Error("a long message"); + throw new Error('a long message'); }, result; result = matcher.compare(fn, /foo/); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected function to throw an exception with a message matching /foo/, but it threw an exception with message 'a long message'."); + expect(result.message()).toEqual( + "Expected function to throw an exception with a message matching /foo/, but it threw an exception with message 'a long message'." + ); }); - it("passes if thrown is an Error and the expected the same Error", function() { + it('passes if thrown is an Error and the expected the same Error', function() { var matcher = jasmineUnderTest.matchers.toThrowError(), fn = function() { throw new Error(); @@ -201,12 +220,14 @@ describe("toThrowError", function() { result = matcher.compare(fn, Error); expect(result.pass).toBe(true); - expect(result.message()).toEqual("Expected function not to throw Error."); + expect(result.message()).toEqual('Expected function not to throw Error.'); }); - it("passes if thrown is a custom error that takes arguments and the expected is the same error", function() { + it('passes if thrown is a custom error that takes arguments and the expected is the same error', function() { var matcher = jasmineUnderTest.matchers.toThrowError(), - CustomError = function CustomError(arg) { arg.x }, + CustomError = function CustomError(arg) { + arg.x; + }, fn = function() { throw new CustomError({ x: 1 }); }, @@ -217,10 +238,12 @@ describe("toThrowError", function() { result = matcher.compare(fn, CustomError); expect(result.pass).toBe(true); - expect(result.message()).toEqual("Expected function not to throw CustomError."); + expect(result.message()).toEqual( + 'Expected function not to throw CustomError.' + ); }); - it("fails if thrown is an Error and the expected is a different Error", function() { + it('fails if thrown is an Error and the expected is a different Error', function() { var matcher = jasmineUnderTest.matchers.toThrowError(), fn = function() { throw new Error(); @@ -230,94 +253,108 @@ describe("toThrowError", function() { result = matcher.compare(fn, TypeError); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected function to throw TypeError, but it threw Error."); + expect(result.message()).toEqual( + 'Expected function to throw TypeError, but it threw Error.' + ); }); - it("passes if thrown is a type of Error and it is equal to the expected Error and message", function() { + it('passes if thrown is a type of Error and it is equal to the expected Error and message', function() { var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(true), pp: jasmineUnderTest.makePrettyPrinter() }, matcher = jasmineUnderTest.matchers.toThrowError(matchersUtil), fn = function() { - throw new TypeError("foo"); + throw new TypeError('foo'); }, result; - result = matcher.compare(fn, TypeError, "foo"); + result = matcher.compare(fn, TypeError, 'foo'); expect(result.pass).toBe(true); - expect(result.message()).toEqual("Expected function not to throw TypeError with message 'foo'."); + expect(result.message()).toEqual( + "Expected function not to throw TypeError with message 'foo'." + ); }); - it("passes if thrown is a custom error that takes arguments and it is equal to the expected custom error and message", function() { + it('passes if thrown is a custom error that takes arguments and it is equal to the expected custom error and message', function() { var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(true), pp: jasmineUnderTest.makePrettyPrinter() }, matcher = jasmineUnderTest.matchers.toThrowError(matchersUtil), - CustomError = function CustomError(arg) { this.message = arg.message; }, + CustomError = function CustomError(arg) { + this.message = arg.message; + }, fn = function() { - throw new CustomError({message: "foo"}); + throw new CustomError({ message: 'foo' }); }, result; CustomError.prototype = new Error(); - result = matcher.compare(fn, CustomError, "foo"); + result = matcher.compare(fn, CustomError, 'foo'); expect(result.pass).toBe(true); - expect(result.message()).toEqual("Expected function not to throw CustomError with message 'foo'."); + expect(result.message()).toEqual( + "Expected function not to throw CustomError with message 'foo'." + ); }); - it("fails if thrown is a type of Error and the expected is a different Error", function() { + it('fails if thrown is a type of Error and the expected is a different Error', function() { var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(false), pp: jasmineUnderTest.makePrettyPrinter() }, matcher = jasmineUnderTest.matchers.toThrowError(matchersUtil), fn = function() { - throw new TypeError("foo"); + throw new TypeError('foo'); }, result; - result = matcher.compare(fn, TypeError, "bar"); + result = matcher.compare(fn, TypeError, 'bar'); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected function to throw TypeError with message 'bar', but it threw TypeError with message 'foo'."); + expect(result.message()).toEqual( + "Expected function to throw TypeError with message 'bar', but it threw TypeError with message 'foo'." + ); }); - it("passes if thrown is a type of Error and has the same type as the expected Error and the message matches the expected message", function() { + it('passes if thrown is a type of Error and has the same type as the expected Error and the message matches the expected message', function() { var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(true), pp: jasmineUnderTest.makePrettyPrinter() }, matcher = jasmineUnderTest.matchers.toThrowError(matchersUtil), fn = function() { - throw new TypeError("foo"); + throw new TypeError('foo'); }, result; result = matcher.compare(fn, TypeError, /foo/); expect(result.pass).toBe(true); - expect(result.message()).toEqual("Expected function not to throw TypeError with a message matching /foo/."); + expect(result.message()).toEqual( + 'Expected function not to throw TypeError with a message matching /foo/.' + ); }); - it("fails if thrown is a type of Error and the expected is a different Error", function() { + it('fails if thrown is a type of Error and the expected is a different Error', function() { var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(false), pp: jasmineUnderTest.makePrettyPrinter() }, matcher = jasmineUnderTest.matchers.toThrowError(matchersUtil), fn = function() { - throw new TypeError("foo"); + throw new TypeError('foo'); }, result; result = matcher.compare(fn, TypeError, /bar/); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected function to throw TypeError with a message matching /bar/, but it threw TypeError with message 'foo'."); + expect(result.message()).toEqual( + "Expected function to throw TypeError with a message matching /bar/, but it threw TypeError with message 'foo'." + ); }); }); diff --git a/spec/core/matchers/toThrowMatchingSpec.js b/spec/core/matchers/toThrowMatchingSpec.js index 507683b0..a5ed2c5c 100644 --- a/spec/core/matchers/toThrowMatchingSpec.js +++ b/spec/core/matchers/toThrowMatchingSpec.js @@ -1,16 +1,18 @@ -describe("toThrowMatching", function() { - it("throws an error when the actual is not a function", function() { +describe('toThrowMatching', function() { + it('throws an error when the actual is not a function', function() { var matcher = jasmineUnderTest.matchers.toThrowMatching(); expect(function() { - matcher.compare({}, function() { return true; }); + matcher.compare({}, function() { + return true; + }); }).toThrowError(/Actual is not a Function/); }); - it("throws an error when the expected is not a function", function() { + it('throws an error when the expected is not a function', function() { var matcher = jasmineUnderTest.matchers.toThrowMatching(), fn = function() { - throw new Error("foo"); + throw new Error('foo'); }; expect(function() { @@ -18,20 +20,22 @@ describe("toThrowMatching", function() { }).toThrowError(/Predicate is not a Function/); }); - it("fails if actual does not throw at all", function() { + it('fails if actual does not throw at all', function() { var matcher = jasmineUnderTest.matchers.toThrowMatching(), fn = function() { return true; }, result; - result = matcher.compare(fn, function() { return true; }); + result = matcher.compare(fn, function() { + return true; + }); expect(result.pass).toBe(false); - expect(result.message).toEqual("Expected function to throw an exception."); + expect(result.message).toEqual('Expected function to throw an exception.'); }); - it("fails with the correct message if thrown is a falsy value", function() { + it('fails with the correct message if thrown is a falsy value', function() { var matcher = jasmineUnderTest.matchers.toThrowMatching({ pp: jasmineUnderTest.makePrettyPrinter() }), @@ -40,38 +44,50 @@ describe("toThrowMatching", function() { }, result; - result = matcher.compare(fn, function() { return false; }); + result = matcher.compare(fn, function() { + return false; + }); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected function to throw an exception matching a predicate, but it threw undefined."); + expect(result.message()).toEqual( + 'Expected function to throw an exception matching a predicate, but it threw undefined.' + ); }); - it("passes if the argument is a function that returns true when called with the error", function() { + it('passes if the argument is a function that returns true when called with the error', function() { var matcher = jasmineUnderTest.matchers.toThrowMatching(), - predicate = function(e) { return e.message === "nope" }, + predicate = function(e) { + return e.message === 'nope'; + }, fn = function() { - throw new TypeError("nope"); + throw new TypeError('nope'); }, result; result = matcher.compare(fn, predicate); expect(result.pass).toBe(true); - expect(result.message).toEqual("Expected function not to throw an exception matching a predicate."); + expect(result.message).toEqual( + 'Expected function not to throw an exception matching a predicate.' + ); }); - it("fails if the argument is a function that returns false when called with the error", function() { + it('fails if the argument is a function that returns false when called with the error', function() { var matcher = jasmineUnderTest.matchers.toThrowMatching({ pp: jasmineUnderTest.makePrettyPrinter() }), - predicate = function(e) { return e.message === "oh no" }, + predicate = function(e) { + return e.message === 'oh no'; + }, fn = function() { - throw new TypeError("nope"); + throw new TypeError('nope'); }, result; result = matcher.compare(fn, predicate); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected function to throw an exception matching a predicate, but it threw TypeError with message 'nope'."); + expect(result.message()).toEqual( + "Expected function to throw an exception matching a predicate, but it threw TypeError with message 'nope'." + ); }); }); diff --git a/spec/core/matchers/toThrowSpec.js b/spec/core/matchers/toThrowSpec.js index 7144b2b3..0ed049d3 100644 --- a/spec/core/matchers/toThrowSpec.js +++ b/spec/core/matchers/toThrowSpec.js @@ -1,6 +1,5 @@ -describe("toThrow", function() { - - it("throws an error when the actual is not a function", function() { +describe('toThrow', function() { + it('throws an error when the actual is not a function', function() { var matcher = jasmineUnderTest.matchers.toThrow(); expect(function() { @@ -9,7 +8,7 @@ describe("toThrow", function() { }).toThrowError(/Actual is not a Function/); }); - it("fails if actual does not throw", function() { + it('fails if actual does not throw', function() { var matcher = jasmineUnderTest.matchers.toThrow(), fn = function() { return true; @@ -19,10 +18,10 @@ describe("toThrow", function() { result = matcher.compare(fn); expect(result.pass).toBe(false); - expect(result.message).toEqual("Expected function to throw an exception."); + expect(result.message).toEqual('Expected function to throw an exception.'); }); - it("passes if it throws but there is no expected", function() { + it('passes if it throws but there is no expected', function() { var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(true), pp: jasmineUnderTest.makePrettyPrinter() @@ -36,10 +35,12 @@ describe("toThrow", function() { result = matcher.compare(fn); expect(result.pass).toBe(true); - expect(result.message()).toEqual("Expected function not to throw, but it threw 5."); + expect(result.message()).toEqual( + 'Expected function not to throw, but it threw 5.' + ); }); - it("passes even if what is thrown is falsy", function() { + it('passes even if what is thrown is falsy', function() { var matcher = jasmineUnderTest.matchers.toThrow({ pp: jasmineUnderTest.makePrettyPrinter() }), @@ -50,10 +51,12 @@ describe("toThrow", function() { result = matcher.compare(fn); expect(result.pass).toBe(true); - expect(result.message()).toEqual("Expected function not to throw, but it threw undefined."); + expect(result.message()).toEqual( + 'Expected function not to throw, but it threw undefined.' + ); }); - it("passes if what is thrown is equivalent to what is expected", function() { + it('passes if what is thrown is equivalent to what is expected', function() { var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(true), pp: jasmineUnderTest.makePrettyPrinter() @@ -67,10 +70,10 @@ describe("toThrow", function() { result = matcher.compare(fn, 5); expect(result.pass).toBe(true); - expect(result.message()).toEqual("Expected function not to throw 5."); + expect(result.message()).toEqual('Expected function not to throw 5.'); }); - it("fails if what is thrown is not equivalent to what is expected", function() { + it('fails if what is thrown is not equivalent to what is expected', function() { var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(false), pp: jasmineUnderTest.makePrettyPrinter() @@ -81,13 +84,15 @@ describe("toThrow", function() { }, result; - result = matcher.compare(fn, "foo"); + result = matcher.compare(fn, 'foo'); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected function to throw 'foo', but it threw 5."); + expect(result.message()).toEqual( + "Expected function to throw 'foo', but it threw 5." + ); }); - it("fails if what is thrown is not equivalent to undefined", function() { + it('fails if what is thrown is not equivalent to undefined', function() { var matchersUtil = { equals: jasmine.createSpy('delegated-equal').and.returnValue(false), pp: jasmineUnderTest.makePrettyPrinter() @@ -101,6 +106,8 @@ describe("toThrow", function() { result = matcher.compare(fn, void 0); expect(result.pass).toBe(false); - expect(result.message()).toEqual("Expected function to throw undefined, but it threw 5."); + expect(result.message()).toEqual( + 'Expected function to throw undefined, but it threw 5.' + ); }); }); diff --git a/src/core/asymmetric_equality/Any.js b/src/core/asymmetric_equality/Any.js index 61273deb..bbee1bdc 100644 --- a/src/core/asymmetric_equality/Any.js +++ b/src/core/asymmetric_equality/Any.js @@ -1,10 +1,9 @@ getJasmineRequireObj().Any = function(j$) { - function Any(expectedObject) { if (typeof expectedObject === 'undefined') { throw new TypeError( 'jasmine.any() expects to be passed a constructor function. ' + - 'Please pass one or use jasmine.anything() to match any object.' + 'Please pass one or use jasmine.anything() to match any object.' ); } this.expectedObject = expectedObject; diff --git a/src/core/asymmetric_equality/Anything.js b/src/core/asymmetric_equality/Anything.js index 11c6571c..ce436cb4 100644 --- a/src/core/asymmetric_equality/Anything.js +++ b/src/core/asymmetric_equality/Anything.js @@ -1,5 +1,4 @@ getJasmineRequireObj().Anything = function(j$) { - function Anything() {} Anything.prototype.asymmetricMatch = function(other) { diff --git a/src/core/asymmetric_equality/ArrayContaining.js b/src/core/asymmetric_equality/ArrayContaining.js index 7faea8b4..c00a2dc0 100644 --- a/src/core/asymmetric_equality/ArrayContaining.js +++ b/src/core/asymmetric_equality/ArrayContaining.js @@ -5,7 +5,11 @@ getJasmineRequireObj().ArrayContaining = function(j$) { ArrayContaining.prototype.asymmetricMatch = function(other, matchersUtil) { if (!j$.isArray_(this.sample)) { - throw new Error('You must provide an array to arrayContaining, not ' + j$.pp(this.sample) + '.'); + throw new Error( + 'You must provide an array to arrayContaining, not ' + + j$.pp(this.sample) + + '.' + ); } // If the actual parameter is not an array, we can fail immediately, since it couldn't @@ -25,8 +29,8 @@ getJasmineRequireObj().ArrayContaining = function(j$) { return true; }; - ArrayContaining.prototype.jasmineToString = function (pp) { - return ''; + ArrayContaining.prototype.jasmineToString = function(pp) { + return ''; }; return ArrayContaining; diff --git a/src/core/asymmetric_equality/ArrayWithExactContents.js b/src/core/asymmetric_equality/ArrayWithExactContents.js index d2049047..f207dc7a 100644 --- a/src/core/asymmetric_equality/ArrayWithExactContents.js +++ b/src/core/asymmetric_equality/ArrayWithExactContents.js @@ -1,12 +1,18 @@ getJasmineRequireObj().ArrayWithExactContents = function(j$) { - function ArrayWithExactContents(sample) { this.sample = sample; } - ArrayWithExactContents.prototype.asymmetricMatch = function(other, matchersUtil) { + ArrayWithExactContents.prototype.asymmetricMatch = function( + other, + matchersUtil + ) { if (!j$.isArray_(this.sample)) { - throw new Error('You must provide an array to arrayWithExactContents, not ' + j$.pp(this.sample) + '.'); + throw new Error( + 'You must provide an array to arrayWithExactContents, not ' + + j$.pp(this.sample) + + '.' + ); } if (this.sample.length !== other.length) { diff --git a/src/core/asymmetric_equality/Empty.js b/src/core/asymmetric_equality/Empty.js index 224c0f5f..1dd28948 100644 --- a/src/core/asymmetric_equality/Empty.js +++ b/src/core/asymmetric_equality/Empty.js @@ -1,8 +1,7 @@ -getJasmineRequireObj().Empty = function (j$) { - +getJasmineRequireObj().Empty = function(j$) { function Empty() {} - Empty.prototype.asymmetricMatch = function (other) { + Empty.prototype.asymmetricMatch = function(other) { if (j$.isString_(other) || j$.isArray_(other) || j$.isTypedArray_(other)) { return other.length === 0; } @@ -17,7 +16,7 @@ getJasmineRequireObj().Empty = function (j$) { return false; }; - Empty.prototype.jasmineToString = function () { + Empty.prototype.jasmineToString = function() { return ''; }; diff --git a/src/core/asymmetric_equality/Falsy.js b/src/core/asymmetric_equality/Falsy.js index 242e0af3..d1d3c8ff 100644 --- a/src/core/asymmetric_equality/Falsy.js +++ b/src/core/asymmetric_equality/Falsy.js @@ -1,5 +1,4 @@ getJasmineRequireObj().Falsy = function(j$) { - function Falsy() {} Falsy.prototype.asymmetricMatch = function(other) { diff --git a/src/core/asymmetric_equality/MapContaining.js b/src/core/asymmetric_equality/MapContaining.js index ba6b0ce9..0270d1be 100644 --- a/src/core/asymmetric_equality/MapContaining.js +++ b/src/core/asymmetric_equality/MapContaining.js @@ -1,7 +1,9 @@ getJasmineRequireObj().MapContaining = function(j$) { function MapContaining(sample) { if (!j$.isMap(sample)) { - throw new Error('You must provide a map to `mapContaining`, not ' + j$.pp(sample)); + throw new Error( + 'You must provide a map to `mapContaining`, not ' + j$.pp(sample) + ); } this.sample = sample; @@ -17,8 +19,8 @@ getJasmineRequireObj().MapContaining = function(j$) { var hasMatch = false; j$.util.forEachBreakable(other, function(oBreakLoop, oValue, oKey) { if ( - matchersUtil.equals(oKey, key) - && matchersUtil.equals(oValue, value) + matchersUtil.equals(oKey, key) && + matchersUtil.equals(oValue, value) ) { hasMatch = true; oBreakLoop(); diff --git a/src/core/asymmetric_equality/NotEmpty.js b/src/core/asymmetric_equality/NotEmpty.js index 3c0368cf..361b6978 100644 --- a/src/core/asymmetric_equality/NotEmpty.js +++ b/src/core/asymmetric_equality/NotEmpty.js @@ -1,8 +1,7 @@ -getJasmineRequireObj().NotEmpty = function (j$) { - +getJasmineRequireObj().NotEmpty = function(j$) { function NotEmpty() {} - NotEmpty.prototype.asymmetricMatch = function (other) { + NotEmpty.prototype.asymmetricMatch = function(other) { if (j$.isString_(other) || j$.isArray_(other) || j$.isTypedArray_(other)) { return other.length !== 0; } @@ -18,7 +17,7 @@ getJasmineRequireObj().NotEmpty = function (j$) { return false; }; - NotEmpty.prototype.jasmineToString = function () { + NotEmpty.prototype.jasmineToString = function() { return ''; }; diff --git a/src/core/asymmetric_equality/ObjectContaining.js b/src/core/asymmetric_equality/ObjectContaining.js index 4a8f4385..5e473033 100644 --- a/src/core/asymmetric_equality/ObjectContaining.js +++ b/src/core/asymmetric_equality/ObjectContaining.js @@ -1,5 +1,4 @@ getJasmineRequireObj().ObjectContaining = function(j$) { - function ObjectContaining(sample) { this.sample = sample; } @@ -17,7 +16,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } function hasProperty(obj, property) { - if (!obj || typeof(obj) !== 'object') { + if (!obj || typeof obj !== 'object') { return false; } @@ -29,12 +28,22 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } ObjectContaining.prototype.asymmetricMatch = function(other, matchersUtil) { - if (typeof(this.sample) !== 'object') { throw new Error('You must provide an object to objectContaining, not \''+this.sample+'\'.'); } - if (typeof(other) !== 'object') { return false; } + if (typeof this.sample !== 'object') { + throw new Error( + "You must provide an object to objectContaining, not '" + + this.sample + + "'." + ); + } + if (typeof other !== 'object') { + return false; + } for (var property in this.sample) { - if (!hasProperty(other, property) || - !matchersUtil.equals(this.sample[property], other[property])) { + if ( + !hasProperty(other, property) || + !matchersUtil.equals(this.sample[property], other[property]) + ) { return false; } } @@ -51,7 +60,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } var filteredOther = {}; - Object.keys(this.sample).forEach(function (k) { + Object.keys(this.sample).forEach(function(k) { // eq short-circuits comparison of objects that have different key sets, // so include all keys even if undefined. filteredOther[k] = other[k]; diff --git a/src/core/asymmetric_equality/SetContaining.js b/src/core/asymmetric_equality/SetContaining.js index f3ad3527..56828085 100644 --- a/src/core/asymmetric_equality/SetContaining.js +++ b/src/core/asymmetric_equality/SetContaining.js @@ -1,7 +1,9 @@ getJasmineRequireObj().SetContaining = function(j$) { function SetContaining(sample) { if (!j$.isSet(sample)) { - throw new Error('You must provide a set to `setContaining`, not ' + j$.pp(sample)); + throw new Error( + 'You must provide a set to `setContaining`, not ' + j$.pp(sample) + ); } this.sample = sample; diff --git a/src/core/asymmetric_equality/StringMatching.js b/src/core/asymmetric_equality/StringMatching.js index 72334723..ebcc1738 100644 --- a/src/core/asymmetric_equality/StringMatching.js +++ b/src/core/asymmetric_equality/StringMatching.js @@ -1,5 +1,4 @@ getJasmineRequireObj().StringMatching = function(j$) { - function StringMatching(expected) { if (!j$.isString_(expected) && !j$.isA_('RegExp', expected)) { throw new Error('Expected is not a String or a RegExp'); diff --git a/src/core/asymmetric_equality/Truthy.js b/src/core/asymmetric_equality/Truthy.js index a852fdaf..9e527164 100644 --- a/src/core/asymmetric_equality/Truthy.js +++ b/src/core/asymmetric_equality/Truthy.js @@ -1,5 +1,4 @@ getJasmineRequireObj().Truthy = function(j$) { - function Truthy() {} Truthy.prototype.asymmetricMatch = function(other) { diff --git a/src/core/matchers/DiffBuilder.js b/src/core/matchers/DiffBuilder.js index 70b52ea7..c8c0e497 100644 --- a/src/core/matchers/DiffBuilder.js +++ b/src/core/matchers/DiffBuilder.js @@ -1,4 +1,4 @@ -getJasmineRequireObj().DiffBuilder = function (j$) { +getJasmineRequireObj().DiffBuilder = function(j$) { return function DiffBuilder(config) { var prettyPrinter = (config || {}).prettyPrinter || j$.makePrettyPrinter(), mismatches = new j$.MismatchTree(), @@ -7,21 +7,28 @@ getJasmineRequireObj().DiffBuilder = function (j$) { expectedRoot = undefined; return { - setRoots: function (actual, expected) { + setRoots: function(actual, expected) { actualRoot = actual; expectedRoot = expected; }, - recordMismatch: function (formatter) { + recordMismatch: function(formatter) { mismatches.add(path, formatter); }, - getMessage: function () { + getMessage: function() { var messages = []; - mismatches.traverse(function (path, isLeaf, formatter) { - var actualCustom, expectedCustom, useCustom, - derefResult = dereferencePath(path, actualRoot, expectedRoot, prettyPrinter), + mismatches.traverse(function(path, isLeaf, formatter) { + var actualCustom, + expectedCustom, + useCustom, + derefResult = dereferencePath( + path, + actualRoot, + expectedRoot, + prettyPrinter + ), actual = derefResult.actual, expected = derefResult.expected; @@ -32,15 +39,22 @@ getJasmineRequireObj().DiffBuilder = function (j$) { actualCustom = prettyPrinter.customFormat_(actual); expectedCustom = prettyPrinter.customFormat_(expected); - useCustom = !(j$.util.isUndefined(actualCustom) && j$.util.isUndefined(expectedCustom)); + useCustom = !( + j$.util.isUndefined(actualCustom) && + j$.util.isUndefined(expectedCustom) + ); if (useCustom) { - messages.push(wrapPrettyPrinted(actualCustom, expectedCustom, path)); + messages.push( + wrapPrettyPrinted(actualCustom, expectedCustom, path) + ); return false; // don't recurse further } if (isLeaf) { - messages.push(defaultFormatter(actual, expected, path, prettyPrinter)); + messages.push( + defaultFormatter(actual, expected, path, prettyPrinter) + ); } return true; @@ -49,7 +63,7 @@ getJasmineRequireObj().DiffBuilder = function (j$) { return messages.join('\n'); }, - withPath: function (pathComponent, block) { + withPath: function(pathComponent, block) { var oldPath = path; path = path.add(pathComponent); block(); @@ -58,22 +72,32 @@ getJasmineRequireObj().DiffBuilder = function (j$) { }; function defaultFormatter(actual, expected, path, prettyPrinter) { - return wrapPrettyPrinted(prettyPrinter(actual), prettyPrinter(expected), path); + return wrapPrettyPrinted( + prettyPrinter(actual), + prettyPrinter(expected), + path + ); } function wrapPrettyPrinted(actual, expected, path) { - return 'Expected ' + - path + (path.depth() ? ' = ' : '') + + return ( + 'Expected ' + + path + + (path.depth() ? ' = ' : '') + actual + ' to equal ' + expected + - '.'; + '.' + ); } }; function dereferencePath(objectPath, actual, expected, pp) { function handleAsymmetricExpected() { - if (j$.isAsymmetricEqualityTester_(expected) && j$.isFunction_(expected.valuesForDiff_)) { + if ( + j$.isAsymmetricEqualityTester_(expected) && + j$.isFunction_(expected.valuesForDiff_) + ) { var asymmetricResult = expected.valuesForDiff_(actual, pp); expected = asymmetricResult.self; actual = asymmetricResult.other; @@ -89,7 +113,6 @@ getJasmineRequireObj().DiffBuilder = function (j$) { handleAsymmetricExpected(); } - return {actual: actual, expected: expected}; + return { actual: actual, expected: expected }; } - }; diff --git a/src/core/matchers/MismatchTree.js b/src/core/matchers/MismatchTree.js index 1ce356de..3fdab889 100644 --- a/src/core/matchers/MismatchTree.js +++ b/src/core/matchers/MismatchTree.js @@ -1,5 +1,4 @@ -getJasmineRequireObj().MismatchTree = function (j$) { - +getJasmineRequireObj().MismatchTree = function(j$) { /* To be able to apply custom object formatters at all possible levels of an object graph, DiffBuilder needs to be able to know not just where the @@ -14,7 +13,7 @@ getJasmineRequireObj().MismatchTree = function (j$) { this.isMismatch = false; } - MismatchTree.prototype.add = function (path, formatter) { + MismatchTree.prototype.add = function(path, formatter) { var key, child; if (path.depth() === 0) { @@ -34,8 +33,9 @@ getJasmineRequireObj().MismatchTree = function (j$) { } }; - MismatchTree.prototype.traverse = function (visit) { - var i, hasChildren = this.children.length > 0; + MismatchTree.prototype.traverse = function(visit) { + var i, + hasChildren = this.children.length > 0; if (this.isMismatch || hasChildren) { if (visit(this.path, !hasChildren, this.formatter)) { @@ -59,4 +59,3 @@ getJasmineRequireObj().MismatchTree = function (j$) { return MismatchTree; }; - diff --git a/src/core/matchers/ObjectPath.js b/src/core/matchers/ObjectPath.js index a9acfdb2..2ffc8843 100644 --- a/src/core/matchers/ObjectPath.js +++ b/src/core/matchers/ObjectPath.js @@ -32,7 +32,7 @@ getJasmineRequireObj().ObjectPath = function(j$) { return '.' + prop; } - return '[\'' + prop + '\']'; + return "['" + prop + "']"; } function map(array, fn) { diff --git a/src/core/matchers/async/toBePending.js b/src/core/matchers/async/toBePending.js index c73aa3d3..1e438d4f 100644 --- a/src/core/matchers/async/toBePending.js +++ b/src/core/matchers/async/toBePending.js @@ -17,8 +17,12 @@ getJasmineRequireObj().toBePending = function(j$) { } var want = {}; return Promise.race([actual, Promise.resolve(want)]).then( - function(got) { return {pass: want === got}; }, - function() { return {pass: false}; } + function(got) { + return { pass: want === got }; + }, + function() { + return { pass: false }; + } ); } }; diff --git a/src/core/matchers/async/toBeRejected.js b/src/core/matchers/async/toBeRejected.js index 3ec95bf3..d75fa34f 100644 --- a/src/core/matchers/async/toBeRejected.js +++ b/src/core/matchers/async/toBeRejected.js @@ -17,8 +17,12 @@ getJasmineRequireObj().toBeRejected = function(j$) { throw new Error('Expected toBeRejected to be called on a promise.'); } return actual.then( - function() { return {pass: false}; }, - function() { return {pass: true}; } + function() { + return { pass: false }; + }, + function() { + return { pass: true }; + } ); } }; diff --git a/src/core/matchers/async/toBeRejectedWith.js b/src/core/matchers/async/toBeRejectedWith.js index 6c0af904..7436dbc7 100644 --- a/src/core/matchers/async/toBeRejectedWith.js +++ b/src/core/matchers/async/toBeRejectedWith.js @@ -15,35 +15,44 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { return { compare: function(actualPromise, expectedValue) { if (!j$.isPromiseLike(actualPromise)) { - throw new Error('Expected toBeRejectedWith to be called on a promise.'); + throw new Error( + 'Expected toBeRejectedWith to be called on a promise.' + ); } function prefix(passed) { - return 'Expected a promise ' + + return ( + 'Expected a promise ' + (passed ? 'not ' : '') + - 'to be rejected with ' + matchersUtil.pp(expectedValue); + 'to be rejected with ' + + matchersUtil.pp(expectedValue) + ); } return actualPromise.then( function() { - return { - pass: false, - message: prefix(false) + ' but it was resolved.' - }; - }, - function(actualValue) { - if (matchersUtil.equals(actualValue, expectedValue)) { - return { - pass: true, - message: prefix(true) + '.' - }; - } else { return { pass: false, - message: prefix(false) + ' but it was rejected with ' + matchersUtil.pp(actualValue) + '.' + message: prefix(false) + ' but it was resolved.' }; + }, + function(actualValue) { + if (matchersUtil.equals(actualValue, expectedValue)) { + return { + pass: true, + message: prefix(true) + '.' + }; + } else { + return { + pass: false, + message: + prefix(false) + + ' but it was rejected with ' + + matchersUtil.pp(actualValue) + + '.' + }; + } } - } ); } }; diff --git a/src/core/matchers/async/toBeRejectedWithError.js b/src/core/matchers/async/toBeRejectedWithError.js index 203cd863..5b2aed52 100644 --- a/src/core/matchers/async/toBeRejectedWithError.js +++ b/src/core/matchers/async/toBeRejectedWithError.js @@ -18,7 +18,9 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return { compare: function(actualPromise, arg1, arg2) { if (!j$.isPromiseLike(actualPromise)) { - throw new Error('Expected toBeRejectedWithError to be called on a promise.'); + throw new Error( + 'Expected toBeRejectedWithError to be called on a promise.' + ); } var expected = getExpectedFromArgs(arg1, arg2, matchersUtil); @@ -30,7 +32,9 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { message: 'Expected a promise to be rejected but it was resolved.' }; }, - function(actualValue) { return matchError(actualValue, expected, matchersUtil); } + function(actualValue) { + return matchError(actualValue, expected, matchersUtil); + } ); } }; @@ -42,16 +46,25 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { } if (!(actual instanceof expected.error)) { - return fail(expected, 'rejected with type ' + j$.fnNameFor(actual.constructor)); + return fail( + expected, + 'rejected with type ' + j$.fnNameFor(actual.constructor) + ); } var actualMessage = actual.message; - if (actualMessage === expected.message || typeof expected.message === 'undefined') { + if ( + actualMessage === expected.message || + typeof expected.message === 'undefined' + ) { return pass(expected); } - if (expected.message instanceof RegExp && expected.message.test(actualMessage)) { + if ( + expected.message instanceof RegExp && + expected.message.test(actualMessage) + ) { return pass(expected); } @@ -61,18 +74,25 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { function pass(expected) { return { pass: true, - message: 'Expected a promise not to be rejected with ' + expected.printValue + ', but it was.' + message: + 'Expected a promise not to be rejected with ' + + expected.printValue + + ', but it was.' }; } function fail(expected, message) { return { pass: false, - message: 'Expected a promise to be rejected with ' + expected.printValue + ' but it was ' + message + '.' + message: + 'Expected a promise to be rejected with ' + + expected.printValue + + ' but it was ' + + message + + '.' }; } - function getExpectedFromArgs(arg1, arg2, matchersUtil) { var error, message; @@ -87,11 +107,16 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return { error: error, message: message, - printValue: j$.fnNameFor(error) + (typeof message === 'undefined' ? '' : ': ' + matchersUtil.pp(message)) + printValue: + j$.fnNameFor(error) + + (typeof message === 'undefined' ? '' : ': ' + matchersUtil.pp(message)) }; } function isErrorConstructor(value) { - return typeof value === 'function' && (value === Error || j$.isError_(value.prototype)); + return ( + typeof value === 'function' && + (value === Error || j$.isError_(value.prototype)) + ); } }; diff --git a/src/core/matchers/async/toBeResolved.js b/src/core/matchers/async/toBeResolved.js index 997ddeea..b9dda27a 100644 --- a/src/core/matchers/async/toBeResolved.js +++ b/src/core/matchers/async/toBeResolved.js @@ -18,8 +18,12 @@ getJasmineRequireObj().toBeResolved = function(j$) { } return actual.then( - function() { return {pass: true}; }, - function() { return {pass: false}; } + function() { + return { pass: true }; + }, + function() { + return { pass: false }; + } ); } }; diff --git a/src/core/matchers/async/toBeResolvedTo.js b/src/core/matchers/async/toBeResolvedTo.js index 61abb9f2..f95e7b10 100644 --- a/src/core/matchers/async/toBeResolvedTo.js +++ b/src/core/matchers/async/toBeResolvedTo.js @@ -19,9 +19,12 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { } function prefix(passed) { - return 'Expected a promise ' + + return ( + 'Expected a promise ' + (passed ? 'not ' : '') + - 'to be resolved to ' + matchersUtil.pp(expectedValue); + 'to be resolved to ' + + matchersUtil.pp(expectedValue) + ); } return actualPromise.then( @@ -34,7 +37,11 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { } else { return { pass: false, - message: prefix(false) + ' but it was resolved to ' + matchersUtil.pp(actualValue) + '.' + message: + prefix(false) + + ' but it was resolved to ' + + matchersUtil.pp(actualValue) + + '.' }; } }, diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index d473976d..6a74d89d 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -21,7 +21,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { * @return {string} The pretty-printed value */ this.pp = options.pp || function() {}; - }; + } /** * Determines whether `haystack` contains `needle`, using the same comparison @@ -39,9 +39,10 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return haystack.has(needle); } - if ((Object.prototype.toString.apply(haystack) === '[object Array]') || - (!!haystack && !haystack.indexOf)) - { + if ( + Object.prototype.toString.apply(haystack) === '[object Array]' || + (!!haystack && !haystack.indexOf) + ) { for (var i = 0; i < haystack.length; i++) { if (this.equals(haystack[i], needle, customTesters)) { return true; @@ -60,9 +61,12 @@ getJasmineRequireObj().MatchersUtil = function(j$) { isNot = args[1], actual = args[2], expected = args.slice(3), - englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { return ' ' + s.toLowerCase(); }); + englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { + return ' ' + s.toLowerCase(); + }); - var message = 'Expected ' + + var message = + 'Expected ' + self.pp(actual) + (isNot ? ' not ' : ' ') + englishyPredicate; @@ -79,20 +83,41 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return message + '.'; }; - MatchersUtil.prototype.asymmetricDiff_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { + MatchersUtil.prototype.asymmetricDiff_ = function( + a, + b, + aStack, + bStack, + customTesters, + diffBuilder + ) { if (j$.isFunction_(b.valuesForDiff_)) { var values = b.valuesForDiff_(a, this.pp); - this.eq_(values.other, values.self, aStack, bStack, customTesters, diffBuilder); + this.eq_( + values.other, + values.self, + aStack, + bStack, + customTesters, + diffBuilder + ); } else { diffBuilder.recordMismatch(); } }; - MatchersUtil.prototype.asymmetricMatch_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { + MatchersUtil.prototype.asymmetricMatch_ = function( + a, + b, + aStack, + bStack, + customTesters, + diffBuilder + ) { var asymmetricA = j$.isAsymmetricEqualityTester_(a), - asymmetricB = j$.isAsymmetricEqualityTester_(b), - shim, - result; + asymmetricB = j$.isAsymmetricEqualityTester_(b), + shim, + result; if (asymmetricA === asymmetricB) { return undefined; @@ -127,7 +152,12 @@ getJasmineRequireObj().MatchersUtil = function(j$) { * @param [customTesters] An array of custom equality testers * @returns {boolean} True if the values are equal */ - MatchersUtil.prototype.equals = function(a, b, customTestersOrDiffBuilder, diffBuilderOrNothing) { + MatchersUtil.prototype.equals = function( + a, + b, + customTestersOrDiffBuilder, + diffBuilderOrNothing + ) { var customTesters, diffBuilder; if (isDiffBuilder(customTestersOrDiffBuilder)) { @@ -146,10 +176,26 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // Equality function lovingly adapted from isEqual in // [Underscore](http://underscorejs.org) - MatchersUtil.prototype.eq_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { - var result = true, self = this, i; + MatchersUtil.prototype.eq_ = function( + a, + b, + aStack, + bStack, + customTesters, + diffBuilder + ) { + var result = true, + self = this, + i; - var asymmetricResult = this.asymmetricMatch_(a, b, aStack, bStack, customTesters, diffBuilder); + var asymmetricResult = this.asymmetricMatch_( + a, + b, + aStack, + bStack, + customTesters, + diffBuilder + ); if (!j$.util.isUndefined(asymmetricResult)) { return asymmetricResult; } @@ -207,7 +253,8 @@ getJasmineRequireObj().MatchersUtil = function(j$) { case '[object Number]': // `NaN`s are equivalent, but non-reflexive. An `egal` comparison is performed for // other numeric values. - result = a != +a ? b != +b : (a === 0 && b === 0 ? 1 / a == 1 / b : a == +b); + result = + a != +a ? b != +b : a === 0 && b === 0 ? 1 / a == 1 / b : a == +b; if (!result) { diffBuilder.recordMismatch(); } @@ -224,10 +271,12 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return result; // RegExps are compared by their source patterns and flags. case '[object RegExp]': - return a.source == b.source && + return ( + a.source == b.source && a.global == b.global && a.multiline == b.multiline && - a.ignoreCase == b.ignoreCase; + a.ignoreCase == b.ignoreCase + ); } if (typeof a != 'object' || typeof b != 'object') { diffBuilder.recordMismatch(); @@ -261,7 +310,9 @@ getJasmineRequireObj().MatchersUtil = function(j$) { while (length--) { // Linear search. Performance is inversely proportional to the number of // unique nested structures. - if (aStack[length] == a) { return bStack[length] == b; } + if (aStack[length] == a) { + return bStack[length] == b; + } } // Add the first object to the stack of traversed objects. aStack.push(a); @@ -283,10 +334,20 @@ getJasmineRequireObj().MatchersUtil = function(j$) { for (i = 0; i < aLength || i < bLength; i++) { diffBuilder.withPath(i, function() { if (i >= bLength) { - diffBuilder.recordMismatch(actualArrayIsLongerFormatter.bind(null, self.pp)); + diffBuilder.recordMismatch( + actualArrayIsLongerFormatter.bind(null, self.pp) + ); result = false; } else { - result = self.eq_(i < aLength ? a[i] : void 0, i < bLength ? b[i] : void 0, aStack, bStack, customTesters, diffBuilder) && result; + result = + self.eq_( + i < aLength ? a[i] : void 0, + i < bLength ? b[i] : void 0, + aStack, + bStack, + customTesters, + diffBuilder + ) && result; } }); } @@ -301,11 +362,11 @@ getJasmineRequireObj().MatchersUtil = function(j$) { var keysA = []; var keysB = []; - a.forEach( function( valueA, keyA ) { - keysA.push( keyA ); + a.forEach(function(valueA, keyA) { + keysA.push(keyA); }); - b.forEach( function( valueB, keyB ) { - keysB.push( keyB ); + b.forEach(function(valueB, keyB) { + keysB.push(keyB); }); // For both sets of keys, check they map to equal values in both maps. @@ -326,13 +387,30 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // Only use the cmpKey when one of the keys is asymmetric and the corresponding key matches, // otherwise explicitly look up the mapKey in the other Map since we want keys with unique // obj identity (that are otherwise equal) to not match. - if (j$.isAsymmetricEqualityTester_(mapKey) || j$.isAsymmetricEqualityTester_(cmpKey) && - this.eq_(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { + if ( + j$.isAsymmetricEqualityTester_(mapKey) || + (j$.isAsymmetricEqualityTester_(cmpKey) && + this.eq_( + mapKey, + cmpKey, + aStack, + bStack, + customTesters, + j$.NullDiffBuilder() + )) + ) { mapValueB = b.get(cmpKey); } else { mapValueB = b.get(mapKey); } - result = this.eq_(mapValueA, mapValueB, aStack, bStack, customTesters, j$.NullDiffBuilder()); + result = this.eq_( + mapValueA, + mapValueB, + aStack, + bStack, + customTesters, + j$.NullDiffBuilder() + ); } } @@ -347,12 +425,12 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } var valuesA = []; - a.forEach( function( valueA ) { - valuesA.push( valueA ); + a.forEach(function(valueA) { + valuesA.push(valueA); }); var valuesB = []; - b.forEach( function( valueB ) { - valuesB.push( valueB ); + b.forEach(function(valueB) { + valuesB.push(valueB); }); // For both sets, check they are all contained in the other set @@ -376,7 +454,14 @@ getJasmineRequireObj().MatchersUtil = function(j$) { otherValue = otherValues[l]; prevStackSize = baseStack.length; // compare by value equality - found = this.eq_(baseValue, otherValue, baseStack, otherStack, customTesters, j$.NullDiffBuilder()); + found = this.eq_( + baseValue, + otherValue, + baseStack, + otherStack, + customTesters, + j$.NullDiffBuilder() + ); if (!found && prevStackSize !== baseStack.length) { baseStack.splice(prevStackSize); otherStack.splice(prevStackSize); @@ -391,27 +476,35 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return false; } } else { - // Objects with different constructors are not equivalent, but `Object`s // or `Array`s from different frames are. - var aCtor = a.constructor, bCtor = b.constructor; - if (aCtor !== bCtor && - isFunction(aCtor) && isFunction(bCtor) && - a instanceof aCtor && b instanceof bCtor && - !(aCtor instanceof aCtor && bCtor instanceof bCtor)) { - - diffBuilder.recordMismatch(constructorsAreDifferentFormatter.bind(null, this.pp)); + var aCtor = a.constructor, + bCtor = b.constructor; + if ( + aCtor !== bCtor && + isFunction(aCtor) && + isFunction(bCtor) && + a instanceof aCtor && + b instanceof bCtor && + !(aCtor instanceof aCtor && bCtor instanceof bCtor) + ) { + diffBuilder.recordMismatch( + constructorsAreDifferentFormatter.bind(null, this.pp) + ); return false; } } // Deep compare objects. - var aKeys = keys(a, className == '[object Array]'), key; + var aKeys = keys(a, className == '[object Array]'), + key; size = aKeys.length; // Ensure that both objects contain the same number of properties before comparing deep equality. if (keys(b, className == '[object Array]').length !== size) { - diffBuilder.recordMismatch(objectKeysAreDifferentFormatter.bind(null, this.pp)); + diffBuilder.recordMismatch( + objectKeysAreDifferentFormatter.bind(null, this.pp) + ); return false; } @@ -419,13 +512,17 @@ getJasmineRequireObj().MatchersUtil = function(j$) { key = aKeys[i]; // Deep compare each member if (!j$.util.has(b, key)) { - diffBuilder.recordMismatch(objectKeysAreDifferentFormatter.bind(null, this.pp)); + diffBuilder.recordMismatch( + objectKeysAreDifferentFormatter.bind(null, this.pp) + ); result = false; continue; } diffBuilder.withPath(key, function() { - if(!self.eq_(a[key], b[key], aStack, bStack, customTesters, diffBuilder)) { + if ( + !self.eq_(a[key], b[key], aStack, bStack, customTesters, diffBuilder) + ) { result = false; } }); @@ -443,23 +540,24 @@ getJasmineRequireObj().MatchersUtil = function(j$) { }; function keys(obj, isArray) { - var allKeys = Object.keys ? Object.keys(obj) : - (function(o) { + var allKeys = Object.keys + ? Object.keys(obj) + : (function(o) { var keys = []; for (var key in o) { - if (j$.util.has(o, key)) { - keys.push(key); - } + if (j$.util.has(o, key)) { + keys.push(key); + } } return keys; - })(obj); + })(obj); if (!isArray) { return allKeys; } if (allKeys.length === 0) { - return allKeys; + return allKeys; } var extraKeys = []; @@ -478,21 +576,25 @@ getJasmineRequireObj().MatchersUtil = function(j$) { function objectKeysAreDifferentFormatter(pp, actual, expected, path) { var missingProperties = j$.util.objectDifference(expected, actual), - extraProperties = j$.util.objectDifference(actual, expected), - missingPropertiesMessage = formatKeyValuePairs(pp, missingProperties), - extraPropertiesMessage = formatKeyValuePairs(pp, extraProperties), - messages = []; + extraProperties = j$.util.objectDifference(actual, expected), + missingPropertiesMessage = formatKeyValuePairs(pp, missingProperties), + extraPropertiesMessage = formatKeyValuePairs(pp, extraProperties), + messages = []; if (!path.depth()) { path = 'object'; } if (missingPropertiesMessage.length) { - messages.push('Expected ' + path + ' to have properties' + missingPropertiesMessage); + messages.push( + 'Expected ' + path + ' to have properties' + missingPropertiesMessage + ); } if (extraPropertiesMessage.length) { - messages.push('Expected ' + path + ' not to have properties' + extraPropertiesMessage); + messages.push( + 'Expected ' + path + ' not to have properties' + extraPropertiesMessage + ); } return messages.join('\n'); @@ -503,17 +605,25 @@ getJasmineRequireObj().MatchersUtil = function(j$) { path = 'object'; } - return 'Expected ' + - path + ' to be a kind of ' + + return ( + 'Expected ' + + path + + ' to be a kind of ' + j$.fnNameFor(expected.constructor) + - ', but was ' + pp(actual) + '.'; + ', but was ' + + pp(actual) + + '.' + ); } function actualArrayIsLongerFormatter(pp, actual, expected, path) { - return 'Unexpected ' + - path + (path.depth() ? ' = ' : '') + + return ( + 'Unexpected ' + + path + + (path.depth() ? ' = ' : '') + pp(actual) + - ' in array.'; + ' in array.' + ); } function formatKeyValuePairs(pp, obj) { diff --git a/src/core/matchers/toBe.js b/src/core/matchers/toBe.js index 8115adc0..81177c28 100644 --- a/src/core/matchers/toBe.js +++ b/src/core/matchers/toBe.js @@ -9,7 +9,8 @@ getJasmineRequireObj().toBe = function(j$) { * expect(thing).toBe(realThing); */ function toBe(matchersUtil) { - var tip = ' Tip: To check for deep equality, use .toEqual() instead of .toBe().'; + var tip = + ' Tip: To check for deep equality, use .toEqual() instead of .toBe().'; return { compare: function(actual, expected) { @@ -18,7 +19,13 @@ getJasmineRequireObj().toBe = function(j$) { }; if (typeof expected === 'object') { - result.message = matchersUtil.buildFailureMessage('toBe', result.pass, actual, expected) + tip; + result.message = + matchersUtil.buildFailureMessage( + 'toBe', + result.pass, + actual, + expected + ) + tip; } return result; diff --git a/src/core/matchers/toBeCloseTo.js b/src/core/matchers/toBeCloseTo.js index 6cd0a018..b5392144 100644 --- a/src/core/matchers/toBeCloseTo.js +++ b/src/core/matchers/toBeCloseTo.js @@ -17,8 +17,13 @@ getJasmineRequireObj().toBeCloseTo = function() { } if (expected === null || actual === null) { - throw new Error('Cannot use toBeCloseTo with null. Arguments evaluated to: ' + - 'expect(' + actual + ').toBeCloseTo(' + expected + ').' + throw new Error( + 'Cannot use toBeCloseTo with null. Arguments evaluated to: ' + + 'expect(' + + actual + + ').toBeCloseTo(' + + expected + + ').' ); } diff --git a/src/core/matchers/toBeDefined.js b/src/core/matchers/toBeDefined.js index ae95091a..0c43f7d2 100644 --- a/src/core/matchers/toBeDefined.js +++ b/src/core/matchers/toBeDefined.js @@ -11,7 +11,7 @@ getJasmineRequireObj().toBeDefined = function() { return { compare: function(actual) { return { - pass: (void 0 !== actual) + pass: void 0 !== actual }; } }; diff --git a/src/core/matchers/toBeGreaterThan.js b/src/core/matchers/toBeGreaterThan.js index ffe7ad61..07dad333 100644 --- a/src/core/matchers/toBeGreaterThan.js +++ b/src/core/matchers/toBeGreaterThan.js @@ -20,4 +20,3 @@ getJasmineRequireObj().toBeGreaterThan = function() { return toBeGreaterThan; }; - diff --git a/src/core/matchers/toBeInstanceOf.js b/src/core/matchers/toBeInstanceOf.js index 609b9301..2241402e 100644 --- a/src/core/matchers/toBeInstanceOf.js +++ b/src/core/matchers/toBeInstanceOf.js @@ -1,5 +1,8 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { - var usageError = j$.formatErrorMsg('', 'expect(value).toBeInstanceOf()'); + var usageError = j$.formatErrorMsg( + '', + 'expect(value).toBeInstanceOf()' + ); /** * {@link expect} the actual to be an instance of the expected class @@ -15,27 +18,42 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { function toBeInstanceOf(matchersUtil) { return { compare: function(actual, expected) { - var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : matchersUtil.pp(actual), - expectedType = expected ? j$.fnNameFor(expected) : matchersUtil.pp(expected), - expectedMatcher, - pass; + var actualType = + actual && actual.constructor + ? j$.fnNameFor(actual.constructor) + : matchersUtil.pp(actual), + expectedType = expected + ? j$.fnNameFor(expected) + : matchersUtil.pp(expected), + expectedMatcher, + pass; try { - expectedMatcher = new j$.Any(expected); - pass = expectedMatcher.asymmetricMatch(actual); + expectedMatcher = new j$.Any(expected); + pass = expectedMatcher.asymmetricMatch(actual); } catch (error) { - throw new Error(usageError('Expected value is not a constructor function')); + throw new Error( + usageError('Expected value is not a constructor function') + ); } if (pass) { return { pass: true, - message: 'Expected instance of ' + actualType + ' not to be an instance of ' + expectedType + message: + 'Expected instance of ' + + actualType + + ' not to be an instance of ' + + expectedType }; } else { return { pass: false, - message: 'Expected instance of ' + actualType + ' to be an instance of ' + expectedType + message: + 'Expected instance of ' + + actualType + + ' to be an instance of ' + + expectedType }; } } diff --git a/src/core/matchers/toBeLessThan.js b/src/core/matchers/toBeLessThan.js index 319113a0..162e52f1 100644 --- a/src/core/matchers/toBeLessThan.js +++ b/src/core/matchers/toBeLessThan.js @@ -10,7 +10,6 @@ getJasmineRequireObj().toBeLessThan = function() { */ function toBeLessThan() { return { - compare: function(actual, expected) { return { pass: actual < expected diff --git a/src/core/matchers/toBeLessThanOrEqual.js b/src/core/matchers/toBeLessThanOrEqual.js index 4820fc97..f2d47b69 100644 --- a/src/core/matchers/toBeLessThanOrEqual.js +++ b/src/core/matchers/toBeLessThanOrEqual.js @@ -10,7 +10,6 @@ getJasmineRequireObj().toBeLessThanOrEqual = function() { */ function toBeLessThanOrEqual() { return { - compare: function(actual, expected) { return { pass: actual <= expected diff --git a/src/core/matchers/toBeNaN.js b/src/core/matchers/toBeNaN.js index 7adf5b34..b26ef5fc 100644 --- a/src/core/matchers/toBeNaN.js +++ b/src/core/matchers/toBeNaN.js @@ -11,13 +11,15 @@ getJasmineRequireObj().toBeNaN = function(j$) { return { compare: function(actual) { var result = { - pass: (actual !== actual) + pass: actual !== actual }; if (result.pass) { result.message = 'Expected actual not to be NaN.'; } else { - result.message = function() { return 'Expected ' + matchersUtil.pp(actual) + ' to be NaN.'; }; + result.message = function() { + return 'Expected ' + matchersUtil.pp(actual) + ' to be NaN.'; + }; } return result; diff --git a/src/core/matchers/toBeNegativeInfinity.js b/src/core/matchers/toBeNegativeInfinity.js index fe2de803..2518a9c8 100644 --- a/src/core/matchers/toBeNegativeInfinity.js +++ b/src/core/matchers/toBeNegativeInfinity.js @@ -11,13 +11,15 @@ getJasmineRequireObj().toBeNegativeInfinity = function(j$) { return { compare: function(actual) { var result = { - pass: (actual === Number.NEGATIVE_INFINITY) + pass: actual === Number.NEGATIVE_INFINITY }; if (result.pass) { result.message = 'Expected actual not to be -Infinity.'; } else { - result.message = function() { return 'Expected ' + matchersUtil.pp(actual) + ' to be -Infinity.'; }; + result.message = function() { + return 'Expected ' + matchersUtil.pp(actual) + ' to be -Infinity.'; + }; } return result; diff --git a/src/core/matchers/toBePositiveInfinity.js b/src/core/matchers/toBePositiveInfinity.js index 39cb5e34..17523c97 100644 --- a/src/core/matchers/toBePositiveInfinity.js +++ b/src/core/matchers/toBePositiveInfinity.js @@ -11,13 +11,15 @@ getJasmineRequireObj().toBePositiveInfinity = function(j$) { return { compare: function(actual) { var result = { - pass: (actual === Number.POSITIVE_INFINITY) + pass: actual === Number.POSITIVE_INFINITY }; if (result.pass) { result.message = 'Expected actual not to be Infinity.'; } else { - result.message = function() { return 'Expected ' + matchersUtil.pp(actual) + ' to be Infinity.'; }; + result.message = function() { + return 'Expected ' + matchersUtil.pp(actual) + ' to be Infinity.'; + }; } return result; diff --git a/src/core/matchers/toContain.js b/src/core/matchers/toContain.js index 5732447e..9ab30154 100644 --- a/src/core/matchers/toContain.js +++ b/src/core/matchers/toContain.js @@ -12,7 +12,6 @@ getJasmineRequireObj().toContain = function() { function toContain(matchersUtil) { return { compare: function(actual, expected) { - return { pass: matchersUtil.contains(actual, expected) }; diff --git a/src/core/matchers/toEqual.js b/src/core/matchers/toEqual.js index 3a7add38..d2db1bd8 100644 --- a/src/core/matchers/toEqual.js +++ b/src/core/matchers/toEqual.js @@ -14,7 +14,7 @@ getJasmineRequireObj().toEqual = function(j$) { var result = { pass: false }, - diffBuilder = j$.DiffBuilder({prettyPrinter: matchersUtil.pp}); + diffBuilder = j$.DiffBuilder({ prettyPrinter: matchersUtil.pp }); result.pass = matchersUtil.equals(actual, expected, diffBuilder); diff --git a/src/core/matchers/toHaveBeenCalled.js b/src/core/matchers/toHaveBeenCalled.js index 3e6d2601..ef1ea60c 100644 --- a/src/core/matchers/toHaveBeenCalled.js +++ b/src/core/matchers/toHaveBeenCalled.js @@ -1,6 +1,8 @@ getJasmineRequireObj().toHaveBeenCalled = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalled()'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalled()' + ); /** * {@link expect} the actual (a {@link Spy}) to have been called. @@ -17,18 +19,24 @@ getJasmineRequireObj().toHaveBeenCalled = function(j$) { var result = {}; if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(actual) + '.')); + throw new Error( + getErrorMsg( + 'Expected a spy, but got ' + matchersUtil.pp(actual) + '.' + ) + ); } if (arguments.length > 1) { - throw new Error(getErrorMsg('Does not take arguments, use toHaveBeenCalledWith')); + throw new Error( + getErrorMsg('Does not take arguments, use toHaveBeenCalledWith') + ); } result.pass = actual.calls.any(); - result.message = result.pass ? - 'Expected spy ' + actual.and.identity + ' not to have been called.' : - 'Expected spy ' + actual.and.identity + ' to have been called.'; + result.message = result.pass + ? 'Expected spy ' + actual.and.identity + ' not to have been called.' + : 'Expected spy ' + actual.and.identity + ' to have been called.'; return result; } diff --git a/src/core/matchers/toHaveBeenCalledBefore.js b/src/core/matchers/toHaveBeenCalledBefore.js index 293e73ff..ad1de7c0 100644 --- a/src/core/matchers/toHaveBeenCalledBefore.js +++ b/src/core/matchers/toHaveBeenCalledBefore.js @@ -1,6 +1,8 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledBefore()'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalledBefore()' + ); /** * {@link expect} the actual value (a {@link Spy}) to have been called before another {@link Spy}. @@ -15,20 +17,30 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { return { compare: function(firstSpy, latterSpy) { if (!j$.isSpy(firstSpy)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(firstSpy) + '.')); + throw new Error( + getErrorMsg( + 'Expected a spy, but got ' + matchersUtil.pp(firstSpy) + '.' + ) + ); } if (!j$.isSpy(latterSpy)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(latterSpy) + '.')); + throw new Error( + getErrorMsg( + 'Expected a spy, but got ' + matchersUtil.pp(latterSpy) + '.' + ) + ); } var result = { pass: false }; if (!firstSpy.calls.count()) { - result.message = 'Expected spy ' + firstSpy.and.identity + ' to have been called.'; + result.message = + 'Expected spy ' + firstSpy.and.identity + ' to have been called.'; return result; } if (!latterSpy.calls.count()) { - result.message = 'Expected spy ' + latterSpy.and.identity + ' to have been called.'; + result.message = + 'Expected spy ' + latterSpy.and.identity + ' to have been called.'; return result; } @@ -38,17 +50,36 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { result.pass = latest1stSpyCall < first2ndSpyCall; if (result.pass) { - result.message = 'Expected spy ' + firstSpy.and.identity + ' to not have been called before spy ' + latterSpy.and.identity + ', but it was'; + result.message = + 'Expected spy ' + + firstSpy.and.identity + + ' to not have been called before spy ' + + latterSpy.and.identity + + ', but it was'; } else { var first1stSpyCall = firstSpy.calls.first().invocationOrder; var latest2ndSpyCall = latterSpy.calls.mostRecent().invocationOrder; - if(first1stSpyCall < first2ndSpyCall) { - result.message = 'Expected latest call to spy ' + firstSpy.and.identity + ' to have been called before first call to spy ' + latterSpy.and.identity + ' (no interleaved calls)'; + if (first1stSpyCall < first2ndSpyCall) { + result.message = + 'Expected latest call to spy ' + + firstSpy.and.identity + + ' to have been called before first call to spy ' + + latterSpy.and.identity + + ' (no interleaved calls)'; } else if (latest2ndSpyCall > latest1stSpyCall) { - result.message = 'Expected first call to spy ' + latterSpy.and.identity + ' to have been called after latest call to spy ' + firstSpy.and.identity + ' (no interleaved calls)'; + result.message = + 'Expected first call to spy ' + + latterSpy.and.identity + + ' to have been called after latest call to spy ' + + firstSpy.and.identity + + ' (no interleaved calls)'; } else { - result.message = 'Expected spy ' + firstSpy.and.identity + ' to have been called before spy ' + latterSpy.and.identity; + result.message = + 'Expected spy ' + + firstSpy.and.identity + + ' to have been called before spy ' + + latterSpy.and.identity; } } diff --git a/src/core/matchers/toHaveBeenCalledOnceWith.js b/src/core/matchers/toHaveBeenCalledOnceWith.js index 2cd607f8..d3d6b4ef 100644 --- a/src/core/matchers/toHaveBeenCalledOnceWith.js +++ b/src/core/matchers/toHaveBeenCalledOnceWith.js @@ -1,6 +1,8 @@ -getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledOnceWith(...arguments)'); +getJasmineRequireObj().toHaveBeenCalledOnceWith = function(j$) { + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalledOnceWith(...arguments)' + ); /** * {@link expect} the actual (a {@link Spy}) to have been called exactly once, and exactly with the particular arguments. @@ -13,31 +15,44 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { */ function toHaveBeenCalledOnceWith(util) { return { - compare: function () { + compare: function() { var args = Array.prototype.slice.call(arguments, 0), actual = args[0], expectedArgs = args.slice(1); if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + util.pp(actual) + '.')); + throw new Error( + getErrorMsg('Expected a spy, but got ' + util.pp(actual) + '.') + ); } - var prettyPrintedCalls = actual.calls.allArgs().map(function (argsForCall) { - return ' ' + util.pp(argsForCall); - }); + var prettyPrintedCalls = actual.calls + .allArgs() + .map(function(argsForCall) { + return ' ' + util.pp(argsForCall); + }); - if (actual.calls.count() === 1 && util.contains(actual.calls.allArgs(), expectedArgs)) { + if ( + actual.calls.count() === 1 && + util.contains(actual.calls.allArgs(), expectedArgs) + ) { return { pass: true, - message: 'Expected spy ' + actual.and.identity + ' to have been called 0 times, multiple times, or once, but with arguments different from:\n' - + ' ' + util.pp(expectedArgs) + '\n' - + 'But the actual call was:\n' - + prettyPrintedCalls.join(',\n') + '.\n\n' + message: + 'Expected spy ' + + actual.and.identity + + ' to have been called 0 times, multiple times, or once, but with arguments different from:\n' + + ' ' + + util.pp(expectedArgs) + + '\n' + + 'But the actual call was:\n' + + prettyPrintedCalls.join(',\n') + + '.\n\n' }; } function getDiffs() { - return actual.calls.allArgs().map(function (argsForCall, callIx) { + return actual.calls.allArgs().map(function(argsForCall, callIx) { var diffBuilder = new j$.DiffBuilder(); util.equals(argsForCall, expectedArgs, diffBuilder); return diffBuilder.getMessage(); @@ -49,17 +64,32 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { case 0: return 'But it was never called.\n\n'; case 1: - return 'But the actual call was:\n' + prettyPrintedCalls.join(',\n') + '.\n' + getDiffs().join('\n') + '\n\n'; + return ( + 'But the actual call was:\n' + + prettyPrintedCalls.join(',\n') + + '.\n' + + getDiffs().join('\n') + + '\n\n' + ); default: - return 'But the actual calls were:\n' + prettyPrintedCalls.join(',\n') + '.\n\n'; + return ( + 'But the actual calls were:\n' + + prettyPrintedCalls.join(',\n') + + '.\n\n' + ); } } return { pass: false, - message: 'Expected spy ' + actual.and.identity + ' to have been called only once, and with given args:\n' - + ' ' + util.pp(expectedArgs) + '\n' - + butString() + message: + 'Expected spy ' + + actual.and.identity + + ' to have been called only once, and with given args:\n' + + ' ' + + util.pp(expectedArgs) + + '\n' + + butString() }; } }; diff --git a/src/core/matchers/toHaveBeenCalledTimes.js b/src/core/matchers/toHaveBeenCalledTimes.js index fa3eef3d..f3bcac3f 100644 --- a/src/core/matchers/toHaveBeenCalledTimes.js +++ b/src/core/matchers/toHaveBeenCalledTimes.js @@ -1,6 +1,8 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledTimes()'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalledTimes()' + ); /** * {@link expect} the actual (a {@link Spy}) to have been called the specified number of times. @@ -15,23 +17,43 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { return { compare: function(actual, expected) { if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(actual) + '.')); + throw new Error( + getErrorMsg( + 'Expected a spy, but got ' + matchersUtil.pp(actual) + '.' + ) + ); } var args = Array.prototype.slice.call(arguments, 0), result = { pass: false }; if (!j$.isNumber_(expected)) { - throw new Error(getErrorMsg('The expected times failed is a required argument and must be a number.')); + throw new Error( + getErrorMsg( + 'The expected times failed is a required argument and must be a number.' + ) + ); } actual = args[0]; var calls = actual.calls.count(); var timesMessage = expected === 1 ? 'once' : expected + ' times'; result.pass = calls === expected; - result.message = result.pass ? - 'Expected spy ' + actual.and.identity + ' not to have been called ' + timesMessage + '. It was called ' + calls + ' times.' : - 'Expected spy ' + actual.and.identity + ' to have been called ' + timesMessage + '. It was called ' + calls + ' times.'; + result.message = result.pass + ? 'Expected spy ' + + actual.and.identity + + ' not to have been called ' + + timesMessage + + '. It was called ' + + calls + + ' times.' + : 'Expected spy ' + + actual.and.identity + + ' to have been called ' + + timesMessage + + '. It was called ' + + calls + + ' times.'; return result; } }; diff --git a/src/core/matchers/toHaveBeenCalledWith.js b/src/core/matchers/toHaveBeenCalledWith.js index 76628b55..0a646b89 100644 --- a/src/core/matchers/toHaveBeenCalledWith.js +++ b/src/core/matchers/toHaveBeenCalledWith.js @@ -1,6 +1,8 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledWith(...arguments)'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalledWith(...arguments)' + ); /** * {@link expect} the actual (a {@link Spy}) to have been called with particular arguments at least once. @@ -20,14 +22,23 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { result = { pass: false }; if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(actual) + '.')); + throw new Error( + getErrorMsg( + 'Expected a spy, but got ' + matchersUtil.pp(actual) + '.' + ) + ); } if (!actual.calls.any()) { result.message = function() { - return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + - ' ' + matchersUtil.pp(expectedArgs) + - '\nbut it was never called.'; + return ( + 'Expected spy ' + + actual.and.identity + + ' to have been called with:\n' + + ' ' + + matchersUtil.pp(expectedArgs) + + '\nbut it was never called.' + ); }; return result; } @@ -35,28 +46,49 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { if (matchersUtil.contains(actual.calls.allArgs(), expectedArgs)) { result.pass = true; result.message = function() { - return 'Expected spy ' + actual.and.identity + ' not to have been called with:\n' + - ' ' + matchersUtil.pp(expectedArgs) + - '\nbut it was.'; + return ( + 'Expected spy ' + + actual.and.identity + + ' not to have been called with:\n' + + ' ' + + matchersUtil.pp(expectedArgs) + + '\nbut it was.' + ); }; } else { result.message = function() { - var prettyPrintedCalls = actual.calls.allArgs().map(function(argsForCall) { - return ' ' + matchersUtil.pp(argsForCall); - }); + var prettyPrintedCalls = actual.calls + .allArgs() + .map(function(argsForCall) { + return ' ' + matchersUtil.pp(argsForCall); + }); - var diffs = actual.calls.allArgs().map(function(argsForCall, callIx) { - var diffBuilder = new j$.DiffBuilder(); - matchersUtil.equals(argsForCall, expectedArgs, diffBuilder); - return 'Call ' + callIx + ':\n' + - diffBuilder.getMessage().replace(/^/mg, ' '); - }); + var diffs = actual.calls + .allArgs() + .map(function(argsForCall, callIx) { + var diffBuilder = new j$.DiffBuilder(); + matchersUtil.equals(argsForCall, expectedArgs, diffBuilder); + return ( + 'Call ' + + callIx + + ':\n' + + diffBuilder.getMessage().replace(/^/gm, ' ') + ); + }); - return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + - ' ' + matchersUtil.pp(expectedArgs) + '\n' + '' + + return ( + 'Expected spy ' + + actual.and.identity + + ' to have been called with:\n' + + ' ' + + matchersUtil.pp(expectedArgs) + + '\n' + + '' + 'but actual calls were:\n' + - prettyPrintedCalls.join(',\n') + '.\n\n' + - diffs.join('\n'); + prettyPrintedCalls.join(',\n') + + '.\n\n' + + diffs.join('\n') + ); }; } diff --git a/src/core/matchers/toHaveClass.js b/src/core/matchers/toHaveClass.js index efe17f10..218e729c 100644 --- a/src/core/matchers/toHaveClass.js +++ b/src/core/matchers/toHaveClass.js @@ -25,9 +25,9 @@ getJasmineRequireObj().toHaveClass = function(j$) { } function isElement(maybeEl) { - return maybeEl && - maybeEl.classList && - j$.isFunction_(maybeEl.classList.contains); + return ( + maybeEl && maybeEl.classList && j$.isFunction_(maybeEl.classList.contains) + ); } return toHaveClass; diff --git a/src/core/matchers/toHaveSize.js b/src/core/matchers/toHaveSize.js index 03c8d431..403080a8 100644 --- a/src/core/matchers/toHaveSize.js +++ b/src/core/matchers/toHaveSize.js @@ -13,10 +13,14 @@ getJasmineRequireObj().toHaveSize = function(j$) { return { compare: function(actual, expected) { var result = { - pass: false - }; + pass: false + }; - if (j$.isA_('WeakSet', actual) || j$.isWeakMap(actual) || j$.isDataView(actual)) { + if ( + j$.isA_('WeakSet', actual) || + j$.isWeakMap(actual) || + j$.isDataView(actual) + ) { throw new Error('Cannot get size of ' + actual + '.'); } @@ -33,9 +37,14 @@ getJasmineRequireObj().toHaveSize = function(j$) { }; } - var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || 9007199254740991; // eslint-disable-line compat/compat + var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || 9007199254740991; // eslint-disable-line compat/compat function isLength(value) { - return (typeof value == 'number') && value > -1 && value % 1 === 0 && value <= MAX_SAFE_INTEGER; + return ( + typeof value == 'number' && + value > -1 && + value % 1 === 0 && + value <= MAX_SAFE_INTEGER + ); } return toHaveSize; diff --git a/src/core/matchers/toMatch.js b/src/core/matchers/toMatch.js index 7d8f658c..bb3ca3a9 100644 --- a/src/core/matchers/toMatch.js +++ b/src/core/matchers/toMatch.js @@ -1,6 +1,8 @@ getJasmineRequireObj().toMatch = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toMatch( || )'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toMatch( || )' + ); /** * {@link expect} the actual value to match a regular expression diff --git a/src/core/matchers/toThrow.js b/src/core/matchers/toThrow.js index a471a5d9..b1db2b4c 100644 --- a/src/core/matchers/toThrow.js +++ b/src/core/matchers/toThrow.js @@ -1,6 +1,8 @@ getJasmineRequireObj().toThrow = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect(function() {}).toThrow()'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect(function() {}).toThrow()' + ); /** * {@link expect} a function to `throw` something. @@ -37,16 +39,36 @@ getJasmineRequireObj().toThrow = function(j$) { if (arguments.length == 1) { result.pass = true; - result.message = function() { return 'Expected function not to throw, but it threw ' + matchersUtil.pp(thrown) + '.'; }; + result.message = function() { + return ( + 'Expected function not to throw, but it threw ' + + matchersUtil.pp(thrown) + + '.' + ); + }; return result; } if (matchersUtil.equals(thrown, expected)) { result.pass = true; - result.message = function() { return 'Expected function not to throw ' + matchersUtil.pp(expected) + '.'; }; + result.message = function() { + return ( + 'Expected function not to throw ' + + matchersUtil.pp(expected) + + '.' + ); + }; } else { - result.message = function() { return 'Expected function to throw ' + matchersUtil.pp(expected) + ', but it threw ' + matchersUtil.pp(thrown) + '.'; }; + result.message = function() { + return ( + 'Expected function to throw ' + + matchersUtil.pp(expected) + + ', but it threw ' + + matchersUtil.pp(thrown) + + '.' + ); + }; } return result; diff --git a/src/core/matchers/toThrowError.js b/src/core/matchers/toThrowError.js index 00f3e69a..38513603 100644 --- a/src/core/matchers/toThrowError.js +++ b/src/core/matchers/toThrowError.js @@ -1,6 +1,8 @@ getJasmineRequireObj().toThrowError = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect(function() {}).toThrowError(, )'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect(function() {}).toThrowError(, )' + ); /** * {@link expect} a function to `throw` an `Error`. @@ -34,7 +36,13 @@ getJasmineRequireObj().toThrowError = function(j$) { } if (!j$.isError_(thrown)) { - return fail(function() { return 'Expected function to throw an Error, but it threw ' + matchersUtil.pp(thrown) + '.'; }); + return fail(function() { + return ( + 'Expected function to throw an Error, but it threw ' + + matchersUtil.pp(thrown) + + '.' + ); + }); } return errorMatcher.match(thrown); @@ -68,7 +76,11 @@ getJasmineRequireObj().toThrowError = function(j$) { function anyMatcher() { return { match: function(error) { - return pass('Expected function not to throw an Error, but it threw ' + j$.fnNameFor(error) + '.'); + return pass( + 'Expected function not to throw an Error, but it threw ' + + j$.fnNameFor(error) + + '.' + ); } }; } @@ -76,9 +88,13 @@ getJasmineRequireObj().toThrowError = function(j$) { function exactMatcher(expected, errorType) { if (expected && !isStringOrRegExp(expected)) { if (errorType) { - throw new Error(getErrorMsg('Expected error message is not a string or RegExp.')); + throw new Error( + getErrorMsg('Expected error message is not a string or RegExp.') + ); } else { - throw new Error(getErrorMsg('Expected is not an Error, string, or RegExp.')); + throw new Error( + getErrorMsg('Expected is not an Error, string, or RegExp.') + ); } } @@ -90,11 +106,15 @@ getJasmineRequireObj().toThrowError = function(j$) { } } - var errorTypeDescription = errorType ? j$.fnNameFor(errorType) : 'an exception'; + var errorTypeDescription = errorType + ? j$.fnNameFor(errorType) + : 'an exception'; function thrownDescription(thrown) { - var thrownName = errorType ? j$.fnNameFor(thrown.constructor) : 'an exception', - thrownMessage = ''; + var thrownName = errorType + ? j$.fnNameFor(thrown.constructor) + : 'an exception', + thrownMessage = ''; if (expected) { thrownMessage = ' with message ' + matchersUtil.pp(thrown.message); @@ -114,20 +134,33 @@ getJasmineRequireObj().toThrowError = function(j$) { } function matches(error) { - return (errorType === null || error instanceof errorType) && - (expected === null || messageMatch(error.message)); + return ( + (errorType === null || error instanceof errorType) && + (expected === null || messageMatch(error.message)) + ); } return { match: function(thrown) { if (matches(thrown)) { return pass(function() { - return 'Expected function not to throw ' + errorTypeDescription + messageDescription() + '.'; + return ( + 'Expected function not to throw ' + + errorTypeDescription + + messageDescription() + + '.' + ); }); } else { return fail(function() { - return 'Expected function to throw ' + errorTypeDescription + messageDescription() + - ', but it threw ' + thrownDescription(thrown) + '.'; + return ( + 'Expected function to throw ' + + errorTypeDescription + + messageDescription() + + ', but it threw ' + + thrownDescription(thrown) + + '.' + ); }); } } @@ -135,7 +168,7 @@ getJasmineRequireObj().toThrowError = function(j$) { } function isStringOrRegExp(potential) { - return potential instanceof RegExp || (typeof potential == 'string'); + return potential instanceof RegExp || typeof potential == 'string'; } function isAnErrorType(type) { diff --git a/src/core/matchers/toThrowMatching.js b/src/core/matchers/toThrowMatching.js index 45e3fc85..e594b1f5 100644 --- a/src/core/matchers/toThrowMatching.js +++ b/src/core/matchers/toThrowMatching.js @@ -1,5 +1,8 @@ getJasmineRequireObj().toThrowMatching = function(j$) { - var usageError = j$.formatErrorMsg('', 'expect(function() {}).toThrowMatching()'); + var usageError = j$.formatErrorMsg( + '', + 'expect(function() {}).toThrowMatching()' + ); /** * {@link expect} a function to `throw` something matching a predicate. @@ -31,20 +34,29 @@ getJasmineRequireObj().toThrowMatching = function(j$) { } if (predicate(thrown)) { - return pass('Expected function not to throw an exception matching a predicate.'); + return pass( + 'Expected function not to throw an exception matching a predicate.' + ); } else { - return fail(function() { - return 'Expected function to throw an exception matching a predicate, ' + - 'but it threw ' + thrownDescription(thrown) + '.'; - }); + return fail(function() { + return ( + 'Expected function to throw an exception matching a predicate, ' + + 'but it threw ' + + thrownDescription(thrown) + + '.' + ); + }); } } }; function thrownDescription(thrown) { if (thrown && thrown.constructor) { - return j$.fnNameFor(thrown.constructor) + ' with message ' + - matchersUtil.pp(thrown.message); + return ( + j$.fnNameFor(thrown.constructor) + + ' with message ' + + matchersUtil.pp(thrown.message) + ); } else { return matchersUtil.pp(thrown); } From d5d5d1965fa48f10b5ddd741dadb07af3a08ebac Mon Sep 17 00:00:00 2001 From: DCtheTall Date: Fri, 2 Oct 2020 13:49:34 -0400 Subject: [PATCH 182/201] Have properties added by createSpyObj() be enumerable. --- spec/core/SpySpec.js | 9 +++++---- src/core/SpyFactory.js | 1 + 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/spec/core/SpySpec.js b/spec/core/SpySpec.js index 97d9f03b..f7a2c9ec 100644 --- a/spec/core/SpySpec.js +++ b/spec/core/SpySpec.js @@ -183,14 +183,13 @@ describe('Spies', function() { var spyObj = env.createSpyObj('base', ['method1'], ['prop1']); expect(spyObj).toEqual({ - method1: jasmine.any(Function) + method1: jasmine.any(Function), + prop1: undefined }); var descriptor = Object.getOwnPropertyDescriptor(spyObj, 'prop1'); expect(descriptor.get.and.identity).toEqual('base.prop1.get'); expect(descriptor.set.and.identity).toEqual('base.prop1.set'); - - expect(spyObj.prop1).toBeUndefined(); }); it('creates an object with property names and return values if second object is passed', function() { @@ -200,7 +199,9 @@ describe('Spies', function() { }); expect(spyObj).toEqual({ - method1: jasmine.any(Function) + method1: jasmine.any(Function), + prop1: 'foo', + prop2: 37 }); expect(spyObj.prop1).toEqual('foo'); diff --git a/src/core/SpyFactory.js b/src/core/SpyFactory.js index 80c6b954..0f29a3b1 100644 --- a/src/core/SpyFactory.js +++ b/src/core/SpyFactory.js @@ -38,6 +38,7 @@ getJasmineRequireObj().SpyFactory = function(j$) { var properties = normalizeKeyValues(propertyNames); for (var i = 0; i < properties.length; i++) { descriptor = { + enumerable: true, get: self.createSpy(baseName + '.' + properties[i][0] + '.get'), set: self.createSpy(baseName + '.' + properties[i][0] + '.set') }; From c24aef15b1971ae53383cb42f5130021360c207f Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 10 Oct 2020 17:59:50 -0700 Subject: [PATCH 183/201] Built distribution --- lib/jasmine-core/jasmine.js | 1008 +++++++++++++++++++++++++---------- 1 file changed, 721 insertions(+), 287 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index f86e9f55..919bdf5d 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -2369,12 +2369,11 @@ getJasmineRequireObj().JsApiReporter = function(j$) { }; getJasmineRequireObj().Any = function(j$) { - function Any(expectedObject) { if (typeof expectedObject === 'undefined') { throw new TypeError( 'jasmine.any() expects to be passed a constructor function. ' + - 'Please pass one or use jasmine.anything() to match any object.' + 'Please pass one or use jasmine.anything() to match any object.' ); } this.expectedObject = expectedObject; @@ -2419,7 +2418,6 @@ getJasmineRequireObj().Any = function(j$) { }; getJasmineRequireObj().Anything = function(j$) { - function Anything() {} Anything.prototype.asymmetricMatch = function(other) { @@ -2440,7 +2438,11 @@ getJasmineRequireObj().ArrayContaining = function(j$) { ArrayContaining.prototype.asymmetricMatch = function(other, matchersUtil) { if (!j$.isArray_(this.sample)) { - throw new Error('You must provide an array to arrayContaining, not ' + j$.pp(this.sample) + '.'); + throw new Error( + 'You must provide an array to arrayContaining, not ' + + j$.pp(this.sample) + + '.' + ); } // If the actual parameter is not an array, we can fail immediately, since it couldn't @@ -2460,22 +2462,28 @@ getJasmineRequireObj().ArrayContaining = function(j$) { return true; }; - ArrayContaining.prototype.jasmineToString = function (pp) { - return ''; + ArrayContaining.prototype.jasmineToString = function(pp) { + return ''; }; return ArrayContaining; }; getJasmineRequireObj().ArrayWithExactContents = function(j$) { - function ArrayWithExactContents(sample) { this.sample = sample; } - ArrayWithExactContents.prototype.asymmetricMatch = function(other, matchersUtil) { + ArrayWithExactContents.prototype.asymmetricMatch = function( + other, + matchersUtil + ) { if (!j$.isArray_(this.sample)) { - throw new Error('You must provide an array to arrayWithExactContents, not ' + j$.pp(this.sample) + '.'); + throw new Error( + 'You must provide an array to arrayWithExactContents, not ' + + j$.pp(this.sample) + + '.' + ); } if (this.sample.length !== other.length) { @@ -2499,11 +2507,10 @@ getJasmineRequireObj().ArrayWithExactContents = function(j$) { return ArrayWithExactContents; }; -getJasmineRequireObj().Empty = function (j$) { - +getJasmineRequireObj().Empty = function(j$) { function Empty() {} - Empty.prototype.asymmetricMatch = function (other) { + Empty.prototype.asymmetricMatch = function(other) { if (j$.isString_(other) || j$.isArray_(other) || j$.isTypedArray_(other)) { return other.length === 0; } @@ -2518,7 +2525,7 @@ getJasmineRequireObj().Empty = function (j$) { return false; }; - Empty.prototype.jasmineToString = function () { + Empty.prototype.jasmineToString = function() { return ''; }; @@ -2526,7 +2533,6 @@ getJasmineRequireObj().Empty = function (j$) { }; getJasmineRequireObj().Falsy = function(j$) { - function Falsy() {} Falsy.prototype.asymmetricMatch = function(other) { @@ -2543,7 +2549,9 @@ getJasmineRequireObj().Falsy = function(j$) { getJasmineRequireObj().MapContaining = function(j$) { function MapContaining(sample) { if (!j$.isMap(sample)) { - throw new Error('You must provide a map to `mapContaining`, not ' + j$.pp(sample)); + throw new Error( + 'You must provide a map to `mapContaining`, not ' + j$.pp(sample) + ); } this.sample = sample; @@ -2559,8 +2567,8 @@ getJasmineRequireObj().MapContaining = function(j$) { var hasMatch = false; j$.util.forEachBreakable(other, function(oBreakLoop, oValue, oKey) { if ( - matchersUtil.equals(oKey, key) - && matchersUtil.equals(oValue, value) + matchersUtil.equals(oKey, key) && + matchersUtil.equals(oValue, value) ) { hasMatch = true; oBreakLoop(); @@ -2582,11 +2590,10 @@ getJasmineRequireObj().MapContaining = function(j$) { return MapContaining; }; -getJasmineRequireObj().NotEmpty = function (j$) { - +getJasmineRequireObj().NotEmpty = function(j$) { function NotEmpty() {} - NotEmpty.prototype.asymmetricMatch = function (other) { + NotEmpty.prototype.asymmetricMatch = function(other) { if (j$.isString_(other) || j$.isArray_(other) || j$.isTypedArray_(other)) { return other.length !== 0; } @@ -2602,7 +2609,7 @@ getJasmineRequireObj().NotEmpty = function (j$) { return false; }; - NotEmpty.prototype.jasmineToString = function () { + NotEmpty.prototype.jasmineToString = function() { return ''; }; @@ -2610,7 +2617,6 @@ getJasmineRequireObj().NotEmpty = function (j$) { }; getJasmineRequireObj().ObjectContaining = function(j$) { - function ObjectContaining(sample) { this.sample = sample; } @@ -2628,7 +2634,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } function hasProperty(obj, property) { - if (!obj || typeof(obj) !== 'object') { + if (!obj || typeof obj !== 'object') { return false; } @@ -2640,12 +2646,22 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } ObjectContaining.prototype.asymmetricMatch = function(other, matchersUtil) { - if (typeof(this.sample) !== 'object') { throw new Error('You must provide an object to objectContaining, not \''+this.sample+'\'.'); } - if (typeof(other) !== 'object') { return false; } + if (typeof this.sample !== 'object') { + throw new Error( + "You must provide an object to objectContaining, not '" + + this.sample + + "'." + ); + } + if (typeof other !== 'object') { + return false; + } for (var property in this.sample) { - if (!hasProperty(other, property) || - !matchersUtil.equals(this.sample[property], other[property])) { + if ( + !hasProperty(other, property) || + !matchersUtil.equals(this.sample[property], other[property]) + ) { return false; } } @@ -2662,7 +2678,7 @@ getJasmineRequireObj().ObjectContaining = function(j$) { } var filteredOther = {}; - Object.keys(this.sample).forEach(function (k) { + Object.keys(this.sample).forEach(function(k) { // eq short-circuits comparison of objects that have different key sets, // so include all keys even if undefined. filteredOther[k] = other[k]; @@ -2684,7 +2700,9 @@ getJasmineRequireObj().ObjectContaining = function(j$) { getJasmineRequireObj().SetContaining = function(j$) { function SetContaining(sample) { if (!j$.isSet(sample)) { - throw new Error('You must provide a set to `setContaining`, not ' + j$.pp(sample)); + throw new Error( + 'You must provide a set to `setContaining`, not ' + j$.pp(sample) + ); } this.sample = sample; @@ -2722,7 +2740,6 @@ getJasmineRequireObj().SetContaining = function(j$) { }; getJasmineRequireObj().StringMatching = function(j$) { - function StringMatching(expected) { if (!j$.isString_(expected) && !j$.isA_('RegExp', expected)) { throw new Error('Expected is not a String or a RegExp'); @@ -2743,7 +2760,6 @@ getJasmineRequireObj().StringMatching = function(j$) { }; getJasmineRequireObj().Truthy = function(j$) { - function Truthy() {} Truthy.prototype.asymmetricMatch = function(other) { @@ -4164,8 +4180,12 @@ getJasmineRequireObj().toBePending = function(j$) { } var want = {}; return Promise.race([actual, Promise.resolve(want)]).then( - function(got) { return {pass: want === got}; }, - function() { return {pass: false}; } + function(got) { + return { pass: want === got }; + }, + function() { + return { pass: false }; + } ); } }; @@ -4191,8 +4211,12 @@ getJasmineRequireObj().toBeRejected = function(j$) { throw new Error('Expected toBeRejected to be called on a promise.'); } return actual.then( - function() { return {pass: false}; }, - function() { return {pass: true}; } + function() { + return { pass: false }; + }, + function() { + return { pass: true }; + } ); } }; @@ -4216,35 +4240,44 @@ getJasmineRequireObj().toBeRejectedWith = function(j$) { return { compare: function(actualPromise, expectedValue) { if (!j$.isPromiseLike(actualPromise)) { - throw new Error('Expected toBeRejectedWith to be called on a promise.'); + throw new Error( + 'Expected toBeRejectedWith to be called on a promise.' + ); } function prefix(passed) { - return 'Expected a promise ' + + return ( + 'Expected a promise ' + (passed ? 'not ' : '') + - 'to be rejected with ' + matchersUtil.pp(expectedValue); + 'to be rejected with ' + + matchersUtil.pp(expectedValue) + ); } return actualPromise.then( function() { - return { - pass: false, - message: prefix(false) + ' but it was resolved.' - }; - }, - function(actualValue) { - if (matchersUtil.equals(actualValue, expectedValue)) { - return { - pass: true, - message: prefix(true) + '.' - }; - } else { return { pass: false, - message: prefix(false) + ' but it was rejected with ' + matchersUtil.pp(actualValue) + '.' + message: prefix(false) + ' but it was resolved.' }; + }, + function(actualValue) { + if (matchersUtil.equals(actualValue, expectedValue)) { + return { + pass: true, + message: prefix(true) + '.' + }; + } else { + return { + pass: false, + message: + prefix(false) + + ' but it was rejected with ' + + matchersUtil.pp(actualValue) + + '.' + }; + } } - } ); } }; @@ -4271,7 +4304,9 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return { compare: function(actualPromise, arg1, arg2) { if (!j$.isPromiseLike(actualPromise)) { - throw new Error('Expected toBeRejectedWithError to be called on a promise.'); + throw new Error( + 'Expected toBeRejectedWithError to be called on a promise.' + ); } var expected = getExpectedFromArgs(arg1, arg2, matchersUtil); @@ -4283,7 +4318,9 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { message: 'Expected a promise to be rejected but it was resolved.' }; }, - function(actualValue) { return matchError(actualValue, expected, matchersUtil); } + function(actualValue) { + return matchError(actualValue, expected, matchersUtil); + } ); } }; @@ -4295,16 +4332,25 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { } if (!(actual instanceof expected.error)) { - return fail(expected, 'rejected with type ' + j$.fnNameFor(actual.constructor)); + return fail( + expected, + 'rejected with type ' + j$.fnNameFor(actual.constructor) + ); } var actualMessage = actual.message; - if (actualMessage === expected.message || typeof expected.message === 'undefined') { + if ( + actualMessage === expected.message || + typeof expected.message === 'undefined' + ) { return pass(expected); } - if (expected.message instanceof RegExp && expected.message.test(actualMessage)) { + if ( + expected.message instanceof RegExp && + expected.message.test(actualMessage) + ) { return pass(expected); } @@ -4314,18 +4360,25 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { function pass(expected) { return { pass: true, - message: 'Expected a promise not to be rejected with ' + expected.printValue + ', but it was.' + message: + 'Expected a promise not to be rejected with ' + + expected.printValue + + ', but it was.' }; } function fail(expected, message) { return { pass: false, - message: 'Expected a promise to be rejected with ' + expected.printValue + ' but it was ' + message + '.' + message: + 'Expected a promise to be rejected with ' + + expected.printValue + + ' but it was ' + + message + + '.' }; } - function getExpectedFromArgs(arg1, arg2, matchersUtil) { var error, message; @@ -4340,12 +4393,17 @@ getJasmineRequireObj().toBeRejectedWithError = function(j$) { return { error: error, message: message, - printValue: j$.fnNameFor(error) + (typeof message === 'undefined' ? '' : ': ' + matchersUtil.pp(message)) + printValue: + j$.fnNameFor(error) + + (typeof message === 'undefined' ? '' : ': ' + matchersUtil.pp(message)) }; } function isErrorConstructor(value) { - return typeof value === 'function' && (value === Error || j$.isError_(value.prototype)); + return ( + typeof value === 'function' && + (value === Error || j$.isError_(value.prototype)) + ); } }; @@ -4369,8 +4427,12 @@ getJasmineRequireObj().toBeResolved = function(j$) { } return actual.then( - function() { return {pass: true}; }, - function() { return {pass: false}; } + function() { + return { pass: true }; + }, + function() { + return { pass: false }; + } ); } }; @@ -4398,9 +4460,12 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { } function prefix(passed) { - return 'Expected a promise ' + + return ( + 'Expected a promise ' + (passed ? 'not ' : '') + - 'to be resolved to ' + matchersUtil.pp(expectedValue); + 'to be resolved to ' + + matchersUtil.pp(expectedValue) + ); } return actualPromise.then( @@ -4413,7 +4478,11 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { } else { return { pass: false, - message: prefix(false) + ' but it was resolved to ' + matchersUtil.pp(actualValue) + '.' + message: + prefix(false) + + ' but it was resolved to ' + + matchersUtil.pp(actualValue) + + '.' }; } }, @@ -4429,7 +4498,7 @@ getJasmineRequireObj().toBeResolvedTo = function(j$) { }; }; -getJasmineRequireObj().DiffBuilder = function (j$) { +getJasmineRequireObj().DiffBuilder = function(j$) { return function DiffBuilder(config) { var prettyPrinter = (config || {}).prettyPrinter || j$.makePrettyPrinter(), mismatches = new j$.MismatchTree(), @@ -4438,21 +4507,28 @@ getJasmineRequireObj().DiffBuilder = function (j$) { expectedRoot = undefined; return { - setRoots: function (actual, expected) { + setRoots: function(actual, expected) { actualRoot = actual; expectedRoot = expected; }, - recordMismatch: function (formatter) { + recordMismatch: function(formatter) { mismatches.add(path, formatter); }, - getMessage: function () { + getMessage: function() { var messages = []; - mismatches.traverse(function (path, isLeaf, formatter) { - var actualCustom, expectedCustom, useCustom, - derefResult = dereferencePath(path, actualRoot, expectedRoot, prettyPrinter), + mismatches.traverse(function(path, isLeaf, formatter) { + var actualCustom, + expectedCustom, + useCustom, + derefResult = dereferencePath( + path, + actualRoot, + expectedRoot, + prettyPrinter + ), actual = derefResult.actual, expected = derefResult.expected; @@ -4463,15 +4539,22 @@ getJasmineRequireObj().DiffBuilder = function (j$) { actualCustom = prettyPrinter.customFormat_(actual); expectedCustom = prettyPrinter.customFormat_(expected); - useCustom = !(j$.util.isUndefined(actualCustom) && j$.util.isUndefined(expectedCustom)); + useCustom = !( + j$.util.isUndefined(actualCustom) && + j$.util.isUndefined(expectedCustom) + ); if (useCustom) { - messages.push(wrapPrettyPrinted(actualCustom, expectedCustom, path)); + messages.push( + wrapPrettyPrinted(actualCustom, expectedCustom, path) + ); return false; // don't recurse further } if (isLeaf) { - messages.push(defaultFormatter(actual, expected, path, prettyPrinter)); + messages.push( + defaultFormatter(actual, expected, path, prettyPrinter) + ); } return true; @@ -4480,7 +4563,7 @@ getJasmineRequireObj().DiffBuilder = function (j$) { return messages.join('\n'); }, - withPath: function (pathComponent, block) { + withPath: function(pathComponent, block) { var oldPath = path; path = path.add(pathComponent); block(); @@ -4489,22 +4572,32 @@ getJasmineRequireObj().DiffBuilder = function (j$) { }; function defaultFormatter(actual, expected, path, prettyPrinter) { - return wrapPrettyPrinted(prettyPrinter(actual), prettyPrinter(expected), path); + return wrapPrettyPrinted( + prettyPrinter(actual), + prettyPrinter(expected), + path + ); } function wrapPrettyPrinted(actual, expected, path) { - return 'Expected ' + - path + (path.depth() ? ' = ' : '') + + return ( + 'Expected ' + + path + + (path.depth() ? ' = ' : '') + actual + ' to equal ' + expected + - '.'; + '.' + ); } }; function dereferencePath(objectPath, actual, expected, pp) { function handleAsymmetricExpected() { - if (j$.isAsymmetricEqualityTester_(expected) && j$.isFunction_(expected.valuesForDiff_)) { + if ( + j$.isAsymmetricEqualityTester_(expected) && + j$.isFunction_(expected.valuesForDiff_) + ) { var asymmetricResult = expected.valuesForDiff_(actual, pp); expected = asymmetricResult.self; actual = asymmetricResult.other; @@ -4520,9 +4613,8 @@ getJasmineRequireObj().DiffBuilder = function (j$) { handleAsymmetricExpected(); } - return {actual: actual, expected: expected}; + return { actual: actual, expected: expected }; } - }; getJasmineRequireObj().MatchersUtil = function(j$) { @@ -4548,7 +4640,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { * @return {string} The pretty-printed value */ this.pp = options.pp || function() {}; - }; + } /** * Determines whether `haystack` contains `needle`, using the same comparison @@ -4566,9 +4658,10 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return haystack.has(needle); } - if ((Object.prototype.toString.apply(haystack) === '[object Array]') || - (!!haystack && !haystack.indexOf)) - { + if ( + Object.prototype.toString.apply(haystack) === '[object Array]' || + (!!haystack && !haystack.indexOf) + ) { for (var i = 0; i < haystack.length; i++) { if (this.equals(haystack[i], needle, customTesters)) { return true; @@ -4587,9 +4680,12 @@ getJasmineRequireObj().MatchersUtil = function(j$) { isNot = args[1], actual = args[2], expected = args.slice(3), - englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { return ' ' + s.toLowerCase(); }); + englishyPredicate = matcherName.replace(/[A-Z]/g, function(s) { + return ' ' + s.toLowerCase(); + }); - var message = 'Expected ' + + var message = + 'Expected ' + self.pp(actual) + (isNot ? ' not ' : ' ') + englishyPredicate; @@ -4606,20 +4702,41 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return message + '.'; }; - MatchersUtil.prototype.asymmetricDiff_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { + MatchersUtil.prototype.asymmetricDiff_ = function( + a, + b, + aStack, + bStack, + customTesters, + diffBuilder + ) { if (j$.isFunction_(b.valuesForDiff_)) { var values = b.valuesForDiff_(a, this.pp); - this.eq_(values.other, values.self, aStack, bStack, customTesters, diffBuilder); + this.eq_( + values.other, + values.self, + aStack, + bStack, + customTesters, + diffBuilder + ); } else { diffBuilder.recordMismatch(); } }; - MatchersUtil.prototype.asymmetricMatch_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { + MatchersUtil.prototype.asymmetricMatch_ = function( + a, + b, + aStack, + bStack, + customTesters, + diffBuilder + ) { var asymmetricA = j$.isAsymmetricEqualityTester_(a), - asymmetricB = j$.isAsymmetricEqualityTester_(b), - shim, - result; + asymmetricB = j$.isAsymmetricEqualityTester_(b), + shim, + result; if (asymmetricA === asymmetricB) { return undefined; @@ -4654,7 +4771,12 @@ getJasmineRequireObj().MatchersUtil = function(j$) { * @param [customTesters] An array of custom equality testers * @returns {boolean} True if the values are equal */ - MatchersUtil.prototype.equals = function(a, b, customTestersOrDiffBuilder, diffBuilderOrNothing) { + MatchersUtil.prototype.equals = function( + a, + b, + customTestersOrDiffBuilder, + diffBuilderOrNothing + ) { var customTesters, diffBuilder; if (isDiffBuilder(customTestersOrDiffBuilder)) { @@ -4673,10 +4795,26 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // Equality function lovingly adapted from isEqual in // [Underscore](http://underscorejs.org) - MatchersUtil.prototype.eq_ = function(a, b, aStack, bStack, customTesters, diffBuilder) { - var result = true, self = this, i; + MatchersUtil.prototype.eq_ = function( + a, + b, + aStack, + bStack, + customTesters, + diffBuilder + ) { + var result = true, + self = this, + i; - var asymmetricResult = this.asymmetricMatch_(a, b, aStack, bStack, customTesters, diffBuilder); + var asymmetricResult = this.asymmetricMatch_( + a, + b, + aStack, + bStack, + customTesters, + diffBuilder + ); if (!j$.util.isUndefined(asymmetricResult)) { return asymmetricResult; } @@ -4734,7 +4872,8 @@ getJasmineRequireObj().MatchersUtil = function(j$) { case '[object Number]': // `NaN`s are equivalent, but non-reflexive. An `egal` comparison is performed for // other numeric values. - result = a != +a ? b != +b : (a === 0 && b === 0 ? 1 / a == 1 / b : a == +b); + result = + a != +a ? b != +b : a === 0 && b === 0 ? 1 / a == 1 / b : a == +b; if (!result) { diffBuilder.recordMismatch(); } @@ -4751,10 +4890,12 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return result; // RegExps are compared by their source patterns and flags. case '[object RegExp]': - return a.source == b.source && + return ( + a.source == b.source && a.global == b.global && a.multiline == b.multiline && - a.ignoreCase == b.ignoreCase; + a.ignoreCase == b.ignoreCase + ); } if (typeof a != 'object' || typeof b != 'object') { diffBuilder.recordMismatch(); @@ -4788,7 +4929,9 @@ getJasmineRequireObj().MatchersUtil = function(j$) { while (length--) { // Linear search. Performance is inversely proportional to the number of // unique nested structures. - if (aStack[length] == a) { return bStack[length] == b; } + if (aStack[length] == a) { + return bStack[length] == b; + } } // Add the first object to the stack of traversed objects. aStack.push(a); @@ -4810,10 +4953,20 @@ getJasmineRequireObj().MatchersUtil = function(j$) { for (i = 0; i < aLength || i < bLength; i++) { diffBuilder.withPath(i, function() { if (i >= bLength) { - diffBuilder.recordMismatch(actualArrayIsLongerFormatter.bind(null, self.pp)); + diffBuilder.recordMismatch( + actualArrayIsLongerFormatter.bind(null, self.pp) + ); result = false; } else { - result = self.eq_(i < aLength ? a[i] : void 0, i < bLength ? b[i] : void 0, aStack, bStack, customTesters, diffBuilder) && result; + result = + self.eq_( + i < aLength ? a[i] : void 0, + i < bLength ? b[i] : void 0, + aStack, + bStack, + customTesters, + diffBuilder + ) && result; } }); } @@ -4828,11 +4981,11 @@ getJasmineRequireObj().MatchersUtil = function(j$) { var keysA = []; var keysB = []; - a.forEach( function( valueA, keyA ) { - keysA.push( keyA ); + a.forEach(function(valueA, keyA) { + keysA.push(keyA); }); - b.forEach( function( valueB, keyB ) { - keysB.push( keyB ); + b.forEach(function(valueB, keyB) { + keysB.push(keyB); }); // For both sets of keys, check they map to equal values in both maps. @@ -4853,13 +5006,30 @@ getJasmineRequireObj().MatchersUtil = function(j$) { // Only use the cmpKey when one of the keys is asymmetric and the corresponding key matches, // otherwise explicitly look up the mapKey in the other Map since we want keys with unique // obj identity (that are otherwise equal) to not match. - if (j$.isAsymmetricEqualityTester_(mapKey) || j$.isAsymmetricEqualityTester_(cmpKey) && - this.eq_(mapKey, cmpKey, aStack, bStack, customTesters, j$.NullDiffBuilder())) { + if ( + j$.isAsymmetricEqualityTester_(mapKey) || + (j$.isAsymmetricEqualityTester_(cmpKey) && + this.eq_( + mapKey, + cmpKey, + aStack, + bStack, + customTesters, + j$.NullDiffBuilder() + )) + ) { mapValueB = b.get(cmpKey); } else { mapValueB = b.get(mapKey); } - result = this.eq_(mapValueA, mapValueB, aStack, bStack, customTesters, j$.NullDiffBuilder()); + result = this.eq_( + mapValueA, + mapValueB, + aStack, + bStack, + customTesters, + j$.NullDiffBuilder() + ); } } @@ -4874,12 +5044,12 @@ getJasmineRequireObj().MatchersUtil = function(j$) { } var valuesA = []; - a.forEach( function( valueA ) { - valuesA.push( valueA ); + a.forEach(function(valueA) { + valuesA.push(valueA); }); var valuesB = []; - b.forEach( function( valueB ) { - valuesB.push( valueB ); + b.forEach(function(valueB) { + valuesB.push(valueB); }); // For both sets, check they are all contained in the other set @@ -4903,7 +5073,14 @@ getJasmineRequireObj().MatchersUtil = function(j$) { otherValue = otherValues[l]; prevStackSize = baseStack.length; // compare by value equality - found = this.eq_(baseValue, otherValue, baseStack, otherStack, customTesters, j$.NullDiffBuilder()); + found = this.eq_( + baseValue, + otherValue, + baseStack, + otherStack, + customTesters, + j$.NullDiffBuilder() + ); if (!found && prevStackSize !== baseStack.length) { baseStack.splice(prevStackSize); otherStack.splice(prevStackSize); @@ -4918,27 +5095,35 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return false; } } else { - // Objects with different constructors are not equivalent, but `Object`s // or `Array`s from different frames are. - var aCtor = a.constructor, bCtor = b.constructor; - if (aCtor !== bCtor && - isFunction(aCtor) && isFunction(bCtor) && - a instanceof aCtor && b instanceof bCtor && - !(aCtor instanceof aCtor && bCtor instanceof bCtor)) { - - diffBuilder.recordMismatch(constructorsAreDifferentFormatter.bind(null, this.pp)); + var aCtor = a.constructor, + bCtor = b.constructor; + if ( + aCtor !== bCtor && + isFunction(aCtor) && + isFunction(bCtor) && + a instanceof aCtor && + b instanceof bCtor && + !(aCtor instanceof aCtor && bCtor instanceof bCtor) + ) { + diffBuilder.recordMismatch( + constructorsAreDifferentFormatter.bind(null, this.pp) + ); return false; } } // Deep compare objects. - var aKeys = keys(a, className == '[object Array]'), key; + var aKeys = keys(a, className == '[object Array]'), + key; size = aKeys.length; // Ensure that both objects contain the same number of properties before comparing deep equality. if (keys(b, className == '[object Array]').length !== size) { - diffBuilder.recordMismatch(objectKeysAreDifferentFormatter.bind(null, this.pp)); + diffBuilder.recordMismatch( + objectKeysAreDifferentFormatter.bind(null, this.pp) + ); return false; } @@ -4946,13 +5131,17 @@ getJasmineRequireObj().MatchersUtil = function(j$) { key = aKeys[i]; // Deep compare each member if (!j$.util.has(b, key)) { - diffBuilder.recordMismatch(objectKeysAreDifferentFormatter.bind(null, this.pp)); + diffBuilder.recordMismatch( + objectKeysAreDifferentFormatter.bind(null, this.pp) + ); result = false; continue; } diffBuilder.withPath(key, function() { - if(!self.eq_(a[key], b[key], aStack, bStack, customTesters, diffBuilder)) { + if ( + !self.eq_(a[key], b[key], aStack, bStack, customTesters, diffBuilder) + ) { result = false; } }); @@ -4970,23 +5159,24 @@ getJasmineRequireObj().MatchersUtil = function(j$) { }; function keys(obj, isArray) { - var allKeys = Object.keys ? Object.keys(obj) : - (function(o) { + var allKeys = Object.keys + ? Object.keys(obj) + : (function(o) { var keys = []; for (var key in o) { - if (j$.util.has(o, key)) { - keys.push(key); - } + if (j$.util.has(o, key)) { + keys.push(key); + } } return keys; - })(obj); + })(obj); if (!isArray) { return allKeys; } if (allKeys.length === 0) { - return allKeys; + return allKeys; } var extraKeys = []; @@ -5005,21 +5195,25 @@ getJasmineRequireObj().MatchersUtil = function(j$) { function objectKeysAreDifferentFormatter(pp, actual, expected, path) { var missingProperties = j$.util.objectDifference(expected, actual), - extraProperties = j$.util.objectDifference(actual, expected), - missingPropertiesMessage = formatKeyValuePairs(pp, missingProperties), - extraPropertiesMessage = formatKeyValuePairs(pp, extraProperties), - messages = []; + extraProperties = j$.util.objectDifference(actual, expected), + missingPropertiesMessage = formatKeyValuePairs(pp, missingProperties), + extraPropertiesMessage = formatKeyValuePairs(pp, extraProperties), + messages = []; if (!path.depth()) { path = 'object'; } if (missingPropertiesMessage.length) { - messages.push('Expected ' + path + ' to have properties' + missingPropertiesMessage); + messages.push( + 'Expected ' + path + ' to have properties' + missingPropertiesMessage + ); } if (extraPropertiesMessage.length) { - messages.push('Expected ' + path + ' not to have properties' + extraPropertiesMessage); + messages.push( + 'Expected ' + path + ' not to have properties' + extraPropertiesMessage + ); } return messages.join('\n'); @@ -5030,17 +5224,25 @@ getJasmineRequireObj().MatchersUtil = function(j$) { path = 'object'; } - return 'Expected ' + - path + ' to be a kind of ' + + return ( + 'Expected ' + + path + + ' to be a kind of ' + j$.fnNameFor(expected.constructor) + - ', but was ' + pp(actual) + '.'; + ', but was ' + + pp(actual) + + '.' + ); } function actualArrayIsLongerFormatter(pp, actual, expected, path) { - return 'Unexpected ' + - path + (path.depth() ? ' = ' : '') + + return ( + 'Unexpected ' + + path + + (path.depth() ? ' = ' : '') + pp(actual) + - ' in array.'; + ' in array.' + ); } function formatKeyValuePairs(pp, obj) { @@ -5058,8 +5260,7 @@ getJasmineRequireObj().MatchersUtil = function(j$) { return MatchersUtil; }; -getJasmineRequireObj().MismatchTree = function (j$) { - +getJasmineRequireObj().MismatchTree = function(j$) { /* To be able to apply custom object formatters at all possible levels of an object graph, DiffBuilder needs to be able to know not just where the @@ -5074,7 +5275,7 @@ getJasmineRequireObj().MismatchTree = function (j$) { this.isMismatch = false; } - MismatchTree.prototype.add = function (path, formatter) { + MismatchTree.prototype.add = function(path, formatter) { var key, child; if (path.depth() === 0) { @@ -5094,8 +5295,9 @@ getJasmineRequireObj().MismatchTree = function (j$) { } }; - MismatchTree.prototype.traverse = function (visit) { - var i, hasChildren = this.children.length > 0; + MismatchTree.prototype.traverse = function(visit) { + var i, + hasChildren = this.children.length > 0; if (this.isMismatch || hasChildren) { if (visit(this.path, !hasChildren, this.formatter)) { @@ -5120,7 +5322,6 @@ getJasmineRequireObj().MismatchTree = function (j$) { return MismatchTree; }; - getJasmineRequireObj().nothing = function() { /** * {@link expect} nothing explicitly. @@ -5189,7 +5390,7 @@ getJasmineRequireObj().ObjectPath = function(j$) { return '.' + prop; } - return '[\'' + prop + '\']'; + return "['" + prop + "']"; } function map(array, fn) { @@ -5237,7 +5438,8 @@ getJasmineRequireObj().toBe = function(j$) { * expect(thing).toBe(realThing); */ function toBe(matchersUtil) { - var tip = ' Tip: To check for deep equality, use .toEqual() instead of .toBe().'; + var tip = + ' Tip: To check for deep equality, use .toEqual() instead of .toBe().'; return { compare: function(actual, expected) { @@ -5246,7 +5448,13 @@ getJasmineRequireObj().toBe = function(j$) { }; if (typeof expected === 'object') { - result.message = matchersUtil.buildFailureMessage('toBe', result.pass, actual, expected) + tip; + result.message = + matchersUtil.buildFailureMessage( + 'toBe', + result.pass, + actual, + expected + ) + tip; } return result; @@ -5276,8 +5484,13 @@ getJasmineRequireObj().toBeCloseTo = function() { } if (expected === null || actual === null) { - throw new Error('Cannot use toBeCloseTo with null. Arguments evaluated to: ' + - 'expect(' + actual + ').toBeCloseTo(' + expected + ').' + throw new Error( + 'Cannot use toBeCloseTo with null. Arguments evaluated to: ' + + 'expect(' + + actual + + ').toBeCloseTo(' + + expected + + ').' ); } @@ -5308,7 +5521,7 @@ getJasmineRequireObj().toBeDefined = function() { return { compare: function(actual) { return { - pass: (void 0 !== actual) + pass: void 0 !== actual }; } }; @@ -5384,7 +5597,6 @@ getJasmineRequireObj().toBeGreaterThan = function() { return toBeGreaterThan; }; - getJasmineRequireObj().toBeGreaterThanOrEqual = function() { /** * {@link expect} the actual value to be greater than or equal to the expected value. @@ -5409,7 +5621,10 @@ getJasmineRequireObj().toBeGreaterThanOrEqual = function() { }; getJasmineRequireObj().toBeInstanceOf = function(j$) { - var usageError = j$.formatErrorMsg('', 'expect(value).toBeInstanceOf()'); + var usageError = j$.formatErrorMsg( + '', + 'expect(value).toBeInstanceOf()' + ); /** * {@link expect} the actual to be an instance of the expected class @@ -5425,27 +5640,42 @@ getJasmineRequireObj().toBeInstanceOf = function(j$) { function toBeInstanceOf(matchersUtil) { return { compare: function(actual, expected) { - var actualType = actual && actual.constructor ? j$.fnNameFor(actual.constructor) : matchersUtil.pp(actual), - expectedType = expected ? j$.fnNameFor(expected) : matchersUtil.pp(expected), - expectedMatcher, - pass; + var actualType = + actual && actual.constructor + ? j$.fnNameFor(actual.constructor) + : matchersUtil.pp(actual), + expectedType = expected + ? j$.fnNameFor(expected) + : matchersUtil.pp(expected), + expectedMatcher, + pass; try { - expectedMatcher = new j$.Any(expected); - pass = expectedMatcher.asymmetricMatch(actual); + expectedMatcher = new j$.Any(expected); + pass = expectedMatcher.asymmetricMatch(actual); } catch (error) { - throw new Error(usageError('Expected value is not a constructor function')); + throw new Error( + usageError('Expected value is not a constructor function') + ); } if (pass) { return { pass: true, - message: 'Expected instance of ' + actualType + ' not to be an instance of ' + expectedType + message: + 'Expected instance of ' + + actualType + + ' not to be an instance of ' + + expectedType }; } else { return { pass: false, - message: 'Expected instance of ' + actualType + ' to be an instance of ' + expectedType + message: + 'Expected instance of ' + + actualType + + ' to be an instance of ' + + expectedType }; } } @@ -5467,7 +5697,6 @@ getJasmineRequireObj().toBeLessThan = function() { */ function toBeLessThan() { return { - compare: function(actual, expected) { return { pass: actual < expected @@ -5491,7 +5720,6 @@ getJasmineRequireObj().toBeLessThanOrEqual = function() { */ function toBeLessThanOrEqual() { return { - compare: function(actual, expected) { return { pass: actual <= expected @@ -5516,13 +5744,15 @@ getJasmineRequireObj().toBeNaN = function(j$) { return { compare: function(actual) { var result = { - pass: (actual !== actual) + pass: actual !== actual }; if (result.pass) { result.message = 'Expected actual not to be NaN.'; } else { - result.message = function() { return 'Expected ' + matchersUtil.pp(actual) + ' to be NaN.'; }; + result.message = function() { + return 'Expected ' + matchersUtil.pp(actual) + ' to be NaN.'; + }; } return result; @@ -5546,13 +5776,15 @@ getJasmineRequireObj().toBeNegativeInfinity = function(j$) { return { compare: function(actual) { var result = { - pass: (actual === Number.NEGATIVE_INFINITY) + pass: actual === Number.NEGATIVE_INFINITY }; if (result.pass) { result.message = 'Expected actual not to be -Infinity.'; } else { - result.message = function() { return 'Expected ' + matchersUtil.pp(actual) + ' to be -Infinity.'; }; + result.message = function() { + return 'Expected ' + matchersUtil.pp(actual) + ' to be -Infinity.'; + }; } return result; @@ -5598,13 +5830,15 @@ getJasmineRequireObj().toBePositiveInfinity = function(j$) { return { compare: function(actual) { var result = { - pass: (actual === Number.POSITIVE_INFINITY) + pass: actual === Number.POSITIVE_INFINITY }; if (result.pass) { result.message = 'Expected actual not to be Infinity.'; } else { - result.message = function() { return 'Expected ' + matchersUtil.pp(actual) + ' to be Infinity.'; }; + result.message = function() { + return 'Expected ' + matchersUtil.pp(actual) + ' to be Infinity.'; + }; } return result; @@ -5695,7 +5929,6 @@ getJasmineRequireObj().toContain = function() { function toContain(matchersUtil) { return { compare: function(actual, expected) { - return { pass: matchersUtil.contains(actual, expected) }; @@ -5722,7 +5955,7 @@ getJasmineRequireObj().toEqual = function(j$) { var result = { pass: false }, - diffBuilder = j$.DiffBuilder({prettyPrinter: matchersUtil.pp}); + diffBuilder = j$.DiffBuilder({ prettyPrinter: matchersUtil.pp }); result.pass = matchersUtil.equals(actual, expected, diffBuilder); @@ -5738,8 +5971,10 @@ getJasmineRequireObj().toEqual = function(j$) { }; getJasmineRequireObj().toHaveBeenCalled = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalled()'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalled()' + ); /** * {@link expect} the actual (a {@link Spy}) to have been called. @@ -5756,18 +5991,24 @@ getJasmineRequireObj().toHaveBeenCalled = function(j$) { var result = {}; if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(actual) + '.')); + throw new Error( + getErrorMsg( + 'Expected a spy, but got ' + matchersUtil.pp(actual) + '.' + ) + ); } if (arguments.length > 1) { - throw new Error(getErrorMsg('Does not take arguments, use toHaveBeenCalledWith')); + throw new Error( + getErrorMsg('Does not take arguments, use toHaveBeenCalledWith') + ); } result.pass = actual.calls.any(); - result.message = result.pass ? - 'Expected spy ' + actual.and.identity + ' not to have been called.' : - 'Expected spy ' + actual.and.identity + ' to have been called.'; + result.message = result.pass + ? 'Expected spy ' + actual.and.identity + ' not to have been called.' + : 'Expected spy ' + actual.and.identity + ' to have been called.'; return result; } @@ -5778,8 +6019,10 @@ getJasmineRequireObj().toHaveBeenCalled = function(j$) { }; getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledBefore()'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalledBefore()' + ); /** * {@link expect} the actual value (a {@link Spy}) to have been called before another {@link Spy}. @@ -5794,20 +6037,30 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { return { compare: function(firstSpy, latterSpy) { if (!j$.isSpy(firstSpy)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(firstSpy) + '.')); + throw new Error( + getErrorMsg( + 'Expected a spy, but got ' + matchersUtil.pp(firstSpy) + '.' + ) + ); } if (!j$.isSpy(latterSpy)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(latterSpy) + '.')); + throw new Error( + getErrorMsg( + 'Expected a spy, but got ' + matchersUtil.pp(latterSpy) + '.' + ) + ); } var result = { pass: false }; if (!firstSpy.calls.count()) { - result.message = 'Expected spy ' + firstSpy.and.identity + ' to have been called.'; + result.message = + 'Expected spy ' + firstSpy.and.identity + ' to have been called.'; return result; } if (!latterSpy.calls.count()) { - result.message = 'Expected spy ' + latterSpy.and.identity + ' to have been called.'; + result.message = + 'Expected spy ' + latterSpy.and.identity + ' to have been called.'; return result; } @@ -5817,17 +6070,36 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { result.pass = latest1stSpyCall < first2ndSpyCall; if (result.pass) { - result.message = 'Expected spy ' + firstSpy.and.identity + ' to not have been called before spy ' + latterSpy.and.identity + ', but it was'; + result.message = + 'Expected spy ' + + firstSpy.and.identity + + ' to not have been called before spy ' + + latterSpy.and.identity + + ', but it was'; } else { var first1stSpyCall = firstSpy.calls.first().invocationOrder; var latest2ndSpyCall = latterSpy.calls.mostRecent().invocationOrder; - if(first1stSpyCall < first2ndSpyCall) { - result.message = 'Expected latest call to spy ' + firstSpy.and.identity + ' to have been called before first call to spy ' + latterSpy.and.identity + ' (no interleaved calls)'; + if (first1stSpyCall < first2ndSpyCall) { + result.message = + 'Expected latest call to spy ' + + firstSpy.and.identity + + ' to have been called before first call to spy ' + + latterSpy.and.identity + + ' (no interleaved calls)'; } else if (latest2ndSpyCall > latest1stSpyCall) { - result.message = 'Expected first call to spy ' + latterSpy.and.identity + ' to have been called after latest call to spy ' + firstSpy.and.identity + ' (no interleaved calls)'; + result.message = + 'Expected first call to spy ' + + latterSpy.and.identity + + ' to have been called after latest call to spy ' + + firstSpy.and.identity + + ' (no interleaved calls)'; } else { - result.message = 'Expected spy ' + firstSpy.and.identity + ' to have been called before spy ' + latterSpy.and.identity; + result.message = + 'Expected spy ' + + firstSpy.and.identity + + ' to have been called before spy ' + + latterSpy.and.identity; } } @@ -5839,9 +6111,11 @@ getJasmineRequireObj().toHaveBeenCalledBefore = function(j$) { return toHaveBeenCalledBefore; }; -getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledOnceWith(...arguments)'); +getJasmineRequireObj().toHaveBeenCalledOnceWith = function(j$) { + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalledOnceWith(...arguments)' + ); /** * {@link expect} the actual (a {@link Spy}) to have been called exactly once, and exactly with the particular arguments. @@ -5854,31 +6128,44 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { */ function toHaveBeenCalledOnceWith(util) { return { - compare: function () { + compare: function() { var args = Array.prototype.slice.call(arguments, 0), actual = args[0], expectedArgs = args.slice(1); if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + util.pp(actual) + '.')); + throw new Error( + getErrorMsg('Expected a spy, but got ' + util.pp(actual) + '.') + ); } - var prettyPrintedCalls = actual.calls.allArgs().map(function (argsForCall) { - return ' ' + util.pp(argsForCall); - }); + var prettyPrintedCalls = actual.calls + .allArgs() + .map(function(argsForCall) { + return ' ' + util.pp(argsForCall); + }); - if (actual.calls.count() === 1 && util.contains(actual.calls.allArgs(), expectedArgs)) { + if ( + actual.calls.count() === 1 && + util.contains(actual.calls.allArgs(), expectedArgs) + ) { return { pass: true, - message: 'Expected spy ' + actual.and.identity + ' to have been called 0 times, multiple times, or once, but with arguments different from:\n' - + ' ' + util.pp(expectedArgs) + '\n' - + 'But the actual call was:\n' - + prettyPrintedCalls.join(',\n') + '.\n\n' + message: + 'Expected spy ' + + actual.and.identity + + ' to have been called 0 times, multiple times, or once, but with arguments different from:\n' + + ' ' + + util.pp(expectedArgs) + + '\n' + + 'But the actual call was:\n' + + prettyPrintedCalls.join(',\n') + + '.\n\n' }; } function getDiffs() { - return actual.calls.allArgs().map(function (argsForCall, callIx) { + return actual.calls.allArgs().map(function(argsForCall, callIx) { var diffBuilder = new j$.DiffBuilder(); util.equals(argsForCall, expectedArgs, diffBuilder); return diffBuilder.getMessage(); @@ -5890,17 +6177,32 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { case 0: return 'But it was never called.\n\n'; case 1: - return 'But the actual call was:\n' + prettyPrintedCalls.join(',\n') + '.\n' + getDiffs().join('\n') + '\n\n'; + return ( + 'But the actual call was:\n' + + prettyPrintedCalls.join(',\n') + + '.\n' + + getDiffs().join('\n') + + '\n\n' + ); default: - return 'But the actual calls were:\n' + prettyPrintedCalls.join(',\n') + '.\n\n'; + return ( + 'But the actual calls were:\n' + + prettyPrintedCalls.join(',\n') + + '.\n\n' + ); } } return { pass: false, - message: 'Expected spy ' + actual.and.identity + ' to have been called only once, and with given args:\n' - + ' ' + util.pp(expectedArgs) + '\n' - + butString() + message: + 'Expected spy ' + + actual.and.identity + + ' to have been called only once, and with given args:\n' + + ' ' + + util.pp(expectedArgs) + + '\n' + + butString() }; } }; @@ -5910,8 +6212,10 @@ getJasmineRequireObj().toHaveBeenCalledOnceWith = function (j$) { }; getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledTimes()'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalledTimes()' + ); /** * {@link expect} the actual (a {@link Spy}) to have been called the specified number of times. @@ -5926,23 +6230,43 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { return { compare: function(actual, expected) { if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(actual) + '.')); + throw new Error( + getErrorMsg( + 'Expected a spy, but got ' + matchersUtil.pp(actual) + '.' + ) + ); } var args = Array.prototype.slice.call(arguments, 0), result = { pass: false }; if (!j$.isNumber_(expected)) { - throw new Error(getErrorMsg('The expected times failed is a required argument and must be a number.')); + throw new Error( + getErrorMsg( + 'The expected times failed is a required argument and must be a number.' + ) + ); } actual = args[0]; var calls = actual.calls.count(); var timesMessage = expected === 1 ? 'once' : expected + ' times'; result.pass = calls === expected; - result.message = result.pass ? - 'Expected spy ' + actual.and.identity + ' not to have been called ' + timesMessage + '. It was called ' + calls + ' times.' : - 'Expected spy ' + actual.and.identity + ' to have been called ' + timesMessage + '. It was called ' + calls + ' times.'; + result.message = result.pass + ? 'Expected spy ' + + actual.and.identity + + ' not to have been called ' + + timesMessage + + '. It was called ' + + calls + + ' times.' + : 'Expected spy ' + + actual.and.identity + + ' to have been called ' + + timesMessage + + '. It was called ' + + calls + + ' times.'; return result; } }; @@ -5952,8 +6276,10 @@ getJasmineRequireObj().toHaveBeenCalledTimes = function(j$) { }; getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toHaveBeenCalledWith(...arguments)'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toHaveBeenCalledWith(...arguments)' + ); /** * {@link expect} the actual (a {@link Spy}) to have been called with particular arguments at least once. @@ -5973,14 +6299,23 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { result = { pass: false }; if (!j$.isSpy(actual)) { - throw new Error(getErrorMsg('Expected a spy, but got ' + matchersUtil.pp(actual) + '.')); + throw new Error( + getErrorMsg( + 'Expected a spy, but got ' + matchersUtil.pp(actual) + '.' + ) + ); } if (!actual.calls.any()) { result.message = function() { - return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + - ' ' + matchersUtil.pp(expectedArgs) + - '\nbut it was never called.'; + return ( + 'Expected spy ' + + actual.and.identity + + ' to have been called with:\n' + + ' ' + + matchersUtil.pp(expectedArgs) + + '\nbut it was never called.' + ); }; return result; } @@ -5988,28 +6323,49 @@ getJasmineRequireObj().toHaveBeenCalledWith = function(j$) { if (matchersUtil.contains(actual.calls.allArgs(), expectedArgs)) { result.pass = true; result.message = function() { - return 'Expected spy ' + actual.and.identity + ' not to have been called with:\n' + - ' ' + matchersUtil.pp(expectedArgs) + - '\nbut it was.'; + return ( + 'Expected spy ' + + actual.and.identity + + ' not to have been called with:\n' + + ' ' + + matchersUtil.pp(expectedArgs) + + '\nbut it was.' + ); }; } else { result.message = function() { - var prettyPrintedCalls = actual.calls.allArgs().map(function(argsForCall) { - return ' ' + matchersUtil.pp(argsForCall); - }); + var prettyPrintedCalls = actual.calls + .allArgs() + .map(function(argsForCall) { + return ' ' + matchersUtil.pp(argsForCall); + }); - var diffs = actual.calls.allArgs().map(function(argsForCall, callIx) { - var diffBuilder = new j$.DiffBuilder(); - matchersUtil.equals(argsForCall, expectedArgs, diffBuilder); - return 'Call ' + callIx + ':\n' + - diffBuilder.getMessage().replace(/^/mg, ' '); - }); + var diffs = actual.calls + .allArgs() + .map(function(argsForCall, callIx) { + var diffBuilder = new j$.DiffBuilder(); + matchersUtil.equals(argsForCall, expectedArgs, diffBuilder); + return ( + 'Call ' + + callIx + + ':\n' + + diffBuilder.getMessage().replace(/^/gm, ' ') + ); + }); - return 'Expected spy ' + actual.and.identity + ' to have been called with:\n' + - ' ' + matchersUtil.pp(expectedArgs) + '\n' + '' + + return ( + 'Expected spy ' + + actual.and.identity + + ' to have been called with:\n' + + ' ' + + matchersUtil.pp(expectedArgs) + + '\n' + + '' + 'but actual calls were:\n' + - prettyPrintedCalls.join(',\n') + '.\n\n' + - diffs.join('\n'); + prettyPrintedCalls.join(',\n') + + '.\n\n' + + diffs.join('\n') + ); }; } @@ -6048,9 +6404,9 @@ getJasmineRequireObj().toHaveClass = function(j$) { } function isElement(maybeEl) { - return maybeEl && - maybeEl.classList && - j$.isFunction_(maybeEl.classList.contains); + return ( + maybeEl && maybeEl.classList && j$.isFunction_(maybeEl.classList.contains) + ); } return toHaveClass; @@ -6071,10 +6427,14 @@ getJasmineRequireObj().toHaveSize = function(j$) { return { compare: function(actual, expected) { var result = { - pass: false - }; + pass: false + }; - if (j$.isA_('WeakSet', actual) || j$.isWeakMap(actual) || j$.isDataView(actual)) { + if ( + j$.isA_('WeakSet', actual) || + j$.isWeakMap(actual) || + j$.isDataView(actual) + ) { throw new Error('Cannot get size of ' + actual + '.'); } @@ -6091,17 +6451,24 @@ getJasmineRequireObj().toHaveSize = function(j$) { }; } - var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || 9007199254740991; // eslint-disable-line compat/compat + var MAX_SAFE_INTEGER = Number.MAX_SAFE_INTEGER || 9007199254740991; // eslint-disable-line compat/compat function isLength(value) { - return (typeof value == 'number') && value > -1 && value % 1 === 0 && value <= MAX_SAFE_INTEGER; + return ( + typeof value == 'number' && + value > -1 && + value % 1 === 0 && + value <= MAX_SAFE_INTEGER + ); } return toHaveSize; }; getJasmineRequireObj().toMatch = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect().toMatch( || )'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect().toMatch( || )' + ); /** * {@link expect} the actual value to match a regular expression @@ -6133,8 +6500,10 @@ getJasmineRequireObj().toMatch = function(j$) { }; getJasmineRequireObj().toThrow = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect(function() {}).toThrow()'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect(function() {}).toThrow()' + ); /** * {@link expect} a function to `throw` something. @@ -6171,16 +6540,36 @@ getJasmineRequireObj().toThrow = function(j$) { if (arguments.length == 1) { result.pass = true; - result.message = function() { return 'Expected function not to throw, but it threw ' + matchersUtil.pp(thrown) + '.'; }; + result.message = function() { + return ( + 'Expected function not to throw, but it threw ' + + matchersUtil.pp(thrown) + + '.' + ); + }; return result; } if (matchersUtil.equals(thrown, expected)) { result.pass = true; - result.message = function() { return 'Expected function not to throw ' + matchersUtil.pp(expected) + '.'; }; + result.message = function() { + return ( + 'Expected function not to throw ' + + matchersUtil.pp(expected) + + '.' + ); + }; } else { - result.message = function() { return 'Expected function to throw ' + matchersUtil.pp(expected) + ', but it threw ' + matchersUtil.pp(thrown) + '.'; }; + result.message = function() { + return ( + 'Expected function to throw ' + + matchersUtil.pp(expected) + + ', but it threw ' + + matchersUtil.pp(thrown) + + '.' + ); + }; } return result; @@ -6192,8 +6581,10 @@ getJasmineRequireObj().toThrow = function(j$) { }; getJasmineRequireObj().toThrowError = function(j$) { - - var getErrorMsg = j$.formatErrorMsg('', 'expect(function() {}).toThrowError(, )'); + var getErrorMsg = j$.formatErrorMsg( + '', + 'expect(function() {}).toThrowError(, )' + ); /** * {@link expect} a function to `throw` an `Error`. @@ -6227,7 +6618,13 @@ getJasmineRequireObj().toThrowError = function(j$) { } if (!j$.isError_(thrown)) { - return fail(function() { return 'Expected function to throw an Error, but it threw ' + matchersUtil.pp(thrown) + '.'; }); + return fail(function() { + return ( + 'Expected function to throw an Error, but it threw ' + + matchersUtil.pp(thrown) + + '.' + ); + }); } return errorMatcher.match(thrown); @@ -6261,7 +6658,11 @@ getJasmineRequireObj().toThrowError = function(j$) { function anyMatcher() { return { match: function(error) { - return pass('Expected function not to throw an Error, but it threw ' + j$.fnNameFor(error) + '.'); + return pass( + 'Expected function not to throw an Error, but it threw ' + + j$.fnNameFor(error) + + '.' + ); } }; } @@ -6269,9 +6670,13 @@ getJasmineRequireObj().toThrowError = function(j$) { function exactMatcher(expected, errorType) { if (expected && !isStringOrRegExp(expected)) { if (errorType) { - throw new Error(getErrorMsg('Expected error message is not a string or RegExp.')); + throw new Error( + getErrorMsg('Expected error message is not a string or RegExp.') + ); } else { - throw new Error(getErrorMsg('Expected is not an Error, string, or RegExp.')); + throw new Error( + getErrorMsg('Expected is not an Error, string, or RegExp.') + ); } } @@ -6283,11 +6688,15 @@ getJasmineRequireObj().toThrowError = function(j$) { } } - var errorTypeDescription = errorType ? j$.fnNameFor(errorType) : 'an exception'; + var errorTypeDescription = errorType + ? j$.fnNameFor(errorType) + : 'an exception'; function thrownDescription(thrown) { - var thrownName = errorType ? j$.fnNameFor(thrown.constructor) : 'an exception', - thrownMessage = ''; + var thrownName = errorType + ? j$.fnNameFor(thrown.constructor) + : 'an exception', + thrownMessage = ''; if (expected) { thrownMessage = ' with message ' + matchersUtil.pp(thrown.message); @@ -6307,20 +6716,33 @@ getJasmineRequireObj().toThrowError = function(j$) { } function matches(error) { - return (errorType === null || error instanceof errorType) && - (expected === null || messageMatch(error.message)); + return ( + (errorType === null || error instanceof errorType) && + (expected === null || messageMatch(error.message)) + ); } return { match: function(thrown) { if (matches(thrown)) { return pass(function() { - return 'Expected function not to throw ' + errorTypeDescription + messageDescription() + '.'; + return ( + 'Expected function not to throw ' + + errorTypeDescription + + messageDescription() + + '.' + ); }); } else { return fail(function() { - return 'Expected function to throw ' + errorTypeDescription + messageDescription() + - ', but it threw ' + thrownDescription(thrown) + '.'; + return ( + 'Expected function to throw ' + + errorTypeDescription + + messageDescription() + + ', but it threw ' + + thrownDescription(thrown) + + '.' + ); }); } } @@ -6328,7 +6750,7 @@ getJasmineRequireObj().toThrowError = function(j$) { } function isStringOrRegExp(potential) { - return potential instanceof RegExp || (typeof potential == 'string'); + return potential instanceof RegExp || typeof potential == 'string'; } function isAnErrorType(type) { @@ -6360,7 +6782,10 @@ getJasmineRequireObj().toThrowError = function(j$) { }; getJasmineRequireObj().toThrowMatching = function(j$) { - var usageError = j$.formatErrorMsg('', 'expect(function() {}).toThrowMatching()'); + var usageError = j$.formatErrorMsg( + '', + 'expect(function() {}).toThrowMatching()' + ); /** * {@link expect} a function to `throw` something matching a predicate. @@ -6392,20 +6817,29 @@ getJasmineRequireObj().toThrowMatching = function(j$) { } if (predicate(thrown)) { - return pass('Expected function not to throw an exception matching a predicate.'); + return pass( + 'Expected function not to throw an exception matching a predicate.' + ); } else { - return fail(function() { - return 'Expected function to throw an exception matching a predicate, ' + - 'but it threw ' + thrownDescription(thrown) + '.'; - }); + return fail(function() { + return ( + 'Expected function to throw an exception matching a predicate, ' + + 'but it threw ' + + thrownDescription(thrown) + + '.' + ); + }); } } }; function thrownDescription(thrown) { if (thrown && thrown.constructor) { - return j$.fnNameFor(thrown.constructor) + ' with message ' + - matchersUtil.pp(thrown.message); + return ( + j$.fnNameFor(thrown.constructor) + + ' with message ' + + matchersUtil.pp(thrown.message) + ); } else { return matchersUtil.pp(thrown); } From 204acf72978d520188aafeccbdf87c8e44cdcf94 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Tue, 20 Oct 2020 14:14:24 -0700 Subject: [PATCH 184/201] Updated Node versions in .travis.yml --- .travis.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.travis.yml b/.travis.yml index dadd8965..9d7f3f44 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,5 +1,5 @@ language: node_js -node_js: 10 +node_js: 14 script: $TEST_COMMAND @@ -12,11 +12,11 @@ env: matrix: include: - - node_js: "10" + - node_js: "14" env: JASMINE_LONG_PROPERTY_TESTS="y" TEST_COMMAND="npm test" - node_js: "12" env: TEST_COMMAND="npm test" - - node_js: "8" + - node_js: "10" env: TEST_COMMAND="npm test" - env: JASMINE_BROWSER="internet explorer" SAUCE_BROWSER_VERSION=11 SAUCE_OS="Windows 8.1" if: type != pull_request From b1bcd6e82537ff1849e2d95afa5480101bc85282 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 29 Oct 2020 15:10:54 -0700 Subject: [PATCH 185/201] Pointed Travis badge at travis-ci.com, not .org --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index c7189c1d..15dcc5ba 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ [](http://jasmine.github.io) -[![Build Status](https://travis-ci.org/jasmine/jasmine.svg?branch=main)](https://travis-ci.org/jasmine/jasmine) +[![Build Status](https://travis-ci.com/jasmine/jasmine.svg?branch=main)](https://travis-ci.com/jasmine/jasmine) [![Open Source Helpers](https://www.codetriage.com/jasmine/jasmine/badges/users.svg)](https://www.codetriage.com/jasmine/jasmine) [![FOSSA Status](https://app.fossa.io/api/projects/git%2Bgithub.com%2Fjasmine%2Fjasmine.svg?type=shield)](https://app.fossa.io/projects/git%2Bgithub.com%2Fjasmine%2Fjasmine?ref=badge_shield) From 623e638cd4f4e6a786fe2e2c0c253ac3d950c2ca Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Mon, 2 Nov 2020 16:26:55 -0800 Subject: [PATCH 186/201] Updated supported Node versions in README --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 15dcc5ba..795ce1f7 100644 --- a/README.md +++ b/README.md @@ -56,7 +56,7 @@ Jasmine tests itself across many browsers (Safari, Chrome, Firefox, Microsoft Ed | Environment | Supported versions | |-------------------|--------------------| -| Node | 8, 10, 12 | +| Node | 10, 12, 14 | | Safari | 8-13 | | Chrome | Evergreen | | Firefox | Evergreen, 68 | From 60bbe6814846cdf213cd29105eb8fff90fb21206 Mon Sep 17 00:00:00 2001 From: Jannes Meyer Date: Mon, 2 Nov 2020 12:50:19 +0100 Subject: [PATCH 187/201] Support source maps --- spec/core/ExceptionFormatterSpec.js | 31 +++++++++++++++++++++++++++++ src/core/ExceptionFormatter.js | 2 +- 2 files changed, 32 insertions(+), 1 deletion(-) diff --git a/spec/core/ExceptionFormatterSpec.js b/spec/core/ExceptionFormatterSpec.js index 2242cf27..1c4a1c62 100644 --- a/spec/core/ExceptionFormatterSpec.js +++ b/spec/core/ExceptionFormatterSpec.js @@ -86,6 +86,37 @@ describe('ExceptionFormatter', function() { ); }); + it('filters Jasmine stack frames from V8-style traces but leaves unmatched lines intact', function() { + var error = { + message: 'nope', + stack: + 'C:\\__spec__\\core\\UtilSpec.ts:120\n' + + " new Error('nope');\n" + + ' ^\n' + + '\n' + + 'Error: nope\n' + + ' at fn1 (C:\\__spec__\\core\\UtilSpec.js:115:19)\n' + + ' -> C:\\__spec__\\core\\UtilSpec.ts:120:15\n' + + ' at fn2 (C:\\__jasmine__\\lib\\jasmine-core\\jasmine.js:7533:40)\n' + + ' at fn3 (C:\\__jasmine__\\lib\\jasmine-core\\jasmine.js:7575:25)\n' + + ' at fn4 (node:internal/timers:462:21)\n' + }; + var subject = new jasmineUnderTest.ExceptionFormatter({ + jasmineFile: 'C:\\__jasmine__\\lib\\jasmine-core\\jasmine.js' + }); + var result = subject.stack(error); + expect(result).toEqual( + 'C:\\__spec__\\core\\UtilSpec.ts:120\n' + + " new Error('nope');\n" + + ' ^\n' + + 'Error: nope\n' + + ' at fn1 (C:\\__spec__\\core\\UtilSpec.js:115:19)\n' + + ' -> C:\\__spec__\\core\\UtilSpec.ts:120:15\n' + + ' at \n' + + ' at fn4 (node:internal/timers:462:21)' + ); + }); + it('filters Jasmine stack frames from V8 style traces', function() { var error = { message: 'nope', diff --git a/src/core/ExceptionFormatter.js b/src/core/ExceptionFormatter.js index 14534bb2..72981da1 100644 --- a/src/core/ExceptionFormatter.js +++ b/src/core/ExceptionFormatter.js @@ -63,7 +63,7 @@ getJasmineRequireObj().ExceptionFormatter = function(j$) { stackTrace.style === 'webkit' ? '' : ' at '; stackTrace.frames.forEach(function(frame) { - if (frame.file && frame.file !== jasmineFile) { + if (frame.file !== jasmineFile) { result.push(frame.raw); } else if (result[result.length - 1] !== jasmineMarker) { result.push(jasmineMarker); From 89331bb1bbda9a86f8eea7db43ee8605b414bff1 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 21 Nov 2020 13:35:10 -0800 Subject: [PATCH 188/201] Fixed comparison between URL objects * Fixes #1866 --- lib/jasmine-core/jasmine.js | 13 +++++++ spec/core/baseSpec.js | 13 +++++++ spec/core/matchers/matchersUtilSpec.js | 48 ++++++++++++++++++++++++++ spec/helpers/checkForUrl.js | 17 +++++++++ spec/support/jasmine-browser.js | 1 + spec/support/jasmine.json | 1 + src/core/base.js | 9 +++++ src/core/matchers/matchersUtil.js | 4 +++ 8 files changed, 106 insertions(+) create mode 100644 spec/helpers/checkForUrl.js diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 4cc2b45f..527f3fb4 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -329,6 +329,15 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { ); }; + j$.isURL = function(obj) { + return ( + obj !== null && + typeof obj !== 'undefined' && + typeof jasmineGlobal.URL !== 'undefined' && + obj.constructor === jasmineGlobal.URL + ); + }; + j$.isDataView = function(obj) { return ( obj !== null && @@ -5094,6 +5103,10 @@ getJasmineRequireObj().MatchersUtil = function(j$) { diffBuilder.recordMismatch(); return false; } + } else if (j$.isURL(a) && j$.isURL(b)) { + // URLs have no enumrable properties, so the default object comparison + // would consider any two URLs to be equal. + return a.toString() === b.toString(); } else { // Objects with different constructors are not equivalent, but `Object`s // or `Array`s from different frames are. diff --git a/spec/core/baseSpec.js b/spec/core/baseSpec.js index fbdf9d9d..99a0e668 100644 --- a/spec/core/baseSpec.js +++ b/spec/core/baseSpec.js @@ -62,4 +62,17 @@ describe('base helpers', function() { expect(jasmineUnderTest.isSet({})).toBe(false); }); }); + + describe('isURL', function() { + it('returns true when the object is a URL', function() { + jasmine.getEnv().requireUrls(); + // eslint-disable-next-line compat/compat + expect(jasmineUnderTest.isURL(new URL('http://localhost/'))).toBe(true); + }); + + it('returns false when the object is not a URL', function() { + jasmine.getEnv().requireUrls(); + expect(jasmineUnderTest.isURL({})).toBe(false); + }); + }); }); diff --git a/spec/core/matchers/matchersUtilSpec.js b/spec/core/matchers/matchersUtilSpec.js index ed03f38e..839b7e67 100644 --- a/spec/core/matchers/matchersUtilSpec.js +++ b/spec/core/matchers/matchersUtilSpec.js @@ -837,6 +837,54 @@ describe('matchersUtil', function() { expect(matchersUtil.equals(mapA, mapB)).toBe(false); }); + it('passes when comparing two identical URLs', function() { + jasmine.getEnv().requireUrls(); + + var matchersUtil = new jasmineUnderTest.MatchersUtil(); + + expect( + matchersUtil.equals( + // eslint-disable-next-line compat/compat + new URL('http://localhost/1'), + // eslint-disable-next-line compat/compat + new URL('http://localhost/1') + ) + ).toBe(true); + }); + + it('fails when comparing two different URLs', function() { + jasmine.getEnv().requireUrls(); + + var matchersUtil = new jasmineUnderTest.MatchersUtil(), + // eslint-disable-next-line compat/compat + url1 = new URL('http://localhost/1'); + + // eslint-disable-next-line compat/compat + expect(matchersUtil.equals(url1, new URL('http://localhost/2'))).toBe( + false + ); + // eslint-disable-next-line compat/compat + expect(matchersUtil.equals(url1, new URL('http://localhost/1?foo'))).toBe( + false + ); + // eslint-disable-next-line compat/compat + expect(matchersUtil.equals(url1, new URL('http://localhost/1#foo'))).toBe( + false + ); + // eslint-disable-next-line compat/compat + expect(matchersUtil.equals(url1, new URL('https://localhost/1'))).toBe( + false + ); + expect( + // eslint-disable-next-line compat/compat + matchersUtil.equals(url1, new URL('http://localhost:8080/1')) + ).toBe(false); + // eslint-disable-next-line compat/compat + expect(matchersUtil.equals(url1, new URL('http://example.com/1'))).toBe( + false + ); + }); + describe('when running in an environment with array polyfills', function() { var findIndexDescriptor = Object.getOwnPropertyDescriptor( Array.prototype, diff --git a/spec/helpers/checkForUrl.js b/spec/helpers/checkForUrl.js new file mode 100644 index 00000000..f8401fbb --- /dev/null +++ b/spec/helpers/checkForUrl.js @@ -0,0 +1,17 @@ +/* eslint-disable compat/compat */ +(function(env) { + function hasUrlConstructor() { + try { + new URL('http://localhost/'); + return true; + } catch (e) { + return false; + } + } + + env.requireUrls = function() { + if (!hasUrlConstructor()) { + env.pending('Environment does not support URLs'); + } + }; +})(jasmine.getEnv()); diff --git a/spec/support/jasmine-browser.js b/spec/support/jasmine-browser.js index 2f5f7146..1f1e8bef 100644 --- a/spec/support/jasmine-browser.js +++ b/spec/support/jasmine-browser.js @@ -24,6 +24,7 @@ module.exports = { 'helpers/checkForSet.js', 'helpers/checkForSymbol.js', 'helpers/checkForTypedArrays.js', + 'helpers/checkForUrl.js', 'helpers/domHelpers.js', 'helpers/integrationMatchers.js', 'helpers/promises.js', diff --git a/spec/support/jasmine.json b/spec/support/jasmine.json index 0276ca92..56ed17c0 100644 --- a/spec/support/jasmine.json +++ b/spec/support/jasmine.json @@ -11,6 +11,7 @@ "helpers/checkForSet.js", "helpers/checkForSymbol.js", "helpers/checkForTypedArrays.js", + "helpers/checkForUrl.js", "helpers/domHelpers.js", "helpers/integrationMatchers.js", "helpers/promises.js", diff --git a/src/core/base.js b/src/core/base.js index d02606d5..5ff9441e 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -161,6 +161,15 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { ); }; + j$.isURL = function(obj) { + return ( + obj !== null && + typeof obj !== 'undefined' && + typeof jasmineGlobal.URL !== 'undefined' && + obj.constructor === jasmineGlobal.URL + ); + }; + j$.isDataView = function(obj) { return ( obj !== null && diff --git a/src/core/matchers/matchersUtil.js b/src/core/matchers/matchersUtil.js index 6a74d89d..5f75a4ed 100644 --- a/src/core/matchers/matchersUtil.js +++ b/src/core/matchers/matchersUtil.js @@ -475,6 +475,10 @@ getJasmineRequireObj().MatchersUtil = function(j$) { diffBuilder.recordMismatch(); return false; } + } else if (j$.isURL(a) && j$.isURL(b)) { + // URLs have no enumrable properties, so the default object comparison + // would consider any two URLs to be equal. + return a.toString() === b.toString(); } else { // Objects with different constructors are not equivalent, but `Object`s // or `Array`s from different frames are. From 905e3fc3f9082d8daed8f04f930deb5f282cc910 Mon Sep 17 00:00:00 2001 From: Gregory Huczynski Date: Fri, 13 Nov 2020 12:06:10 +0000 Subject: [PATCH 189/201] Enable custom promise error handling through overriding of global.onerror --- spec/core/GlobalErrorsSpec.js | 76 +++++++++++++++++++++++++++++++++++ src/core/GlobalErrors.js | 4 +- 2 files changed, 78 insertions(+), 2 deletions(-) diff --git a/spec/core/GlobalErrorsSpec.js b/spec/core/GlobalErrorsSpec.js index 16657a7f..38ee5a55 100644 --- a/spec/core/GlobalErrorsSpec.js +++ b/spec/core/GlobalErrorsSpec.js @@ -12,6 +12,23 @@ describe('GlobalErrors', function() { expect(handler).toHaveBeenCalledWith('foo'); }); + it('enables external interception of error by overriding global.onerror', function() { + var fakeGlobal = { onerror: null }, + handler = jasmine.createSpy('errorHandler'), + hijackHandler = jasmine.createSpy('hijackErrorHandler'), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); + + errors.install(); + errors.pushListener(handler); + + fakeGlobal.onerror = hijackHandler; + + fakeGlobal.onerror('foo'); + + expect(hijackHandler).toHaveBeenCalledWith('foo'); + expect(handler).not.toHaveBeenCalled(); + }); + it('calls the global error handler with all parameters', function() { var fakeGlobal = { onerror: null }, handler = jasmine.createSpy('errorHandler'), @@ -285,5 +302,64 @@ describe('GlobalErrors', function() { }) ); }); + + describe('Enabling external interception of reported rejections by overriding global.onerror', function() { + it('overriding global.onerror intercepts rejections whose reason is a string', function() { + var fakeGlobal = jasmine.createSpyObj('globalErrors', [ + 'addEventListener' + ]), + handler = jasmine.createSpy('errorHandler'), + hijackHandler = jasmine.createSpy('hijackErrorHandler'), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); + + errors.install(); + errors.pushListener(handler); + + fakeGlobal.onerror = hijackHandler; + + var addedListener = fakeGlobal.addEventListener.calls.argsFor(0)[1]; + addedListener({ reason: 'nope' }); + + expect(hijackHandler).toHaveBeenCalledWith( + 'Unhandled promise rejection: nope' + ); + expect(handler).not.toHaveBeenCalled(); + }); + + it('overriding global.onerror intercepts rejections whose reason is an Error', function() { + var fakeGlobal = jasmine.createSpyObj('globalErrors', [ + 'addEventListener' + ]), + handler = jasmine.createSpy('errorHandler'), + hijackHandler = jasmine.createSpy('hijackErrorHandler'), + errors = new jasmineUnderTest.GlobalErrors(fakeGlobal); + + errors.install(); + errors.pushListener(handler); + + fakeGlobal.onerror = hijackHandler; + + var addedListener = fakeGlobal.addEventListener.calls.argsFor(0)[1]; + var reason; + + try { + // Throwing ensures that we get a stack property in all browsers + throw new Error('bar'); + } catch (e) { + reason = e; + } + + addedListener({ reason: reason }); + + expect(hijackHandler).toHaveBeenCalledWith( + jasmine.objectContaining({ + jasmineMessage: 'Unhandled promise rejection: Error: bar', + message: reason.message, + stack: reason.stack + }) + ); + expect(handler).not.toHaveBeenCalled(); + }); + }); }); }); diff --git a/src/core/GlobalErrors.js b/src/core/GlobalErrors.js index b79976d9..4e8fb7eb 100644 --- a/src/core/GlobalErrors.js +++ b/src/core/GlobalErrors.js @@ -67,9 +67,9 @@ getJasmineRequireObj().GlobalErrors = function(j$) { if (j$.isError_(event.reason)) { event.reason.jasmineMessage = 'Unhandled promise rejection: ' + event.reason; - onerror(event.reason); + global.onerror(event.reason); } else { - onerror('Unhandled promise rejection: ' + event.reason); + global.onerror('Unhandled promise rejection: ' + event.reason); } }; From 3f5c47dff3aa1889b5b1bab10f96b96e1d41f62e Mon Sep 17 00:00:00 2001 From: Yasin Kocak Date: Sat, 2 Jan 2021 10:55:14 +0100 Subject: [PATCH 190/201] expect all truthy and falsy --- spec/core/matchers/toBeFalsySpec.js | 9 +++++++++ spec/core/matchers/toBeTruthySpec.js | 9 +++++++++ 2 files changed, 18 insertions(+) diff --git a/spec/core/matchers/toBeFalsySpec.js b/spec/core/matchers/toBeFalsySpec.js index ec4a98e4..feb1d058 100644 --- a/spec/core/matchers/toBeFalsySpec.js +++ b/spec/core/matchers/toBeFalsySpec.js @@ -15,6 +15,9 @@ describe('toBeFalsy', function() { result = matcher.compare(null); expect(result.pass).toBe(true); + result = matcher.compare(undefined); + expect(result.pass).toBe(true); + result = matcher.compare(void 0); expect(result.pass).toBe(true); }); @@ -34,5 +37,11 @@ describe('toBeFalsy', function() { result = matcher.compare({}); expect(result.pass).toBe(false); + + result = matcher.compare([]); + expect(result.pass).toBe(false); + + result = matcher.compare(function() {}); + expect(result.pass).toBe(false); }); }); diff --git a/spec/core/matchers/toBeTruthySpec.js b/spec/core/matchers/toBeTruthySpec.js index f7bb258b..134210be 100644 --- a/spec/core/matchers/toBeTruthySpec.js +++ b/spec/core/matchers/toBeTruthySpec.js @@ -14,6 +14,12 @@ describe('toBeTruthy', function() { result = matcher.compare({}); expect(result.pass).toBe(true); + + result = matcher.compare([]); + expect(result.pass).toBe(true); + + result = matcher.compare(function() {}); + expect(result.pass).toBe(true); }); it("fails for 'falsy' values", function() { @@ -32,6 +38,9 @@ describe('toBeTruthy', function() { result = matcher.compare(null); expect(result.pass).toBe(false); + result = matcher.compare(undefined); + expect(result.pass).toBe(false); + result = matcher.compare(void 0); expect(result.pass).toBe(false); }); From 46e7158c77c0b26684f2d90bae2dba2f52104aa4 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 4 Mar 2021 12:46:23 -0800 Subject: [PATCH 191/201] Removed unused util.htmlEscape --- src/core/util.js | 10 ---------- 1 file changed, 10 deletions(-) diff --git a/src/core/util.js b/src/core/util.js index 4118deec..64aedef1 100644 --- a/src/core/util.js +++ b/src/core/util.js @@ -7,16 +7,6 @@ getJasmineRequireObj().util = function(j$) { childClass.prototype = new Subclass(); }; - util.htmlEscape = function(str) { - if (!str) { - return str; - } - return str - .replace(/&/g, '&') - .replace(//g, '>'); - }; - util.argsToArray = function(args) { var arrayOfArgs = []; for (var i = 0; i < args.length; i++) { From 76f34e90dcb1ba0945436547483ee1bfabbeaac3 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 13 Mar 2021 13:49:30 -0800 Subject: [PATCH 192/201] Allow custom object formatters to be added in beforeAll Fixes #1876. --- spec/core/integration/CustomObjectFormatterSpec.js | 2 +- src/core/Env.js | 3 +++ 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/spec/core/integration/CustomObjectFormatterSpec.js b/spec/core/integration/CustomObjectFormatterSpec.js index 2c61d9e0..eec264dc 100644 --- a/spec/core/integration/CustomObjectFormatterSpec.js +++ b/spec/core/integration/CustomObjectFormatterSpec.js @@ -42,7 +42,7 @@ describe('Custom object formatters', function() { }); env.describe('with custom pretty-printer', function() { - env.beforeEach(function() { + env.beforeAll(function() { env.addCustomObjectFormatter(function(obj) { return 'custom(' + obj + ')'; }); diff --git a/src/core/Env.js b/src/core/Env.js index a70413b8..62454373 100644 --- a/src/core/Env.js +++ b/src/core/Env.js @@ -424,6 +424,9 @@ getJasmineRequireObj().Env = function(j$) { resources.customAsyncMatchers = j$.util.clone( runnableResources[parentRunnableId].customAsyncMatchers ); + resources.customObjectFormatters = j$.util.clone( + runnableResources[parentRunnableId].customObjectFormatters + ); resources.defaultStrategyFn = runnableResources[parentRunnableId].defaultStrategyFn; } From 324bc201c287c1550c5c6626fcc52637ca285105 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sat, 13 Mar 2021 13:52:10 -0800 Subject: [PATCH 193/201] Built distribution --- lib/jasmine-core/boot.js | 2 +- lib/jasmine-core/jasmine-html.js | 2 +- lib/jasmine-core/jasmine.js | 15 ++++----------- lib/jasmine-core/node_boot.js | 2 +- 4 files changed, 7 insertions(+), 14 deletions(-) diff --git a/lib/jasmine-core/boot.js b/lib/jasmine-core/boot.js index acd4c5a8..9c9aee42 100644 --- a/lib/jasmine-core/boot.js +++ b/lib/jasmine-core/boot.js @@ -1,5 +1,5 @@ /* -Copyright (c) 2008-2020 Pivotal Labs +Copyright (c) 2008-2021 Pivotal Labs Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the diff --git a/lib/jasmine-core/jasmine-html.js b/lib/jasmine-core/jasmine-html.js index 5e436b3e..8539c76c 100644 --- a/lib/jasmine-core/jasmine-html.js +++ b/lib/jasmine-core/jasmine-html.js @@ -1,5 +1,5 @@ /* -Copyright (c) 2008-2020 Pivotal Labs +Copyright (c) 2008-2021 Pivotal Labs Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 51c2d0ad..36f1e822 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -1,5 +1,5 @@ /* -Copyright (c) 2008-2020 Pivotal Labs +Copyright (c) 2008-2021 Pivotal Labs Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the @@ -532,16 +532,6 @@ getJasmineRequireObj().util = function(j$) { childClass.prototype = new Subclass(); }; - util.htmlEscape = function(str) { - if (!str) { - return str; - } - return str - .replace(/&/g, '&') - .replace(//g, '>'); - }; - util.argsToArray = function(args) { var arrayOfArgs = []; for (var i = 0; i < args.length; i++) { @@ -1389,6 +1379,9 @@ getJasmineRequireObj().Env = function(j$) { resources.customAsyncMatchers = j$.util.clone( runnableResources[parentRunnableId].customAsyncMatchers ); + resources.customObjectFormatters = j$.util.clone( + runnableResources[parentRunnableId].customObjectFormatters + ); resources.defaultStrategyFn = runnableResources[parentRunnableId].defaultStrategyFn; } diff --git a/lib/jasmine-core/node_boot.js b/lib/jasmine-core/node_boot.js index d62c7d36..4016e3b8 100644 --- a/lib/jasmine-core/node_boot.js +++ b/lib/jasmine-core/node_boot.js @@ -1,5 +1,5 @@ /* -Copyright (c) 2008-2020 Pivotal Labs +Copyright (c) 2008-2021 Pivotal Labs Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the From de91427356767f2f4dce714457916537b90753bc Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sun, 14 Mar 2021 11:43:38 -0700 Subject: [PATCH 194/201] Fixed instructions for running Jasmine's ci script --- .github/CONTRIBUTING.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/CONTRIBUTING.md b/.github/CONTRIBUTING.md index 3a23f9a5..8f592ea0 100644 --- a/.github/CONTRIBUTING.md +++ b/.github/CONTRIBUTING.md @@ -101,7 +101,7 @@ Follow these tips and your pull request, patch, or suggestion is much more likel Jasmine uses some internal tooling to test itself in browser on Travis. This tooling _should_ work locally as well. - $ node ci.js + $ node spec/support/ci.js You can also set the `JASMINE_BROWSER` environment variable to specify which browser should be used. From 8d0c52e2ecb4eca09fa382154c70334b00f64411 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sun, 14 Mar 2021 11:46:23 -0700 Subject: [PATCH 195/201] Temporarily removed global error handler stack validation This fails somewhat frequently (every 2-4 runs of Jasmine's own test suite) on Safari. Until we get to the bottom of that, it's removed. --- lib/jasmine-core/jasmine.js | 6 ------ spec/core/GlobalErrorsSpec.js | 10 ---------- src/core/GlobalErrors.js | 6 ------ 3 files changed, 22 deletions(-) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 36f1e822..93cf9a75 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -4150,12 +4150,6 @@ getJasmineRequireObj().GlobalErrors = function(j$) { throw new Error('popListener expects a listener'); } - if (listener !== handlers[handlers.length - 1]) { - throw new Error( - 'popListener was passed a different listener than the current one' - ); - } - handlers.pop(); }; } diff --git a/spec/core/GlobalErrorsSpec.js b/spec/core/GlobalErrorsSpec.js index 38ee5a55..4fb41c21 100644 --- a/spec/core/GlobalErrorsSpec.js +++ b/spec/core/GlobalErrorsSpec.js @@ -90,16 +90,6 @@ describe('GlobalErrors', function() { }).toThrowError('popListener expects a listener'); }); - it('throws when the argument to #popListener is not the current listener', function() { - var errors = new jasmineUnderTest.GlobalErrors({}); - errors.pushListener(function() {}); - expect(function() { - errors.popListener(function() {}); - }).toThrowError( - 'popListener was passed a different listener than the current one' - ); - }); - it('uninstalls itself, putting back a previous callback', function() { var originalCallback = jasmine.createSpy('error'), fakeGlobal = { onerror: originalCallback }, diff --git a/src/core/GlobalErrors.js b/src/core/GlobalErrors.js index 4e8fb7eb..f0253b2d 100644 --- a/src/core/GlobalErrors.js +++ b/src/core/GlobalErrors.js @@ -101,12 +101,6 @@ getJasmineRequireObj().GlobalErrors = function(j$) { throw new Error('popListener expects a listener'); } - if (listener !== handlers[handlers.length - 1]) { - throw new Error( - 'popListener was passed a different listener than the current one' - ); - } - handlers.pop(); }; } From 050c1f051c02e387cf3f4c4884dd179f8005f9bf Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sun, 14 Mar 2021 12:23:17 -0700 Subject: [PATCH 196/201] Fixed intermittent test failures --- spec/core/integration/EnvSpec.js | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/spec/core/integration/EnvSpec.js b/spec/core/integration/EnvSpec.js index a8497985..e6ccedb2 100644 --- a/spec/core/integration/EnvSpec.js +++ b/spec/core/integration/EnvSpec.js @@ -656,7 +656,8 @@ describe('Env integration', function() { }); env.execute(null, function() { - expect(duration).toBeGreaterThanOrEqual(10); + // Expect >= 9 rather than >= 10 to compensate for clock imprecision + expect(duration).toBeGreaterThanOrEqual(9); done(); }); }); @@ -682,7 +683,8 @@ describe('Env integration', function() { }); env.execute(null, function() { - expect(duration).toBeGreaterThanOrEqual(10); + // Expect >= 9 rather than >= 10 to compensate for clock imprecision + expect(duration).toBeGreaterThanOrEqual(9); done(); }); }); From 58ef707bc6ad9e67a911e56426502544ebc09021 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 17 Mar 2021 17:58:51 -0700 Subject: [PATCH 197/201] Added jasmine.isSpy to the public interface * Fixes #1880 --- lib/jasmine-core/jasmine.js | 8 ++++++++ src/core/base.js | 8 ++++++++ 2 files changed, 16 insertions(+) diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index 93cf9a75..f96e205c 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -512,6 +512,14 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return new j$.SetContaining(sample); }; + /** + * Determines whether the provided function is a Jasmine spy. + * @name jasmine.isSpy + * @since 2.0.0 + * @function + * @param {Function} putativeSpy - The function to check. + * @return {Boolean} + */ j$.isSpy = function(putativeSpy) { if (!putativeSpy) { return false; diff --git a/src/core/base.js b/src/core/base.js index 5ff9441e..3c1da322 100644 --- a/src/core/base.js +++ b/src/core/base.js @@ -344,6 +344,14 @@ getJasmineRequireObj().base = function(j$, jasmineGlobal) { return new j$.SetContaining(sample); }; + /** + * Determines whether the provided function is a Jasmine spy. + * @name jasmine.isSpy + * @since 2.0.0 + * @function + * @param {Function} putativeSpy - The function to check. + * @return {Boolean} + */ j$.isSpy = function(putativeSpy) { if (!putativeSpy) { return false; From 592fba22b8c3bf733c8552302148b1a8dc906bdb Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 17 Mar 2021 18:38:01 -0700 Subject: [PATCH 198/201] Bump version to 3.7.0 --- lib/jasmine-core/version.rb | 2 +- package.json | 2 +- release_notes/3.7.0.md | 80 +++++++++++++++++++++++++++++++++++++ 3 files changed, 82 insertions(+), 2 deletions(-) create mode 100644 release_notes/3.7.0.md diff --git a/lib/jasmine-core/version.rb b/lib/jasmine-core/version.rb index 5dd3e13b..e87815de 100644 --- a/lib/jasmine-core/version.rb +++ b/lib/jasmine-core/version.rb @@ -4,6 +4,6 @@ # module Jasmine module Core - VERSION = "3.6.0" + VERSION = "3.7.0" end end diff --git a/package.json b/package.json index ae77c27f..62637443 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "jasmine-core", "license": "MIT", - "version": "3.6.0", + "version": "3.7.0", "repository": { "type": "git", "url": "https://github.com/jasmine/jasmine.git" diff --git a/release_notes/3.7.0.md b/release_notes/3.7.0.md new file mode 100644 index 00000000..d836338b --- /dev/null +++ b/release_notes/3.7.0.md @@ -0,0 +1,80 @@ +# Jasmine Core 3.7 Release Notes + +## Summary + +This is a maintenance release of Jasmine with a number of new features and fixes. + + +## New features and bug fixes + +* Allow custom object formatters to be added in beforeAll + - Fixes [#1876](http://github.com/jasmine/jasmine/issues/1876) + +* Allow specs to disable Jasmine's global error handling by overwriting `onerror`. + - Merges [#1860](https://github.com/jasmine/jasmine/pull/1860) from @greghuc + +* Fixed comparison between URL objects + - Fixes [#1866](http://github.com/jasmine/jasmine/issues/1866) + +* Added support for stack traces created by `node --enable-source-maps` + with tools like the Typescript compiler. + - Merges [#1862](https://github.com/jasmine/jasmine/pull/1862) from @JannesMeyer + +* Made properties added by createSpyObj() enumerable. + - Merges [#1859](https://github.com/jasmine/jasmine/pull/1859) from DCtheTall + - Fixes [#1837](http://github.com/jasmine/jasmine/issues/1837) + +* Show the name of the spec/suite that caused a deprecation + +* Warn if a spec or before/after function both takes a callback and returns a promise + +* Don't overwrite MatchersUtil methods with ones that were added to + `Array.prototype`, esp. `contains` + - Fixes [#1849](http://github.com/jasmine/jasmine/issues/1849) + +* Allow generator functions to be passed to `.and.callFake` + - Fixes [#1848](http://github.com/jasmine/jasmine/issues/1848) + + +## Documentation updates + +* Fixed instructions for contributors to run Jasmine's ci script + +* Updated supported Node versions in README + +* Fixed script and CSS URLs in standalone example in README + - Merges [#1839](https://github.com/jasmine/jasmine/pull/1839) from @snowman + +* Fixed typo in asyncMatcher toBePending comment + - Merges [#1847](https://github.com/jasmine/jasmine/pull/1847) from @SnailCoil + +* Fixed link to custom object formatter tutorial + +* Added jasmine.isSpy to the public interface + - Fixes [#1880](http://github.com/jasmine/jasmine/issues/1880) + + + +## Internal notes + +* Fixed intermittent test failures + +* Added additional assertions to tests for toBeTruthy and toBeFalsy + - Merges [#1875](https://github.com/jasmine/jasmine/pull/1875) from @yasinkocak + +* Pointed Travis badge at travis-ci.com, not .org + +* Fixed file globs so that Prettier runs on all files + +* Check for forgotten console and debugger statements + +* Fixed code in Jasmine that will trigger deprecations in 3.99 + +* Use jasmine-browser from npm rather than from the main branch + - The current released version now works with IE, so we no longer need to +depend on main. + + +------ + +_Release Notes generated with _[Anchorman](http://github.com/infews/anchorman)_ From 5c17456925398f89c4f0123b270ba3081d79874c Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Wed, 17 Mar 2021 19:44:16 -0700 Subject: [PATCH 199/201] Updated release instructions --- RELEASE.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/RELEASE.md b/RELEASE.md index b388cf85..f69663e0 100644 --- a/RELEASE.md +++ b/RELEASE.md @@ -41,6 +41,7 @@ When ready to release - specs are all green and the stories are done: ### Build standalone distribution 1. Build the standalone distribution with `grunt buildStandaloneDist` +1. This will generate `dist/jasmine-standalone-.zip`, which you will upload later (see "Finally" below). ### Release the core Ruby gem @@ -76,8 +77,7 @@ Probably only need to do this when releasing a minor version, and not a patch ve 1. In `package.json`, update both the package version and the jasmine-core dependency version 1. Commit and push. 1. Wait for Travis to go green again. -1. `grunt release ` -1. `npm publish .` +1. `grunt release `. (Note: This will publish the package by running `npm publish`.) #### Gem From cb044aa2735e32bff9e99e4c92d5c639af05abf5 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Thu, 18 Mar 2021 17:28:04 -0700 Subject: [PATCH 200/201] Bump version to 3.7.1 --- RELEASE.md | 1 + lib/jasmine-core/jasmine.js | 2 +- lib/jasmine-core/version.rb | 2 +- package.json | 2 +- release_notes/3.7.1.md | 8 ++++++++ 5 files changed, 12 insertions(+), 3 deletions(-) create mode 100644 release_notes/3.7.1.md diff --git a/RELEASE.md b/RELEASE.md index f69663e0..8d0689b1 100644 --- a/RELEASE.md +++ b/RELEASE.md @@ -30,6 +30,7 @@ When ready to release - specs are all green and the stories are done: 1. Update the release notes in `release_notes` - use the Anchorman gem to generate the markdown file and edit accordingly 1. Update the version in `package.json` +1. Run `npm run build`. 1. Copy version to the Ruby gem with `grunt build:copyVersionToGem` ### Commit and push core changes diff --git a/lib/jasmine-core/jasmine.js b/lib/jasmine-core/jasmine.js index f96e205c..d0b944f4 100644 --- a/lib/jasmine-core/jasmine.js +++ b/lib/jasmine-core/jasmine.js @@ -9469,5 +9469,5 @@ getJasmineRequireObj().UserContext = function(j$) { }; getJasmineRequireObj().version = function() { - return '3.6.0'; + return '3.7.1'; }; diff --git a/lib/jasmine-core/version.rb b/lib/jasmine-core/version.rb index e87815de..9f6452ff 100644 --- a/lib/jasmine-core/version.rb +++ b/lib/jasmine-core/version.rb @@ -4,6 +4,6 @@ # module Jasmine module Core - VERSION = "3.7.0" + VERSION = "3.7.1" end end diff --git a/package.json b/package.json index 62637443..e65e990f 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "jasmine-core", "license": "MIT", - "version": "3.7.0", + "version": "3.7.1", "repository": { "type": "git", "url": "https://github.com/jasmine/jasmine.git" diff --git a/release_notes/3.7.1.md b/release_notes/3.7.1.md new file mode 100644 index 00000000..f383cff6 --- /dev/null +++ b/release_notes/3.7.1.md @@ -0,0 +1,8 @@ +# Jasmine Core 3.7.1 Release Notes + +## Summary + +This is a bug fix release of Jasmine. It's identical to 3.7.0 except that it +correctly reports its version number. Please see the +[3.7.0 release notes](https://github.com/jasmine/jasmine/blob/main/release_notes/3.7.0.md) +if you're upgrading directly from 3.6.0 or earlier. From 503b653a1070ebde94a282a2210f7373ecf1f1d1 Mon Sep 17 00:00:00 2001 From: Steve Gravrock Date: Sun, 21 Mar 2021 11:29:46 -0700 Subject: [PATCH 201/201] Travis browser matrix updates * Added latest Safari * Added the Firefox version that's closest to current ESR --- .travis.yml | 8 ++++++++ README.md | 4 ++-- 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index 9d7f3f44..4015d631 100644 --- a/.travis.yml +++ b/.travis.yml @@ -30,6 +30,10 @@ matrix: if: type != pull_request addons: sauce_connect: true + - env: JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='78' SAUCE_OS="Windows 10" + if: type != pull_request + addons: + sauce_connect: true - env: JASMINE_BROWSER="firefox" SAUCE_BROWSER_VERSION='68' SAUCE_OS="Windows 10" if: type != pull_request addons: @@ -38,6 +42,10 @@ matrix: if: type != pull_request addons: sauce_connect: true + - env: JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="14" SAUCE_OS="OS X 11.0" + if: type != pull_request + addons: + sauce_connect: true - env: JASMINE_BROWSER="safari" SAUCE_BROWSER_VERSION="13" SAUCE_OS="OS X 10.13" if: type != pull_request addons: diff --git a/README.md b/README.md index 795ce1f7..d10056ca 100644 --- a/README.md +++ b/README.md @@ -57,9 +57,9 @@ Jasmine tests itself across many browsers (Safari, Chrome, Firefox, Microsoft Ed | Environment | Supported versions | |-------------------|--------------------| | Node | 10, 12, 14 | -| Safari | 8-13 | +| Safari | 8-14 | | Chrome | Evergreen | -| Firefox | Evergreen, 68 | +| Firefox | Evergreen, 68, 78 | | Edge | Evergreen | | Internet Explorer | 10, 11 |