Socket
Socket
Sign inDemoInstall

mocha-typescript

Package Overview
Dependencies
59
Maintainers
2
Versions
39
Alerts
File Explorer

Advanced tools

Install Socket

Detect and block malicious and high-risk dependencies

Install

Comparing version 1.1.14 to 1.1.15

74

bin/watch.js
#!/usr/bin/env node
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const chalk_1 = require("chalk");
const spawn = require("cross-spawn");
const readline = require("readline");
const chalk = require("chalk");
const yargs = require("yargs");
const cross_spawn_1 = require("cross-spawn");
var argv = yargs
const argv = yargs
.options({
"p": {
p: {
alias: "project",

@@ -15,5 +15,5 @@ demand: false,

describe: "Path to tsconfig file or directory containing tsconfig, passed to `tsc -p <value>`.",
type: "string"
type: "string",
},
"t": {
t: {
alias: "tsc",

@@ -23,5 +23,5 @@ demand: false,

describe: "Path to executable tsc, by default points to typescript installed as dev dependency. Set to 'tsc' for global tsc installation.",
type: "string"
type: "string",
},
"o": {
o: {
alias: "opts",

@@ -31,5 +31,5 @@ demand: false,

describe: "Path to mocha.opts file containing additional mocha configuration.",
type: "string"
type: "string",
},
"m": {
m: {
alias: "mocha",

@@ -39,5 +39,5 @@ demand: false,

describe: "Path to executable mocha, by default points to mocha installed as dev dependency.",
type: "string"
type: "string",
},
"g": {
g: {
alias: "grep",

@@ -47,5 +47,5 @@ demand: false,

describe: "Passed down to mocha: only run tests matching <pattern>",
type: "string"
type: "string",
},
"f": {
f: {
alias: "fgrep",

@@ -55,4 +55,4 @@ demand: false,

describe: "Passed down to mocha: only run tests containing <string>",
type: "string"
}
type: "string",
},
})

@@ -62,9 +62,9 @@ .help("h")

.argv;
var stdl = readline.createInterface({ input: process.stdin, });
stdl.on("line", line => {
const stdl = readline.createInterface({ input: process.stdin });
stdl.on("line", (line) => {
// TODO: handle "g <pattern>" or "f <pattern>" to run mocha with pattern
// Ctrl + R may restart mocha test run?
});
var mochap = null;
var errors = 0;
let mochap = null;
let errors = 0;
function compilationStarted() {

@@ -83,23 +83,23 @@ if (mochap) {

if (errors) {
console.log(chalk.red("TS errors!"));
console.log(chalk_1.default.red("TS errors!"));
return;
}
else {
console.log(chalk.gray("Run mocha."));
console.log(chalk_1.default.gray("Run mocha."));
}
var mocha_options = ["--opts", argv.opts, "--colors"].concat(argv._);
const mochaOptions = ["--opts", argv.opts, "--colors"].concat(argv._);
if (argv.g) {
mocha_options.push("-g");
mocha_options.push(argv.g);
mochaOptions.push("-g");
mochaOptions.push(argv.g);
}
if (argv.f) {
mocha_options.push("-f");
mocha_options.push(argv.f);
mochaOptions.push("-f");
mochaOptions.push(argv.f);
}
mochap = cross_spawn_1.spawn(argv.mocha, mocha_options);
let source = mochap;
mochap.on("close", code => {
mochap = spawn(argv.mocha, mochaOptions);
const source = mochap;
mochap.on("close", (code) => {
if (source === mochap) {
if (code) {
console.log(chalk.red("Exited with " + code));
console.log(chalk_1.default.red("Exited with " + code));
}

@@ -111,3 +111,3 @@ else {

});
mochap.stdout.on("data", chunk => {
mochap.stdout.on("data", (chunk) => {
// Ensure old processes won't interfere tsc, .pipe here may be good enough.

@@ -118,3 +118,3 @@ if (source === mochap) {

});
mochap.stderr.on("data", chunk => {
mochap.stderr.on("data", (chunk) => {
// Ensure old processes won't interfere tsc, .pipe here may be good enough.

@@ -126,6 +126,6 @@ if (source === mochap) {

}
var tscp = cross_spawn_1.spawn(argv.tsc, ["-p", argv.project, "-w"]);
var tscl = readline.createInterface({ input: tscp.stdout });
tscl.on("line", line => {
if (line.indexOf("Compilation complete.") >= 0) {
const tscp = spawn(argv.tsc, ["-p", argv.project, "-w"]);
const tscl = readline.createInterface({ input: tscp.stdout });
tscl.on("line", (line) => {
if (line.indexOf("Compilation complete.") >= 0 || line.indexOf("Found ") >= 0) {
console.log(line);

@@ -132,0 +132,0 @@ compilationComplete();

@@ -5,5 +5,11 @@ declare namespace Mocha {

}
export interface Test {
<T>(target: Object, propertyKey: string | symbol, descriptor: TypedPropertyDescriptor<T>): TypedPropertyDescriptor<T> | void;
}
export interface ISuite {
<TFunction extends Function>(target: TFunction): TFunction | void;
}
export interface Suite {
<TFunction extends Function>(target: TFunction): TFunction | void;
}
}

@@ -10,0 +16,0 @@

"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const Mocha = require("mocha");
const Common = require("mocha/lib/interfaces/common");
const Test = require("mocha/lib/test");
const Common = require("mocha/lib/interfaces/common");
const globalTestFunctions = {

@@ -11,18 +12,21 @@ get describe() { return global.describe; },

get beforeEach() { return global.beforeEach; },
get afterEach() { return global.afterEach; }
get afterEach() { return global.afterEach; },
};
// key => Symbol("mocha-typescript:" + key)
let nodeSymbol = key => "__mts_" + key;
let testNameSymbol = nodeSymbol("test");
let slowSymbol = nodeSymbol("slow");
let timeoutSymbol = nodeSymbol("timout");
let retriesSymbol = nodeSymbol("retries");
let onlySymbol = nodeSymbol("only");
let pendingSumbol = nodeSymbol("pending");
let skipSymbol = nodeSymbol("skip");
let traitsSymbol = nodeSymbol("traits");
let isTraitSymbol = nodeSymbol("isTrait");
let contextSymbol = nodeSymbol("context");
let handled = nodeSymbol("handled");
const noname = cb => cb;
const nodeSymbol = (key) => "__mts_" + key;
const suiteSymbol = nodeSymbol("suite");
const testNameSymbol = nodeSymbol("test");
const parametersSymbol = nodeSymbol("parametersSymbol");
const nameForParametersSymbol = nodeSymbol("nameForParameters");
const slowSymbol = nodeSymbol("slow");
const timeoutSymbol = nodeSymbol("timout");
const retriesSymbol = nodeSymbol("retries");
const onlySymbol = nodeSymbol("only");
const pendingSymbol = nodeSymbol("pending");
const skipSymbol = nodeSymbol("skip");
const traitsSymbol = nodeSymbol("traits");
const isTraitSymbol = nodeSymbol("isTrait");
const contextSymbol = nodeSymbol("context");
const handled = nodeSymbol("handled");
const noname = (cb) => cb;
function applyDecorators(mocha, ctorOrProto, method, instance) {

@@ -34,8 +38,8 @@ const timeoutValue = method[timeoutSymbol];

const slowValue = method[slowSymbol];
if (mocha['slow'] && typeof slowValue === "number") {
mocha['slow'](slowValue);
if (mocha.slow && typeof slowValue === "number") {
mocha.slow(slowValue);
}
const retriesValue = method[retriesSymbol];
if (mocha['retries'] && typeof retriesValue === "number") {
mocha['retries'](retriesValue);
if (mocha.retries && typeof retriesValue === "number") {
mocha.retries(retriesValue);
}

@@ -50,3 +54,3 @@ const contextProperty = ctorOrProto[contextSymbol];

if (traits) {
traits.forEach(trait => {
traits.forEach((trait) => {
trait.call(context, context, instance, method);

@@ -59,3 +63,3 @@ });

if (traits) {
traits.forEach(trait => {
traits.forEach((trait) => {
trait.call(context, context, target);

@@ -98,3 +102,3 @@ });

}
let prototype = target.prototype;
const prototype = target.prototype;
let beforeEachFunction;

@@ -154,48 +158,83 @@ if (prototype.before) {

context.afterEach(afterEachFunction);
function runTests(prototype) {
Object.getOwnPropertyNames(prototype).forEach(key => {
try {
let method = prototype[key];
if (method === target) {
return;
}
let testName = method[testNameSymbol];
let shouldSkip = method[skipSymbol];
let shouldOnly = method[onlySymbol];
let shouldPending = method[pendingSumbol];
let testFunc = (shouldSkip && context.it.skip)
|| (shouldOnly && context.it.only)
|| context.it;
if (testName || shouldOnly || shouldPending || shouldSkip) {
testName = testName || method.name;
if (shouldPending && !shouldSkip && !shouldOnly) {
function runTest(prototype, method) {
const testName = method[testNameSymbol] || method.name;
const shouldSkip = method[skipSymbol];
const shouldOnly = method[onlySymbol];
const shouldPending = method[pendingSymbol];
const parameters = method[parametersSymbol];
if (testName || shouldOnly || shouldPending || shouldSkip) {
if (shouldPending && !shouldSkip && !shouldOnly) {
context.it.skip(testName);
}
else if (parameters) {
const nameForParameters = method[nameForParametersSymbol];
parameters.forEach((parameterOptions, i) => {
const { mark, name, params } = parameterOptions;
let parametersTestName = `${testName}_${i}`;
if (name) {
parametersTestName = name;
}
else if (nameForParameters) {
parametersTestName = nameForParameters(params);
}
const shouldSkipParam = shouldSkip || (mark === 1 /* skip */);
const shouldOnlyParam = shouldOnly || (mark === 2 /* only */);
const shouldPendingParam = shouldPending || (mark === 3 /* pending */);
if (shouldPendingParam && !shouldSkipParam && !shouldOnlyParam) {
context.it.skip(testName);
}
else if (method.length > 0) {
testFunc(testName, noname(function (done) {
applyDecorators(this, prototype, method, instance);
applyTestTraits(this, instance, method);
return method.call(instance, done);
}));
}
else {
testFunc(testName, noname(function () {
applyDecorators(this, prototype, method, instance);
applyTestTraits(this, instance, method);
return method.call(instance);
}));
const testFunc = (shouldSkipParam && context.it.skip)
|| (shouldOnlyParam && context.it.only)
|| context.it;
applyTestFunc(testFunc, parametersTestName, method, [params], method.length <= 1);
}
}
});
}
catch (e) {
// console.log(e);
else {
const testFunc = (shouldSkip && context.it.skip)
|| (shouldOnly && context.it.only)
|| context.it;
applyTestFunc(testFunc, testName, method, [], method.length === 0);
}
});
}
}
// run all tests along the inheritance chain
function applyTestFunc(testFunc, testName, method, callArgs, sync = true) {
if (sync) {
testFunc(testName, noname(function () {
applyDecorators(this, prototype, method, instance);
applyTestTraits(this, instance, method);
return method.call(instance, ...callArgs);
}));
}
else {
testFunc(testName, noname(function (done) {
applyDecorators(this, prototype, method, instance);
applyTestTraits(this, instance, method);
return method.call(instance, ...callArgs, done);
}));
}
}
// collect all tests along the inheritance chain, allow overrides
const collectedTests = {};
let currentPrototype = prototype;
while (currentPrototype !== Object.prototype) {
runTests(currentPrototype);
Object.getOwnPropertyNames(currentPrototype).forEach((key) => {
if (typeof prototype[key] === "function") {
const method = prototype[key];
if (method[testNameSymbol] && !collectedTests[key]) {
collectedTests[key] = [prototype, method];
}
}
});
currentPrototype = Object.getPrototypeOf(currentPrototype);
if (currentPrototype !== Object.prototype && currentPrototype.constructor[suiteSymbol]) {
throw new Error("deriving from other suites is bad practice and thus prohibited");
}
}
// run all collected tests
for (const key in collectedTests) {
const value = collectedTests[key];
runTest(value[0], value[1]);
}
};

@@ -205,3 +244,3 @@ }

return function () {
if (arguments.length == 2 && typeof arguments[0] === "string" && typeof arguments[1] === "function" && !arguments[1][isTraitSymbol]) {
if (arguments.length === 2 && typeof arguments[0] === "string" && typeof arguments[1] === "function" && !arguments[1][isTraitSymbol]) {
return overloads.suite.apply(this, arguments);

@@ -226,2 +265,3 @@ }

suiteCtor(ctor) {
ctor[suiteSymbol] = true;
suiteFunc(ctor)(ctor.name, suiteClassCallback(ctor, context));

@@ -231,2 +271,3 @@ },

return function (ctor) {
ctor[suiteSymbol] = true;
ctor[traitsSymbol] = traits;

@@ -238,6 +279,7 @@ suiteFunc(ctor)(ctor.name, suiteClassCallback(ctor, context));

return function (ctor) {
ctor[suiteSymbol] = true;
ctor[traitsSymbol] = traits;
suiteFunc(ctor)(name, suiteClassCallback(ctor, context));
};
}
},
});

@@ -248,5 +290,5 @@ }

if (ctor) {
let shouldSkip = ctor[skipSymbol];
let shouldOnly = ctor[onlySymbol];
let shouldPending = ctor[pendingSumbol];
const shouldSkip = ctor[skipSymbol];
const shouldOnly = ctor[onlySymbol];
const shouldPending = ctor[pendingSymbol];
return (shouldSkip && context.describe.skip)

@@ -266,9 +308,41 @@ || (shouldOnly && context.describe.only)

only: makeSuiteFunction(() => context.describe.only, context),
pending: makeSuiteFunction(() => context.describe.skip, context)
pending: makeSuiteFunction(() => context.describe.skip, context),
});
}
exports.suite = makeSuiteObject(globalTestFunctions);
var Mark;
(function (Mark) {
Mark[Mark["test"] = 0] = "test";
Mark[Mark["skip"] = 1] = "skip";
Mark[Mark["only"] = 2] = "only";
Mark[Mark["pending"] = 3] = "pending";
})(Mark || (Mark = {}));
function makeParamsFunction(mark) {
return (params, name) => {
return (target, propertyKey) => {
target[propertyKey][testNameSymbol] = propertyKey ? propertyKey.toString() : "";
target[propertyKey][parametersSymbol] = target[propertyKey][parametersSymbol] || [];
target[propertyKey][parametersSymbol].push({ mark, name, params });
};
};
}
function makeParamsNameFunction() {
return (nameForParameters) => {
return (target, propertyKey) => {
target[propertyKey][nameForParametersSymbol] = nameForParameters;
};
};
}
function makeParamsObject(context) {
return Object.assign(makeParamsFunction(0 /* test */), {
skip: makeParamsFunction(1 /* skip */),
only: makeParamsFunction(2 /* only */),
pending: makeParamsFunction(3 /* pending */),
naming: makeParamsNameFunction(),
});
}
exports.params = makeParamsObject(globalTestFunctions);
function testOverload(overloads) {
return function () {
if (arguments.length == 2 && typeof arguments[0] === "string" && typeof arguments[1] === "function" && !arguments[1][isTraitSymbol]) {
if (arguments.length === 2 && typeof arguments[0] === "string" && typeof arguments[1] === "function" && !arguments[1][isTraitSymbol]) {
return overloads.test.apply(this, arguments);

@@ -294,3 +368,5 @@ }

target[propertyKey][testNameSymbol] = propertyKey ? propertyKey.toString() : "";
mark && (target[propertyKey][mark] = true);
if (mark) {
target[propertyKey][mark] = true;
}
},

@@ -301,3 +377,5 @@ testDecorator(...traits) {

target[propertyKey][traitsSymbol] = traits;
mark && (target[propertyKey][mark] = true);
if (mark) {
target[propertyKey][mark] = true;
}
};

@@ -309,5 +387,7 @@ },

target[propertyKey][traitsSymbol] = traits;
mark && (target[propertyKey][mark] = true);
if (mark) {
target[propertyKey][mark] = true;
}
};
}
},
});

@@ -319,3 +399,3 @@ }

only: makeTestFunction(() => context.it.only, onlySymbol),
pending: makeTestFunction(() => context.it.skip, pendingSumbol)
pending: makeTestFunction(() => context.it.skip, pendingSymbol),
});

@@ -459,6 +539,6 @@ }

if (arguments.length === 1) {
target[pendingSumbol] = true;
target[pendingSymbol] = true;
}
else {
target[propertyKey][pendingSumbol] = true;
target[propertyKey][pendingSymbol] = true;
}

@@ -507,5 +587,5 @@ }

function tsdd(suite) {
var suites = [suite];
suite.on('pre-require', function (context, file, mocha) {
var common = Common(suites, context, mocha);
const suites = [suite];
suite.on("pre-require", function (context, file, mocha) {
const common = Common(suites, context, mocha);
context.before = common.before;

@@ -519,5 +599,5 @@ context.after = common.after;

return common.suite.create({
title: title,
file: file,
fn: fn
title,
file,
fn,
});

@@ -527,5 +607,5 @@ };

return common.suite.skip({
title: title,
file: file,
fn: fn
title,
file,
fn,
});

@@ -535,13 +615,13 @@ };

return common.suite.only({
title: title,
file: file,
fn: fn
title,
file,
fn,
});
};
context.it = context.specify = function (title, fn) {
var suite = suites[0];
const suite = suites[0];
if (suite.isPending()) {
fn = null;
}
var test = new Test(title, fn);
const test = new Test(title, fn);
test.file = file;

@@ -561,2 +641,3 @@ suite.addTest(test);

context.suite = makeSuiteObject(context);
context.params = makeParamsObject(context);
context.test = makeTestObject(context);

@@ -570,4 +651,4 @@ context.test.retries = common.test.retries;

}
;
module.exports = Object.assign(tsdd, exports);
Mocha.interfaces["mocha-typescript"] = tsdd;
//# sourceMappingURL=index.js.map
import * as Mocha from "mocha";
import * as Common from "mocha/lib/interfaces/common";
import * as Suite from "mocha/lib/suite";
import * as Test from "mocha/lib/test";
import * as Common from "mocha/lib/interfaces/common";
interface TestFunctions {
it: {
(name: string, fn: Function): void,
only(name: string, fn: Function): void;
skip(name: string, fn?: Function): void;
},
describe: {
(name: string, fn: Function): void,
only(name: string, fn: Function): void;
skip(name: string, fn?: Function): void;
},
before: any,
after: any,
beforeEach: any,
afterEach: any
it: {
(name: string, fn: Function): void,
only(name: string, fn: Function): void;
skip(name: string, fn?: Function): void;
};
describe: {
(name: string, fn: Function): void,
only(name: string, fn: Function): void;
skip(name: string, fn?: Function): void;
};
before: any;
after: any;
beforeEach: any;
afterEach: any;
}
const globalTestFunctions: TestFunctions = {
get describe() { return (<any>global).describe; },
get it() { return (<any>global).it; },
get before() { return (<any>global).before; },
get after() { return (<any>global).after; },
get beforeEach() { return (<any>global).beforeEach; },
get afterEach() { return (<any>global).afterEach; }
get describe() { return (global as any).describe; },
get it() { return (global as any).it; },
get before() { return (global as any).before; },
get after() { return (global as any).after; },
get beforeEach() { return (global as any).beforeEach; },
get afterEach() { return (global as any).afterEach; },
};
// key => Symbol("mocha-typescript:" + key)
let nodeSymbol = key => "__mts_" + key;
const nodeSymbol = (key) => "__mts_" + key;
let testNameSymbol = nodeSymbol("test");
let slowSymbol = nodeSymbol("slow");
let timeoutSymbol = nodeSymbol("timout");
let retriesSymbol = nodeSymbol("retries");
let onlySymbol = nodeSymbol("only");
let pendingSumbol = nodeSymbol("pending");
let skipSymbol = nodeSymbol("skip");
let traitsSymbol = nodeSymbol("traits");
let isTraitSymbol = nodeSymbol("isTrait");
let contextSymbol = nodeSymbol("context");
let handled = nodeSymbol("handled");
const suiteSymbol = nodeSymbol("suite");
const testNameSymbol = nodeSymbol("test");
const parametersSymbol = nodeSymbol("parametersSymbol");
const nameForParametersSymbol = nodeSymbol("nameForParameters");
const slowSymbol = nodeSymbol("slow");
const timeoutSymbol = nodeSymbol("timout");
const retriesSymbol = nodeSymbol("retries");
const onlySymbol = nodeSymbol("only");
const pendingSymbol = nodeSymbol("pending");
const skipSymbol = nodeSymbol("skip");
const traitsSymbol = nodeSymbol("traits");
const isTraitSymbol = nodeSymbol("isTrait");
const contextSymbol = nodeSymbol("context");
const handled = nodeSymbol("handled");
interface MochaDone {
(error?: any): any;
}
type MochaDone = (error?: any) => any;
interface SuiteCtor {
prototype: SuiteProto;
before?: (done?: MochaDone) => void;
after?: (done?: MochaDone) => void;
new();
prototype: SuiteProto;
before?: (done?: MochaDone) => void;
after?: (done?: MochaDone) => void;
new();
}
interface SuiteProto {
before?: (done?: MochaDone) => void;
after?: (done?: MochaDone) => void;
before?: (done?: MochaDone) => void;
after?: (done?: MochaDone) => void;
[key: string]: any;
}
export interface SuiteTrait {
(this: Mocha.ISuiteCallbackContext, ctx: Mocha.ISuiteCallbackContext, ctor: SuiteCtor): void;
}
export interface TestTrait {
(this: Mocha.ITestCallbackContext, ctx: Mocha.ITestCallbackContext, instance: SuiteProto, method: Function): void;
}
export type SuiteTrait = (this: Mocha.ISuiteCallbackContext, ctx: Mocha.ISuiteCallbackContext, ctor: SuiteCtor) => void;
export type TestTrait = (this: Mocha.ITestCallbackContext, ctx: Mocha.ITestCallbackContext, instance: SuiteProto, method: Function) => void;
const noname = cb => cb;
const noname = (cb) => cb;
function applyDecorators(mocha: Mocha.IHookCallbackContext, ctorOrProto, method, instance) {
const timeoutValue = method[timeoutSymbol];
if (typeof timeoutValue === "number") {
mocha.timeout(timeoutValue);
}
const slowValue = method[slowSymbol];
if (mocha['slow'] && typeof slowValue === "number") {
mocha['slow'](slowValue);
}
const retriesValue = method[retriesSymbol];
if (mocha['retries'] && typeof retriesValue === "number") {
mocha['retries'](retriesValue);
}
const contextProperty = ctorOrProto[contextSymbol];
if (contextProperty) {
instance[contextProperty] = mocha;
}
const timeoutValue = method[timeoutSymbol];
if (typeof timeoutValue === "number") {
mocha.timeout(timeoutValue);
}
const slowValue = method[slowSymbol];
if (mocha.slow && typeof slowValue === "number") {
mocha.slow(slowValue);
}
const retriesValue = method[retriesSymbol];
if (mocha.retries && typeof retriesValue === "number") {
mocha.retries(retriesValue);
}
const contextProperty = ctorOrProto[contextSymbol];
if (contextProperty) {
instance[contextProperty] = mocha;
}
}
function applyTestTraits(context: Mocha.ITestCallbackContext, instance: SuiteProto, method: Function) {
const traits: TestTrait[] = method[traitsSymbol];
if (traits) {
traits.forEach(trait => {
trait.call(context, context, instance, method);
});
}
const traits: TestTrait[] = method[traitsSymbol];
if (traits) {
traits.forEach((trait) => {
trait.call(context, context, instance, method);
});
}
}
function applySuiteTraits(context: Mocha.ISuiteCallbackContext, target: SuiteCtor) {
const traits: SuiteTrait[] = target[traitsSymbol];
if (traits) {
traits.forEach(trait => {
trait.call(context, context, target);
});
}
const traits: SuiteTrait[] = target[traitsSymbol];
if (traits) {
traits.forEach((trait) => {
trait.call(context, context, target);
});
}
}
function suiteClassCallback(target: SuiteCtor, context: TestFunctions) {
return function () {
applySuiteTraits(this, target);
applyDecorators(this, target, target, target);
let instance;
if (target.before) {
if (target.before.length > 0) {
context.before(function (done) {
applyDecorators(this, target, target.before, target);
return target.before(done);
});
} else {
context.before(function () {
applyDecorators(this, target, target.before, target);
return target.before();
});
}
}
if (target.after) {
if (target.after.length > 0) {
context.after(function (done) {
applyDecorators(this, target, target.after, target);
return target.after(done);
});
} else {
context.after(function () {
applyDecorators(this, target, target.after, target);
return target.after();
});
}
}
let prototype = target.prototype;
let beforeEachFunction: { (): any } | { (done: Function): any };
if (prototype.before) {
if (prototype.before.length > 0) {
beforeEachFunction = noname(function (this: Mocha.IHookCallbackContext, done: Function) {
instance = new target();
applyDecorators(this, prototype, prototype.before, instance);
return prototype.before.call(instance, done);
});
} else {
beforeEachFunction = noname(function (this: Mocha.IHookCallbackContext) {
instance = new target();
applyDecorators(this, prototype, prototype.before, instance);
return prototype.before.call(instance);
});
}
} else {
beforeEachFunction = noname(function (this: Mocha.IHookCallbackContext) {
instance = new target();
});
}
context.beforeEach(beforeEachFunction);
return function() {
applySuiteTraits(this, target);
applyDecorators(this, target, target, target);
let instance;
if (target.before) {
if (target.before.length > 0) {
context.before(function(done) {
applyDecorators(this, target, target.before, target);
return target.before(done);
});
} else {
context.before(function() {
applyDecorators(this, target, target.before, target);
return target.before();
});
}
}
if (target.after) {
if (target.after.length > 0) {
context.after(function(done) {
applyDecorators(this, target, target.after, target);
return target.after(done);
});
} else {
context.after(function() {
applyDecorators(this, target, target.after, target);
return target.after();
});
}
}
const prototype = target.prototype;
let beforeEachFunction: (() => any) | ((done: Function) => any);
if (prototype.before) {
if (prototype.before.length > 0) {
beforeEachFunction = noname(function(this: Mocha.IHookCallbackContext, done: Function) {
instance = new target();
applyDecorators(this, prototype, prototype.before, instance);
return prototype.before.call(instance, done);
});
} else {
beforeEachFunction = noname(function(this: Mocha.IHookCallbackContext) {
instance = new target();
applyDecorators(this, prototype, prototype.before, instance);
return prototype.before.call(instance);
});
}
} else {
beforeEachFunction = noname(function(this: Mocha.IHookCallbackContext) {
instance = new target();
});
}
context.beforeEach(beforeEachFunction);
let afterEachFunction: { (): any } | { (done: Function): any };
if (prototype.after) {
if (prototype.after.length > 0) {
afterEachFunction = noname(function (this: Mocha.IHookCallbackContext, done) {
try {
applyDecorators(this, prototype, prototype.after, instance);
return prototype.after.call(instance, done);
} finally {
instance = undefined;
}
});
} else {
afterEachFunction = noname(function (this: Mocha.IHookCallbackContext) {
try {
applyDecorators(this, prototype, prototype.after, instance);
return prototype.after.call(instance);
} finally {
instance = undefined;
}
});
}
} else {
afterEachFunction = noname(function (this: Mocha.IHookCallbackContext) {
instance = undefined;
});
}
context.afterEach(afterEachFunction);
let afterEachFunction: (() => any) | ((done: Function) => any);
if (prototype.after) {
if (prototype.after.length > 0) {
afterEachFunction = noname(function(this: Mocha.IHookCallbackContext, done) {
try {
applyDecorators(this, prototype, prototype.after, instance);
return prototype.after.call(instance, done);
} finally {
instance = undefined;
}
});
} else {
afterEachFunction = noname(function(this: Mocha.IHookCallbackContext) {
try {
applyDecorators(this, prototype, prototype.after, instance);
return prototype.after.call(instance);
} finally {
instance = undefined;
}
});
}
} else {
afterEachFunction = noname(function(this: Mocha.IHookCallbackContext) {
instance = undefined;
});
}
context.afterEach(afterEachFunction);
function runTests(prototype: any) {
(<any>Object).getOwnPropertyNames(prototype).forEach(key => {
try {
let method = <Function>prototype[key];
if (method === target) {
return;
}
function runTest(prototype: any, method: Function) {
const testName = method[testNameSymbol] || (method as any).name;
const shouldSkip = method[skipSymbol];
const shouldOnly = method[onlySymbol];
const shouldPending = method[pendingSymbol];
const parameters = method[parametersSymbol] as TestParams[];
let testName = method[testNameSymbol];
let shouldSkip = method[skipSymbol];
let shouldOnly = method[onlySymbol];
let shouldPending = method[pendingSumbol];
if (testName || shouldOnly || shouldPending || shouldSkip) {
if (shouldPending && !shouldSkip && !shouldOnly) {
context.it.skip(testName);
} else if (parameters) {
const nameForParameters = method[nameForParametersSymbol];
parameters.forEach((parameterOptions, i) => {
const { mark, name, params } = parameterOptions;
let testFunc = (shouldSkip && context.it.skip)
|| (shouldOnly && context.it.only)
|| context.it;
let parametersTestName = `${testName}_${i}`;
if (name) {
parametersTestName = name;
} else if (nameForParameters) {
parametersTestName = nameForParameters(params);
}
if (testName || shouldOnly || shouldPending || shouldSkip) {
testName = testName || (<any>method).name;
if (shouldPending && !shouldSkip && !shouldOnly) {
context.it.skip(testName);
} else if (method.length > 0) {
testFunc(testName, noname(function(this: Mocha.ITestCallbackContext, done) {
applyDecorators(this, prototype, method, instance);
applyTestTraits(this, instance, method);
return method.call(instance, done);
}));
const shouldSkipParam = shouldSkip || (mark === Mark.skip);
const shouldOnlyParam = shouldOnly || (mark === Mark.only);
const shouldPendingParam = shouldPending || (mark === Mark.pending);
if (shouldPendingParam && !shouldSkipParam && !shouldOnlyParam) {
context.it.skip(testName);
} else {
const testFunc = (shouldSkipParam && context.it.skip)
|| (shouldOnlyParam && context.it.only)
|| context.it;
applyTestFunc(testFunc, parametersTestName, method, [params], method.length <= 1);
}
});
} else {
const testFunc = (shouldSkip && context.it.skip)
|| (shouldOnly && context.it.only)
|| context.it;
applyTestFunc(testFunc, testName, method, [], method.length === 0);
}
}
}
function applyTestFunc(testFunc: Function, testName: string,
method: Function, callArgs: any[],
sync: boolean = true) {
if (sync) {
testFunc(testName, noname(function(this: Mocha.ITestCallbackContext) {
applyDecorators(this, prototype, method, instance);
applyTestTraits(this, instance, method);
return method.call(instance, ...callArgs);
}));
} else {
testFunc(testName, noname(function(this: Mocha.ITestCallbackContext) {
applyDecorators(this, prototype, method, instance);
applyTestTraits(this, instance, method);
return method.call(instance);
}));
testFunc(testName, noname(function(this: Mocha.ITestCallbackContext, done) {
applyDecorators(this, prototype, method, instance);
applyTestTraits(this, instance, method);
return method.call(instance, ...callArgs, done);
}));
}
}
} catch (e) {
// console.log(e);
}
});
}
// run all tests along the inheritance chain
let currentPrototype = prototype;
while (currentPrototype !== Object.prototype) {
runTests(currentPrototype);
currentPrototype = (<any>Object).getPrototypeOf(currentPrototype);
}
}
// collect all tests along the inheritance chain, allow overrides
const collectedTests: { [key: string]: any[] } = {};
let currentPrototype = prototype;
while (currentPrototype !== Object.prototype) {
Object.getOwnPropertyNames(currentPrototype).forEach((key) => {
if (typeof prototype[key] === "function") {
const method = prototype[key];
if (method[testNameSymbol] && !collectedTests[key]) {
collectedTests[key] = [prototype, method];
}
}
});
currentPrototype = (Object as any).getPrototypeOf(currentPrototype);
if (currentPrototype !== Object.prototype && currentPrototype.constructor[suiteSymbol]) {
throw new Error("deriving from other suites is bad practice and thus prohibited");
}
}
// run all collected tests
for (const key in collectedTests) {
const value = collectedTests[key];
runTest(value[0], value[1]);
}
};
}
function suiteOverload(overloads: {
suite(name: string, fn: Function): any;
suiteCtor(ctor: SuiteCtor): void;
suiteDecorator(... traits: SuiteTrait[]): ClassDecorator;
suiteDecoratorNamed(name: string, ... traits: SuiteTrait[]): ClassDecorator;
suite(name: string, fn: Function): any;
suiteCtor(ctor: SuiteCtor): void;
suiteDecorator(...traits: SuiteTrait[]): ClassDecorator;
suiteDecoratorNamed(name: string, ...traits: SuiteTrait[]): ClassDecorator;
}) {
return function() {
if (arguments.length == 2 && typeof arguments[0] === "string" && typeof arguments[1] === "function" && !arguments[1][isTraitSymbol]) {
return overloads.suite.apply(this, arguments);
} else if (arguments.length === 1 && typeof arguments[0] === "function" && !arguments[0][isTraitSymbol]) {
overloads.suiteCtor.apply(this, arguments);
} else if (arguments.length >= 1 && typeof arguments[0] === "string") {
return overloads.suiteDecoratorNamed.apply(this, arguments);
} else {
return overloads.suiteDecorator.apply(this, arguments);
}
}
return function() {
if (arguments.length === 2 && typeof arguments[0] === "string" && typeof arguments[1] === "function" && !arguments[1][isTraitSymbol]) {
return overloads.suite.apply(this, arguments);
} else if (arguments.length === 1 && typeof arguments[0] === "function" && !arguments[0][isTraitSymbol]) {
overloads.suiteCtor.apply(this, arguments);
} else if (arguments.length >= 1 && typeof arguments[0] === "string") {
return overloads.suiteDecoratorNamed.apply(this, arguments);
} else {
return overloads.suiteDecorator.apply(this, arguments);
}
};
}
function makeSuiteFunction(suiteFunc: (ctor?: SuiteCtor) => Function, context: TestFunctions) {
return suiteOverload({
suite(name: string, fn: Function): any {
return suiteFunc()(name, fn);
},
suiteCtor(ctor: SuiteCtor): void {
suiteFunc(ctor)(ctor.name, suiteClassCallback(ctor, context));
},
suiteDecorator(... traits: SuiteTrait[]): ClassDecorator {
return function<TFunction extends Function>(ctor: TFunction): void {
ctor[traitsSymbol] = traits;
suiteFunc(<any>ctor)(ctor.name, suiteClassCallback(<any>ctor, context));
}
},
suiteDecoratorNamed(name: string, ... traits: SuiteTrait[]): ClassDecorator {
return function<TFunction extends Function>(ctor: TFunction): void {
ctor[traitsSymbol] = traits;
suiteFunc(<any>ctor)(name, suiteClassCallback(<any>ctor, context));
}
}
});
return suiteOverload({
suite(name: string, fn: Function): any {
return suiteFunc()(name, fn);
},
suiteCtor(ctor: SuiteCtor): void {
ctor[suiteSymbol] = true;
suiteFunc(ctor)(ctor.name, suiteClassCallback(ctor, context));
},
suiteDecorator(...traits: SuiteTrait[]): ClassDecorator {
return function <TFunction extends Function>(ctor: TFunction): void {
ctor[suiteSymbol] = true;
ctor[traitsSymbol] = traits;
suiteFunc(ctor as any)(ctor.name, suiteClassCallback(ctor as any, context));
};
},
suiteDecoratorNamed(name: string, ...traits: SuiteTrait[]): ClassDecorator {
return function <TFunction extends Function>(ctor: TFunction): void {
ctor[suiteSymbol] = true;
ctor[traitsSymbol] = traits;
suiteFunc(ctor as any)(name, suiteClassCallback(ctor as any, context));
};
},
});
}
function suiteFuncCheckingDecorators(context: TestFunctions) {
return function(ctor?: SuiteCtor) {
if (ctor) {
let shouldSkip = ctor[skipSymbol];
let shouldOnly = ctor[onlySymbol];
let shouldPending = ctor[pendingSumbol];
return (shouldSkip && context.describe.skip)
|| (shouldOnly && context.describe.only)
|| (shouldPending && context.describe.skip)
|| context.describe;
} else {
return context.describe;
}
}
return function(ctor?: SuiteCtor) {
if (ctor) {
const shouldSkip = ctor[skipSymbol];
const shouldOnly = ctor[onlySymbol];
const shouldPending = ctor[pendingSymbol];
return (shouldSkip && context.describe.skip)
|| (shouldOnly && context.describe.only)
|| (shouldPending && context.describe.skip)
|| context.describe;
} else {
return context.describe;
}
};
}
function makeSuiteObject(context: TestFunctions): Suite {
return Object.assign(makeSuiteFunction(suiteFuncCheckingDecorators(context), context), {
skip: makeSuiteFunction(() => context.describe.skip, context),
only: makeSuiteFunction(() => context.describe.only, context),
pending: makeSuiteFunction(() => context.describe.skip, context)
});
return Object.assign(makeSuiteFunction(suiteFuncCheckingDecorators(context), context), {
skip: makeSuiteFunction(() => context.describe.skip, context),
only: makeSuiteFunction(() => context.describe.only, context),
pending: makeSuiteFunction(() => context.describe.skip, context),
});
}
export const suite = makeSuiteObject(globalTestFunctions);
const enum Mark { test, skip, only, pending }
interface TestParams {
mark: Mark;
name?: string;
params: any;
}
function makeParamsFunction(mark: Mark) {
return (params: any, name?: string) => {
return (target: Object, propertyKey: string) => {
target[propertyKey][testNameSymbol] = propertyKey ? propertyKey.toString() : "";
target[propertyKey][parametersSymbol] = target[propertyKey][parametersSymbol] || [];
target[propertyKey][parametersSymbol].push({ mark, name, params } as TestParams);
};
};
}
function makeParamsNameFunction() {
return (nameForParameters: (parameters: any) => string) => {
return (target: Object, propertyKey: string) => {
target[propertyKey][nameForParametersSymbol] = nameForParameters;
};
};
}
function makeParamsObject(context: TestFunctions) {
return Object.assign(makeParamsFunction(Mark.test), {
skip: makeParamsFunction(Mark.skip),
only: makeParamsFunction(Mark.only),
pending: makeParamsFunction(Mark.pending),
naming: makeParamsNameFunction(),
});
}
export const params = makeParamsObject(globalTestFunctions);
function testOverload(overloads: {
test(name: string, fn: Function);
testProperty(target: Object, propertyKey: string | symbol, descriptor?: PropertyDescriptor): void;
testDecorator(... traits: TestTrait[]): PropertyDecorator & MethodDecorator;
testDecoratorNamed(name: string, ... traits: TestTrait[]): PropertyDecorator & MethodDecorator;
test(name: string, fn: Function);
testProperty(target: Object, propertyKey: string | symbol, descriptor?: PropertyDescriptor): void;
testDecorator(...traits: TestTrait[]): PropertyDecorator & MethodDecorator;
testDecoratorNamed(name: string, ...traits: TestTrait[]): PropertyDecorator & MethodDecorator;
}) {
return function() {
if (arguments.length == 2 && typeof arguments[0] === "string" && typeof arguments[1] === "function" && !arguments[1][isTraitSymbol]) {
return overloads.test.apply(this, arguments);
} else if (arguments.length >= 2 && typeof arguments[0] !== "string" && typeof arguments[0] !== "function") {
overloads.testProperty.apply(this, arguments);
} else if (arguments.length >= 1 && typeof arguments[0] === "string") {
return overloads.testDecoratorNamed.apply(this, arguments);
} else {
return overloads.testDecorator.apply(this, arguments);
}
}
return function() {
if (arguments.length === 2 && typeof arguments[0] === "string" && typeof arguments[1] === "function" && !arguments[1][isTraitSymbol]) {
return overloads.test.apply(this, arguments);
} else if (arguments.length >= 2 && typeof arguments[0] !== "string" && typeof arguments[0] !== "function") {
overloads.testProperty.apply(this, arguments);
} else if (arguments.length >= 1 && typeof arguments[0] === "string") {
return overloads.testDecoratorNamed.apply(this, arguments);
} else {
return overloads.testDecorator.apply(this, arguments);
}
};
}
function makeTestFunction(testFunc: () => Function, mark: null | string | symbol) {
return testOverload({
test(name: string, fn: Function) {
testFunc()(name, fn);
},
testProperty(target: Object, propertyKey: string | symbol, descriptor?: PropertyDescriptor): void {
target[propertyKey][testNameSymbol] = propertyKey ? propertyKey.toString() : "";
mark && (target[propertyKey][mark] = true);
},
testDecorator(... traits: TestTrait[]): PropertyDecorator & MethodDecorator {
return function(target: Object, propertyKey: string | symbol, descriptor?: PropertyDescriptor): void {
target[propertyKey][testNameSymbol] = propertyKey ? propertyKey.toString() : "";
target[propertyKey][traitsSymbol] = traits;
mark && (target[propertyKey][mark] = true);
}
},
testDecoratorNamed(name: string, ... traits: TestTrait[]): PropertyDecorator & MethodDecorator {
return function(target: Object, propertyKey: string | symbol, descriptor?: PropertyDescriptor): void {
target[propertyKey][testNameSymbol] = name;
target[propertyKey][traitsSymbol] = traits;
mark && (target[propertyKey][mark] = true);
}
}
});
return testOverload({
test(name: string, fn: Function) {
testFunc()(name, fn);
},
testProperty(target: Object, propertyKey: string | symbol, descriptor?: PropertyDescriptor): void {
target[propertyKey][testNameSymbol] = propertyKey ? propertyKey.toString() : "";
if (mark) {
target[propertyKey][mark] = true;
}
},
testDecorator(...traits: TestTrait[]): PropertyDecorator & MethodDecorator {
return function(target: Object, propertyKey: string | symbol, descriptor?: PropertyDescriptor): void {
target[propertyKey][testNameSymbol] = propertyKey ? propertyKey.toString() : "";
target[propertyKey][traitsSymbol] = traits;
if (mark) {
target[propertyKey][mark] = true;
}
};
},
testDecoratorNamed(name: string, ...traits: TestTrait[]): PropertyDecorator & MethodDecorator {
return function(target: Object, propertyKey: string | symbol, descriptor?: PropertyDescriptor): void {
target[propertyKey][testNameSymbol] = name;
target[propertyKey][traitsSymbol] = traits;
if (mark) {
target[propertyKey][mark] = true;
}
};
},
});
}
function makeTestObject(context: TestFunctions): Test {
return Object.assign(makeTestFunction(() => context.it, null), {
skip: makeTestFunction(() => context.it.skip, skipSymbol),
only: makeTestFunction(() => context.it.only, onlySymbol),
pending: makeTestFunction(() => context.it.skip, pendingSumbol)
});
return Object.assign(makeTestFunction(() => context.it, null), {
skip: makeTestFunction(() => context.it.skip, skipSymbol),
only: makeTestFunction(() => context.it.only, onlySymbol),
pending: makeTestFunction(() => context.it.skip, pendingSymbol),
});
}

@@ -359,4 +447,4 @@ export const test = makeTestObject(globalTestFunctions);

export function trait<T extends SuiteTrait | TestTrait>(arg: T): T {
arg[isTraitSymbol] = true;
return arg;
arg[isTraitSymbol] = true;
return arg;
}

@@ -369,28 +457,28 @@

export function slow(time: number): PropertyDecorator & ClassDecorator & SuiteTrait & TestTrait {
return trait(function() {
if (arguments.length === 1) {
const target = arguments[0];
target[slowSymbol] = time;
} else if (arguments.length === 2 && typeof arguments[1] === "string" || typeof arguments[1] === "symbol") {
const target = arguments[0];
const property = arguments[1];
target[property][slowSymbol] = time;
} else if (arguments.length === 2) {
const context: Mocha.ISuiteCallbackContext = arguments[0];
const ctor = arguments[1];
context.slow(time);
} else if (arguments.length === 3) {
if (typeof arguments[2] === "function") {
const context: Mocha.ITestCallbackContext = arguments[0];
const instance = arguments[1];
const method = arguments[2];
context.slow(time);
} else if (typeof arguments[1] === "string" || typeof arguments[1] === "symbol") {
const proto: Mocha.ITestCallbackContext = arguments[0];
const prop = arguments[1];
const descriptor = arguments[2];
proto[prop][slowSymbol] = time;
}
}
});
return trait(function() {
if (arguments.length === 1) {
const target = arguments[0];
target[slowSymbol] = time;
} else if (arguments.length === 2 && typeof arguments[1] === "string" || typeof arguments[1] === "symbol") {
const target = arguments[0];
const property = arguments[1];
target[property][slowSymbol] = time;
} else if (arguments.length === 2) {
const context: Mocha.ISuiteCallbackContext = arguments[0];
const ctor = arguments[1];
context.slow(time);
} else if (arguments.length === 3) {
if (typeof arguments[2] === "function") {
const context: Mocha.ITestCallbackContext = arguments[0];
const instance = arguments[1];
const method = arguments[2];
context.slow(time);
} else if (typeof arguments[1] === "string" || typeof arguments[1] === "symbol") {
const proto: Mocha.ITestCallbackContext = arguments[0];
const prop = arguments[1];
const descriptor = arguments[2];
proto[prop][slowSymbol] = time;
}
}
});
}

@@ -403,28 +491,28 @@

export function timeout(time: number): MethodDecorator & PropertyDecorator & ClassDecorator & SuiteTrait & TestTrait {
return trait(function() {
if (arguments.length === 1) {
const target = arguments[0];
target[timeoutSymbol] = time;
} else if (arguments.length === 2 && typeof arguments[1] === "string" || typeof arguments[1] === "symbol") {
const target = arguments[0];
const property = arguments[1];
target[property][timeoutSymbol] = time;
} else if (arguments.length === 2) {
const context: Mocha.ISuiteCallbackContext = arguments[0];
const ctor = arguments[1];
context.timeout(time);
} else if (arguments.length === 3) {
if (typeof arguments[2] === "function") {
const context: Mocha.ITestCallbackContext = arguments[0];
const instance = arguments[1];
const method = arguments[2];
context.timeout(time);
} else if (typeof arguments[1] === "string" || typeof arguments[1] === "symbol") {
const proto: Mocha.ITestCallbackContext = arguments[0];
const prop = arguments[1];
const descriptor = arguments[2];
proto[prop][timeoutSymbol] = time;
}
}
});
return trait(function() {
if (arguments.length === 1) {
const target = arguments[0];
target[timeoutSymbol] = time;
} else if (arguments.length === 2 && typeof arguments[1] === "string" || typeof arguments[1] === "symbol") {
const target = arguments[0];
const property = arguments[1];
target[property][timeoutSymbol] = time;
} else if (arguments.length === 2) {
const context: Mocha.ISuiteCallbackContext = arguments[0];
const ctor = arguments[1];
context.timeout(time);
} else if (arguments.length === 3) {
if (typeof arguments[2] === "function") {
const context: Mocha.ITestCallbackContext = arguments[0];
const instance = arguments[1];
const method = arguments[2];
context.timeout(time);
} else if (typeof arguments[1] === "string" || typeof arguments[1] === "symbol") {
const proto: Mocha.ITestCallbackContext = arguments[0];
const prop = arguments[1];
const descriptor = arguments[2];
proto[prop][timeoutSymbol] = time;
}
}
});
}

@@ -437,28 +525,28 @@

export function retries(count: number): MethodDecorator & PropertyDecorator & ClassDecorator & SuiteTrait & TestTrait {
return trait(function() {
if (arguments.length === 1) {
const target = arguments[0];
target[retriesSymbol] = count;
} else if (arguments.length === 2 && typeof arguments[1] === "string" || typeof arguments[1] === "symbol") {
const target = arguments[0];
const property = arguments[1];
target[property][retriesSymbol] = count;
} else if (arguments.length === 2) {
const context: Mocha.ISuiteCallbackContext = arguments[0];
const ctor = arguments[1];
context.retries(count);
} else if (arguments.length === 3) {
if (typeof arguments[2] === "function") {
const context: Mocha.ITestCallbackContext = arguments[0];
const instance = arguments[1];
const method = arguments[2];
context.retries(count);
} else if (typeof arguments[1] === "string" || typeof arguments[1] === "symbol") {
const proto: Mocha.ITestCallbackContext = arguments[0];
const prop = arguments[1];
const descriptor = arguments[2];
proto[prop][retriesSymbol] = count;
}
}
});
return trait(function() {
if (arguments.length === 1) {
const target = arguments[0];
target[retriesSymbol] = count;
} else if (arguments.length === 2 && typeof arguments[1] === "string" || typeof arguments[1] === "symbol") {
const target = arguments[0];
const property = arguments[1];
target[property][retriesSymbol] = count;
} else if (arguments.length === 2) {
const context: Mocha.ISuiteCallbackContext = arguments[0];
const ctor = arguments[1];
context.retries(count);
} else if (arguments.length === 3) {
if (typeof arguments[2] === "function") {
const context: Mocha.ITestCallbackContext = arguments[0];
const instance = arguments[1];
const method = arguments[2];
context.retries(count);
} else if (typeof arguments[1] === "string" || typeof arguments[1] === "symbol") {
const proto: Mocha.ITestCallbackContext = arguments[0];
const prop = arguments[1];
const descriptor = arguments[2];
proto[prop][retriesSymbol] = count;
}
}
});
}

@@ -485,7 +573,7 @@

export function pending<TFunction extends Function>(target: Object | TFunction, propertyKey?: string | symbol): void {
if (arguments.length === 1) {
target[pendingSumbol] = true;
} else {
target[propertyKey][pendingSumbol] = true;
}
if (arguments.length === 1) {
target[pendingSymbol] = true;
} else {
target[propertyKey][pendingSymbol] = true;
}
}

@@ -499,7 +587,7 @@

export function only<TFunction extends Function>(target: Object, propertyKey?: string | symbol): void {
if (arguments.length === 1) {
target[onlySymbol] = true;
} else {
target[propertyKey][onlySymbol] = true;
}
if (arguments.length === 1) {
target[onlySymbol] = true;
} else {
target[propertyKey][onlySymbol] = true;
}
}

@@ -513,7 +601,7 @@

export function skip<TFunction extends Function>(target: Object | TFunction, propertyKey?: string | symbol): void {
if (arguments.length === 1) {
target[onlySymbol] = true;
} else {
target[propertyKey][skipSymbol] = true;
}
if (arguments.length === 1) {
target[onlySymbol] = true;
} else {
target[propertyKey][skipSymbol] = true;
}
}

@@ -525,3 +613,3 @@

export function context(target: Object, propertyKey: string | symbol): void {
target[contextSymbol] = propertyKey;
target[contextSymbol] = propertyKey;
}

@@ -534,66 +622,68 @@

function tsdd(suite) {
var suites = [suite];
const suites = [suite];
suite.on('pre-require', function (context, file, mocha) {
var common = Common(suites, context, mocha);
suite.on("pre-require", function(context, file, mocha) {
const common = Common(suites, context, mocha);
context.before = common.before;
context.after = common.after;
context.beforeEach = common.beforeEach;
context.afterEach = common.afterEach;
context.run = mocha.options.delay && common.runWithSuite(suite);
context.before = common.before;
context.after = common.after;
context.beforeEach = common.beforeEach;
context.afterEach = common.afterEach;
context.run = mocha.options.delay && common.runWithSuite(suite);
// Copy of bdd
context.describe = context.context = function (title, fn) {
return common.suite.create({
title: title,
file: file,
fn: fn
});
};
context.xdescribe = context.xcontext = context.describe.skip = function (title, fn) {
return common.suite.skip({
title: title,
file: file,
fn: fn
});
};
context.describe.only = function (title, fn) {
return common.suite.only({
title: title,
file: file,
fn: fn
});
};
context.it = context.specify = function (title, fn) {
var suite = suites[0];
if (suite.isPending()) {
fn = null;
}
var test = new Test(title, fn);
test.file = file;
suite.addTest(test);
return test;
};
context.it.only = function (title, fn) {
return common.test.only(mocha, context.it(title, fn));
};
context.xit = context.xspecify = context.it.skip = function (title) {
context.it(title);
};
context.it.retries = function (n) {
context.retries(n);
};
// Copy of bdd
context.describe = context.context = function(title, fn) {
return common.suite.create({
title,
file,
fn,
});
};
context.xdescribe = context.xcontext = context.describe.skip = function(title, fn) {
return common.suite.skip({
title,
file,
fn,
});
};
context.describe.only = function(title, fn) {
return common.suite.only({
title,
file,
fn,
});
};
context.it = context.specify = function(title, fn) {
const suite = suites[0];
if (suite.isPending()) {
fn = null;
}
const test = new Test(title, fn);
test.file = file;
suite.addTest(test);
return test;
};
context.it.only = function(title, fn) {
return common.test.only(mocha, context.it(title, fn));
};
context.xit = context.xspecify = context.it.skip = function(title) {
context.it(title);
};
context.it.retries = function(n) {
context.retries(n);
};
context.suite = makeSuiteObject(context);
context.test = makeTestObject(context);
context.suite = makeSuiteObject(context);
context.params = makeParamsObject(context);
context.test = makeTestObject(context);
context.test.retries = common.test.retries;
context.test.retries = common.test.retries;
context.timeout = timeout;
context.slow = slow;
context.retries = retries;
context.skipOnError = skipOnError;
});
};
context.timeout = timeout;
context.slow = slow;
context.retries = retries;
context.skipOnError = skipOnError;
});
}
module.exports = Object.assign(tsdd, exports);
(Mocha as any).interfaces["mocha-typescript"] = tsdd;
{
"name": "mocha-typescript",
"version": "1.1.14",
"version": "1.1.15",
"description": "TypeScript decorators based wrapper over mocha's interface",

@@ -16,24 +16,31 @@ "main": "index.js",

"pretest": "tsc",
"test": "mocha test.js --opts mocha.opts",
"prepare": "tsc"
"test": "mocha test.js --opts mocha.opts && tslint --project .",
"prepare": "tsc",
"tslint-fix": "tslint --fix --project .",
"tslint": "tslint --project ."
},
"author": "Panayot Cankov",
"contributors": [
{
"name": "silkentrance",
"url": "https://github.com/silkentrance"
}
],
"license": "Apache-2.0",
"dependencies": {
"@types/mocha": "*",
"chalk": "^1.1.3",
"cross-spawn": "^5.1.0",
"yargs": "^6.5.0"
"@types/mocha": "^5.2.0",
"chalk": "^2.4.1",
"cross-spawn": "^6.0.5",
"yargs": "^11.0.0"
},
"devDependencies": {
"@types/chai": "^3.4.35",
"@types/mocha": "^5.0.0",
"@types/node": "^7.0.60",
"assert": "^1.3.0",
"better-assert": "^1.0.2",
"chai": "^3.5.0",
"mocha": "^4.0.1",
"rimraf": "^2.6.1",
"source-map-support": "^0.4.15",
"typescript": "^2.4.1"
"@types/chai": "^4.1.3",
"@types/node": "^10.1.4",
"@types/cross-spawn": "^6.0.0",
"chai": "^4.1.2",
"mocha": "^5.2.0",
"rimraf": "^2.6.2",
"source-map-support": "^0.5.6",
"tslint": "^5.10.0",
"typescript": "^2.9.1"
},

@@ -40,0 +47,0 @@ "files": [

@@ -30,2 +30,3 @@ Writing mocha tests with style - OOP style:

- [Test Inheritance](#test-inheritance)
- [Overriding Tests](#overriding-tests)
- [Inheritance and Both Synchronous and Asynchronous Before and After Actions](#inheritance-and-both-synchronous-and-asynchronous-before-and-after-actions)

@@ -339,7 +340,32 @@ - [Generated Suites and Tests](#generated-suites-and-tests)

One can also inherit from another concrete test class or suite, but keep in mind that that the tests declared by that suite will
be run multiple times and not just in the context of the concrete test classes, see the example provided in `tests/ts/suite.inheritance.suite.ts`.
Note: You can override test methods inherited from a base class and then call `super()` in order to run the assertions implemented by the super class.
Important: One should not override test methods inherited from a base class and then call `super()` as this will run the tests from the base class twice.
Best practice: You must not inherit from other classes that have been decorated with the ``suite`` decorator. Doing so will result in an exception. Use abstract base classes instead.
### Overriding Tests
Sometimes you might want to override tests inherited from a given base class. You can do this by redeclaring the same test method in your sub class, e.g.
``` TypeScript
export abstract class AbstractTestBase {
@test 'test that will be overridden by sub classes'() {
chai.assert.fail('sub classes must override this');
}
}
export class ConcreteTest extends AbstractTestBase {
@test 'test that will be overridden by sub classes'() {
chai.assertTrue(somethingTruthy);
}
}
```
You may now either implement the test or simply just skip it.
Given that ``skip`` actually marks the test as pending, this might not be what you want for your test reports. In that case, you could just override the test with an empty body.
Which, of course, is considered to be a bad practice, yet sometimes it will become a necessity when testing class hierarchies. So the best practice is to actually
provide an assertion for that test.
### Inheritance and Both Synchronous and Asynchronous Before and After Actions

@@ -346,0 +372,0 @@ As for both static and instance `before()` and `after()` actions, one must make sure that the hooks from the parent class are called, see the

Sorry, the diff of this file is not supported yet

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc