diff --git a/README.md b/README.md index 2dd22375..47dac633 100644 --- a/README.md +++ b/README.md @@ -263,23 +263,24 @@ opening an example template: -| Command | Description | flags & args | Example | -|----------|----------------------------------------------------------------------|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -| `.open` | Interactive command to open a template (defaults to examples folder) | | `.open` | -| `.cd` | Change directory (then use .open command) | | `.cd ..` | -| `.init` | Initialize the template from a JSON file. | • `-f `
• `--tags=`
•`--options=`
• `--xf=`
• `--importPath=`
• `--tail ""` | `.init -f "example/hello.json" --tags=FOO,BAR --xf=~/falken/myEnv.json --options={"strict":{"refs":true}} --importPath=~/falken/mytemplates --tail "/ until msg='hello world'"` | -| `.set` | Set data to a JSON pointer path. | ` ` | `.set /to "jsonata"` | -| `.from` | Show the dependents of a given JSON pointer. | `` | `.from /a` | -| `.to` | Show the dependencies of a given JSON pointer. | `` | `.to /b` | -| `.in` | Show the input template. | `None` | `.in` | -| `.out` | Show the current state of the template. | `[]` | `.out`
`.out /data/accounts` | -| `.state` | Show the current state of the template metadata. | `None` | `.state` | -| `.plan` | Show the execution plan for rendering the template. | `None` | `.plan` | -| `.note` | Show a separator line with a comment in the REPL output. | `` | `.note "Example 8"` | -| `.log` | Set the logging level | `[silent, error, warn, info, verbose, debug]` | `.log silent` | -| `.color` | Enable Colors | `[on,off]` | `.color on` | -| `.tail` | Tail part of the document for changes | ` (until )?` | `.tail /`
`.tail "/ until foo='bar'"` | -| `.svg` | Serve an SVG diagram of the DAG | `--port ` (defaults to 4242) | `.svg --port 3000` | +| Command | Description | flags & args | Example | +|------------|----------------------------------------------------------------------|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| +| `.open` | Interactive command to open a template (defaults to examples folder) | | `.open` | +| `.cd` | Change directory (then use .open command) | | `.cd ..` | +| `.init` | Initialize the template from a JSON file. | • `-f `
• `--tags=`
•`--options=`
• `--xf=`
• `--importPath=`
• `--tail ""` | `.init -f "example/hello.json" --tags=FOO,BAR --xf=~/falken/myEnv.json --options={"strict":{"refs":true}} --importPath=~/falken/mytemplates --tail "/ until msg='hello world'"` | +| `.set` | Set data to a JSON pointer path. | ` ` | `.set /to "jsonata"` | +| `.from` | Show the dependents of a given JSON pointer. | `` | `.from /a` | +| `.to` | Show the dependencies of a given JSON pointer. | `` | `.to /b` | +| `.in` | Show the input template. | `None` | `.in` | +| `.out` | Show the current state of the template. | `[]` | `.out`
`.out /data/accounts` | +| `.state` | Show the current state of the template metadata. | `None` | `.state` | +| `.plan` | Show the execution plan for rendering the template. | `None` | `.plan` | +| `.note` | Show a separator line with a comment in the REPL output. | `` | `.note "Example 8"` | +| `.log` | Set the logging level | `[silent, error, warn, info, verbose, debug]` | `.log silent` | +| `.color` | Enable Colors | `[on,off]` | `.color on` | +| `.tail` | Tail part of the document for changes | ` (until )?` | `.tail /`
`.tail "/ until foo='bar'"` | +| `.svg` | Serve an SVG diagram of the DAG | `--port ` (defaults to 4242) | `.svg --port 3000` | +| `.restore` | Restore from a snapshot | • `-f `
• `--tags=`
• `--xf=`
• `--importPath=`
• `--tail ""` | `.restore -f "example/restoreSnapshot.json" --tail "/count until $=10"` | The stated repl lets you experiment with templates. The simplest thing to do in the REPL is load a json file. The REPL @@ -1663,7 +1664,6 @@ In the example below `$set('/systems/1', 'JOSHUA')` is used to push the string " ] } ``` - # options The cli and REPL both support `--options`. Options are set using a json object ## strict @@ -1942,7 +1942,7 @@ we want to ensure that a function calling external APIs does not overload it. Below output demonstrates, that `rateLimit` function calls to to set `acc` to once in no less than 100ms, which will result in only 10 counts added o the `acc` array, the first one, the last one, and 10 in between. ```json ["data.accCounter = 12"] -.init -f example/rateLimit.yaml --tail "/ until accCount=12" +>.init -f example/rateLimit.yaml --tail "/ until accCount=12" Started tailing... Press Ctrl+C to stop. { "acc": [ @@ -1966,6 +1966,32 @@ Started tailing... Press Ctrl+C to stop. "accCount": 12 } ``` +# TemplateProcessor Snapshots +TemplateProcessor.snapshot allows you to capture template state at a point in time. The snapshot can be used to restore +and continue template execution from that point. The snapshot is a JSON object that can be serialized and stored in a +file. + +To create a periodic snapshot of the template every time it changes +```js +const tempalte = { + "count": 0, + "counter": "${ $setInterval(function(){$set('/count', count+1)}, 10) }", + "stop": "${ count=10?($clearInterval($$.counter);'done'):'not done' }" +}; +const tp = new TemplateProcessor(template); +await tp.initialize(); +await fs.writeFile("./myTemplateSnapshot.json", tp.snapshot()); +``` +To continue template execution from the snapshot, you can either programmatically restore the snapshot + +or use +`.restore` command in the REPL. +```json ["data=10"] +> .restore -f example/restoreSnapshot.json --tail "/count until $=10" +Started tailing... Press Ctrl+C to stop. +10 +``` + # Understanding Plans This information is to explain the planning algorithms to comitters. As a user you do not need to understand how Stated formulates plans. Before explaining how a plan is made, let's show the end-to-end flow of how a plan is used diff --git a/example/restoreSnapshot.json b/example/restoreSnapshot.json new file mode 100644 index 00000000..7e8513ab --- /dev/null +++ b/example/restoreSnapshot.json @@ -0,0 +1,18 @@ +{ + "template": { + "count": 0, + "counter": "${ $setInterval(function(){$set('/count', count+1)}, 10) }", + "stop": "${ count=10?($clearInterval($$.counter);'done'):'not done' }" + }, + "output": { + "count": 3, + "counter": "--interval/timeout--", + "stop": "not done" + }, + "options": { + "snapshot": { + "seconds": 1 + }, + "importPath": "/Users/sesergee/projects/sandbox/workflows/stated-workflow" + } +} diff --git a/src/CliCore.ts b/src/CliCore.ts index 66eaeebe..10fb8fa1 100644 --- a/src/CliCore.ts +++ b/src/CliCore.ts @@ -122,8 +122,28 @@ export default class CliCore { return path.join(process.cwd(), filepath); } - //replCmdInoutStr like: -f "example/ex23.json" --tags=["PEACE"] --xf=example/myEnv.json - async init(replCmdInputStr) { + //replCmdInoutStr like: -f "defaultSnapshot.json" + + /** + * replCmdInoutStr example: -f "example/restoreSnapshot.json" --tags=["PEACE"] --xf=example/myEnv.json + * @param replCmdInputStr - the command line string that will be parsed into arguments + */ + async restore(replCmdInputStr: string) { + return this.init(replCmdInputStr, true); + + } + + /** + * This Cli core command may be invoked directly from the REPL init command or from restore command + * + * - fromSnapshot=false, replCmdInoutStr example: -f "example/ex23.json" --tags=["PEACE"] --xf=example/myEnv.json + * - fromSnapshot=true, replCmdInoutStr example: -f "example/restoreSnapshot.json" --tags=["PEACE"] --xf=example/myEnv.json + * + * @param replCmdInputStr + * @param fromSnapshot - when set to true, template processor will treat input as a snapshot of a previous + * templateProcessor state + */ + async init(replCmdInputStr, fromSnapshot: boolean=false) { if(this.templateProcessor){ this.templateProcessor.close(); } @@ -136,8 +156,10 @@ export default class CliCore { const contextData = contextFilePath ? await this.readFileAndParse(contextFilePath, importPath) : {}; options.importPath = importPath; //path is where local imports will be sourced from. We sneak path in with the options // if we initialize for the first time, we need to create a new instance of TemplateProcessor - if (!this.templateProcessor) { + if (!this.templateProcessor && !fromSnapshot) { this.templateProcessor = new TemplateProcessor(input, contextData, options); + } else if (!this.templateProcessor && fromSnapshot) { + this.templateProcessor = new TemplateProcessor(input.template, contextData, input.options); } else { // if we are re-initializing, we need to reset the tagSet and options, if provided this.templateProcessor.tagSet = new Set(); this.templateProcessor.options = options; @@ -160,7 +182,11 @@ export default class CliCore { if(tail !== undefined){ tailPromise = this.tail(tail); } - await this.templateProcessor.initialize(input); + if (fromSnapshot) { + await this.templateProcessor.initialize(input.template,"/", input.output); + } else { + await this.templateProcessor.initialize(input); + } if(tail !== undefined){ return tailPromise; } diff --git a/src/StatedREPL.ts b/src/StatedREPL.ts index edb6a08f..6e6ef486 100755 --- a/src/StatedREPL.ts +++ b/src/StatedREPL.ts @@ -27,6 +27,28 @@ export default class StatedREPL { this.cliCore = new CliCore(temaplateProcessor); } + // a list of commands that are available in the CLI + // this list can be extended if CLICORE is extended as well + static CLICORE_COMMANDS: string[][] = [ + ["open", 'interactive command to open select and open a template'], + ["cd", "change directory for example 'cd ..' "], + ["init", '-f to Initialize the template'], + ["set", 'Set data to a JSON pointer path and show the executed output'], + ["in", 'Show the input template'], + ["out", '[jsonPointer] Show the executed output'], + ["state", 'Show the current state of the templateMeta'], + ["from", 'Show the dependents of a given JSON pointer'], + ["to", 'Show the dependencies of a given JSON pointer'], + ["plan", 'Show the evaluation plan'], + ["note", "returns ═══ ... for creating documentation"], + ["log", "set the log level [debug, info, warn, error]"], + ["debug", "set debug commands (WIP)"], + ["errors", "return an error report"], + ["tail", 'tail "/ until count=100" will tail the template root until its count field is 100'], + ["svg", 'serve SVG of depedency graph off http://localhost:3000'], + ["restore", 'restore the template from a snapshot'], + ]; + async initialize() { this.isColorized = false; const cmdLineArgsStr = process.argv.slice(2).join(" "); @@ -52,25 +74,7 @@ export default class StatedREPL { } registerCommands() { - [ //these are CLICore commands - ["open", 'interactive command to open select and open a template'], - ["cd", "change directory for example 'cd ..' "], - ["init", '-f to Initialize the template'], - ["set", 'Set data to a JSON pointer path and show the executed output'], - ["in", 'Show the input template'], - ["out", '[jsonPointer] Show the executed output'], - ["state", 'Show the current state of the templateMeta'], - ["from", 'Show the dependents of a given JSON pointer'], - ["to", 'Show the dependencies of a given JSON pointer'], - ["plan", 'Show the evaluation plan'], - ["note", "returns ═══ ... for creating documentation"], - ["log", "set the log level [debug, info, warn, error]"], - ["debug", "set debug commands (WIP)"], - ["errors", "return an error report"], - ["tail", 'tail "/ until count=100" will tail the template root until its count field is 100'], - ["svg", 'serve SVG of depedency graph off http://localhost:3000'], - - ].map(c=>{ + StatedREPL.CLICORE_COMMANDS.map(c=>{ const [cmdName, helpMsg] = c; this.r.defineCommand(cmdName, { help: helpMsg, diff --git a/src/TemplateProcessor.ts b/src/TemplateProcessor.ts index c181a39f..5b767948 100644 --- a/src/TemplateProcessor.ts +++ b/src/TemplateProcessor.ts @@ -346,7 +346,7 @@ export default class TemplateProcessor { * @param snapshottedOutput - if provided, output is set to this initial value * */ - public async initialize(importedSubtemplate: {} = undefined, jsonPtr = "/", snapshottedOutput?:any):Promise { + public async initialize(importedSubtemplate: {} = undefined, jsonPtr: string = "/", snapshottedOutput: {} = undefined):Promise { if(jsonPtr === "/"){ this.timerManager.clearAll(); } diff --git a/src/TestUtils.ts b/src/TestUtils.ts index 14675e8c..145085a0 100644 --- a/src/TestUtils.ts +++ b/src/TestUtils.ts @@ -98,7 +98,7 @@ function runMarkdownTests(testData: CommandAndResponse[], cliCore:CliCore, print const compiledExpr = jsonata(jsonataExpr); const success = await compiledExpr.evaluate(responseNormalized); if (success === false) { - throw new Error(`Markdown codeblock contained custom jsonata test expression that returned false: ${jsonataExpr} \n data was: ${responseNormalized}` ); + throw new Error(`Markdown codeblock contained custom jsonata test expression that returned false: ${StatedREPL.stringify(jsonataExpr)} \n data was: ${StatedREPL.stringify(responseNormalized)}` ); } } else { let expected; diff --git a/src/test/StatedREPL.test.js b/src/test/StatedREPL.test.js index 557e96c9..20a8d845 100644 --- a/src/test/StatedREPL.test.js +++ b/src/test/StatedREPL.test.js @@ -77,4 +77,36 @@ test("TemplateProcessor keeps context on init", async () => { ); }); +// Validates restore command +test("Extend CliCore with restore command", async () => { + // ensure jest argv does not interfere with the test + const originalCmdLineArgsStr = process.argv; + process.argv = ["node", "dist/stated.js"]; // this is an argv when running stated.js repl. + + // extend CliCore with restore command + const repl = new StatedREPL(); + + try { + await repl.initialize(); + + // we call restore on the repl, which will expect it to be defined in CliCore. + await repl.cli('restore', '-f example/restoreSnapshot.json'); + + + console.log(StatedREPL.stringify(repl.cliCore.templateProcessor.output)); + expect(repl.cliCore.templateProcessor.output).toBeDefined(); + expect(repl.cliCore.templateProcessor.output.count).toBeGreaterThanOrEqual(3); // should be 3 or more right after restoring from the snapshot + expect(repl.cliCore.templateProcessor.output.count).toBeLessThan(10); // ... but less than 10 + + + while (repl.cliCore.templateProcessor.output.count < 10) { // validates that templateProcessor picks up where it was left in the snapshot. + console.log("waiting for output.count to reach 10") + await new Promise(resolve => setTimeout(resolve, 50)); + } + expect(repl.cliCore.templateProcessor.output.count).toBe(10); + } finally { + process.argv = originalCmdLineArgsStr; + if (repl !== undefined) repl.close(); + } +}); \ No newline at end of file diff --git a/yarn.lock b/yarn.lock index 6b65fff8..620f0962 100644 --- a/yarn.lock +++ b/yarn.lock @@ -23,7 +23,7 @@ resolved "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.22.20.tgz" integrity sha512-BQYjKbpXjoXwFW5jGqiizJQQT/aC7pFm9Ok1OWssonuguICi264lbgMzRp2ZMmRSlfkX6DsWDDcsrctK8Rwfiw== -"@babel/core@^7.0.0", "@babel/core@^7.0.0-0", "@babel/core@^7.0.0-0 || ^8.0.0-0 <8.0.0", "@babel/core@^7.11.6", "@babel/core@^7.12.0", "@babel/core@^7.12.3", "@babel/core@^7.13.0", "@babel/core@^7.22.20", "@babel/core@^7.4.0 || ^8.0.0-0 <8.0.0", "@babel/core@^7.8.0": +"@babel/core@^7.11.6", "@babel/core@^7.12.3", "@babel/core@^7.22.20": version "7.22.20" resolved "https://registry.npmjs.org/@babel/core/-/core-7.22.20.tgz" integrity sha512-Y6jd1ahLubuYweD/zJH+vvOY141v4f9igNQAQ+MBgq9JlHS2iTsZKn1aMsb3vGccZsXI16VzTBw52Xx0DWmtnA== @@ -1222,16 +1222,16 @@ "@jridgewell/gen-mapping" "^0.3.0" "@jridgewell/trace-mapping" "^0.3.9" -"@jridgewell/sourcemap-codec@^1.4.10": - version "1.4.15" - resolved "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.15.tgz" - integrity sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg== - "@jridgewell/sourcemap-codec@1.4.14": version "1.4.14" resolved "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.14.tgz" integrity sha512-XPSJHWmi394fuUuzDnGz1wiKqWfo1yXecHQMRf2l6hztTO+nPru658AyDngaBe7isIxEkRsPR3FZh+s7iVa4Uw== +"@jridgewell/sourcemap-codec@^1.4.10": + version "1.4.15" + resolved "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.15.tgz" + integrity sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg== + "@jridgewell/trace-mapping@^0.3.12", "@jridgewell/trace-mapping@^0.3.17", "@jridgewell/trace-mapping@^0.3.18", "@jridgewell/trace-mapping@^0.3.9": version "0.3.18" resolved "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.18.tgz" @@ -1248,7 +1248,7 @@ "@nodelib/fs.stat" "2.0.5" run-parallel "^1.1.9" -"@nodelib/fs.stat@^2.0.2", "@nodelib/fs.stat@2.0.5": +"@nodelib/fs.stat@2.0.5", "@nodelib/fs.stat@^2.0.2": version "2.0.5" resolved "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz" integrity sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A== @@ -1392,7 +1392,7 @@ dependencies: "@types/yargs-parser" "*" -"@webassemblyjs/ast@^1.11.5", "@webassemblyjs/ast@1.11.6": +"@webassemblyjs/ast@1.11.6", "@webassemblyjs/ast@^1.11.5": version "1.11.6" resolved "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.11.6.tgz" integrity sha512-IN1xI7PwOvLPgjcf180gC1bqn3q/QaOCwYUahIOhbYUu8KA/3tw2RT/T0Gidi1l7Hhj5D/INhJxiICObqpMu4Q== @@ -1493,7 +1493,7 @@ "@webassemblyjs/wasm-gen" "1.11.6" "@webassemblyjs/wasm-parser" "1.11.6" -"@webassemblyjs/wasm-parser@^1.11.5", "@webassemblyjs/wasm-parser@1.11.6": +"@webassemblyjs/wasm-parser@1.11.6", "@webassemblyjs/wasm-parser@^1.11.5": version "1.11.6" resolved "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.11.6.tgz" integrity sha512-6ZwPeGzMJM3Dqp3hCsLgESxBGtT/OeCvCZ4TA1JUPYgmhAx38tTPR9JaKy0S5H3evQpO/h2uWs2j6Yc/fjkpTQ== @@ -1543,7 +1543,7 @@ acorn-import-assertions@^1.9.0: resolved "https://registry.npmjs.org/acorn-import-assertions/-/acorn-import-assertions-1.9.0.tgz" integrity sha512-cmMwop9x+8KFhxvKrKfPYmN6/pKTYYHBqLa0DfvVZcKMJWNyWLnaqND7dx/qn66R7ewM1UX5XMaDVP5wlVTaVA== -acorn@^8, acorn@^8.7.1, acorn@^8.8.2: +acorn@^8.7.1, acorn@^8.8.2: version "8.10.0" resolved "https://registry.npmjs.org/acorn/-/acorn-8.10.0.tgz" integrity sha512-F0SAmZ8iUtS//m8DmCTA0jlh6TDKkHQyK6xc6V4KDTyZKA9dnvX9/3sRTVQrWm79glUAZbnmmNcdYwUIHWVybw== @@ -1567,7 +1567,7 @@ ajv-keywords@^5.1.0: dependencies: fast-deep-equal "^3.1.3" -ajv@^6.12.5, ajv@^6.9.1: +ajv@^6.12.5: version "6.12.6" resolved "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz" integrity sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g== @@ -1577,7 +1577,7 @@ ajv@^6.12.5, ajv@^6.9.1: json-schema-traverse "^0.4.1" uri-js "^4.2.2" -ajv@^8.0.0, ajv@^8.8.2, ajv@^8.9.0: +ajv@^8.0.0, ajv@^8.9.0: version "8.12.0" resolved "https://registry.npmjs.org/ajv/-/ajv-8.12.0.tgz" integrity sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA== @@ -1767,7 +1767,7 @@ braces@^3.0.2: dependencies: fill-range "^7.0.1" -browserslist@^4.14.5, browserslist@^4.21.10, browserslist@^4.21.9, "browserslist@>= 4.21.0": +browserslist@^4.14.5, browserslist@^4.21.10, browserslist@^4.21.9: version "4.21.10" resolved "https://registry.npmjs.org/browserslist/-/browserslist-4.21.10.tgz" integrity sha512-bipEBdZfVH5/pwrvqc+Ub0kUPVfGUhlKxbvfD+z1BDnPEO/X98ruXGA1WP5ASpAFKan7Qr6j736IacbZQuAlKQ== @@ -1809,16 +1809,7 @@ caniuse-lite@^1.0.30001517: resolved "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001535.tgz" integrity sha512-48jLyUkiWFfhm/afF7cQPqPjaUmSraEhK4j+FCTJpgnGGEZHqyLe3hmWH7lIooZdSzXL0ReMvHz0vKDoTBsrwg== -chalk@^2.4.1: - version "2.4.2" - resolved "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz" - integrity sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ== - dependencies: - ansi-styles "^3.2.1" - escape-string-regexp "^1.0.5" - supports-color "^5.3.0" - -chalk@^2.4.2: +chalk@^2.4.1, chalk@^2.4.2: version "2.4.2" resolved "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz" integrity sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ== @@ -1902,7 +1893,7 @@ color-convert@^2.0.1: dependencies: color-name "~1.1.4" -color-name@^1.0.0, color-name@1.1.3: +color-name@1.1.3, color-name@^1.0.0: version "1.1.3" resolved "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz" integrity sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw== @@ -2403,7 +2394,7 @@ inflight@^1.0.4: once "^1.3.0" wrappy "1" -inherits@^2.0.3, inherits@2: +inherits@2, inherits@^2.0.3: version "2.0.4" resolved "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz" integrity sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ== @@ -2736,7 +2727,7 @@ jest-resolve-dependencies@^29.7.0: jest-regex-util "^29.6.3" jest-snapshot "^29.7.0" -jest-resolve@*, jest-resolve@^29.7.0: +jest-resolve@^29.7.0: version "29.7.0" resolved "https://registry.npmjs.org/jest-resolve/-/jest-resolve-29.7.0.tgz" integrity sha512-IOVhZSrg+UvVAshDSDtHyFCCBUl/Q3AAJv8iZ6ZjnZ74xzvwuzLXid9IIIPgTnY62SJjfuupMKZsZQRsCvxEgA== @@ -3135,7 +3126,7 @@ minimist@^1.2.8: resolved "https://registry.npmjs.org/minimist/-/minimist-1.2.8.tgz" integrity sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA== -ms@^2.1.1, ms@2.1.2: +ms@2.1.2, ms@^2.1.1: version "2.1.2" resolved "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz" integrity sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w== @@ -3502,14 +3493,7 @@ semver@^6.3.0, semver@^6.3.1: resolved "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz" integrity sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA== -semver@^7.5.3: - version "7.5.4" - resolved "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz" - integrity sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA== - dependencies: - lru-cache "^6.0.0" - -semver@^7.5.4: +semver@^7.5.3, semver@^7.5.4: version "7.5.4" resolved "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz" integrity sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA== @@ -3579,14 +3563,6 @@ slash@^4.0.0: resolved "https://registry.npmjs.org/slash/-/slash-4.0.0.tgz" integrity sha512-3dOsAHXXUkQTpOYcoAxLIorMTp4gIQr5IW3iVb7A7lFIp0VHhnynm9izx6TssdrIcVIESAlVjtnO2K8bg+Coew== -source-map-support@~0.5.20: - version "0.5.21" - resolved "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.21.tgz" - integrity sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w== - dependencies: - buffer-from "^1.0.0" - source-map "^0.6.0" - source-map-support@0.5.13: version "0.5.13" resolved "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.13.tgz" @@ -3595,6 +3571,14 @@ source-map-support@0.5.13: buffer-from "^1.0.0" source-map "^0.6.0" +source-map-support@~0.5.20: + version "0.5.21" + resolved "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.21.tgz" + integrity sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w== + dependencies: + buffer-from "^1.0.0" + source-map "^0.6.0" + source-map@^0.6.0, source-map@^0.6.1: version "0.6.1" resolved "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz" @@ -3617,13 +3601,6 @@ stack-utils@^2.0.3: dependencies: escape-string-regexp "^2.0.0" -string_decoder@^1.1.1: - version "1.3.0" - resolved "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz" - integrity sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA== - dependencies: - safe-buffer "~5.2.0" - string-argv@^0.3.2: version "0.3.2" resolved "https://registry.npmjs.org/string-argv/-/string-argv-0.3.2.tgz" @@ -3646,6 +3623,13 @@ string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2.3: is-fullwidth-code-point "^3.0.0" strip-ansi "^6.0.1" +string_decoder@^1.1.1: + version "1.3.0" + resolved "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz" + integrity sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA== + dependencies: + safe-buffer "~5.2.0" + strip-ansi@^6.0.0, strip-ansi@^6.0.1: version "6.0.1" resolved "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz" @@ -3776,7 +3760,7 @@ typedoc@^0.25.7: minimatch "^9.0.3" shiki "^0.14.7" -typescript@^5.3.3, "typescript@4.6.x || 4.7.x || 4.8.x || 4.9.x || 5.0.x || 5.1.x || 5.2.x || 5.3.x": +typescript@^5.3.3: version "5.3.3" resolved "https://registry.npmjs.org/typescript/-/typescript-5.3.3.tgz" integrity sha512-pXWcraxM0uxAS+tN0AG/BF2TyqmHO014Z070UsJ+pFvYuRSq8KH8DmWpnbXe0pEPDHXZV3FcAbJkijJ5oNEnWw== @@ -3858,7 +3842,7 @@ watchpack@^2.4.0: glob-to-regexp "^0.4.1" graceful-fs "^4.1.2" -webpack-cli@^5.1.4, webpack-cli@5.x.x: +webpack-cli@^5.1.4: version "5.1.4" resolved "https://registry.npmjs.org/webpack-cli/-/webpack-cli-5.1.4.tgz" integrity sha512-pIDJHIEI9LR0yxHXQ+Qh95k2EvXpWzZ5l+d+jIo+RdSm9MiHfzazIxwwni/p7+x4eJZuvG1AJwgC4TNQ7NRgsg== @@ -3895,7 +3879,7 @@ webpack-sources@^3.2.3: resolved "https://registry.npmjs.org/webpack-sources/-/webpack-sources-3.2.3.tgz" integrity sha512-/DyMEOrDgLKKIG0fmvtz+4dUX/3Ghozwgm6iPp8KRhvn+eQf9+Q7GWxVNMk3+uCPWfdXYC4ExGBckIXdFEfH1w== -webpack@^5.1.0, webpack@^5.88.2, webpack@>=5, webpack@5.x.x: +webpack@^5.88.2: version "5.88.2" resolved "https://registry.npmjs.org/webpack/-/webpack-5.88.2.tgz" integrity sha512-JmcgNZ1iKj+aiR0OvTYtWQqJwq37Pf683dY9bVORwVbUrDhLhdn/PlO2sHsFHPkj7sHNQF3JwaAkp49V+Sq1tQ==