From e1c62582cb5279c732f56675b7bcf7eab5fbd735 Mon Sep 17 00:00:00 2001 From: pietervdvn <pietervdvn@posteo.net> Date: Fri, 25 Mar 2022 15:47:14 +0100 Subject: [PATCH] Improve doctests --- README.md | 138 +--- examples/OtherClass.ts | 9 + examples/example0.ts | 24 - examples/someClass.ts | 27 + package.json | 17 +- src/ExtractComments.ts | 97 +++ src/TestCreator.ts | 131 ++++ src/TestSuite.ts | 17 + src/UnitTest.ts | 150 ++++ src/internal.ts | 276 ------- src/main.ts | 93 +-- test/hasFoo.ts | 13 - test/test.ts | 152 ---- tsconfig.json | 38 +- unused-test-files/c.ts | 7 - unused-test-files/ex.ts | 11 - unused-test-files/example.ts | 89 --- unused-test-files/i.ts | 23 - unused-test-files/main2.ts | 417 ---------- unused-test-files/visitor_test.ts | 46 -- yarn.lock | 1173 ++++++++++++----------------- 21 files changed, 1019 insertions(+), 1929 deletions(-) create mode 100644 examples/OtherClass.ts delete mode 100644 examples/example0.ts create mode 100644 examples/someClass.ts create mode 100644 src/ExtractComments.ts create mode 100644 src/TestCreator.ts create mode 100644 src/TestSuite.ts create mode 100644 src/UnitTest.ts delete mode 100644 src/internal.ts delete mode 100644 test/hasFoo.ts delete mode 100644 test/test.ts delete mode 100644 unused-test-files/c.ts delete mode 100644 unused-test-files/ex.ts delete mode 100644 unused-test-files/example.ts delete mode 100644 unused-test-files/i.ts delete mode 100644 unused-test-files/main2.ts delete mode 100644 unused-test-files/visitor_test.ts diff --git a/README.md b/README.md index 879ddd5..a3aba0a 100644 --- a/README.md +++ b/README.md @@ -1,124 +1,30 @@ -# doctest-ts: doctests for TypeScript +# doctest-ts-improved: doctests for TypeScript -Say you have a file src/hasFoo.ts with a function like hasFoo: +Easy doctests for typescript modules, including private methods and extra imports: -```typescript -function hasFoo(s: string): boolean { - return null != s.match(/foo/i) +``` +export default class SomeClass { + /** + * Gets the field doubled + * @example xyz + * + * import OtherClass from "./OtherClass"; + * + * // Should equal 42 + * SomeClass.get() // => 42 + * + * SomeClass.get() + 1 // => 43 + * + * new OtherClass().doSomething(new SomeClass()) // => 5 + */ + private static get() : number{ + // a comment + // @ts-ignore + return 42 + } } ``` -You can now make documentation and unit tests for this function in one go: - -```typescript -/** Does this string contain foo, ignoring case? - - hasFoo('___foo__') // => true - hasFoo(' fOO ') // => true - hasFoo('Foo.') // => true - hasFoo('bar') // => false - hasFoo('fo') // => false - hasFoo('oo') // => false - -*/ -function hasFoo(s: string): boolean { - return null != s.match(/foo/i) -} -``` - -Since the function is not exported we can only test this by either editing or copying the entire file and gluing on tests at the end. -This library goes for the second approach: making a copy of the file with the translated tests at the end. Run it like so: - -```sh -$ doctest-ts src/hasFoo.ts -Writing src/hasFoo.doctest.ts -``` - -The contents of `src/hasFoo.doctest.ts` is the original file prepended to the doctests rewritten as unit tests. - -```typescript -/** Does this string contain foo, ignoring case? - - hasFoo('___foo__') // => true - hasFoo(' fOO ') // => true - hasFoo('Foo.') // => true - hasFoo('bar') // => false - hasFoo('fo') // => false - hasFoo('oo') // => false - -*/ -function hasFoo(s: string): boolean { - return null != s.match(/foo/i) -} - -import * as __test from "tape" -__test("hasFoo", t => {t.deepEqual(hasFoo("___foo__"), true, "true") -t.deepEqual(hasFoo(" fOO "), true, "true") -t.deepEqual(hasFoo("Foo."), true, "true") -t.deepEqual(hasFoo("bar"), false, "false") -t.deepEqual(hasFoo("fo"), false, "false") -t.deepEqual(hasFoo("oo"), false, "false") -;t.end()}) -``` - -This can now be run with the tape runner or ts-node: - -``` -$ ts-node src/hasFoo.doctest.ts | tap-diff - hasFoo - ✔ true - ✔ true - ✔ true - ✔ false - ✔ false - ✔ false - Done in 0.37s. - -passed: 6 failed: 0 of 6 tests (171ms) - -All of 6 tests passed! -``` - -There are four different outputs available: - -* tape -* AVA -* jest -* mocha (using chai) - -Pull requests for other test runners are welcome. - -## Watching file changes - -We can tell `doctest-ts` to watch for file changes and report which files it has written. -It tries to be a good unix citizen and thus writes the files it has created on stdout (and some info on stderr). -This makes it possible to run test runners on each line on stdout like so: - -```sh -ts-node src/main.ts --watch src/hasFo.ts | -while read file; do echo running tape on $file; ts-node $file | tap-diff; done -``` - -Let's say we remove the ignore case `i` flag from the regex in `hasFoo`. We get this output (automatically): -``` -Writing src/hasFoo.doctest.ts -running tape on src/hasFoo.doctest.ts - - hasFoo - ✔ true - ✖ true at Test.t (src/hasFoo.doctest.ts:18:3) - [-false-][+true+] - ✖ true at Test.t (src/hasFoo.doctest.ts:19:3) - [-false-][+true+] - ✔ false - ✔ false - ✔ false - -passed: 4 failed: 2 of 6 tests (264ms) - -2 of 6 tests failed. -``` - # License MIT diff --git a/examples/OtherClass.ts b/examples/OtherClass.ts new file mode 100644 index 0000000..5979587 --- /dev/null +++ b/examples/OtherClass.ts @@ -0,0 +1,9 @@ +import SomeClass from "./someClass"; + +export default class OtherClass { + + public doSomething(c: SomeClass){ + return c.xyz() + } + +} \ No newline at end of file diff --git a/examples/example0.ts b/examples/example0.ts deleted file mode 100644 index a31f73b..0000000 --- a/examples/example0.ts +++ /dev/null @@ -1,24 +0,0 @@ - - -export default class Example0 { - - /** - * Gets the field doubled - * @example xyz - * - * // Should equal 42 - * Example0.get() // => 42 - * - * Example0.get() + 1 // => 43 - */ - private static get(){ - // a comment - // @ts-ignore - return 42 - } - - public testMore(){ - return ({} as any) ?.xyz?.abc ?? 0 - } - -} \ No newline at end of file diff --git a/examples/someClass.ts b/examples/someClass.ts new file mode 100644 index 0000000..a671254 --- /dev/null +++ b/examples/someClass.ts @@ -0,0 +1,27 @@ + +export default class SomeClass { + + /** + * Gets the field doubled + * @example xyz + * + * import OtherClass from "./OtherClass"; + * + * // Should equal 42 + * SomeClass.get() // => 42 + * + * SomeClass.get() + 1 // => 43 + * + * new OtherClass().doSomething(new SomeClass()) // => 5 + */ + private static get() : number{ + // a comment + // @ts-ignore + return 42 + } + + public xyz(){ + return 5 + } + +} \ No newline at end of file diff --git a/package.json b/package.json index 305cc69..05bd59d 100644 --- a/package.json +++ b/package.json @@ -1,17 +1,16 @@ { "$schema": "http://json.schemastore.org/package", - "name": "doctest-ts", - "version": "0.6.0", - "description": "doctest support for typescript", + "name": "doctest-ts-improved", + "version": "0.7.0", + "description": "doctest support for typescript with Mocha", "main": "src/main.ts", "bin": { - "doctest-ts": "dist/src/main.js" + "doctest-ts-improved": "dist/src/main.js" }, "scripts": { "build": "tsc && chmod 755 dist/src/main.js", - "test": "ts-node src/main.ts --tape src/*ts test/*ts && ts-node node_modules/.bin/tape test/*.ts src/*doctest*.ts | tap-diff", "doctest:watch": "ts-node src/main.ts --tape --watch {src,test}/*.ts | while read file; do echo tape $file; ts-node $file | tap-diff; done", - "debug": "ts-node src/main.ts --mocha examples/example0.ts", + "test": "ts-node src/main.ts examples/ && ts-node src/main.ts src/ && mocha --require ts-node/register examples/*.ts src/*.ts", "prettier": "rm -v -f {src,test}/*doctest.ts && prettier --list-different --write src/*ts* test/*ts*" }, "repository": { @@ -30,14 +29,16 @@ }, "homepage": "https://github.com/danr/doctest-ts#readme", "dependencies": { - "chokidar": "^2.0.1", + "@types/chai": "^4.3.0", + "chai": "^4.3.6", "global": "^4.3.2", - "minimist": "^1.2.0", + "mocha": "^9.2.2", "typescript": "^4.6.2" }, "devDependencies": { "@types/chokidar": "^1.7.5", "@types/minimist": "^1.2.0", + "@types/mocha": "^9.1.0", "@types/node": "^9.4.6", "@types/tape": "^4.2.31", "faucet": "^0.0.1", diff --git a/src/ExtractComments.ts b/src/ExtractComments.ts new file mode 100644 index 0000000..7d47660 --- /dev/null +++ b/src/ExtractComments.ts @@ -0,0 +1,97 @@ +import * as ts from "typescript"; +import {JSDocComment} from "typescript"; +import {SyntaxKind} from "typescript/lib/tsserverlibrary"; + +export interface Context { + filepath: string, + linenumber?: number, + classname?: string, + functionname?: string, + testname?: string +} + +/** + * Responsible for extracting the testfiles from the .ts files + * + */ +export default class ExtractComments { + + private readonly results: { comment: string, context: Context }[] = [] + private readonly code: string; + + constructor(filepath: string, code: string) { + this.code = code; + const ast = ts.createSourceFile('_.ts', code, ts.ScriptTarget.Latest) + this.traverse(ast, {filepath: filepath}) + } + + public getComments(): { comment: string, context: Context }[] { + return this.results + } + + private getLineNumber(pos: number) { + let line = 0; + for (let i = 0; i < pos; i++) { + if (this.code[i] === "\n") { + line++ + } + } + return line; + } + + private registerComment(context: Context, comment: string | ts.NodeArray<JSDocComment> | undefined, position: number) { + if (comment === undefined) { + return + } + context = {...context, linenumber: this.getLineNumber(position)} + if (typeof comment === "string") { + this.results.push({comment: comment || '', context}); + } else { + comment.forEach(jsDocComment => { + this.results.push({comment: jsDocComment.text || '', context}); + }) + } + } + + private traverse(node: ts.Node, context: Context) { + if (SyntaxKind.ClassDeclaration === node.kind) { + context = {...context, classname: (node as any)["name"].escapedText}; + } + const jsdocs = (node as any).jsDoc || [] + if (jsdocs.length > 0) { + let declName = undefined + try { + declName = (node as any).name.escapedText + } catch (e) { + try { + const decls = (node as any).declarationList.declarations + if (decls.length == 1) { + declName = decls[0].name.escapedText || null + } + } catch (e) { + declName = ts.isConstructorDeclaration(node) ? 'constructor' : undefined + } + } + + context = {...context, functionname: declName} + + jsdocs.forEach((doc: ts.JSDoc) => { + this.registerComment(context, doc.comment, doc.pos) + + // A part of the comment might be in the tags; we simply add those too and figure out later if they contain doctests + const tags = doc.tags; + if (tags !== undefined) { + tags.forEach(tag => { + this.registerComment(context, tag.comment, tag.pos) + }); + } + }) + + } + + + ts.forEachChild(node, n => this.traverse(n, context)) + } + + +} \ No newline at end of file diff --git a/src/TestCreator.ts b/src/TestCreator.ts new file mode 100644 index 0000000..aa5ef90 --- /dev/null +++ b/src/TestCreator.ts @@ -0,0 +1,131 @@ +import UnitTest from "./UnitTest"; +import * as ts from "typescript"; +import ExtractComments from "./ExtractComments"; +import * as fs from 'fs' +import * as path from 'path' + +/** + * Responsible for creating a '.doctest.ts'-file + */ +export default class TestCreator { + private _originalFilepath: string; + + constructor(originalFilepath: string) { + this._originalFilepath = originalFilepath; + if (originalFilepath.includes('doctest')) { + throw "Not creating a doctest for a file which already is a doctest" + } + } + + private static exposePrivates(s: string): string { + const ast = ts.createSourceFile('_.ts', s, ts.ScriptTarget.Latest) as ts.SourceFile + + const transformer = <T extends ts.Node>(context: ts.TransformationContext) => + (rootNode: T) => { + function visit(node: ts.Node): ts.Node { + if (node.kind === ts.SyntaxKind.PrivateKeyword) { + return ts.createModifier(ts.SyntaxKind.PublicKeyword) + } + return ts.visitEachChild(node, visit, context); + } + + return ts.visitNode(rootNode, visit); + }; + + const transformed = ts.transform(ast, [transformer]).transformed[0] + + const pwoc = ts.createPrinter({removeComments: false}) + return pwoc.printNode(ts.EmitHint.Unspecified, transformed, ast) + } + + + private static testCode(tests: UnitTest[]): string[] { + const code: string[] = [] + const exportedTests = new Set<UnitTest>() + + function show(s: string) { + return JSON.stringify(s) + } + + function emit(test: UnitTest, indent: string = "") { + if (exportedTests.has(test)) { + return; + } + const testCode = "\n" + test.generateCode() + code.push(testCode.replace(/\n/g, "\n" + indent)) + exportedTests.add(test) + } + + function emitAllForFunction(functionname: string | undefined, indent: string) { + tests.filter(t => t.context.functionname === functionname).forEach(c => emit(c, " " + indent)) + } + + function emitAllForClass(classname: string | undefined, indent: string) { + const forClass: UnitTest[] = tests.filter(t => t.context.classname === classname) + for (const test of forClass) { + if (exportedTests.has(test)) { + continue + } + + if (test.context.functionname !== undefined) { + code.push(indent+"describe(" + show(test.context.functionname) + ", () => {") + emitAllForFunction(test.context.functionname, " " + indent) + code.push(indent+"})") + } + + } + emitAllForFunction(undefined, indent) + } + + for (const test of tests) { + if (exportedTests.has(test)) { + continue + } + if (test.context.classname !== undefined) { + code.push("describe(" + show(test.context.classname) + ", () => {") + emitAllForClass(test.context.classname, " ") + code.push("})") + } + } + + emitAllForClass(undefined, "") + return code + } + + /** + * Creates a new file with the doctests. + * + * Returns the number of found tests + */ + public createTest(): number { + const file = this._originalFilepath + const {base, ext, ...u} = path.parse(file) + const buffer = fs.readFileSync(file, {encoding: 'utf8'}) + const comments = new ExtractComments(file, buffer).getComments() + const tests: UnitTest[] = UnitTest.FromComments(comments) + + const outfile = path.format({...u, ext: '.doctest' + ext}) + if (tests.length == 0) { + return 0 + } + + const code = [] + const imports = new Set<string>() + for (const test of tests) { + test.getImports().forEach(i => imports.add(i)) + } + + // Add imports needed by the tests + code.push(...Array.from(imports)) + // Adds the original code where the private keywords are removed + code.push(TestCreator.exposePrivates(buffer)) + + // At last, we add all the doctests + code.push(...TestCreator.testCode(tests)) + + fs.writeFileSync(outfile, code.join("\n")) + return tests.length + } + + +} \ No newline at end of file diff --git a/src/TestSuite.ts b/src/TestSuite.ts new file mode 100644 index 0000000..4293bb7 --- /dev/null +++ b/src/TestSuite.ts @@ -0,0 +1,17 @@ +export default interface TestDescription { + + /** + * The name of the module under test + */ + moduleName?: string; + + /** + * The name of the function under testing + */ + functionName?: string + + /** + * The name of the singular test + */ + testName?: string +} \ No newline at end of file diff --git a/src/UnitTest.ts b/src/UnitTest.ts new file mode 100644 index 0000000..9cc11d2 --- /dev/null +++ b/src/UnitTest.ts @@ -0,0 +1,150 @@ +import {Context} from "./ExtractComments"; +import * as ts from "typescript"; + +type Script = (Statement | Equality)[] +interface Equality { + tag: '==' + lhs: string + rhs: string +} + +interface Statement { + tag: 'Statement' + stmt: string +} + +class ScriptExtraction { + /** + * ScriptExtraction.is_doctest('// => true') // => true + * ScriptExtraction.is_doctest('// true') // => false + */ + public static is_doctest(s: string): boolean { + return s.match(/\/\/[ \t]*=>/) != null + } + + /** + * Extracts the expected value + * + * const m = ScriptExtraction.doctest_rhs('// => true') || [] + * m[1] // => ' true' + */ + public static doctest_rhs(s: string) { + return s.match(/^\s*\/\/[ \t]*=>([^\n]*)/m); + } + + public static extractImports(docstring: string){ + return docstring.split("\n").filter(s => s.startsWith("import ")); + } + + public static extractScripts(docstring: string): { script: Script, name?: string, line: number }[] { + const out = [] as { script: Script, name?: string, line: number }[] + let line = 0; + for (const s of docstring.split(/\n\n+/m)) { + const p: number = line; + line += s.split(/\r\n|\r|\n/).length + + if (!ScriptExtraction.is_doctest(s)) { + continue; + } + + const script = ScriptExtraction.extractScript(s) + let name = undefined + const match = s.match(/^[ \t]*\/\/([^\n]*)/) + if (match !== null) { + name = match[1].trim() + } + out.push({script, name, line: p}) + } + return out + } + + /** + * ScriptExtraction.extractScript('s') // => [{tag: 'Statement', stmt: 's;'}] + * ScriptExtraction.extractScript('e // => 1') // => [{tag: '==', lhs: 'e', rhs: '1'}] + * ScriptExtraction.extractScript('s; e // => 1') // => [{tag: 'Statement', stmt: 's;'}, {tag: '==', lhs: 'e', rhs: '1'}] + */ + private static extractScript(s: string): Script { + const pwoc = ts.createPrinter({removeComments: true}) + const ast = ts.createSourceFile('_.ts', s, ts.ScriptTarget.Latest) + return ast.statements.map((stmt, i): Statement | Equality => { + if (ts.isExpressionStatement(stmt)) { + const next = ast.statements[i + 1] // zip with next + const [a, z] = next ? [next.pos, next.end] : [stmt.end, ast.end] + const after = ast.text.slice(a, z) + const m = ScriptExtraction.doctest_rhs(after) + if (m && m[1]) { + const lhs = pwoc.printNode(ts.EmitHint.Expression, stmt.expression, ast) + const rhs = m[1].trim() + return {tag: '==', lhs, rhs} + } + } + + + + return {tag: 'Statement', stmt: pwoc.printNode(ts.EmitHint.Unspecified, stmt, ast)} + }) + } +} + +/** + * Represents a single unit test somewhere in a file. + */ +export default class UnitTest { + + + public body: Script; + public context: Context; + private _extraImports: string[]; + + private constructor(body: Script, context: Context, extraImports: string[]) { + this.body = body; + this.context = context; + this._extraImports = extraImports; + } + + public static FromComment(comment: string, context: Context): UnitTest[] { + const imports = ScriptExtraction.extractImports(comment) + return ScriptExtraction.extractScripts(comment).map(({script, line, name}, i) => + new UnitTest(script, { + ...context, + linenumber: (context.linenumber ?? 0) + line, + testname: name ?? 'doctest ' + i + },imports)) + } + + public static FromComments(comms: { comment: string, context: Context }[]): UnitTest[] { + const result: UnitTest[] = [] + for (const comm of comms) { + result.push(...UnitTest.FromComment(comm.comment, comm.context)) + } + return result + } + + public getImports(): string[] { + return [...this._extraImports, 'import "mocha"', 'import {expect as __expect} from "chai"'] + } + + /** + * Generates the mocha test code for this unit test. + * Will only construct the 'it('should ....') { __expect(x).deep.eq(y) } part + */ + public generateCode() { + const script = this.body + .map(s => { + if (s.tag == 'Statement') { + return s.stmt + } else { + return `__expect(${s.lhs}, "failed at ${this.context.functionname} (${this.context.filepath}:${this.context.linenumber}:1)").to.deep.equal(${s.rhs})` + } + }) + .map(x => '\n ' + x) + .join('') + return `it(${this.getName()}, () => {${script}\n})` + } + + private getName() { + return JSON.stringify(this.context.testname ?? this.context.functionname) + } + + +} \ No newline at end of file diff --git a/src/internal.ts b/src/internal.ts deleted file mode 100644 index 78697c5..0000000 --- a/src/internal.ts +++ /dev/null @@ -1,276 +0,0 @@ -import * as ts from 'typescript' -import {JSDocComment} from 'typescript' -import * as fs from 'fs' -import * as path from 'path' - -//////////////////////////////////////////////////////////// -// Types - -export interface Equality { - tag: '==' - lhs: string - rhs: string -} - -export interface Statement { - tag: 'Statement' - stmt: string -} - -export type Script = (Statement | Equality)[] - -export type Context = string | null - -export interface Comment { - comment: string - context: Context -} - -//////////////////////////////////////////////////////////// -// Extracting docstrings from program - -export function Comments(s: string): Comment[] { - const out: Comment[] = [] - function registerComment(context: string | null,comment: string | ts.NodeArray<JSDocComment> | undefined){ - if(comment === undefined){ - return - } - if(typeof comment === "string"){ - out.push({comment: comment || '', context}); - }else{ - comment.forEach(jsDocComment => { - out.push({comment: jsDocComment.text || '', context}); - }) - } - } - - - function traverse(node: ts.Node) { - const jsdocs = (node as any).jsDoc || [] - if (jsdocs.length > 0) { - let context: string | null = null - try { - context = (node as any).name.escapedText || null - } catch (e) { - try { - const decls = (node as any).declarationList.declarations - if (decls.length == 1) { - context = decls[0].name.escapedText || null - } - } catch (e) { - context = ts.isConstructorDeclaration(node) ? 'constructor' : null - } - } - jsdocs.forEach((doc: ts.JSDoc) => { - registerComment(context, doc.comment) - - // A part of the comment might be in the tags; we simply add those too and figure out later if they contain doctests - const tags = doc.tags; - if(tags !== undefined){ - tags.forEach(tag => { - registerComment(context, tag.comment) - }); - } - }) - - } - ts.forEachChild(node, traverse) - } - - const ast = ts.createSourceFile('_.ts', s, ts.ScriptTarget.Latest) - traverse(ast) - - return out -} - -//////////////////////////////////////////////////////////// -// Extracting test scripts from docstrings - -/** - - is_doctest('// => true') // => true - is_doctest('// true') // => false - -*/ -const is_doctest = (s: string) => s.match(/\/\/[ \t]*=>/) != null - -/** - - const m = doctest_rhs('// => true') || [] - m[1] // => ' true' - -*/ -const doctest_rhs = (s: string) => s.match(/^\s*\/\/[ \t]*=>([^\n]*)/m) - -/** - - extractScript('s') // => [{tag: 'Statement', stmt: 's;'}] - - extractScript('e // => 1') // => [{tag: '==', lhs: 'e', rhs: '1'}] - - extractScript('s; e // => 1') // => [{tag: 'Statement', stmt: 's;'}, {tag: '==', lhs: 'e', rhs: '1'}] - -*/ -export function extractScript(s: string): Script { - const pwoc = ts.createPrinter({removeComments: true}) - const ast = ts.createSourceFile('_.ts', s, ts.ScriptTarget.Latest) - return ast.statements.map((stmt, i): Statement | Equality => { - if (ts.isExpressionStatement(stmt)) { - const next = ast.statements[i + 1] // zip with next - const [a, z] = next ? [next.pos, next.end] : [stmt.end, ast.end] - const after = ast.text.slice(a, z) - const m = doctest_rhs(after) - if (m && m[1]) { - const lhs = pwoc.printNode(ts.EmitHint.Expression, stmt.expression, ast) - const rhs = m[1].trim() - return {tag: '==', lhs, rhs} - } - } - - return {tag: 'Statement', stmt: pwoc.printNode(ts.EmitHint.Unspecified, stmt, ast)} - }) -} - -export function extractScripts(docstring: string): {script: Script, name?: string}[] { - const out = [] as {script: Script, name?: string}[] - docstring.split(/\n\n+/m).forEach(s => { - if (is_doctest(s)) { - const script = extractScript(s) - let name = undefined - const match = s.match(/^[ \t]*\/\/([^\n]*)/) - if(match !== null) - { - name = match[1].trim() - } - out.push({script, name}) - } - }) - return out -} - -//////////////////////////////////////////////////////////// -// Showing test scripts -export interface ShowScript { - showImports: string - showScript(script: Script, c: Context, name?: string): string -} - -/** show("hello") // => '"hello"' */ -export function show(s: any) { - return JSON.stringify(s) -} - -export function showContext(c: Context) { - return show(c || 'doctest') -} - -function tapeOrAVA(script: Script, c: Context, name: string | undefined, before_end = (t: string) => '') { - const t = `t` - const body = script - .map(s => { - if (s.tag == 'Statement') { - return s.stmt - } else { - return `${t}.deepEqual(${s.lhs}, ${s.rhs}, ${show(s.rhs)})` - } - }) - .map(x => '\n ' + x) - .join('') - return ` - __test(${showContext(c)}, ${t} => { - ${body} - ${before_end(t)} - })` -} - -const mochaOrJest = (deepEqual: string): typeof tapeOrAVA => (script, c, name) => { - const body = script - .map(s => { - if (s.tag == 'Statement') { - return s.stmt - } else { - return `__expect(${s.lhs}).${deepEqual}(${s.rhs})` - } - }) - .map(x => '\n ' + x) - .join('') - - return ` - describe(${showContext(c)}, () => { - it(${show(name) || showContext(c)}, () => {${body}}) - }) - ` -} - -export const showScriptInstances: Record<string, ShowScript> = { - ava: { - showImports: 'import {test as __test} from "ava"', - showScript: tapeOrAVA, - }, - - tape: { - showImports: 'import * as __test from "tape"', - showScript: (s, c, name) => tapeOrAVA(s, c, name, t => `\n;${t}.end()`), - }, - - mocha: { - showImports: 'import "mocha"\nimport {expect as __expect} from "chai"', - showScript: mochaOrJest(`to.deep.equal`), - }, - - jest: { - showImports: 'import "jest"\nconst __expect: jest.Expect = expect', - showScript: mochaOrJest(`toEqual`), - }, -} - -function exposePrivates(s: string): string { - const ast = ts.createSourceFile('_.ts', s, ts.ScriptTarget.Latest) as ts.SourceFile - - const transformer = <T extends ts.Node>(context: ts.TransformationContext) => - (rootNode: T) => { - function visit(node: ts.Node): ts.Node { - if (node.kind === ts.SyntaxKind.PrivateKeyword) { - return ts.createModifier(ts.SyntaxKind.PublicKeyword) - } - return ts.visitEachChild(node, visit, context); - } - return ts.visitNode(rootNode, visit); - }; - - const transformed = ts.transform(ast, [transformer]).transformed[0] - - const pwoc = ts.createPrinter({ removeComments: false}) - return pwoc.printNode(ts.EmitHint.Unspecified, transformed, ast) -} - - -export function instrument(d: ShowScript, file: string, mode?: 'watch'): void { - const {base, ext, ...u} = path.parse(file) - if (base.includes('doctest')) { - return - } - const buffer = fs.readFileSync(file, {encoding: 'utf8'}) - const withoutPrivates = exposePrivates(buffer) - const tests = Doctests(d, buffer) - const outfile = path.format({...u, ext: '.doctest' + ext}) - if (tests.length == 0) { - console.error('No doctests found in', file) - } else { - console.error('Writing', outfile) - if (mode == 'watch') { - console.log(outfile) - } - fs.writeFileSync(outfile, withoutPrivates + '\n' + d.showImports + '\n' + tests.join('\n')) - } -} - -function Doctests(d: ShowScript, buffer: string): string[] { - const out: string[] = [] - for (const c of Comments(buffer)) { - for (const script of extractScripts(c.comment)) { - out.push(d.showScript(script.script, c.context, script.name)) - } - } - return out -} diff --git a/src/main.ts b/src/main.ts index b5f765f..72d24ed 100644 --- a/src/main.ts +++ b/src/main.ts @@ -1,49 +1,52 @@ #!/usr/bin/env node -import * as chokidar from 'chokidar' -import * as minimist from 'minimist' -import {instrument, showScriptInstances} from './internal' -function main() { - const outputs = Object.keys(showScriptInstances) - const flags = outputs.map(f => '--' + f) - const boolean = ['watch'].concat(outputs) - const opts = minimist(process.argv.slice(2), {boolean}) - let output: string | null = null - let error: string | null = null - outputs.forEach(k => { - if (opts[k]) { - if (output != null) { - error = `Cannot output both ${output} and ${k}` - } - output = k +import {lstatSync, readdirSync} from "fs"; +import TestCreator from "./TestCreator"; + + +function readDirRecSync(path: string, maxDepth = 999): string[] { + const result = [] + if (maxDepth <= 0) { + return [] } - }) - if (output == null) { - error = `Choose an output from ${flags.join(' ')}` - } - const files = opts._ - if (files.length == 0 || output == null) { - console.error( - ` - Error: ${error || `No files specified!`} - - Usage: - - ${flags.join('|')} [-w|--watch] files globs... - - Your options were:`, - opts, - ` - From:`, - process.argv - ) - return - } - const d = showScriptInstances[output] - files.forEach(file => instrument(d, file)) - if (opts.w == true || opts.watch == true) { - const watcher = chokidar.watch(files, {ignored: '*.doctest.*'}) - watcher.on('change', file => global.setTimeout(() => instrument(d, file, 'watch'), 25)) - } + for (const entry of readdirSync(path)) { + const fullEntry = path + "/" + entry + const stats = lstatSync(fullEntry) + if (stats.isDirectory()) { + // Subdirectory + // @ts-ignore + result.push(...ScriptUtils.readDirRecSync(fullEntry, maxDepth - 1)) + } else { + result.push(fullEntry) + } + } + return result; } -main() +function main(){ + +const args = process.argv +console.log(args.join(",")) +const directory = args[2].replace(/\/$/, "") +if(directory === "--require"){ + console.error("Probably running the testsuite, detects '--require' as second argument. Quitting now") + return; +} +if(directory === undefined){ + console.log("Usage: doctest-ts-improved <directory under test>. This will automatically scan recursively for '.ts'-files, excluding 'node_modules' '*.doctest.ts'-files") +} + +const files = readDirRecSync(directory).filter(p => !p.startsWith("./node_modules") && !p.endsWith(".doctest.ts")) +const noTests : string[] = [] +for (const file of files) { + const generated = new TestCreator(file).createTest() + if(generated === 0){ + noTests.push(file) + }else{ + console.log("Generated tests for "+file+" ("+generated+" tests found)") + } +} +if(noTests.length > 0){ + console.log("No tests found in: "+noTests.join(", ")) +} +} +main() \ No newline at end of file diff --git a/test/hasFoo.ts b/test/hasFoo.ts deleted file mode 100644 index be80d61..0000000 --- a/test/hasFoo.ts +++ /dev/null @@ -1,13 +0,0 @@ -/** Does this string contain foo, ignoring case? - - hasFoo('___foo__') // => true - hasFoo(' fOO ') // => true - hasFoo('Foo.') // => true - hasFoo('bar') // => false - hasFoo('fo') // => false - hasFoo('oo') // => false - -*/ -function hasFoo(s: string): boolean { - return null != s.match(/foo/i) -} diff --git a/test/test.ts b/test/test.ts deleted file mode 100644 index b10adfd..0000000 --- a/test/test.ts +++ /dev/null @@ -1,152 +0,0 @@ -import * as internal from '../src/internal' -import * as test from 'tape' - -test('tests', t => { - t.plan(1) - t.deepEqual( - internal.extractScripts(`* - - foo // => 1 - - `), - [{ script: [{tag: '==', lhs: `foo`, rhs: `1`}], name: undefined }] - ) -}) - -test('tests', t => { - t.plan(1) - t.deepEqual( - internal.extractScripts(`* - - a - b // => 1 + 2 + 3 - c // => 1 - d - - */`).map(s => s.script), - [ - [ - {tag: 'Statement', stmt: 'a;'}, - {tag: '==', lhs: 'b', rhs: '1 + 2 + 3'}, - {tag: '==', lhs: 'c', rhs: '1'}, - {tag: 'Statement', stmt: 'd;'}, - ], - ] - ) -}) - -const c = (comment: string, context: string | null) => ({comment, context}) - -test('modules and namespace', t => { - t.plan(1) - const cs = internal.Comments(` - /** m */ - namespace m {} - - /** ns */ - namespace ns {} - `) - t.deepEqual(cs, [c('m', 'm'), c('ns', 'ns')]) -}) - -test('const', t => { - t.plan(1) - const cs = internal.Comments(` - /** u */ - const u = 1 - `) - t.deepEqual(cs, [c('u', 'u')]) -}) - -test('const object', t => { - t.plan(1) - const cs = internal.Comments(` - /** k */ - const k = { - /** a */ - a: 1, - /** b */ - b(x: string) { return x+x } - } - `) - t.deepEqual(cs, [c('k', 'k'), c('a', 'a'), c('b', 'b')]) -}) - -test('object deconstruction', t => { - t.plan(1) - const cs = internal.Comments(` - /** hello */ - const {u, v} = {u: 1, v: 2} - `) - t.deepEqual(cs, [c('hello', null)]) -}) - -test('function', t => { - t.plan(1) - const cs = internal.Comments(` - /** v */ - function v(s: string): number { - return s.length + 1 - } - `) - t.deepEqual(cs, [c('v', 'v')]) -}) - -test('class', t => { - t.plan(1) - const cs = internal.Comments(` - /** C */ - class C<A> { - /** constructor */ - constructor() {} - /** m */ - m(s: Array<number>): Array<string> { - } - /** p */ - p: Array<number> - } - `) - t.deepEqual(cs, [c('C', 'C'), c('constructor', 'constructor'), c('m', 'm'), c('p', 'p')]) -}) - -test('interface', t => { - t.plan(1) - const cs = internal.Comments(` - /** I */ - interface I<A> { - /** i */ - i: A, - /** j */ - j(a: A): string - } - `) - t.deepEqual(cs, [c('I', 'I'), c('i', 'i'), c('j', 'j')]) -}) - -test('type', t => { - t.plan(1) - const cs = internal.Comments(` - /** T */ - type T = number - `) - t.deepEqual(cs, [c('T', 'T')]) -}) - -test('anywhere', t => { - t.plan(1) - const cs = internal.Comments(` - const $ = () => { - /** test1 */ - const w = 1 - - /** test2 */ - function f(x) { - return x * x - } - - /** test3 */ - return f(f(w)) - } - `) - t.deepEqual(cs, [c('test1', 'w'), c('test2', 'f'), c('test3', null)]) -}) diff --git a/tsconfig.json b/tsconfig.json index b2720aa..a8da009 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -1,21 +1,23 @@ { - "compilerOptions": { - "outDir": "./dist", - "sourceMap": true, - "noImplicitAny": true, - "strict": true, - "target": "es6", - "module": "commonjs", - "moduleResolution": "node", - "lib": ["es6"], - "noEmitOnError": true, - "allowUnreachableCode": true - }, - "include": [ - "src", - "test" + "compilerOptions": { + "outDir": "./dist", + "sourceMap": true, + "noImplicitAny": true, + "strict": true, + "target": "es6", + "module": "commonjs", + "moduleResolution": "node", + "lib": [ + "es6" ], - "parcelTsPluginOptions": { - "transpileOnly": false - } + "noEmitOnError": true, + "allowUnreachableCode": true + }, + "include": [ + "src", + "test" + ], + "parcelTsPluginOptions": { + "transpileOnly": false + } } diff --git a/unused-test-files/c.ts b/unused-test-files/c.ts deleted file mode 100644 index cbd8a2a..0000000 --- a/unused-test-files/c.ts +++ /dev/null @@ -1,7 +0,0 @@ -class X { - J: { - u: number - } = { - u: 1 - } -} diff --git a/unused-test-files/ex.ts b/unused-test-files/ex.ts deleted file mode 100644 index 73be18f..0000000 --- a/unused-test-files/ex.ts +++ /dev/null @@ -1,11 +0,0 @@ -export const j = 1 -export module A { - export const c = 1 - export const s = 1 - export interface J { - u: number - } -} -export namespace N { - export const d = 1 -} diff --git a/unused-test-files/example.ts b/unused-test-files/example.ts deleted file mode 100644 index bf57689..0000000 --- a/unused-test-files/example.ts +++ /dev/null @@ -1,89 +0,0 @@ - -/** I */ -export interface I { - /** k */ - k: number -} - -/** H */ -interface H { - /** k */ - k: number -} - -/** C */ -export class C { - /** f */ - f = 1 - /** g */ - g: number - /** new */ - constructor(x: number) { this.g = x } - /** s */ - static s(y: number): I { return {k: y} } - /** m */ - m(z: number): I { return {k: z} } -} - -/** T */ -type T = C - -/** c */ -const c = new C(1) - -/** M */ -export module M { - /** MI */ - export interface MI { - /** M k */ - k: number - } - - /** MC */ - export class MC { - /** M f */ - f = 1 - /** M g */ - g: number - /** M new */ - constructor(x: number) { this.g = x } - /** M s */ - static s(y: number): MI { return {k: y} } - /** M m */ - m(z: number): MI { return {k: z} } - - /** M p */ - private p(z: number): MI { return {k: z} } - } - - type MT = MC - - export const c = new MC(1) -} - -/** HM */ -module HM { - /** HMI */ - interface HMI { - /** HM k */ - k: number - } - - /** HMC */ - class HMC { - /** HM f */ - f = 1 - /** HM g */ - g: number - /** HM new */ - constructor(x: number) { this.g = x } - /** HM s */ - static s(y: number): HMI { return {k: y} } - /** HM m */ - m(z: number): HMI { return {k: z} } - } - - type HMT = HMC - - const c = new HMC(1) -} diff --git a/unused-test-files/i.ts b/unused-test-files/i.ts deleted file mode 100644 index fe87196..0000000 --- a/unused-test-files/i.ts +++ /dev/null @@ -1,23 +0,0 @@ -/** The awesome iface - -1 // => 1 - -This is not indentend -*/ -export interface B { - b: number -} - -export class C { - /** - - 1 // => 1 - much.to.test() - yes() - - - - more stuff*/ - static boo() { return 1 } -} - diff --git a/unused-test-files/main2.ts b/unused-test-files/main2.ts deleted file mode 100644 index 03a9916..0000000 --- a/unused-test-files/main2.ts +++ /dev/null @@ -1,417 +0,0 @@ -import * as babylon from 'babylon' -import * as babel from 'babel-types' -import generate from 'babel-generator' -import * as fs from 'fs' - -import * as util from 'util' - -util.inspect.defaultOptions.depth = 5 -util.inspect.defaultOptions.colors = true -const pp = (x: any) => (console.dir(x), console.log()) - -const opts: babylon.BabylonOptions = {plugins: [ - 'estree' , - 'jsx' , - 'flow' , - 'classConstructorCall' , - 'doExpressions' , - 'objectRestSpread' , - 'decorators' , - 'classProperties' , - 'exportExtensions' , - 'asyncGenerators' , - 'functionBind' , - 'functionSent' , - 'dynamicImport']} - - - - -const is_doctest = (s: string) => s.match(/\/\/[ \t]*=>/) != null -const doctest_rhs = (s: string) => s.match(/^\s*[ \t]*=>((.|\n)*)$/m) - -interface Equality { - tag: '==', - lhs: string, - rhs: string -} - -interface Statement { - tag: 'Statement' - stmt: string, -} - -type Script = (Statement | Equality)[] - -export function test(s: string): Script { - const lin = (ast: babel.Node) => generate(ast ,{comments: false, compact: true}).code - const ast = babylon.parse(s, opts) - return ast.program.body.map((stmt): Statement | Equality => { - const comment = (stmt.trailingComments || [{value: ''}])[0].value - const rhs = doctest_rhs(comment) - if (babel.isExpressionStatement(stmt) && rhs) { - const rhs = babylon.parseExpression(comment.replace(/^\s*=>/, '')) - return { - tag: '==', - lhs: lin(stmt.expression), - rhs: lin(rhs), - } - } else { - return {tag: 'Statement', stmt: lin(stmt)} - } - }) -} - -export function tests(docstring: string): Script[] { - const out = [] as Script[] - docstring.split(/\n\n+/m).forEach(s => { - if (is_doctest(s)) { - out.push(test(s)) - } - }) - return out -} - - -export interface Comment { - comment: string, - context: string | null -} - -export function Comments(s: string): Comment[] { - const out: Comment[] = [] - function add_comment(c: babel.Comment, context: string | null) { - out.push({comment: c.value, context}) - } - - const ast = babylon.parse(s, opts) - - traverse(ast, node => { - let context: null | string = null - /* - if (babel.isDeclaration(node)) { - util.inspect.defaultOptions.depth = 1 - pp({declaration: node}) - } - if (babel.isMethod(node)) { - util.inspect.defaultOptions.depth = 1 - pp({method: node}) - } - if (isObject(node) && 'type' in node && node.type == 'MethodDefinition') { - util.inspect.defaultOptions.depth = 2 - pp({methodDefn: node}) - } - if (isObject(node) && 'type' in node && node.type == 'ObjectProperty') { - util.inspect.defaultOptions.depth = 2 - pp({objProp: node}) - } - if (isObject(node) && 'type' in node && node.type == 'ObjectMethod') { - util.inspect.defaultOptions.depth = 2 - pp({objMethod: node}) - } - if (isObject(node) && 'type' in node && node.type == 'ObjectExpression') { - util.inspect.defaultOptions.depth = 5 - pp({objExpr: node}) - } - if (isObject(node) && 'type' in node && node.type == 'Property') { - util.inspect.defaultOptions.depth = 5 - pp({property: node}) - } - */ - // context = node as any - function has_key(x: any): x is {key: babel.Identifier} { - return isObject(x) && 'key' in x && babel.isIdentifier((x as any).key) - } - function has_id(x: any): x is {id: babel.Identifier} { - return isObject(x) && 'id' in x && babel.isIdentifier((x as any).id) - } - if (babel.isVariableDeclaration(node)) { - const ds = node.declarations - if (ds.length == 1) { - const d = ds[0] - if (has_id(d)) { - context = d.id.name - } - } - } else if (has_id(node)) { - context = node.id.name - } else if (has_key(node)) { - context = node.key.name - } - if (isObject(node)) { - function add_comments(s: string) { - if (s in node && Array.isArray(node[s])) { - (node[s] as any[]).forEach(c => { - if ('type' in c) { - if (c.type == 'CommentBlock' || c.type == 'CommentLine') { - add_comment(c, context) - if (context == null) { - // pp({c, node}) - } - } - } - }) - } - } - if (isObject(node)) { - add_comments('leadingComments') - add_comments('innerComments') - // add_comments('trailingComments') - } - } - }) - - return out -} - -function isObject(x: any): x is object { - return x !== null && typeof x === 'object' && !Array.isArray(x) -} - -function traverse(x: any, f: (x: any) => void): void { - f(x) - if (Array.isArray(x)) { - x.map(y => traverse(y, f)) - } - if (isObject(x)) { - for (const k in x) { - traverse((x as any)[k], f) - } - } - -} - -false && pp(Comments(`/** test */ function f(x: string): number { return 1 } - -class Apa { - /** something something */ - - /** attached to nothing! */ - - /** returns important stuff - - j(5) // => 6 - - j(9) // => 10 - */ - j(x: number) { - /** important stuff */ - return x + 1 - } -} - -interface B { - /** x docstring */ - x: 1 -} - -/** u docstring */ -const u = { - /** ux docstring */ - ux: 1 -} -`)) - -function script(filename: string, s: string): string[] { - return [] - /* - const pwoc = ts.createPrinter({removeComments: true}) - const f = ts.createSourceFile('_doctest_' + filename, s, ts.ScriptTarget.ES5, true, ts.ScriptKind.TS) - const out = - f.statements.map( - (now, i) => { - if (ts.isExpressionStatement(now)) { - const next = f.statements[i+1] // zip with next - const [a, z] = next ? [next.pos, next.end] : [now.end, f.end] - const after = f.text.slice(a, z) - const m = doctest_rhs(after) - if (m && m[1]) { - const lhs = pwoc.printNode(ts.EmitHint.Expression, now.expression, f) - const rhs = m[1].trim() - return 't.deepEqual(' + lhs + ', ' + rhs + ', ' + JSON.stringify(rhs) + ')' - } - } - return pwoc.printNode(ts.EmitHint.Unspecified, now, f) - }) - return out - */ -} - -/* -const filename = 'unk.ts' - -r.comments.map(d => { - d.value.split(/\n\n+/m).map(s => { - let tests = 0 - if (is_doctest(s)) { - // todo: typecheck s now - const name = 'unk' - console.log( - 'test(' + JSON.stringify(name + ' ' + ++tests) + ', t => {', - ...script(filename, s).map(l => ' ' + l), - '})', - '' - ) - } - }) -}) - -pp(r.program) -pp(r.comments) -*/ - - -/* - - -function script(filename: string, s: string): string[] { - const pwoc = ts.createPrinter({removeComments: true}) - const f = ts.createSourceFile('_doctest_' + filename, s, ts.ScriptTarget.ES5, true, ts.ScriptKind.TS) - const out = - f.statements.map( - (now, i) => { - if (ts.isExpressionStatement(now)) { - const next = f.statements[i+1] // zip with next - const [a, z] = next ? [next.pos, next.end] : [now.end, f.end] - const after = f.text.slice(a, z) - const m = doctest_rhs(after) - if (m && m[1]) { - const lhs = pwoc.printNode(ts.EmitHint.Expression, now.expression, f) - const rhs = m[1].trim() - return 't.deepEqual(' + lhs + ', ' + rhs + ', ' + JSON.stringify(rhs) + ')' - } - } - return pwoc.printNode(ts.EmitHint.Unspecified, now, f) - }) - return out -} - -function test_script_one(filename: string, d: Def): string[] { - const out = [] as string[] - let tests = 0 - d.doc.split(/\n\n+/m).map(s => { - if (is_doctest(s)) { - // todo: typecheck s now - out.push( - 'test(' + JSON.stringify(d.name + ' ' + ++tests) + ', t => {', - ...script(filename, s).map(l => ' ' + l), - '})', - '' - ) - } - }) - return out -} - -function test_script(top: Top) { - return ["import {test} from 'ava'"].concat(...top.map( - ({filename, defs}) => walk(defs, (d) => test_script_one(filename, d))) - ) -} - - -function prettyKind(kind: string) { - return kind.replace('Declaration', '').toLowerCase() -} - -function toc_one(def: Def, i: number): string[] { - if (def.exported || i > 0) { - return [ - replicate(i, ' ').join('') + - '* ' + - (def.children.length == 0 ? '' : (prettyKind(def.kind) + ' ')) + - def.name - ] - } else { - return [] - } -} - -function toc(top: Top): string[] { - return flatten(top.map(({defs}) => walk(defs, toc_one))) -} - -function doc_one(def: Def, i: number): string[] { - const out = [] as string[] - if (def.exported || i > 0) { - let indent = '' - if (def.children.length == 0) { - //const method = (def.kind == 'MethodDeclaration') ? 'method ' : '' - out.push('* ' + '**' + def.name + '**: `' + def.type + '`') - indent = ' ' - } else { - out.push('### ' + prettyKind(def.kind) + ' ' + def.name) - } - def.doc.split(/\n\n+/).forEach(s => { - out.push('') - if (is_doctest(s)) { - out.push(indent + '```typescript') - } - const lines = s.split('\n') - lines.forEach(line => out.push(indent + line)) - if (is_doctest(s)) { - out.push(indent + '```') - } - }) - } - return out -} - -function doc(top: Top) { - return flatten(top.map(({defs}) => walk(defs, doc_one))) -} - -const filenames = [] as string[] -const argv = process.argv.slice(2) -const outputs = [] as ((top: Top) => string[])[] - -{ - let program: ts.Program - let verbose = false - for (let i = 0; i < argv.length; i++) { - const arg = argv[i] - if (arg == '-t' || arg == '--test-script') { - outputs.push(test_script) - } else if (arg == '-d' || arg == '--doc') { - outputs.push(doc) - } else if (arg == '--toc' || arg == '--toc') { - outputs.push(toc) - } else if (arg == '-i' || arg == '--include') { - outputs.push(_top => [fs.readFileSync(argv[++i]).toString()]) - } else if (arg == '-s' || arg == '--string') { - outputs.push(_top => [argv[++i]]) - } else { - filenames.push(arg) - } - } - - if (outputs.length == 0) { - console.log(`typescript-doctests <args> - Each entry in <args> may be: - [-t|--test-script] // write tape test script on stdout - [-d|--doc] // write markdown api documentation on stdout - [--toc] // write markdown table of contents on stdout - [-i|--include] FILENAME // write the contents of a file on stdout - [-s|--string] STRING // write a string literally on stdout - FILENAME // typescript files to look for docstrings in - - Example usages: - - typescript-doctests src/*.ts -s 'import * as App from "../src/App"' -t > test/App.doctest.ts - - typescript-doctests src/*.ts -i Header.md --toc --doc -i Footer.md > README.md - `) - process.exit(1) - } else { - program = ts.createProgram(filenames, { - target: ts.ScriptTarget.ES5, - module: ts.ModuleKind.CommonJS - }) - const top = generateDocumentation(program, filenames) - - outputs.forEach(m => m(top).forEach(line => console.log(line))) - } -} - - -*/ diff --git a/unused-test-files/visitor_test.ts b/unused-test-files/visitor_test.ts deleted file mode 100644 index c73155b..0000000 --- a/unused-test-files/visitor_test.ts +++ /dev/null @@ -1,46 +0,0 @@ -import * as ts from 'typescript' - -const pwoc = ts.createPrinter({removeComments: true}) - -function script(s: string): string { - const f = ts.createSourceFile('test.ts', s, ts.ScriptTarget.ES5, true, ts.ScriptKind.TS) - const out = - f.statements.map( - (now, i) => { - if (ts.isExpressionStatement(now)) { - const next = f.statements[i+1] // zip with next - const [a, z] = next ? [next.pos, next.end] : [now.end, f.end] - const after = f.text.slice(a, z) - const m = after.match(/^\s*\/\/[ \t]*=>([^\n]*)/m) - if (m && m[1]) { - const lhs = pwoc.printNode(ts.EmitHint.Expression, now.expression, f) - const rhs = m[1].trim() - return 'assert.deepEqual(' + lhs + ', ' + rhs + ', ' + JSON.stringify(rhs) + ')' - } - } - return pwoc.printNode(ts.EmitHint.Unspecified, now, f) - }) - return out.join('\n') -} - -const s = ` - const a = 1 - a - // one more - // => 1 - let b = 2 - a + 1 // => 2 - // that's all - a + b - // that's all - // => 3 - function apa(bepa) { - return 1 - } - a++ - b++ - // hehe // => 5 - a // => 4 -` - -console.log(script(s)) diff --git a/yarn.lock b/yarn.lock index fcddfdf..a4151b3 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2,6 +2,11 @@ # yarn lockfile v1 +"@types/chai@^4.3.0": + "integrity" "sha512-/ceqdqeRraGolFTcfoXNiqjyQhZzbINDngeoAq9GoHa8PPK1yNzTaxWjA6BFWp5Ua9JpXEMSS4s5i9tS0hOJtw==" + "resolved" "https://registry.npmjs.org/@types/chai/-/chai-4.3.0.tgz" + "version" "4.3.0" + "@types/chokidar@^1.7.5": "integrity" "sha512-PDkSRY7KltW3M60hSBlerxI8SFPXsO3AL/aRVsO4Kh9IHRW74Ih75gUuTd/aE4LSSFqypb10UIX3QzOJwBQMGQ==" "resolved" "https://registry.npmjs.org/@types/chokidar/-/chokidar-1.7.5.tgz" @@ -20,6 +25,11 @@ "resolved" "https://registry.npmjs.org/@types/minimist/-/minimist-1.2.0.tgz" "version" "1.2.0" +"@types/mocha@^9.1.0": + "integrity" "sha512-QCWHkbMv4Y5U9oW10Uxbr45qMMSzl4OzijsozynUAgx3kEHUdXB00udx2dWDQ7f2TU2a2uuiFaRZjCe3unPpeg==" + "resolved" "https://registry.npmjs.org/@types/mocha/-/mocha-9.1.0.tgz" + "version" "9.1.0" + "@types/node@*", "@types/node@^9.4.6": "integrity" "sha512-5lhC7QM2J3b/+epdwaNfRuG2peN4c9EX+mkd27+SqLKhJSdswHTZvc4aZLBZChi+Wo32+E1DeMZs0fSpu/uBXQ==" "resolved" "https://registry.npmjs.org/@types/node/-/node-9.6.51.tgz" @@ -32,11 +42,26 @@ dependencies: "@types/node" "*" +"@ungap/promise-all-settled@1.1.2": + "integrity" "sha512-sL/cEvJWAnClXw0wHk85/2L0G6Sj8UB0Ctc1TEMbKSsmpRosqhwj9gWgFRZSrBr2f9tiXISwNhCPmlfqUqyb9Q==" + "resolved" "https://registry.npmjs.org/@ungap/promise-all-settled/-/promise-all-settled-1.1.2.tgz" + "version" "1.1.2" + +"ansi-colors@4.1.1": + "integrity" "sha512-JoX0apGbHaUJBNl6yF+p6JAFYZ666/hhCGKN5t9QFjbJQKUU/g8MNbFDbvfrgKXvI1QpZplPOnwIo99lX/AAmA==" + "resolved" "https://registry.npmjs.org/ansi-colors/-/ansi-colors-4.1.1.tgz" + "version" "4.1.1" + "ansi-regex@^2.0.0": "integrity" "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=" "resolved" "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz" "version" "2.1.1" +"ansi-regex@^5.0.1": + "integrity" "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==" + "resolved" "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz" + "version" "5.0.1" + "ansi-styles@^2.2.1": "integrity" "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" "resolved" "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz" @@ -49,13 +74,27 @@ dependencies: "color-convert" "^1.9.0" -"anymatch@^2.0.0": - "integrity" "sha512-5teOsQWABXHHBFP9y3skS5P3d/WfWXpv3FUpy+LorMrNYaT9pI4oLMQX7jzQ2KklNpGpWHzdCXTDT2Y3XGlZBw==" - "resolved" "https://registry.npmjs.org/anymatch/-/anymatch-2.0.0.tgz" - "version" "2.0.0" +"ansi-styles@^4.0.0": + "integrity" "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==" + "resolved" "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz" + "version" "4.3.0" dependencies: - "micromatch" "^3.1.4" - "normalize-path" "^2.1.1" + "color-convert" "^2.0.1" + +"ansi-styles@^4.1.0": + "integrity" "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==" + "resolved" "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz" + "version" "4.3.0" + dependencies: + "color-convert" "^2.0.1" + +"anymatch@~3.1.2": + "integrity" "sha512-P43ePfOAIupkguHUycrc4qJ9kz8ZiuOUijaETwX7THt0Y/GNK7v0aa8rY816xWjZ7rJdA5XdMcpVFTKMq+RvWg==" + "resolved" "https://registry.npmjs.org/anymatch/-/anymatch-3.1.2.tgz" + "version" "3.1.2" + dependencies: + "normalize-path" "^3.0.0" + "picomatch" "^2.0.4" "argparse@^1.0.7": "integrity" "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==" @@ -64,68 +103,30 @@ dependencies: "sprintf-js" "~1.0.2" -"arr-diff@^4.0.0": - "integrity" "sha1-1kYQdP6/7HHn4VI1dhoyml3HxSA=" - "resolved" "https://registry.npmjs.org/arr-diff/-/arr-diff-4.0.0.tgz" - "version" "4.0.0" - -"arr-flatten@^1.1.0": - "integrity" "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==" - "resolved" "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz" - "version" "1.1.0" - -"arr-union@^3.1.0": - "integrity" "sha1-45sJrqne+Gao8gbiiK9jkZuuOcQ=" - "resolved" "https://registry.npmjs.org/arr-union/-/arr-union-3.1.0.tgz" - "version" "3.1.0" - -"array-unique@^0.3.2": - "integrity" "sha1-qJS3XUvE9s1nnvMkSp/Y9Gri1Cg=" - "resolved" "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz" - "version" "0.3.2" +"argparse@^2.0.1": + "integrity" "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==" + "resolved" "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz" + "version" "2.0.1" "arrify@^1.0.0": "integrity" "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=" "resolved" "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz" "version" "1.0.1" -"assign-symbols@^1.0.0": - "integrity" "sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c=" - "resolved" "https://registry.npmjs.org/assign-symbols/-/assign-symbols-1.0.0.tgz" - "version" "1.0.0" - -"async-each@^1.0.1": - "integrity" "sha512-z/WhQ5FPySLdvREByI2vZiTWwCnF0moMJ1hK9YQwDTHKh6I7/uSckMetoRGb5UBZPC1z0jlw+n/XCgjeH7y1AQ==" - "resolved" "https://registry.npmjs.org/async-each/-/async-each-1.0.3.tgz" - "version" "1.0.3" - -"atob@^2.1.1": - "integrity" "sha512-Wm6ukoaOGJi/73p/cl2GvLjTI5JM1k/O14isD73YML8StrH/7/lRFgmg8nICZgD3bZZvjwCGxtMOD3wWNAu8cg==" - "resolved" "https://registry.npmjs.org/atob/-/atob-2.1.2.tgz" - "version" "2.1.2" +"assertion-error@^1.1.0": + "integrity" "sha512-jgsaNduz+ndvGyFt3uSuWqvy4lCnIJiovtouQN5JZHOKCS2QuhEdbcQHFhVksz2N2U9hXJo8odG7ETyWlEeuDw==" + "resolved" "https://registry.npmjs.org/assertion-error/-/assertion-error-1.1.0.tgz" + "version" "1.1.0" "balanced-match@^1.0.0": "integrity" "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" "resolved" "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz" "version" "1.0.0" -"base@^0.11.1": - "integrity" "sha512-5T6P4xPgpp0YDFvSWwEZ4NoE3aM4QBQXDzmVbraCkFj8zHM+mba8SyqB5DbZWyR7mYHo6Y7BdQo3MoA4m0TeQg==" - "resolved" "https://registry.npmjs.org/base/-/base-0.11.2.tgz" - "version" "0.11.2" - dependencies: - "cache-base" "^1.0.1" - "class-utils" "^0.3.5" - "component-emitter" "^1.2.1" - "define-property" "^1.0.0" - "isobject" "^3.0.1" - "mixin-deep" "^1.2.0" - "pascalcase" "^0.1.1" - -"binary-extensions@^1.0.0": - "integrity" "sha512-Un7MIEDdUC5gNpcGDV97op1Ywk748MpHcFTHoYs6qnj1Z3j7I53VG3nwZhKzoBZmbdRNnb6WRdFlwl7tSDuZGw==" - "resolved" "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.13.1.tgz" - "version" "1.13.1" +"binary-extensions@^2.0.0": + "integrity" "sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==" + "resolved" "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.2.0.tgz" + "version" "2.2.0" "brace-expansion@^1.1.7": "integrity" "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==" @@ -135,41 +136,40 @@ "balanced-match" "^1.0.0" "concat-map" "0.0.1" -"braces@^2.3.1", "braces@^2.3.2": - "integrity" "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==" - "resolved" "https://registry.npmjs.org/braces/-/braces-2.3.2.tgz" - "version" "2.3.2" +"braces@~3.0.2": + "integrity" "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==" + "resolved" "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz" + "version" "3.0.2" dependencies: - "arr-flatten" "^1.1.0" - "array-unique" "^0.3.2" - "extend-shallow" "^2.0.1" - "fill-range" "^4.0.0" - "isobject" "^3.0.1" - "repeat-element" "^1.1.2" - "snapdragon" "^0.8.1" - "snapdragon-node" "^2.0.1" - "split-string" "^3.0.2" - "to-regex" "^3.0.1" + "fill-range" "^7.0.1" + +"browser-stdout@1.3.1": + "integrity" "sha512-qhAVI1+Av2X7qelOfAIYwXONood6XlZE/fXaBSmW/T5SzLAmCgzi+eiWE7fUvbHaeNBQH13UftjpXxsfLkMpgw==" + "resolved" "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.1.tgz" + "version" "1.3.1" "buffer-from@^1.0.0": "integrity" "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==" "resolved" "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz" "version" "1.1.1" -"cache-base@^1.0.1": - "integrity" "sha512-AKcdTnFSWATd5/GCPRxr2ChwIJ85CeyrEyjRHlKxQ56d4XJMGym0uAiKn0xbLOGOl3+yRpOTi484dVCEc5AUzQ==" - "resolved" "https://registry.npmjs.org/cache-base/-/cache-base-1.0.1.tgz" - "version" "1.0.1" +"camelcase@^6.0.0": + "integrity" "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==" + "resolved" "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz" + "version" "6.3.0" + +"chai@^4.3.6": + "integrity" "sha512-bbcp3YfHCUzMOvKqsztczerVgBKSsEijCySNlHHbX3VG1nskvqjz5Rfso1gGwD6w6oOV3eI60pKuMOV5MV7p3Q==" + "resolved" "https://registry.npmjs.org/chai/-/chai-4.3.6.tgz" + "version" "4.3.6" dependencies: - "collection-visit" "^1.0.0" - "component-emitter" "^1.2.1" - "get-value" "^2.0.6" - "has-value" "^1.0.0" - "isobject" "^3.0.1" - "set-value" "^2.0.0" - "to-object-path" "^0.3.0" - "union-value" "^1.0.0" - "unset-value" "^1.0.0" + "assertion-error" "^1.1.0" + "check-error" "^1.0.2" + "deep-eql" "^3.0.1" + "get-func-name" "^2.0.0" + "loupe" "^2.3.1" + "pathval" "^1.1.1" + "type-detect" "^4.0.5" "chalk@^1.1.1": "integrity" "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=" @@ -191,42 +191,42 @@ "escape-string-regexp" "^1.0.5" "supports-color" "^5.3.0" -"chokidar@^2.0.1": - "integrity" "sha512-ZmZUazfOzf0Nve7duiCKD23PFSCs4JPoYyccjUFF3aQkQadqBhfzhjkwBH2mNOG9cTBwhamM37EIsIkZw3nRgg==" - "resolved" "https://registry.npmjs.org/chokidar/-/chokidar-2.1.8.tgz" - "version" "2.1.8" +"chalk@^4.1.0": + "integrity" "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==" + "resolved" "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz" + "version" "4.1.2" dependencies: - "anymatch" "^2.0.0" - "async-each" "^1.0.1" - "braces" "^2.3.2" - "glob-parent" "^3.1.0" - "inherits" "^2.0.3" - "is-binary-path" "^1.0.0" - "is-glob" "^4.0.0" - "normalize-path" "^3.0.0" - "path-is-absolute" "^1.0.0" - "readdirp" "^2.2.1" - "upath" "^1.1.1" + "ansi-styles" "^4.1.0" + "supports-color" "^7.1.0" + +"check-error@^1.0.2": + "integrity" "sha1-V00xLt2Iu13YkS6Sht1sCu1KrII=" + "resolved" "https://registry.npmjs.org/check-error/-/check-error-1.0.2.tgz" + "version" "1.0.2" + +"chokidar@3.5.3": + "integrity" "sha512-Dr3sfKRP6oTcjf2JmUmFJfeVMvXBdegxB0iVQ5eb2V10uFJUCAS8OByZdVAyVb8xXNz3GjjTgj9kLWsZTqE6kw==" + "resolved" "https://registry.npmjs.org/chokidar/-/chokidar-3.5.3.tgz" + "version" "3.5.3" + dependencies: + "anymatch" "~3.1.2" + "braces" "~3.0.2" + "glob-parent" "~5.1.2" + "is-binary-path" "~2.1.0" + "is-glob" "~4.0.1" + "normalize-path" "~3.0.0" + "readdirp" "~3.6.0" optionalDependencies: - "fsevents" "^1.2.7" + "fsevents" "~2.3.2" -"class-utils@^0.3.5": - "integrity" "sha512-qOhPa/Fj7s6TY8H8esGu5QNpMMQxz79h+urzrNYN6mn+9BnxlDGf5QZ+XeCDsxSjPqsSR56XOZOJmpeurnLMeg==" - "resolved" "https://registry.npmjs.org/class-utils/-/class-utils-0.3.6.tgz" - "version" "0.3.6" +"cliui@^7.0.2": + "integrity" "sha512-OcRE68cOsVMXp1Yvonl/fzkQOyjLSu/8bhPDfQt0e0/Eb283TKP20Fs2MqoPsr9SwA595rRCA+QMzYc9nBP+JQ==" + "resolved" "https://registry.npmjs.org/cliui/-/cliui-7.0.4.tgz" + "version" "7.0.4" dependencies: - "arr-union" "^3.1.0" - "define-property" "^0.2.5" - "isobject" "^3.0.0" - "static-extend" "^0.1.1" - -"collection-visit@^1.0.0": - "integrity" "sha1-S8A3PBZLwykbTTaMgpzxqApZ3KA=" - "resolved" "https://registry.npmjs.org/collection-visit/-/collection-visit-1.0.0.tgz" - "version" "1.0.0" - dependencies: - "map-visit" "^1.0.0" - "object-visit" "^1.0.0" + "string-width" "^4.2.0" + "strip-ansi" "^6.0.0" + "wrap-ansi" "^7.0.0" "color-convert@^1.9.0": "integrity" "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==" @@ -235,42 +235,51 @@ dependencies: "color-name" "1.1.3" +"color-convert@^2.0.1": + "integrity" "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==" + "resolved" "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz" + "version" "2.0.1" + dependencies: + "color-name" "~1.1.4" + +"color-name@~1.1.4": + "integrity" "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" + "resolved" "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz" + "version" "1.1.4" + "color-name@1.1.3": "integrity" "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=" "resolved" "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz" "version" "1.1.3" -"component-emitter@^1.2.1": - "integrity" "sha512-Rd3se6QB+sO1TwqZjscQrurpEPIfO0/yYnSin6Q/rD3mOutHvUrCAhJub3r90uNb+SESBuE0QYoB90YdfatsRg==" - "resolved" "https://registry.npmjs.org/component-emitter/-/component-emitter-1.3.0.tgz" - "version" "1.3.0" - "concat-map@0.0.1": "integrity" "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" "resolved" "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz" "version" "0.0.1" -"copy-descriptor@^0.1.0": - "integrity" "sha1-Z29us8OZl8LuGsOpJP1hJHSPV40=" - "resolved" "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz" - "version" "0.1.1" - "core-util-is@~1.0.0": "integrity" "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" "resolved" "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz" "version" "1.0.2" -"debug@^2.2.0", "debug@^2.3.3": - "integrity" "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==" - "resolved" "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz" - "version" "2.6.9" +"debug@4.3.3": + "integrity" "sha512-/zxw5+vh1Tfv+4Qn7a5nsbcJKPaSvCDhojn6FEl9vupwK2VCSDtEiEtqr8DFtzYFOdz63LBkxec7DYuc2jon6Q==" + "resolved" "https://registry.npmjs.org/debug/-/debug-4.3.3.tgz" + "version" "4.3.3" dependencies: - "ms" "2.0.0" + "ms" "2.1.2" -"decode-uri-component@^0.2.0": - "integrity" "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=" - "resolved" "https://registry.npmjs.org/decode-uri-component/-/decode-uri-component-0.2.0.tgz" - "version" "0.2.0" +"decamelize@^4.0.0": + "integrity" "sha512-9iE1PgSik9HeIIw2JO94IidnE3eBoQrFJ3w7sFuzSX4DpmZ3v5sZpUiV5Swcf6mQEF+Y0ru8Neo+p+nyh2J+hQ==" + "resolved" "https://registry.npmjs.org/decamelize/-/decamelize-4.0.0.tgz" + "version" "4.0.0" + +"deep-eql@^3.0.1": + "integrity" "sha512-+QeIQyN5ZuO+3Uk5DYh6/1eKO0m0YmJFGNmFHGACpf1ClL1nmlV/p4gNgbl2pJGxgXb4faqo6UE+M5ACEMyVcw==" + "resolved" "https://registry.npmjs.org/deep-eql/-/deep-eql-3.0.1.tgz" + "version" "3.0.1" + dependencies: + "type-detect" "^4.0.0" "deep-equal@~0.1.0": "integrity" "sha1-skbCuApXCkfBG+HZvRBw7IeLh84=" @@ -289,28 +298,6 @@ dependencies: "object-keys" "^1.0.12" -"define-property@^0.2.5": - "integrity" "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=" - "resolved" "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz" - "version" "0.2.5" - dependencies: - "is-descriptor" "^0.1.0" - -"define-property@^1.0.0": - "integrity" "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=" - "resolved" "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz" - "version" "1.0.0" - dependencies: - "is-descriptor" "^1.0.0" - -"define-property@^2.0.2": - "integrity" "sha512-jwK2UV4cnPpbcG7+VRARKTZPUWowwXA8bzH5NP6ud0oeAxyYPuGZUAC7hMugpCdz4BeSZl2Dl9k66CHJ/46ZYQ==" - "resolved" "https://registry.npmjs.org/define-property/-/define-property-2.0.2.tgz" - "version" "2.0.2" - dependencies: - "is-descriptor" "^1.0.2" - "isobject" "^3.0.1" - "defined@~0.0.0", "defined@0.0.0": "integrity" "sha1-817qfXBekzuvE7LwOz+D2SFAOz4=" "resolved" "https://registry.npmjs.org/defined/-/defined-0.0.0.tgz" @@ -331,6 +318,11 @@ "resolved" "https://registry.npmjs.org/diff/-/diff-3.5.0.tgz" "version" "3.5.0" +"diff@5.0.0": + "integrity" "sha512-/VTCrvm5Z0JGty/BWHljh+BAiw3IK+2j87NGMu8Nwc/f48WoDAC395uomO9ZD117ZOBaHmkX1oyLvkVM/aIT3w==" + "resolved" "https://registry.npmjs.org/diff/-/diff-5.0.0.tgz" + "version" "5.0.0" + "dom-walk@^0.1.0": "integrity" "sha1-ZyIm3HTI95mtNTB9+TaroRrNYBg=" "resolved" "https://registry.npmjs.org/dom-walk/-/dom-walk-0.1.1.tgz" @@ -341,6 +333,11 @@ "resolved" "https://registry.npmjs.org/duplexer/-/duplexer-0.1.1.tgz" "version" "0.1.1" +"emoji-regex@^8.0.0": + "integrity" "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==" + "resolved" "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz" + "version" "8.0.0" + "es-abstract@^1.5.0": "integrity" "sha512-vDZfg/ykNxQVwup/8E1BZhVzFfBxs9NqMzGcvIJrqg5k2/5Za2bWo40dK2J1pgLngZ7c+Shh8lwYtLGyrwPutg==" "resolved" "https://registry.npmjs.org/es-abstract/-/es-abstract-1.13.0.tgz" @@ -362,11 +359,21 @@ "is-date-object" "^1.0.1" "is-symbol" "^1.0.2" +"escalade@^3.1.1": + "integrity" "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==" + "resolved" "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz" + "version" "3.1.1" + "escape-string-regexp@^1.0.2", "escape-string-regexp@^1.0.5": "integrity" "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=" "resolved" "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz" "version" "1.0.5" +"escape-string-regexp@4.0.0": + "integrity" "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==" + "resolved" "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz" + "version" "4.0.0" + "esprima@^4.0.0": "integrity" "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==" "resolved" "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz" @@ -377,56 +384,6 @@ "resolved" "https://registry.npmjs.org/events-to-array/-/events-to-array-1.1.2.tgz" "version" "1.1.2" -"expand-brackets@^2.1.4": - "integrity" "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=" - "resolved" "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz" - "version" "2.1.4" - dependencies: - "debug" "^2.3.3" - "define-property" "^0.2.5" - "extend-shallow" "^2.0.1" - "posix-character-classes" "^0.1.0" - "regex-not" "^1.0.0" - "snapdragon" "^0.8.1" - "to-regex" "^3.0.1" - -"extend-shallow@^2.0.1": - "integrity" "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=" - "resolved" "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz" - "version" "2.0.1" - dependencies: - "is-extendable" "^0.1.0" - -"extend-shallow@^3.0.0": - "integrity" "sha1-Jqcarwc7OfshJxcnRhMcJwQCjbg=" - "resolved" "https://registry.npmjs.org/extend-shallow/-/extend-shallow-3.0.2.tgz" - "version" "3.0.2" - dependencies: - "assign-symbols" "^1.0.0" - "is-extendable" "^1.0.1" - -"extend-shallow@^3.0.2": - "integrity" "sha1-Jqcarwc7OfshJxcnRhMcJwQCjbg=" - "resolved" "https://registry.npmjs.org/extend-shallow/-/extend-shallow-3.0.2.tgz" - "version" "3.0.2" - dependencies: - "assign-symbols" "^1.0.0" - "is-extendable" "^1.0.1" - -"extglob@^2.0.4": - "integrity" "sha512-Nmb6QXkELsuBr24CJSkilo6UHHgbekK5UiZgfE6UHD3Eb27YC6oD+bhcT+tJ6cl8dmsgdQxnWlcry8ksBIBLpw==" - "resolved" "https://registry.npmjs.org/extglob/-/extglob-2.0.4.tgz" - "version" "2.0.4" - dependencies: - "array-unique" "^0.3.2" - "define-property" "^1.0.0" - "expand-brackets" "^2.1.4" - "extend-shallow" "^2.0.1" - "fragment-cache" "^0.2.1" - "regex-not" "^1.0.0" - "snapdragon" "^0.8.1" - "to-regex" "^3.0.1" - "faucet@^0.0.1": "integrity" "sha1-WX3PHSGJosBiMhtZHo8VHtIDnZw=" "resolved" "https://registry.npmjs.org/faucet/-/faucet-0.0.1.tgz" @@ -448,15 +405,25 @@ "escape-string-regexp" "^1.0.5" "object-assign" "^4.1.0" -"fill-range@^4.0.0": - "integrity" "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=" - "resolved" "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz" - "version" "4.0.0" +"fill-range@^7.0.1": + "integrity" "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==" + "resolved" "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz" + "version" "7.0.1" dependencies: - "extend-shallow" "^2.0.1" - "is-number" "^3.0.0" - "repeat-string" "^1.6.1" - "to-regex-range" "^2.1.0" + "to-regex-range" "^5.0.1" + +"find-up@5.0.0": + "integrity" "sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==" + "resolved" "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz" + "version" "5.0.0" + dependencies: + "locate-path" "^6.0.0" + "path-exists" "^4.0.0" + +"flat@^5.0.2": + "integrity" "sha512-b6suED+5/3rTpUBdG1gupIl8MPFCAMA0QXwmljLhvCUKcUvdE4gWky9zpuGCcXHOsz4J9wPGNWq6OKpmIzz3hQ==" + "resolved" "https://registry.npmjs.org/flat/-/flat-5.0.2.tgz" + "version" "5.0.2" "for-each@~0.3.3": "integrity" "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==" @@ -465,18 +432,6 @@ dependencies: "is-callable" "^1.1.3" -"for-in@^1.0.2": - "integrity" "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=" - "resolved" "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz" - "version" "1.0.2" - -"fragment-cache@^0.2.1": - "integrity" "sha1-QpD60n8T6Jvn8zeZxrxaCr//DRk=" - "resolved" "https://registry.npmjs.org/fragment-cache/-/fragment-cache-0.2.1.tgz" - "version" "0.2.1" - dependencies: - "map-cache" "^0.2.2" - "fs.realpath@^1.0.0": "integrity" "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" "resolved" "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz" @@ -487,18 +442,22 @@ "resolved" "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz" "version" "1.1.1" -"get-value@^2.0.3", "get-value@^2.0.6": - "integrity" "sha1-3BXKHGcjh8p2vTesCjlbogQqLCg=" - "resolved" "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz" - "version" "2.0.6" +"get-caller-file@^2.0.5": + "integrity" "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==" + "resolved" "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz" + "version" "2.0.5" -"glob-parent@^3.1.0": - "integrity" "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=" - "resolved" "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz" - "version" "3.1.0" +"get-func-name@^2.0.0": + "integrity" "sha1-6td0q+5y4gQJQzoGY2YCPdaIekE=" + "resolved" "https://registry.npmjs.org/get-func-name/-/get-func-name-2.0.0.tgz" + "version" "2.0.0" + +"glob-parent@~5.1.2": + "integrity" "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==" + "resolved" "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz" + "version" "5.1.2" dependencies: - "is-glob" "^3.1.0" - "path-dirname" "^1.0.0" + "is-glob" "^4.0.1" "glob@~7.1.4": "integrity" "sha512-hkLPepehmnKk41pUGm3sYxoFs/umurYfYJCerbXEyFIWcAzvpipAgVkBqqT9RBKMGjnq6kMuyYwha6csxbiM1A==" @@ -512,6 +471,18 @@ "once" "^1.3.0" "path-is-absolute" "^1.0.0" +"glob@7.2.0": + "integrity" "sha512-lmLf6gtyrPq8tTjSmrO94wBeQbFR3HbLHbuyD69wuyQkImp2hWqMGB47OX65FBkPffO641IP9jWa1z4ivqG26Q==" + "resolved" "https://registry.npmjs.org/glob/-/glob-7.2.0.tgz" + "version" "7.2.0" + dependencies: + "fs.realpath" "^1.0.0" + "inflight" "^1.0.4" + "inherits" "2" + "minimatch" "^3.0.4" + "once" "^1.3.0" + "path-is-absolute" "^1.0.0" + "global@^4.3.2": "integrity" "sha512-wv/LAoHdRE3BeTGz53FAamhGlPLhlssK45usmGFThIi4XqnBmjKQ16u+RNbP7WvigRZDxUsM0J3gcQ5yicaL0w==" "resolved" "https://registry.npmjs.org/global/-/global-4.4.0.tgz" @@ -520,10 +491,10 @@ "min-document" "^2.19.0" "process" "^0.11.10" -"graceful-fs@^4.1.11": - "integrity" "sha512-IItsdsea19BoLC7ELy13q1iJFNmd7ofZH5+X/pJr90/nRoPEX0DJo1dHDbgtYWOhJhcCgMDTOw84RZ72q6lB+Q==" - "resolved" "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.2.tgz" - "version" "4.2.2" +"growl@1.10.5": + "integrity" "sha512-qBr4OuELkhPenW6goKVXiv47US3clb3/IbuWF9KNKEijAy9oeHxU9IgzjvJhHkUzhaj7rOUD7+YGWqUjLp5oSA==" + "resolved" "https://registry.npmjs.org/growl/-/growl-1.10.5.tgz" + "version" "1.10.5" "has-ansi@^2.0.0": "integrity" "sha1-NPUEnOHs3ysGSa8+8k5F7TVBbZE=" @@ -537,42 +508,16 @@ "resolved" "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz" "version" "3.0.0" +"has-flag@^4.0.0": + "integrity" "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==" + "resolved" "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz" + "version" "4.0.0" + "has-symbols@^1.0.0": "integrity" "sha1-uhqPGvKg/DllD1yFA2dwQSIGO0Q=" "resolved" "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.0.tgz" "version" "1.0.0" -"has-value@^0.3.1": - "integrity" "sha1-ex9YutpiyoJ+wKIHgCVlSEWZXh8=" - "resolved" "https://registry.npmjs.org/has-value/-/has-value-0.3.1.tgz" - "version" "0.3.1" - dependencies: - "get-value" "^2.0.3" - "has-values" "^0.1.4" - "isobject" "^2.0.0" - -"has-value@^1.0.0": - "integrity" "sha1-GLKB2lhbHFxR3vJMkw7SmgvmsXc=" - "resolved" "https://registry.npmjs.org/has-value/-/has-value-1.0.0.tgz" - "version" "1.0.0" - dependencies: - "get-value" "^2.0.6" - "has-values" "^1.0.0" - "isobject" "^3.0.0" - -"has-values@^0.1.4": - "integrity" "sha1-bWHeldkd/Km5oCCJrThL/49it3E=" - "resolved" "https://registry.npmjs.org/has-values/-/has-values-0.1.4.tgz" - "version" "0.1.4" - -"has-values@^1.0.0": - "integrity" "sha1-lbC2P+whRmGab+V/51Yo1aOe/k8=" - "resolved" "https://registry.npmjs.org/has-values/-/has-values-1.0.0.tgz" - "version" "1.0.0" - dependencies: - "is-number" "^3.0.0" - "kind-of" "^4.0.0" - "has@^1.0.1", "has@^1.0.3", "has@~1.0.3": "integrity" "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==" "resolved" "https://registry.npmjs.org/has/-/has-1.0.3.tgz" @@ -580,6 +525,11 @@ dependencies: "function-bind" "^1.1.1" +"he@1.2.0": + "integrity" "sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw==" + "resolved" "https://registry.npmjs.org/he/-/he-1.2.0.tgz" + "version" "1.2.0" + "inflight@^1.0.4": "integrity" "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=" "resolved" "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz" @@ -588,92 +538,29 @@ "once" "^1.3.0" "wrappy" "1" -"inherits@^2.0.3", "inherits@~2.0.1", "inherits@~2.0.3", "inherits@~2.0.4", "inherits@2": +"inherits@~2.0.1", "inherits@~2.0.3", "inherits@~2.0.4", "inherits@2": "integrity" "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==" "resolved" "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz" "version" "2.0.4" -"is-accessor-descriptor@^0.1.6": - "integrity" "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=" - "resolved" "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz" - "version" "0.1.6" +"is-binary-path@~2.1.0": + "integrity" "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==" + "resolved" "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz" + "version" "2.1.0" dependencies: - "kind-of" "^3.0.2" - -"is-accessor-descriptor@^1.0.0": - "integrity" "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==" - "resolved" "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz" - "version" "1.0.0" - dependencies: - "kind-of" "^6.0.0" - -"is-binary-path@^1.0.0": - "integrity" "sha1-dfFmQrSA8YenEcgUFh/TpKdlWJg=" - "resolved" "https://registry.npmjs.org/is-binary-path/-/is-binary-path-1.0.1.tgz" - "version" "1.0.1" - dependencies: - "binary-extensions" "^1.0.0" - -"is-buffer@^1.1.5": - "integrity" "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==" - "resolved" "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz" - "version" "1.1.6" + "binary-extensions" "^2.0.0" "is-callable@^1.1.3", "is-callable@^1.1.4": "integrity" "sha512-r5p9sxJjYnArLjObpjA4xu5EKI3CuKHkJXMhT7kwbpUyIFD1n5PMAsoPvWnvtZiNz7LjkYDRZhd7FlI0eMijEA==" "resolved" "https://registry.npmjs.org/is-callable/-/is-callable-1.1.4.tgz" "version" "1.1.4" -"is-data-descriptor@^0.1.4": - "integrity" "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=" - "resolved" "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz" - "version" "0.1.4" - dependencies: - "kind-of" "^3.0.2" - -"is-data-descriptor@^1.0.0": - "integrity" "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==" - "resolved" "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz" - "version" "1.0.0" - dependencies: - "kind-of" "^6.0.0" - "is-date-object@^1.0.1": "integrity" "sha1-mqIOtq7rv/d/vTPnTKAbM1gdOhY=" "resolved" "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.1.tgz" "version" "1.0.1" -"is-descriptor@^0.1.0": - "integrity" "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==" - "resolved" "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz" - "version" "0.1.6" - dependencies: - "is-accessor-descriptor" "^0.1.6" - "is-data-descriptor" "^0.1.4" - "kind-of" "^5.0.0" - -"is-descriptor@^1.0.0", "is-descriptor@^1.0.2": - "integrity" "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==" - "resolved" "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz" - "version" "1.0.2" - dependencies: - "is-accessor-descriptor" "^1.0.0" - "is-data-descriptor" "^1.0.0" - "kind-of" "^6.0.2" - -"is-extendable@^0.1.0", "is-extendable@^0.1.1": - "integrity" "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=" - "resolved" "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz" - "version" "0.1.1" - -"is-extendable@^1.0.1": - "integrity" "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==" - "resolved" "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz" - "version" "1.0.1" - dependencies: - "is-plain-object" "^2.0.4" - -"is-extglob@^2.1.0", "is-extglob@^2.1.1": +"is-extglob@^2.1.1": "integrity" "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=" "resolved" "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz" "version" "2.1.1" @@ -685,33 +572,27 @@ dependencies: "number-is-nan" "^1.0.0" -"is-glob@^3.1.0": - "integrity" "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=" - "resolved" "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz" - "version" "3.1.0" - dependencies: - "is-extglob" "^2.1.0" +"is-fullwidth-code-point@^3.0.0": + "integrity" "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==" + "resolved" "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz" + "version" "3.0.0" -"is-glob@^4.0.0": - "integrity" "sha512-5G0tKtBTFImOqDnLB2hG6Bp2qcKEFduo4tZu9MT/H6NQv/ghhy30o55ufafxJ/LdH79LLs2Kfrn85TLKyA7BUg==" - "resolved" "https://registry.npmjs.org/is-glob/-/is-glob-4.0.1.tgz" - "version" "4.0.1" +"is-glob@^4.0.1", "is-glob@~4.0.1": + "integrity" "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==" + "resolved" "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz" + "version" "4.0.3" dependencies: "is-extglob" "^2.1.1" -"is-number@^3.0.0": - "integrity" "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=" - "resolved" "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz" - "version" "3.0.0" - dependencies: - "kind-of" "^3.0.2" +"is-number@^7.0.0": + "integrity" "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==" + "resolved" "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz" + "version" "7.0.0" -"is-plain-object@^2.0.3", "is-plain-object@^2.0.4": - "integrity" "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==" - "resolved" "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz" - "version" "2.0.4" - dependencies: - "isobject" "^3.0.1" +"is-plain-obj@^2.1.0": + "integrity" "sha512-YWnfyRwxL/+SsrWYfOpUtz5b3YD+nyfkHvjbcanzk8zgyO4ASD67uVMRt8k5bM4lLMDnXfriRhOpemw+NfT1eA==" + "resolved" "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-2.1.0.tgz" + "version" "2.1.0" "is-regex@^1.0.4": "integrity" "sha1-VRdIm1RwkbCTDglWVM7SXul+lJE=" @@ -727,12 +608,12 @@ dependencies: "has-symbols" "^1.0.0" -"is-windows@^1.0.2": - "integrity" "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==" - "resolved" "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz" - "version" "1.0.2" +"is-unicode-supported@^0.1.0": + "integrity" "sha512-knxG2q4UC3u8stRGyAVJCOdxFmv5DZiRcdlIaAQXAbSfJya+OhopNotLQrstBhququ4ZpuKbDc/8S6mgXgPFPw==" + "resolved" "https://registry.npmjs.org/is-unicode-supported/-/is-unicode-supported-0.1.0.tgz" + "version" "0.1.0" -"isarray@~1.0.0", "isarray@1.0.0": +"isarray@~1.0.0": "integrity" "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" "resolved" "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz" "version" "1.0.0" @@ -742,17 +623,10 @@ "resolved" "https://registry.npmjs.org/isarray/-/isarray-0.0.1.tgz" "version" "0.0.1" -"isobject@^2.0.0": - "integrity" "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=" - "resolved" "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz" - "version" "2.1.0" - dependencies: - "isarray" "1.0.0" - -"isobject@^3.0.0", "isobject@^3.0.1": - "integrity" "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=" - "resolved" "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz" - "version" "3.0.1" +"isexe@^2.0.0": + "integrity" "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=" + "resolved" "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz" + "version" "2.0.0" "js-yaml@^3.2.7": "integrity" "sha512-YfbcO7jXDdyj0DGxYVSlSeQNHbD7XPWvrVWeVUujrQEoZzWJIRrCPoyk6kL6IAjAG2IolMK4T0hNUe0HOUs5Jw==" @@ -762,76 +636,45 @@ "argparse" "^1.0.7" "esprima" "^4.0.0" +"js-yaml@4.1.0": + "integrity" "sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==" + "resolved" "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz" + "version" "4.1.0" + dependencies: + "argparse" "^2.0.1" + "jsonify@~0.0.0": "integrity" "sha1-LHS27kHZPKUbe1qu6PUDYx0lKnM=" "resolved" "https://registry.npmjs.org/jsonify/-/jsonify-0.0.0.tgz" "version" "0.0.0" -"kind-of@^3.0.2", "kind-of@^3.0.3", "kind-of@^3.2.0": - "integrity" "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=" - "resolved" "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz" - "version" "3.2.2" +"locate-path@^6.0.0": + "integrity" "sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==" + "resolved" "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz" + "version" "6.0.0" dependencies: - "is-buffer" "^1.1.5" + "p-locate" "^5.0.0" -"kind-of@^4.0.0": - "integrity" "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=" - "resolved" "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz" - "version" "4.0.0" +"log-symbols@4.1.0": + "integrity" "sha512-8XPvpAA8uyhfteu8pIvQxpJZ7SYYdpUivZpGy6sFsBuKRY/7rQGavedeB8aK+Zkyq6upMFVL/9AW6vOYzfRyLg==" + "resolved" "https://registry.npmjs.org/log-symbols/-/log-symbols-4.1.0.tgz" + "version" "4.1.0" dependencies: - "is-buffer" "^1.1.5" + "chalk" "^4.1.0" + "is-unicode-supported" "^0.1.0" -"kind-of@^5.0.0": - "integrity" "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==" - "resolved" "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz" - "version" "5.1.0" - -"kind-of@^6.0.0": - "integrity" "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==" - "resolved" "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz" - "version" "6.0.2" - -"kind-of@^6.0.2": - "integrity" "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==" - "resolved" "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz" - "version" "6.0.2" +"loupe@^2.3.1": + "integrity" "sha512-OvKfgCC2Ndby6aSTREl5aCCPTNIzlDfQZvZxNUrBrihDhL3xcrYegTblhmEiCrg2kKQz4XsFIaemE5BF4ybSaQ==" + "resolved" "https://registry.npmjs.org/loupe/-/loupe-2.3.4.tgz" + "version" "2.3.4" + dependencies: + "get-func-name" "^2.0.0" "make-error@^1.1.1": "integrity" "sha512-c3sIjNUow0+8swNwVpqoH4YCShKNFkMaw6oH1mNS2haDZQqkeZFlHS3dhoeEbKKmJB4vXpJucU6oH75aDYeE9g==" "resolved" "https://registry.npmjs.org/make-error/-/make-error-1.3.5.tgz" "version" "1.3.5" -"map-cache@^0.2.2": - "integrity" "sha1-wyq9C9ZSXZsFFkW7TyasXcmKDb8=" - "resolved" "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz" - "version" "0.2.2" - -"map-visit@^1.0.0": - "integrity" "sha1-7Nyo8TFE5mDxtb1B8S80edmN+48=" - "resolved" "https://registry.npmjs.org/map-visit/-/map-visit-1.0.0.tgz" - "version" "1.0.0" - dependencies: - "object-visit" "^1.0.0" - -"micromatch@^3.1.10", "micromatch@^3.1.4": - "integrity" "sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg==" - "resolved" "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz" - "version" "3.1.10" - dependencies: - "arr-diff" "^4.0.0" - "array-unique" "^0.3.2" - "braces" "^2.3.1" - "define-property" "^2.0.2" - "extend-shallow" "^3.0.2" - "extglob" "^2.0.4" - "fragment-cache" "^0.2.1" - "kind-of" "^6.0.2" - "nanomatch" "^1.2.9" - "object.pick" "^1.3.0" - "regex-not" "^1.0.0" - "snapdragon" "^0.8.1" - "to-regex" "^3.0.2" - "min-document@^2.19.0": "integrity" "sha1-e9KC4/WELtKVu3SM3Z8f+iyCRoU=" "resolved" "https://registry.npmjs.org/min-document/-/min-document-2.19.0.tgz" @@ -846,6 +689,13 @@ dependencies: "brace-expansion" "^1.1.7" +"minimatch@4.2.1": + "integrity" "sha512-9Uq1ChtSZO+Mxa/CL1eGizn2vRn3MlLgzhT0Iz8zaY8NdvxvB0d5QdPFmCKf7JKA9Lerx5vRrnwO03jsSfGG9g==" + "resolved" "https://registry.npmjs.org/minimatch/-/minimatch-4.2.1.tgz" + "version" "4.2.1" + dependencies: + "brace-expansion" "^1.1.7" + "minimist@^1.2.0", "minimist@~1.2.0": "integrity" "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=" "resolved" "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz" @@ -861,14 +711,6 @@ "resolved" "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz" "version" "0.0.8" -"mixin-deep@^1.2.0": - "integrity" "sha512-WRoDn//mXBiJ1H40rqa3vH0toePwSsGb45iInWlTySa+Uu4k3tYUSxa2v1KqAiLtvlrSzaExqS1gtk96A9zvEA==" - "resolved" "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.2.tgz" - "version" "1.3.2" - dependencies: - "for-in" "^1.0.2" - "is-extendable" "^1.0.1" - "mkdirp@^0.5.1": "integrity" "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=" "resolved" "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz" @@ -876,36 +718,52 @@ dependencies: "minimist" "0.0.8" -"ms@2.0.0": - "integrity" "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - "resolved" "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz" - "version" "2.0.0" - -"nanomatch@^1.2.9": - "integrity" "sha512-fpoe2T0RbHwBTBUOftAfBPaDEi06ufaUai0mE6Yn1kacc3SnTErfb/h+X94VXzI64rKFHYImXSvdwGGCmwOqCA==" - "resolved" "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.13.tgz" - "version" "1.2.13" +"mocha@^9.2.2": + "integrity" "sha512-L6XC3EdwT6YrIk0yXpavvLkn8h+EU+Y5UcCHKECyMbdUIxyMuZj4bX4U9e1nvnvUUvQVsV2VHQr5zLdcUkhW/g==" + "resolved" "https://registry.npmjs.org/mocha/-/mocha-9.2.2.tgz" + "version" "9.2.2" dependencies: - "arr-diff" "^4.0.0" - "array-unique" "^0.3.2" - "define-property" "^2.0.2" - "extend-shallow" "^3.0.2" - "fragment-cache" "^0.2.1" - "is-windows" "^1.0.2" - "kind-of" "^6.0.2" - "object.pick" "^1.3.0" - "regex-not" "^1.0.0" - "snapdragon" "^0.8.1" - "to-regex" "^3.0.1" + "@ungap/promise-all-settled" "1.1.2" + "ansi-colors" "4.1.1" + "browser-stdout" "1.3.1" + "chokidar" "3.5.3" + "debug" "4.3.3" + "diff" "5.0.0" + "escape-string-regexp" "4.0.0" + "find-up" "5.0.0" + "glob" "7.2.0" + "growl" "1.10.5" + "he" "1.2.0" + "js-yaml" "4.1.0" + "log-symbols" "4.1.0" + "minimatch" "4.2.1" + "ms" "2.1.3" + "nanoid" "3.3.1" + "serialize-javascript" "6.0.0" + "strip-json-comments" "3.1.1" + "supports-color" "8.1.1" + "which" "2.0.2" + "workerpool" "6.2.0" + "yargs" "16.2.0" + "yargs-parser" "20.2.4" + "yargs-unparser" "2.0.0" -"normalize-path@^2.1.1": - "integrity" "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=" - "resolved" "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz" - "version" "2.1.1" - dependencies: - "remove-trailing-separator" "^1.0.1" +"ms@2.1.2": + "integrity" "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" + "resolved" "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz" + "version" "2.1.2" -"normalize-path@^3.0.0": +"ms@2.1.3": + "integrity" "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==" + "resolved" "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz" + "version" "2.1.3" + +"nanoid@3.3.1": + "integrity" "sha512-n6Vs/3KGyxPQd6uO0eH4Bv0ojGSUvuLlIHtC3Y0kEO23YRge8H9x1GCzLn28YX0H66pMkxuaeESFq4tKISKwdw==" + "resolved" "https://registry.npmjs.org/nanoid/-/nanoid-3.3.1.tgz" + "version" "3.3.1" + +"normalize-path@^3.0.0", "normalize-path@~3.0.0": "integrity" "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==" "resolved" "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz" "version" "3.0.0" @@ -920,15 +778,6 @@ "resolved" "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz" "version" "4.1.1" -"object-copy@^0.1.0": - "integrity" "sha1-fn2Fi3gb18mRpBupde04EnVOmYw=" - "resolved" "https://registry.npmjs.org/object-copy/-/object-copy-0.1.0.tgz" - "version" "0.1.0" - dependencies: - "copy-descriptor" "^0.1.0" - "define-property" "^0.2.5" - "kind-of" "^3.0.3" - "object-inspect@~1.6.0": "integrity" "sha512-GJzfBZ6DgDAmnuaM3104jR4s1Myxr3Y3zfIyN4z3UdqN69oSRacNK8UhnobDdC+7J2AHCjGwxQubNJfE70SXXQ==" "resolved" "https://registry.npmjs.org/object-inspect/-/object-inspect-1.6.0.tgz" @@ -944,20 +793,6 @@ "resolved" "https://registry.npmjs.org/object-keys/-/object-keys-0.4.0.tgz" "version" "0.4.0" -"object-visit@^1.0.0": - "integrity" "sha1-95xEk68MU3e1n+OdOV5BBC3QRbs=" - "resolved" "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz" - "version" "1.0.1" - dependencies: - "isobject" "^3.0.0" - -"object.pick@^1.3.0": - "integrity" "sha1-h6EKxMFpS9Lhy/U1kaZhQftd10c=" - "resolved" "https://registry.npmjs.org/object.pick/-/object.pick-1.3.0.tgz" - "version" "1.3.0" - dependencies: - "isobject" "^3.0.1" - "once@^1.3.0": "integrity" "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=" "resolved" "https://registry.npmjs.org/once/-/once-1.4.0.tgz" @@ -965,20 +800,29 @@ dependencies: "wrappy" "1" +"p-limit@^3.0.2": + "integrity" "sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==" + "resolved" "https://registry.npmjs.org/p-limit/-/p-limit-3.1.0.tgz" + "version" "3.1.0" + dependencies: + "yocto-queue" "^0.1.0" + +"p-locate@^5.0.0": + "integrity" "sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==" + "resolved" "https://registry.npmjs.org/p-locate/-/p-locate-5.0.0.tgz" + "version" "5.0.0" + dependencies: + "p-limit" "^3.0.2" + "parse-ms@^1.0.0": "integrity" "sha1-VjRtR0nXjyNDDKDHE4UK75GqNh0=" "resolved" "https://registry.npmjs.org/parse-ms/-/parse-ms-1.0.1.tgz" "version" "1.0.1" -"pascalcase@^0.1.1": - "integrity" "sha1-s2PlXoAGym/iF4TS2yK9FdeRfxQ=" - "resolved" "https://registry.npmjs.org/pascalcase/-/pascalcase-0.1.1.tgz" - "version" "0.1.1" - -"path-dirname@^1.0.0": - "integrity" "sha1-zDPSTVJeCZpTiMAzbG4yuRYGCeA=" - "resolved" "https://registry.npmjs.org/path-dirname/-/path-dirname-1.0.2.tgz" - "version" "1.0.2" +"path-exists@^4.0.0": + "integrity" "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==" + "resolved" "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz" + "version" "4.0.0" "path-is-absolute@^1.0.0": "integrity" "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" @@ -990,16 +834,21 @@ "resolved" "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz" "version" "1.0.6" +"pathval@^1.1.1": + "integrity" "sha512-Dp6zGqpTdETdR63lehJYPeIOqpiNBNtc7BpWSLrOje7UaIsE5aY92r/AunQA7rsXvet3lrJ3JnZX29UPTKXyKQ==" + "resolved" "https://registry.npmjs.org/pathval/-/pathval-1.1.1.tgz" + "version" "1.1.1" + +"picomatch@^2.0.4", "picomatch@^2.2.1": + "integrity" "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==" + "resolved" "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz" + "version" "2.3.1" + "plur@^1.0.0": "integrity" "sha1-24XGgU9eXlo7Se/CjWBP7GKXUVY=" "resolved" "https://registry.npmjs.org/plur/-/plur-1.0.0.tgz" "version" "1.0.0" -"posix-character-classes@^0.1.0": - "integrity" "sha1-AerA/jta9xoqbAL+q7jB/vfgDqs=" - "resolved" "https://registry.npmjs.org/posix-character-classes/-/posix-character-classes-0.1.1.tgz" - "version" "0.1.1" - "prettier@^1.11.0": "integrity" "sha512-OeHeMc0JhFE9idD4ZdtNibzY0+TPHSpSSb9h8FqtP+YnoZZ1sl8Vc9b1sasjfymH3SonAF4QcA2+mzHPhMvIiw==" "resolved" "https://registry.npmjs.org/prettier/-/prettier-1.18.2.tgz" @@ -1024,7 +873,14 @@ "resolved" "https://registry.npmjs.org/process/-/process-0.11.10.tgz" "version" "0.11.10" -"readable-stream@^2", "readable-stream@^2.0.2", "readable-stream@~2.3.6": +"randombytes@^2.1.0": + "integrity" "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==" + "resolved" "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz" + "version" "2.1.0" + dependencies: + "safe-buffer" "^5.1.0" + +"readable-stream@^2", "readable-stream@~2.3.6": "integrity" "sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==" "resolved" "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz" "version" "2.3.6" @@ -1057,42 +913,17 @@ "isarray" "0.0.1" "string_decoder" "~0.10.x" -"readdirp@^2.2.1": - "integrity" "sha512-1JU/8q+VgFZyxwrJ+SVIOsh+KywWGpds3NTqikiKpDMZWScmAYyKIgqkO+ARvNWJfXeXR1zxz7aHF4u4CyH6vQ==" - "resolved" "https://registry.npmjs.org/readdirp/-/readdirp-2.2.1.tgz" - "version" "2.2.1" +"readdirp@~3.6.0": + "integrity" "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==" + "resolved" "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz" + "version" "3.6.0" dependencies: - "graceful-fs" "^4.1.11" - "micromatch" "^3.1.10" - "readable-stream" "^2.0.2" + "picomatch" "^2.2.1" -"regex-not@^1.0.0", "regex-not@^1.0.2": - "integrity" "sha512-J6SDjUgDxQj5NusnOtdFxDwN/+HWykR8GELwctJ7mdqhcyy1xEc4SRFHUXvxTp661YaVKAjfRLZ9cCqS6tn32A==" - "resolved" "https://registry.npmjs.org/regex-not/-/regex-not-1.0.2.tgz" - "version" "1.0.2" - dependencies: - "extend-shallow" "^3.0.2" - "safe-regex" "^1.1.0" - -"remove-trailing-separator@^1.0.1": - "integrity" "sha1-wkvOKig62tW8P1jg1IJJuSN52O8=" - "resolved" "https://registry.npmjs.org/remove-trailing-separator/-/remove-trailing-separator-1.1.0.tgz" - "version" "1.1.0" - -"repeat-element@^1.1.2": - "integrity" "sha512-ahGq0ZnV5m5XtZLMb+vP76kcAM5nkLqk0lpqAuojSKGgQtn4eRi4ZZGm2olo2zKFH+sMsWaqOCW1dqAnOru72g==" - "resolved" "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.3.tgz" - "version" "1.1.3" - -"repeat-string@^1.6.1": - "integrity" "sha1-jcrkcOHIirwtYA//Sndihtp15jc=" - "resolved" "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz" - "version" "1.6.1" - -"resolve-url@^0.2.1": - "integrity" "sha1-LGN/53yJOv0qZj/iGqkIAGjiBSo=" - "resolved" "https://registry.npmjs.org/resolve-url/-/resolve-url-0.2.1.tgz" - "version" "0.2.1" +"require-directory@^2.1.1": + "integrity" "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=" + "resolved" "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz" + "version" "2.1.1" "resolve@~1.11.1": "integrity" "sha512-vIpgF6wfuJOZI7KKKSP+HmiKggadPQAdsp5HiC1mvqnfp0gF1vdwgBWZIdrVft9pgqoMFQN+R7BSWZiBxx+BBw==" @@ -1108,73 +939,17 @@ dependencies: "through" "~2.3.4" -"ret@~0.1.10": - "integrity" "sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg==" - "resolved" "https://registry.npmjs.org/ret/-/ret-0.1.15.tgz" - "version" "0.1.15" - -"safe-buffer@~5.1.0", "safe-buffer@~5.1.1": +"safe-buffer@^5.1.0", "safe-buffer@~5.1.0", "safe-buffer@~5.1.1": "integrity" "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==" "resolved" "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz" "version" "5.1.2" -"safe-regex@^1.1.0": - "integrity" "sha1-QKNmnzsHfR6UPURinhV91IAjvy4=" - "resolved" "https://registry.npmjs.org/safe-regex/-/safe-regex-1.1.0.tgz" - "version" "1.1.0" +"serialize-javascript@6.0.0": + "integrity" "sha512-Qr3TosvguFt8ePWqsvRfrKyQXIiW+nGbYpy8XK24NQHE83caxWt+mIymTT19DGFbNWNLfEwsrkSmN64lVWB9ag==" + "resolved" "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-6.0.0.tgz" + "version" "6.0.0" dependencies: - "ret" "~0.1.10" - -"set-value@^2.0.0", "set-value@^2.0.1": - "integrity" "sha512-JxHc1weCN68wRY0fhCoXpyK55m/XPHafOmK4UWD7m2CI14GMcFypt4w/0+NV5f/ZMby2F6S2wwA7fgynh9gWSw==" - "resolved" "https://registry.npmjs.org/set-value/-/set-value-2.0.1.tgz" - "version" "2.0.1" - dependencies: - "extend-shallow" "^2.0.1" - "is-extendable" "^0.1.1" - "is-plain-object" "^2.0.3" - "split-string" "^3.0.1" - -"snapdragon-node@^2.0.1": - "integrity" "sha512-O27l4xaMYt/RSQ5TR3vpWCAB5Kb/czIcqUFOM/C4fYcLnbZUc1PkjTAMjof2pBWaSTwOUd6qUHcFGVGj7aIwnw==" - "resolved" "https://registry.npmjs.org/snapdragon-node/-/snapdragon-node-2.1.1.tgz" - "version" "2.1.1" - dependencies: - "define-property" "^1.0.0" - "isobject" "^3.0.0" - "snapdragon-util" "^3.0.1" - -"snapdragon-util@^3.0.1": - "integrity" "sha512-mbKkMdQKsjX4BAL4bRYTj21edOf8cN7XHdYUJEe+Zn99hVEYcMvKPct1IqNe7+AZPirn8BCDOQBHQZknqmKlZQ==" - "resolved" "https://registry.npmjs.org/snapdragon-util/-/snapdragon-util-3.0.1.tgz" - "version" "3.0.1" - dependencies: - "kind-of" "^3.2.0" - -"snapdragon@^0.8.1": - "integrity" "sha512-FtyOnWN/wCHTVXOMwvSv26d+ko5vWlIDD6zoUJ7LW8vh+ZBC8QdljveRP+crNrtBwioEUWy/4dMtbBjA4ioNlg==" - "resolved" "https://registry.npmjs.org/snapdragon/-/snapdragon-0.8.2.tgz" - "version" "0.8.2" - dependencies: - "base" "^0.11.1" - "debug" "^2.2.0" - "define-property" "^0.2.5" - "extend-shallow" "^2.0.1" - "map-cache" "^0.2.2" - "source-map" "^0.5.6" - "source-map-resolve" "^0.5.0" - "use" "^3.1.0" - -"source-map-resolve@^0.5.0": - "integrity" "sha512-MjqsvNwyz1s0k81Goz/9vRBe9SZdB09Bdw+/zYyO+3CuPk6fouTaxscHkgtE8jKvf01kVfl8riHzERQ/kefaSA==" - "resolved" "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.2.tgz" - "version" "0.5.2" - dependencies: - "atob" "^2.1.1" - "decode-uri-component" "^0.2.0" - "resolve-url" "^0.2.1" - "source-map-url" "^0.4.0" - "urix" "^0.1.0" + "randombytes" "^2.1.0" "source-map-support@^0.5.3": "integrity" "sha512-SHSKFHadjVA5oR4PPqhtAVdcBWwRYVd6g6cAXnIbRiIwc2EhPrTuKUBdSLvlEKyIP3GCf89fltvcZiP9MMFA1w==" @@ -1184,28 +959,11 @@ "buffer-from" "^1.0.0" "source-map" "^0.6.0" -"source-map-url@^0.4.0": - "integrity" "sha1-PpNdfd1zYxuXZZlW1VEo6HtQhKM=" - "resolved" "https://registry.npmjs.org/source-map-url/-/source-map-url-0.4.0.tgz" - "version" "0.4.0" - -"source-map@^0.5.6": - "integrity" "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=" - "resolved" "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz" - "version" "0.5.7" - "source-map@^0.6.0": "integrity" "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" "resolved" "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz" "version" "0.6.1" -"split-string@^3.0.1", "split-string@^3.0.2": - "integrity" "sha512-NzNVhJDYpwceVVii8/Hu6DKfD2G+NrQHlS/V/qgv763EYudVwEcMQNxd2lh+0VrUByXN/oJkl5grOhYWvQUYiw==" - "resolved" "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz" - "version" "3.1.0" - dependencies: - "extend-shallow" "^3.0.0" - "sprintf-js@~1.0.2": "integrity" "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=" "resolved" "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz" @@ -1216,14 +974,6 @@ "resolved" "https://registry.npmjs.org/sprintf/-/sprintf-0.1.5.tgz" "version" "0.1.5" -"static-extend@^0.1.1": - "integrity" "sha1-YICcOcv/VTNyJv1eC1IPNB8ftcY=" - "resolved" "https://registry.npmjs.org/static-extend/-/static-extend-0.1.2.tgz" - "version" "0.1.2" - dependencies: - "define-property" "^0.2.5" - "object-copy" "^0.1.0" - "string_decoder@~0.10.x": "integrity" "sha1-YuIDvEF2bGwoyfyEMB2rHFMQ+pQ=" "resolved" "https://registry.npmjs.org/string_decoder/-/string_decoder-0.10.31.tgz" @@ -1236,6 +986,15 @@ dependencies: "safe-buffer" "~5.1.0" +"string-width@^4.1.0", "string-width@^4.2.0": + "integrity" "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==" + "resolved" "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz" + "version" "4.2.3" + dependencies: + "emoji-regex" "^8.0.0" + "is-fullwidth-code-point" "^3.0.0" + "strip-ansi" "^6.0.1" + "string.prototype.trim@~1.1.2": "integrity" "sha1-0E3iyJ4Tf019IG8Ia17S+ua+jOo=" "resolved" "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.1.2.tgz" @@ -1252,6 +1011,25 @@ dependencies: "ansi-regex" "^2.0.0" +"strip-ansi@^6.0.0": + "integrity" "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==" + "resolved" "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz" + "version" "6.0.1" + dependencies: + "ansi-regex" "^5.0.1" + +"strip-ansi@^6.0.1": + "integrity" "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==" + "resolved" "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz" + "version" "6.0.1" + dependencies: + "ansi-regex" "^5.0.1" + +"strip-json-comments@3.1.1": + "integrity" "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==" + "resolved" "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz" + "version" "3.1.1" + "supports-color@^2.0.0": "integrity" "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" "resolved" "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz" @@ -1264,6 +1042,20 @@ dependencies: "has-flag" "^3.0.0" +"supports-color@^7.1.0": + "integrity" "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==" + "resolved" "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz" + "version" "7.2.0" + dependencies: + "has-flag" "^4.0.0" + +"supports-color@8.1.1": + "integrity" "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==" + "resolved" "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz" + "version" "8.1.1" + dependencies: + "has-flag" "^4.0.0" + "tap-diff@^0.1.1": "integrity" "sha1-j78zM9hWQ/7qG/F1m5CCCwSjfd8=" "resolved" "https://registry.npmjs.org/tap-diff/-/tap-diff-0.1.1.tgz" @@ -1348,30 +1140,12 @@ "readable-stream" "~1.1.9" "xtend" "~2.1.1" -"to-object-path@^0.3.0": - "integrity" "sha1-KXWIt7Dn4KwI4E5nL4XB9JmeF68=" - "resolved" "https://registry.npmjs.org/to-object-path/-/to-object-path-0.3.0.tgz" - "version" "0.3.0" +"to-regex-range@^5.0.1": + "integrity" "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==" + "resolved" "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz" + "version" "5.0.1" dependencies: - "kind-of" "^3.0.2" - -"to-regex-range@^2.1.0": - "integrity" "sha1-fIDBe53+vlmeJzZ+DU3VWQFB2zg=" - "resolved" "https://registry.npmjs.org/to-regex-range/-/to-regex-range-2.1.1.tgz" - "version" "2.1.1" - dependencies: - "is-number" "^3.0.0" - "repeat-string" "^1.6.1" - -"to-regex@^3.0.1", "to-regex@^3.0.2": - "integrity" "sha512-FWtleNAtZ/Ki2qtqej2CXTOayOH9bHDQF+Q48VpWyDXjbYxA4Yz8iDB31zXOBUlOHHKidDbqGVrTUvQMPmBGBw==" - "resolved" "https://registry.npmjs.org/to-regex/-/to-regex-3.0.2.tgz" - "version" "3.0.2" - dependencies: - "define-property" "^2.0.2" - "extend-shallow" "^3.0.2" - "regex-not" "^1.0.2" - "safe-regex" "^1.1.0" + "is-number" "^7.0.0" "ts-node@^5.0.0": "integrity" "sha512-XK7QmDcNHVmZkVtkiwNDWiERRHPyU8nBqZB1+iv2UhOG0q3RQ9HsZ2CMqISlFbxjrYFGfG2mX7bW4dAyxBVzUw==" @@ -1387,49 +1161,42 @@ "source-map-support" "^0.5.3" "yn" "^2.0.0" +"type-detect@^4.0.0", "type-detect@^4.0.5": + "integrity" "sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g==" + "resolved" "https://registry.npmjs.org/type-detect/-/type-detect-4.0.8.tgz" + "version" "4.0.8" + "typescript@^4.6.2": "integrity" "sha512-HM/hFigTBHZhLXshn9sN37H085+hQGeJHJ/X7LpBWLID/fbc2acUMfU+lGD98X81sKP+pFa9f0DZmCwB9GnbAg==" "resolved" "https://registry.npmjs.org/typescript/-/typescript-4.6.2.tgz" "version" "4.6.2" -"union-value@^1.0.0": - "integrity" "sha512-tJfXmxMeWYnczCVs7XAEvIV7ieppALdyepWMkHkwciRpZraG/xwT+s2JN8+pr1+8jCRf80FFzvr+MpQeeoF4Xg==" - "resolved" "https://registry.npmjs.org/union-value/-/union-value-1.0.1.tgz" - "version" "1.0.1" - dependencies: - "arr-union" "^3.1.0" - "get-value" "^2.0.6" - "is-extendable" "^0.1.1" - "set-value" "^2.0.1" - -"unset-value@^1.0.0": - "integrity" "sha1-g3aHP30jNRef+x5vw6jtDfyKtVk=" - "resolved" "https://registry.npmjs.org/unset-value/-/unset-value-1.0.0.tgz" - "version" "1.0.0" - dependencies: - "has-value" "^0.3.1" - "isobject" "^3.0.0" - -"upath@^1.1.1": - "integrity" "sha512-kXpym8nmDmlCBr7nKdIx8P2jNBa+pBpIUFRnKJ4dr8htyYGJFokkr2ZvERRtUN+9SY+JqXouNgUPtv6JQva/2Q==" - "resolved" "https://registry.npmjs.org/upath/-/upath-1.1.2.tgz" - "version" "1.1.2" - -"urix@^0.1.0": - "integrity" "sha1-2pN/emLiH+wf0Y1Js1wpNQZ6bHI=" - "resolved" "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz" - "version" "0.1.0" - -"use@^3.1.0": - "integrity" "sha512-cwESVXlO3url9YWlFW/TA9cshCEhtu7IKJ/p5soJ/gGpj7vbvFrAY/eIioQ6Dw23KjZhYgiIo8HOs1nQ2vr/oQ==" - "resolved" "https://registry.npmjs.org/use/-/use-3.1.1.tgz" - "version" "3.1.1" - "util-deprecate@~1.0.1": "integrity" "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=" "resolved" "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz" "version" "1.0.2" +"which@2.0.2": + "integrity" "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==" + "resolved" "https://registry.npmjs.org/which/-/which-2.0.2.tgz" + "version" "2.0.2" + dependencies: + "isexe" "^2.0.0" + +"workerpool@6.2.0": + "integrity" "sha512-Rsk5qQHJ9eowMH28Jwhe8HEbmdYDX4lwoMWshiCXugjtHqMD9ZbiqSDLxcsfdqsETPzVUtX5s1Z5kStiIM6l4A==" + "resolved" "https://registry.npmjs.org/workerpool/-/workerpool-6.2.0.tgz" + "version" "6.2.0" + +"wrap-ansi@^7.0.0": + "integrity" "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==" + "resolved" "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz" + "version" "7.0.0" + dependencies: + "ansi-styles" "^4.0.0" + "string-width" "^4.1.0" + "strip-ansi" "^6.0.0" + "wrappy@1": "integrity" "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" "resolved" "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz" @@ -1447,7 +1214,45 @@ "resolved" "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz" "version" "4.0.2" +"y18n@^5.0.5": + "integrity" "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==" + "resolved" "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz" + "version" "5.0.8" + +"yargs-parser@^20.2.2", "yargs-parser@20.2.4": + "integrity" "sha512-WOkpgNhPTlE73h4VFAFsOnomJVaovO8VqLDzy5saChRBFQFBoMYirowyW+Q9HB4HFF4Z7VZTiG3iSzJJA29yRA==" + "resolved" "https://registry.npmjs.org/yargs-parser/-/yargs-parser-20.2.4.tgz" + "version" "20.2.4" + +"yargs-unparser@2.0.0": + "integrity" "sha512-7pRTIA9Qc1caZ0bZ6RYRGbHJthJWuakf+WmHK0rVeLkNrrGhfoabBNdue6kdINI6r4if7ocq9aD/n7xwKOdzOA==" + "resolved" "https://registry.npmjs.org/yargs-unparser/-/yargs-unparser-2.0.0.tgz" + "version" "2.0.0" + dependencies: + "camelcase" "^6.0.0" + "decamelize" "^4.0.0" + "flat" "^5.0.2" + "is-plain-obj" "^2.1.0" + +"yargs@16.2.0": + "integrity" "sha512-D1mvvtDG0L5ft/jGWkLpG1+m0eQxOfaBvTNELraWj22wSVUMWxZUvYgJYcKh6jGGIkJFhH4IZPQhR4TKpc8mBw==" + "resolved" "https://registry.npmjs.org/yargs/-/yargs-16.2.0.tgz" + "version" "16.2.0" + dependencies: + "cliui" "^7.0.2" + "escalade" "^3.1.1" + "get-caller-file" "^2.0.5" + "require-directory" "^2.1.1" + "string-width" "^4.2.0" + "y18n" "^5.0.5" + "yargs-parser" "^20.2.2" + "yn@^2.0.0": "integrity" "sha1-5a2ryKz0CPY4X8dklWhMiOavaJo=" "resolved" "https://registry.npmjs.org/yn/-/yn-2.0.0.tgz" "version" "2.0.0" + +"yocto-queue@^0.1.0": + "integrity" "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==" + "resolved" "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz" + "version" "0.1.0"