Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Browse files

Merge pull request #260 from rgould/master

Guarantee that afterEach and after blocks are always run
  • Loading branch information...
commit 4b48dc1069995d225ca3d9fb6b87b48ba58731ec 2 parents 921f528 + ddd48f2
@ragaskar ragaskar authored
View
35 lib/jasmine-core/jasmine.js
@@ -1961,6 +1961,10 @@ jasmine.StringPrettyPrinter.prototype.append = function(value) {
};
jasmine.Queue = function(env) {
this.env = env;
+
+ // parallel to blocks. each true value in this array means the block will
+ // get executed even if we abort
+ this.ensured = [];
this.blocks = [];
this.running = false;
this.index = 0;
@@ -1968,15 +1972,30 @@ jasmine.Queue = function(env) {
this.abort = false;
};
-jasmine.Queue.prototype.addBefore = function(block) {
+jasmine.Queue.prototype.addBefore = function(block, ensure) {
+ if (ensure === jasmine.undefined) {
+ ensure = false;
+ }
+
this.blocks.unshift(block);
+ this.ensured.unshift(ensure);
};
-jasmine.Queue.prototype.add = function(block) {
+jasmine.Queue.prototype.add = function(block, ensure) {
+ if (ensure === jasmine.undefined) {
+ ensure = false;
+ }
+
this.blocks.push(block);
+ this.ensured.push(ensure);
};
-jasmine.Queue.prototype.insertNext = function(block) {
+jasmine.Queue.prototype.insertNext = function(block, ensure) {
+ if (ensure === jasmine.undefined) {
+ ensure = false;
+ }
+
+ this.ensured.splice((this.index + this.offset + 1), 0, ensure);
this.blocks.splice((this.index + this.offset + 1), 0, block);
this.offset++;
};
@@ -2000,7 +2019,7 @@ jasmine.Queue.prototype.next_ = function() {
while (goAgain) {
goAgain = false;
- if (self.index < self.blocks.length && !this.abort) {
+ if (self.index < self.blocks.length && !(this.abort && !this.ensured[self.index])) {
var calledSynchronously = true;
var completedSynchronously = false;
@@ -2291,7 +2310,7 @@ jasmine.Spec.prototype.finish = function(onComplete) {
jasmine.Spec.prototype.after = function(doAfter) {
if (this.queue.isRunning()) {
- this.queue.add(new jasmine.Block(this.env, doAfter, this));
+ this.queue.add(new jasmine.Block(this.env, doAfter, this), true);
} else {
this.afterCallbacks.unshift(doAfter);
}
@@ -2329,15 +2348,15 @@ jasmine.Spec.prototype.addBeforesAndAftersToQueue = function() {
this.queue.addBefore(new jasmine.Block(this.env, runner.before_[i], this));
}
for (i = 0; i < this.afterCallbacks.length; i++) {
- this.queue.add(new jasmine.Block(this.env, this.afterCallbacks[i], this));
+ this.queue.add(new jasmine.Block(this.env, this.afterCallbacks[i], this), true);
}
for (suite = this.suite; suite; suite = suite.parentSuite) {
for (i = 0; i < suite.after_.length; i++) {
- this.queue.add(new jasmine.Block(this.env, suite.after_[i], this));
+ this.queue.add(new jasmine.Block(this.env, suite.after_[i], this), true);
}
}
for (i = 0; i < runner.after_.length; i++) {
- this.queue.add(new jasmine.Block(this.env, runner.after_[i], this));
+ this.queue.add(new jasmine.Block(this.env, runner.after_[i], this), true);
}
};
View
13 spec/core/RunnerSpec.js
@@ -105,6 +105,19 @@ describe('RunnerTest', function() {
expect(runnerResults.totalCount).toEqual(3);
expect(runnerResults.passedCount).toEqual(3);
});
+
+ it('should run after a failing spec', function () {
+ var afterEach = jasmine.createSpy();
+ env.afterEach(afterEach);
+
+ env.describe('suite', function () {
+ env.it('fails', function () {
+ this.explodes();
+ });
+ }).execute();
+
+ expect(afterEach).toHaveBeenCalled();
+ });
});
View
201 spec/core/SpecRunningSpec.js
@@ -398,6 +398,123 @@ describe("jasmine spec running", function () {
expect(timeoutSpec.results().getItems()[0].message).toEqual('timeout: timed out after 500 msec waiting for something to happen');
expect(subsequentSpecRan).toEqual(true);
});
+
+ it("runs afterEach after timing out", function() {
+ var afterEach = jasmine.createSpy('afterEach');
+
+ env.describe('foo', function () {
+ env.afterEach(afterEach);
+
+ env.it('waitsFor', function () {
+ this.waitsFor(100, function() {
+ return false;
+ });
+ });
+ }).execute();
+
+ fakeTimer.tick(500);
+ expect(afterEach).toHaveBeenCalled();
+ });
+
+ it("runs single-spec after functions after timing out", function() {
+ var after = jasmine.createSpy('after');
+
+ env.describe('foo', function () {
+ env.it('waitsFor', function () {
+ this.after(after);
+ this.waitsFor(100, function() {
+ return false;
+ });
+ });
+ }).execute();
+
+ fakeTimer.tick(500);
+ expect(after).toHaveBeenCalled();
+ });
+
+ describe('with consecutive calls', function () {
+ var foo;
+ beforeEach(function () {
+ foo = 0;
+ });
+
+ it('exits immediately (does not stack) if the latchFunction times out', function () {
+ var reachedFirstWaitsFor = false;
+ var reachedSecondWaitsFor = false;
+ env.describe('suite that waits', function () {
+ env.it('should stack timeouts', function() {
+ this.waitsFor(500, function () {
+ reachedFirstWaitsFor = true;
+ return false;
+ });
+ this.waitsFor(500, function () {
+ reachedSecondWaitsFor = true;
+ });
+ this.runs(function () {
+ foo++;
+ });
+ });
+ });
+
+ expect(reachedFirstWaitsFor).toEqual(false);
+ env.execute();
+
+ expect(reachedFirstWaitsFor).toEqual(true);
+ expect(foo).toEqual(0);
+ expect(reachedSecondWaitsFor).toEqual(false);
+ fakeTimer.tick(500);
+ expect(reachedSecondWaitsFor).toEqual(false);
+ expect(foo).toEqual(0);
+ fakeTimer.tick(500);
+ expect(reachedSecondWaitsFor).toEqual(false);
+ expect(foo).toEqual(0);
+ });
+
+ it('stacks latchFunctions', function () {
+ var firstWaitsResult = false;
+ var secondWaitsResult = false;
+ var waitsSuite = env.describe('suite that waits', function () {
+ env.it('spec with waitsFors', function() {
+ this.waitsFor(600, function () {
+ fakeTimer.setTimeout(function () {
+ firstWaitsResult = true;
+ }, 300);
+ return firstWaitsResult;
+ });
+ this.waitsFor(600, function () {
+ fakeTimer.setTimeout(function () {
+ secondWaitsResult = true;
+ }, 300);
+ return secondWaitsResult;
+ });
+ this.runs(function () {
+ foo++;
+ });
+ });
+ });
+
+ expect(firstWaitsResult).toEqual(false);
+ expect(secondWaitsResult).toEqual(false);
+ waitsSuite.execute();
+
+ expect(firstWaitsResult).toEqual(false);
+ expect(secondWaitsResult).toEqual(false);
+ expect(foo).toEqual(0);
+
+ fakeTimer.tick(300);
+
+ expect(firstWaitsResult).toEqual(true);
+ expect(secondWaitsResult).toEqual(false);
+ expect(foo).toEqual(0);
+
+ fakeTimer.tick(300);
+
+ expect(firstWaitsResult).toEqual(true);
+ expect(secondWaitsResult).toEqual(true);
+ expect(foo).toEqual(1);
+
+ });
+ });
});
it("testSpecAfter", function() {
@@ -579,90 +696,6 @@ describe("jasmine spec running", function () {
expect(quux).toEqual(1);
});
- describe('#waitsFor should allow consecutive calls', function () {
- var foo;
- beforeEach(function () {
- foo = 0;
- });
-
- it('exits immediately (does not stack) if the latchFunction times out', function () {
- var reachedFirstWaitsFor = false;
- var reachedSecondWaitsFor = false;
- env.describe('suite that waits', function () {
- env.it('should stack timeouts', function() {
- this.waitsFor(500, function () {
- reachedFirstWaitsFor = true;
- return false;
- });
- this.waitsFor(500, function () {
- reachedSecondWaitsFor = true;
- });
- this.runs(function () {
- foo++;
- });
- });
- });
-
- expect(reachedFirstWaitsFor).toEqual(false);
- env.execute();
-
- expect(reachedFirstWaitsFor).toEqual(true);
- expect(foo).toEqual(0);
- expect(reachedSecondWaitsFor).toEqual(false);
- fakeTimer.tick(500);
- expect(reachedSecondWaitsFor).toEqual(false);
- expect(foo).toEqual(0);
- fakeTimer.tick(500);
- expect(reachedSecondWaitsFor).toEqual(false);
- expect(foo).toEqual(0);
- });
-
- it('stacks latchFunctions', function () {
- var firstWaitsResult = false;
- var secondWaitsResult = false;
- var waitsSuite = env.describe('suite that waits', function () {
- env.it('spec with waitsFors', function() {
- this.waitsFor(600, function () {
- fakeTimer.setTimeout(function () {
- firstWaitsResult = true;
- }, 300);
- return firstWaitsResult;
- });
- this.waitsFor(600, function () {
- fakeTimer.setTimeout(function () {
- secondWaitsResult = true;
- }, 300);
- return secondWaitsResult;
- });
- this.runs(function () {
- foo++;
- });
- });
- });
-
- expect(firstWaitsResult).toEqual(false);
- expect(secondWaitsResult).toEqual(false);
- waitsSuite.execute();
-
- expect(firstWaitsResult).toEqual(false);
- expect(secondWaitsResult).toEqual(false);
- expect(foo).toEqual(0);
-
- fakeTimer.tick(300);
-
- expect(firstWaitsResult).toEqual(true);
- expect(secondWaitsResult).toEqual(false);
- expect(foo).toEqual(0);
-
- fakeTimer.tick(300);
-
- expect(firstWaitsResult).toEqual(true);
- expect(secondWaitsResult).toEqual(true);
- expect(foo).toEqual(1);
-
- });
- });
-
it("#beforeEach should be able to eval runs and waits blocks", function () {
var foo = 0;
var bar = 0;
View
27 src/core/Queue.js
@@ -1,5 +1,9 @@
jasmine.Queue = function(env) {
this.env = env;
+
+ // parallel to blocks. each true value in this array means the block will
+ // get executed even if we abort
+ this.ensured = [];
this.blocks = [];
this.running = false;
this.index = 0;
@@ -7,15 +11,30 @@ jasmine.Queue = function(env) {
this.abort = false;
};
-jasmine.Queue.prototype.addBefore = function(block) {
+jasmine.Queue.prototype.addBefore = function(block, ensure) {
+ if (ensure === jasmine.undefined) {
+ ensure = false;
+ }
+
this.blocks.unshift(block);
+ this.ensured.unshift(ensure);
};
-jasmine.Queue.prototype.add = function(block) {
+jasmine.Queue.prototype.add = function(block, ensure) {
+ if (ensure === jasmine.undefined) {
+ ensure = false;
+ }
+
this.blocks.push(block);
+ this.ensured.push(ensure);
};
-jasmine.Queue.prototype.insertNext = function(block) {
+jasmine.Queue.prototype.insertNext = function(block, ensure) {
+ if (ensure === jasmine.undefined) {
+ ensure = false;
+ }
+
+ this.ensured.splice((this.index + this.offset + 1), 0, ensure);
this.blocks.splice((this.index + this.offset + 1), 0, block);
this.offset++;
};
@@ -39,7 +58,7 @@ jasmine.Queue.prototype.next_ = function() {
while (goAgain) {
goAgain = false;
- if (self.index < self.blocks.length && !this.abort) {
+ if (self.index < self.blocks.length && !(this.abort && !this.ensured[self.index])) {
var calledSynchronously = true;
var completedSynchronously = false;
View
8 src/core/Spec.js
@@ -154,7 +154,7 @@ jasmine.Spec.prototype.finish = function(onComplete) {
jasmine.Spec.prototype.after = function(doAfter) {
if (this.queue.isRunning()) {
- this.queue.add(new jasmine.Block(this.env, doAfter, this));
+ this.queue.add(new jasmine.Block(this.env, doAfter, this), true);
} else {
this.afterCallbacks.unshift(doAfter);
}
@@ -192,15 +192,15 @@ jasmine.Spec.prototype.addBeforesAndAftersToQueue = function() {
this.queue.addBefore(new jasmine.Block(this.env, runner.before_[i], this));
}
for (i = 0; i < this.afterCallbacks.length; i++) {
- this.queue.add(new jasmine.Block(this.env, this.afterCallbacks[i], this));
+ this.queue.add(new jasmine.Block(this.env, this.afterCallbacks[i], this), true);
}
for (suite = this.suite; suite; suite = suite.parentSuite) {
for (i = 0; i < suite.after_.length; i++) {
- this.queue.add(new jasmine.Block(this.env, suite.after_[i], this));
+ this.queue.add(new jasmine.Block(this.env, suite.after_[i], this), true);
}
}
for (i = 0; i < runner.after_.length; i++) {
- this.queue.add(new jasmine.Block(this.env, runner.after_[i], this));
+ this.queue.add(new jasmine.Block(this.env, runner.after_[i], this), true);
}
};
Please sign in to comment.
Something went wrong with that request. Please try again.