Moved fn skipping policy out of QueueRunner
This should allow us to more easily support complex skipping strategies like skipping nested cleanup fns when the corresponding befores were skipped, or skipping specs and suites when a beforeAll fails. * #1533
This commit is contained in:
19
src/core/CompleteOnFirstErrorSkipPolicy.js
Normal file
19
src/core/CompleteOnFirstErrorSkipPolicy.js
Normal file
@@ -0,0 +1,19 @@
|
||||
getJasmineRequireObj().CompleteOnFirstErrorSkipPolicy = function(j$) {
|
||||
function CompleteOnFirstErrorSkipPolicy(queueableFns, firstCleanupIx) {
|
||||
this.queueableFns_ = queueableFns;
|
||||
this.firstCleanupIx_ = firstCleanupIx;
|
||||
}
|
||||
|
||||
CompleteOnFirstErrorSkipPolicy.prototype.skipTo = function(
|
||||
lastRanFnIx,
|
||||
errored
|
||||
) {
|
||||
if (errored && lastRanFnIx < this.firstCleanupIx_) {
|
||||
return this.firstCleanupIx_;
|
||||
} else {
|
||||
return lastRanFnIx + 1;
|
||||
}
|
||||
};
|
||||
|
||||
return CompleteOnFirstErrorSkipPolicy;
|
||||
};
|
||||
@@ -502,12 +502,17 @@ getJasmineRequireObj().Env = function(j$) {
|
||||
};
|
||||
|
||||
var queueRunnerFactory = function(options, args) {
|
||||
var failFast = false;
|
||||
if (options.isLeaf) {
|
||||
failFast = true;
|
||||
} else if (!options.isReporter) {
|
||||
failFast = config.stopOnSpecFailure;
|
||||
if (
|
||||
// A spec
|
||||
options.isLeaf ||
|
||||
// A suite, and config.stopOnSpecFailure is set
|
||||
(!options.isLeaf && !options.isReporter && config.stopOnSpecFailure)
|
||||
) {
|
||||
options.SkipPolicy = j$.CompleteOnFirstErrorSkipPolicy;
|
||||
} else {
|
||||
options.SkipPolicy = j$.NeverSkipPolicy;
|
||||
}
|
||||
|
||||
options.clearStack = options.clearStack || clearStack;
|
||||
options.timeout = {
|
||||
setTimeout: realSetTimeout,
|
||||
@@ -515,7 +520,6 @@ getJasmineRequireObj().Env = function(j$) {
|
||||
};
|
||||
options.fail = self.fail;
|
||||
options.globalErrors = globalErrors;
|
||||
options.completeOnFirstError = failFast;
|
||||
options.onException =
|
||||
options.onException ||
|
||||
function(e) {
|
||||
|
||||
9
src/core/NeverSkipPolicy.js
Normal file
9
src/core/NeverSkipPolicy.js
Normal file
@@ -0,0 +1,9 @@
|
||||
getJasmineRequireObj().NeverSkipPolicy = function(j$) {
|
||||
function NeverSkipPolicy(queueableFns, firstCleanupIx) {}
|
||||
|
||||
NeverSkipPolicy.prototype.skipTo = function(lastRanFnIx, errored) {
|
||||
return lastRanFnIx + 1;
|
||||
};
|
||||
|
||||
return NeverSkipPolicy;
|
||||
};
|
||||
@@ -56,7 +56,9 @@ getJasmineRequireObj().QueueRunner = function(j$) {
|
||||
pushListener: emptyFn,
|
||||
popListener: emptyFn
|
||||
};
|
||||
this.completeOnFirstError = !!attrs.completeOnFirstError;
|
||||
|
||||
const SkipPolicy = attrs.SkipPolicy || j$.NeverSkipPolicy;
|
||||
this.skipPolicy_ = new SkipPolicy(this.queueableFns, this.firstCleanupIx);
|
||||
this.errored = false;
|
||||
|
||||
if (typeof this.onComplete !== 'function') {
|
||||
@@ -77,14 +79,6 @@ getJasmineRequireObj().QueueRunner = function(j$) {
|
||||
this.run(0);
|
||||
};
|
||||
|
||||
QueueRunner.prototype.skipToCleanup = function(lastRanIndex) {
|
||||
if (lastRanIndex < this.firstCleanupIx) {
|
||||
this.run(this.firstCleanupIx);
|
||||
} else {
|
||||
this.run(lastRanIndex + 1);
|
||||
}
|
||||
};
|
||||
|
||||
QueueRunner.prototype.clearTimeout = function(timeoutId) {
|
||||
Function.prototype.apply.apply(this.timeout.clearTimeout, [
|
||||
j$.getGlobal(),
|
||||
@@ -125,11 +119,7 @@ getJasmineRequireObj().QueueRunner = function(j$) {
|
||||
}
|
||||
|
||||
function runNext() {
|
||||
if (self.completeOnFirstError && errored) {
|
||||
self.skipToCleanup(iterativeIndex);
|
||||
} else {
|
||||
self.run(iterativeIndex + 1);
|
||||
}
|
||||
self.run(self.nextFnIx_(iterativeIndex));
|
||||
}
|
||||
|
||||
if (completedSynchronously) {
|
||||
@@ -227,7 +217,7 @@ getJasmineRequireObj().QueueRunner = function(j$) {
|
||||
for (
|
||||
iterativeIndex = recursiveIndex;
|
||||
iterativeIndex < length;
|
||||
iterativeIndex++
|
||||
iterativeIndex = this.nextFnIx_(iterativeIndex)
|
||||
) {
|
||||
var result = this.attempt(iterativeIndex);
|
||||
|
||||
@@ -236,11 +226,6 @@ getJasmineRequireObj().QueueRunner = function(j$) {
|
||||
}
|
||||
|
||||
self.errored = self.errored || result.errored;
|
||||
|
||||
if (this.completeOnFirstError && result.errored) {
|
||||
this.skipToCleanup(iterativeIndex);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
this.clearStack(function() {
|
||||
@@ -254,6 +239,16 @@ getJasmineRequireObj().QueueRunner = function(j$) {
|
||||
});
|
||||
};
|
||||
|
||||
QueueRunner.prototype.nextFnIx_ = function(currentFnIx) {
|
||||
const result = this.skipPolicy_.skipTo(currentFnIx, this.errored);
|
||||
|
||||
if (result === currentFnIx) {
|
||||
throw new Error("Can't skip to the same queueable fn that just finished");
|
||||
}
|
||||
|
||||
return result;
|
||||
};
|
||||
|
||||
QueueRunner.prototype.diagnoseConflictingAsync_ = function(fn, retval) {
|
||||
var msg;
|
||||
|
||||
|
||||
@@ -60,6 +60,10 @@ var getJasmineRequireObj = (function(jasmineGlobal) {
|
||||
j$.MapContaining = jRequire.MapContaining(j$);
|
||||
j$.SetContaining = jRequire.SetContaining(j$);
|
||||
j$.QueueRunner = jRequire.QueueRunner(j$);
|
||||
j$.NeverSkipPolicy = jRequire.NeverSkipPolicy(j$);
|
||||
j$.CompleteOnFirstErrorSkipPolicy = jRequire.CompleteOnFirstErrorSkipPolicy(
|
||||
j$
|
||||
);
|
||||
j$.ReportDispatcher = jRequire.ReportDispatcher(j$);
|
||||
j$.Spec = jRequire.Spec(j$);
|
||||
j$.Spy = jRequire.Spy(j$);
|
||||
|
||||
Reference in New Issue
Block a user