From bf8e6f742238988093a429a9d009aa193f5ca319 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sat, 4 Feb 2023 23:02:27 +0300 Subject: [PATCH 001/196] init: npm init for client project --- client/.idea/.gitignore | 6 ++++++ client/.idea/client.iml | 12 ++++++++++++ client/.idea/modules.xml | 8 ++++++++ client/.idea/vcs.xml | 6 ++++++ client/package-lock.json | 13 +++++++++++++ client/package.json | 9 +++++++++ 6 files changed, 54 insertions(+) create mode 100644 client/.idea/.gitignore create mode 100644 client/.idea/client.iml create mode 100644 client/.idea/modules.xml create mode 100644 client/.idea/vcs.xml create mode 100644 client/package-lock.json create mode 100644 client/package.json diff --git a/client/.idea/.gitignore b/client/.idea/.gitignore new file mode 100644 index 0000000..df8562c --- /dev/null +++ b/client/.idea/.gitignore @@ -0,0 +1,6 @@ +# Default ignored files +/shelf/ +/workspace.xml +misc.xml +# Editor-based HTTP Client requests +/httpRequests/ diff --git a/client/.idea/client.iml b/client/.idea/client.iml new file mode 100644 index 0000000..ff88395 --- /dev/null +++ b/client/.idea/client.iml @@ -0,0 +1,12 @@ + + + + + + + + + + + + \ No newline at end of file diff --git a/client/.idea/modules.xml b/client/.idea/modules.xml new file mode 100644 index 0000000..0742ebc --- /dev/null +++ b/client/.idea/modules.xml @@ -0,0 +1,8 @@ + + + + + + + + \ No newline at end of file diff --git a/client/.idea/vcs.xml b/client/.idea/vcs.xml new file mode 100644 index 0000000..6c0b863 --- /dev/null +++ b/client/.idea/vcs.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/client/package-lock.json b/client/package-lock.json new file mode 100644 index 0000000..5254794 --- /dev/null +++ b/client/package-lock.json @@ -0,0 +1,13 @@ +{ + "name": "rs-clone-client", + "version": "0.0.1", + "lockfileVersion": 3, + "requires": true, + "packages": { + "": { + "name": "rs-clone-client", + "version": "0.0.1", + "license": "MIT" + } + } +} diff --git a/client/package.json b/client/package.json new file mode 100644 index 0000000..6e6b061 --- /dev/null +++ b/client/package.json @@ -0,0 +1,9 @@ +{ + "name": "rs-clone-client", + "version": "0.0.1", + "private": true, + "scripts": {}, + "keywords": [], + "author": "HardManDev , VasaSkor, Alexey Zhuchkov", + "license": "MIT" +} From 55f08d0f91f465cb770a419547e168acaac067ce Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sat, 4 Feb 2023 23:05:18 +0300 Subject: [PATCH 002/196] feat: add typescript with default config --- client/package-lock.json | 25 +++++++++- client/package.json | 6 ++- client/tsconfig.json | 104 +++++++++++++++++++++++++++++++++++++++ 3 files changed, 133 insertions(+), 2 deletions(-) create mode 100644 client/tsconfig.json diff --git a/client/package-lock.json b/client/package-lock.json index 5254794..ab6823b 100644 --- a/client/package-lock.json +++ b/client/package-lock.json @@ -7,7 +7,30 @@ "": { "name": "rs-clone-client", "version": "0.0.1", - "license": "MIT" + "license": "MIT", + "devDependencies": { + "@types/node": "^18.11.18", + "typescript": "^4.9.5" + } + }, + "node_modules/@types/node": { + "version": "18.11.18", + "resolved": "https://registry.npmjs.org/@types/node/-/node-18.11.18.tgz", + "integrity": "sha512-DHQpWGjyQKSHj3ebjFI/wRKcqQcdR+MoFBygntYOZytCqNfkd2ZC4ARDJ2DQqhjH5p85Nnd3jhUJIXrszFX/JA==", + "dev": true + }, + "node_modules/typescript": { + "version": "4.9.5", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.9.5.tgz", + "integrity": "sha512-1FXk9E2Hm+QzZQ7z+McJiHL4NW1F2EzMu9Nq9i3zAaGqibafqYwCVU6WyWAuyQRRzOlxou8xZSyXLEN8oKj24g==", + "dev": true, + "bin": { + "tsc": "bin/tsc", + "tsserver": "bin/tsserver" + }, + "engines": { + "node": ">=4.2.0" + } } } } diff --git a/client/package.json b/client/package.json index 6e6b061..0826ec4 100644 --- a/client/package.json +++ b/client/package.json @@ -5,5 +5,9 @@ "scripts": {}, "keywords": [], "author": "HardManDev , VasaSkor, Alexey Zhuchkov", - "license": "MIT" + "license": "MIT", + "devDependencies": { + "@types/node": "^18.11.18", + "typescript": "^4.9.5" + } } diff --git a/client/tsconfig.json b/client/tsconfig.json new file mode 100644 index 0000000..26d14a0 --- /dev/null +++ b/client/tsconfig.json @@ -0,0 +1,104 @@ +{ + "compilerOptions": { + /* Visit https://aka.ms/tsconfig.json to read more about this file */ + + /* Projects */ + // "incremental": true, /* Enable incremental compilation */ + // "composite": true, /* Enable constraints that allow a TypeScript project to be used with project references. */ + // "tsBuildInfoFile": "./", /* Specify the folder for .tsbuildinfo incremental compilation files. */ + // "disableSourceOfProjectReferenceRedirect": true, /* Disable preferring source files instead of declaration files when referencing composite projects */ + // "disableSolutionSearching": true, /* Opt a project out of multi-project reference checking when editing. */ + // "disableReferencedProjectLoad": true, /* Reduce the number of projects loaded automatically by TypeScript. */ + + /* Language and Environment */ + "target": "ES5", /* Set the JavaScript language version for emitted JavaScript and include compatible library declarations. */ + // "lib": [], /* Specify a set of bundled library declaration files that describe the target runtime environment. */ + // "jsx": "preserve", /* Specify what JSX code is generated. */ + // "experimentalDecorators": true, /* Enable experimental support for TC39 stage 2 draft decorators. */ + // "emitDecoratorMetadata": true, /* Emit design-type metadata for decorated declarations in source files. */ + // "jsxFactory": "", /* Specify the JSX factory function used when targeting React JSX emit, e.g. 'React.createElement' or 'h' */ + // "jsxFragmentFactory": "", /* Specify the JSX Fragment reference used for fragments when targeting React JSX emit e.g. 'React.Fragment' or 'Fragment'. */ + // "jsxImportSource": "", /* Specify module specifier used to import the JSX factory functions when using `jsx: react-jsx*`.` */ + // "reactNamespace": "", /* Specify the object invoked for `createElement`. This only applies when targeting `react` JSX emit. */ + // "noLib": true, /* Disable including any library files, including the default lib.d.ts. */ + // "useDefineForClassFields": true, /* Emit ECMAScript-standard-compliant class fields. */ + + /* Modules */ + "module": "ESNext", /* Specify what module code is generated. */ + // "rootDir": "./", /* Specify the root folder within your source files. */ + "moduleResolution": "node", /* Specify how TypeScript looks up a file from a given module specifier. */ + // "baseUrl": "./", /* Specify the base directory to resolve non-relative module names. */ + // "paths": {}, /* Specify a set of entries that re-map imports to additional lookup locations. */ + // "rootDirs": [], /* Allow multiple folders to be treated as one when resolving modules. */ + "typeRoots": [ + "node_modules/@types", + "src/types" + ], /* Specify multiple folders that act like `./node_modules/@types`. */ + // "types": [], /* Specify type package names to be included without being referenced in a source file. */ + // "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */ + // "resolveJsonModule": true, /* Enable importing .json files */ + // "noResolve": true, /* Disallow `import`s, `require`s or ``s from expanding the number of files TypeScript should add to a project. */ + + /* JavaScript Support */ + // "allowJs": true, /* Allow JavaScript files to be a part of your program. Use the `checkJS` option to get errors from these files. */ + // "checkJs": true, /* Enable error reporting in type-checked JavaScript files. */ + // "maxNodeModuleJsDepth": 1, /* Specify the maximum folder depth used for checking JavaScript files from `node_modules`. Only applicable with `allowJs`. */ + + /* Emit */ + // "declaration": true, /* Generate .d.ts files from TypeScript and JavaScript files in your project. */ + // "declarationMap": true, /* Create sourcemaps for d.ts files. */ + // "emitDeclarationOnly": true, /* Only output d.ts files and not JavaScript files. */ + // "sourceMap": true, /* Create source map files for emitted JavaScript files. */ + // "outFile": "./", /* Specify a file that bundles all outputs into one JavaScript file. If `declaration` is true, also designates a file that bundles all .d.ts output. */ + "outDir": "./", /* Specify an output folder for all emitted files. */ + // "removeComments": true, /* Disable emitting comments. */ + // "noEmit": true, /* Disable emitting files from a compilation. */ + // "importHelpers": true, /* Allow importing helper functions from tslib once per project, instead of including them per-file. */ + // "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for types */ + // "downlevelIteration": true, /* Emit more compliant, but verbose and less performant JavaScript for iteration. */ + // "sourceRoot": "", /* Specify the root path for debuggers to find the reference source code. */ + // "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */ + // "inlineSourceMap": true, /* Include sourcemap files inside the emitted JavaScript. */ + // "inlineSources": true, /* Include source code in the sourcemaps inside the emitted JavaScript. */ + // "emitBOM": true, /* Emit a UTF-8 Byte Order Mark (BOM) in the beginning of output files. */ + // "newLine": "crlf", /* Set the newline character for emitting files. */ + // "stripInternal": true, /* Disable emitting declarations that have `@internal` in their JSDoc comments. */ + // "noEmitHelpers": true, /* Disable generating custom helper functions like `__extends` in compiled output. */ + // "noEmitOnError": true, /* Disable emitting files if any type checking errors are reported. */ + // "preserveConstEnums": true, /* Disable erasing `const enum` declarations in generated code. */ + // "declarationDir": "./", /* Specify the output directory for generated declaration files. */ + // "preserveValueImports": true, /* Preserve unused imported values in the JavaScript output that would otherwise be removed. */ + + /* Interop Constraints */ + // "isolatedModules": true, /* Ensure that each file can be safely transpiled without relying on other imports. */ + // "allowSyntheticDefaultImports": true, /* Allow 'import x from y' when a module doesn't have a default export. */ + "esModuleInterop": true, /* Emit additional JavaScript to ease support for importing CommonJS modules. This enables `allowSyntheticDefaultImports` for type compatibility. */ + // "preserveSymlinks": true, /* Disable resolving symlinks to their realpath. This correlates to the same flag in node. */ + "forceConsistentCasingInFileNames": true, /* Ensure that casing is correct in imports. */ + + /* Type Checking */ + "strict": true, /* Enable all strict type-checking options. */ + "noImplicitAny": true, /* Enable error reporting for expressions and declarations with an implied `any` type.. */ + "strictNullChecks": true, /* When type checking, take into account `null` and `undefined`. */ + // "strictFunctionTypes": true, /* When assigning functions, check to ensure parameters and the return values are subtype-compatible. */ + // "strictBindCallApply": true, /* Check that the arguments for `bind`, `call`, and `apply` methods match the original function. */ + // "strictPropertyInitialization": true, /* Check for class properties that are declared but not set in the constructor. */ + // "noImplicitThis": true, /* Enable error reporting when `this` is given the type `any`. */ + // "useUnknownInCatchVariables": true, /* Type catch clause variables as 'unknown' instead of 'any'. */ + // "alwaysStrict": true, /* Ensure 'use strict' is always emitted. */ + // "noUnusedLocals": true, /* Enable error reporting when a local variables aren't read. */ + // "noUnusedParameters": true, /* Raise an error when a function parameter isn't read */ + // "exactOptionalPropertyTypes": true, /* Interpret optional property types as written, rather than adding 'undefined'. */ + // "noImplicitReturns": true, /* Enable error reporting for codepaths that do not explicitly return in a function. */ + // "noFallthroughCasesInSwitch": true, /* Enable error reporting for fallthrough cases in switch statements. */ + // "noUncheckedIndexedAccess": true, /* Include 'undefined' in index signature results */ + // "noImplicitOverride": true, /* Ensure overriding members in derived classes are marked with an override modifier. */ + // "noPropertyAccessFromIndexSignature": true, /* Enforces using indexed accessors for keys declared using an indexed type */ + // "allowUnusedLabels": true, /* Disable error reporting for unused labels. */ + // "allowUnreachableCode": true, /* Disable error reporting for unreachable code. */ + + /* Completeness */ + // "skipDefaultLibCheck": true, /* Skip type checking .d.ts files that are included with TypeScript. */ + "skipLibCheck": true /* Skip type checking all .d.ts files. */ + } +} From b3e72f2e0058e0eb8273c703f3ced95990300567 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sat, 4 Feb 2023 23:14:55 +0300 Subject: [PATCH 003/196] feat: create base webpack config --- client/.idea/jsLibraryMappings.xml | 6 + client/package-lock.json | 6674 +++++++++++++++++++++++++++- client/package.json | 26 +- client/webpack.config.js | 133 + 4 files changed, 6836 insertions(+), 3 deletions(-) create mode 100644 client/.idea/jsLibraryMappings.xml create mode 100644 client/webpack.config.js diff --git a/client/.idea/jsLibraryMappings.xml b/client/.idea/jsLibraryMappings.xml new file mode 100644 index 0000000..d23208f --- /dev/null +++ b/client/.idea/jsLibraryMappings.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/client/package-lock.json b/client/package-lock.json index ab6823b..5077bee 100644 --- a/client/package-lock.json +++ b/client/package-lock.json @@ -9,16 +9,6116 @@ "version": "0.0.1", "license": "MIT", "devDependencies": { + "@babel/preset-env": "^7.20.2", + "@babel/preset-typescript": "^7.18.6", "@types/node": "^18.11.18", - "typescript": "^4.9.5" + "autoprefixer": "^10.4.13", + "babel-loader": "^9.1.2", + "clean-webpack-plugin": "^4.0.0", + "css-loader": "^6.7.3", + "html-webpack-plugin": "^5.5.0", + "mini-css-extract-plugin": "^2.7.2", + "postcss": "^8.4.21", + "postcss-loader": "^7.0.2", + "sass": "^1.58.0", + "sass-loader": "^13.2.0", + "typescript": "^4.9.5", + "url-loader": "^4.1.1", + "webpack": "^5.75.0", + "webpack-cli": "^5.0.1", + "webpack-dev-server": "^4.11.1" } }, + "node_modules/@ampproject/remapping": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@ampproject/remapping/-/remapping-2.2.0.tgz", + "integrity": "sha512-qRmjj8nj9qmLTQXXmaR1cck3UXSRMPrbsLJAasZpF+t3riI71BXed5ebIOYwQntykeZuhjsdweEc9BxH5Jc26w==", + "dev": true, + "peer": true, + "dependencies": { + "@jridgewell/gen-mapping": "^0.1.0", + "@jridgewell/trace-mapping": "^0.3.9" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@babel/code-frame": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.18.6.tgz", + "integrity": "sha512-TDCmlK5eOvH+eH7cdAFlNXeVJqWIQ7gW9tY1GJIpUtFb6CmjVyq2VM3u71bOyR8CRihcCgMUYoDNyLXao3+70Q==", + "dev": true, + "dependencies": { + "@babel/highlight": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/compat-data": { + "version": "7.20.14", + "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.20.14.tgz", + "integrity": "sha512-0YpKHD6ImkWMEINCyDAD0HLLUH/lPCefG8ld9it8DJB2wnApraKuhgYTvTY1z7UFIfBTGy5LwncZ+5HWWGbhFw==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/core": { + "version": "7.20.12", + "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.20.12.tgz", + "integrity": "sha512-XsMfHovsUYHFMdrIHkZphTN/2Hzzi78R08NuHfDBehym2VsPDL6Zn/JAD/JQdnRvbSsbQc4mVaU1m6JgtTEElg==", + "dev": true, + "peer": true, + "dependencies": { + "@ampproject/remapping": "^2.1.0", + "@babel/code-frame": "^7.18.6", + "@babel/generator": "^7.20.7", + "@babel/helper-compilation-targets": "^7.20.7", + "@babel/helper-module-transforms": "^7.20.11", + "@babel/helpers": "^7.20.7", + "@babel/parser": "^7.20.7", + "@babel/template": "^7.20.7", + "@babel/traverse": "^7.20.12", + "@babel/types": "^7.20.7", + "convert-source-map": "^1.7.0", + "debug": "^4.1.0", + "gensync": "^1.0.0-beta.2", + "json5": "^2.2.2", + "semver": "^6.3.0" + }, + "engines": { + "node": ">=6.9.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/babel" + } + }, + "node_modules/@babel/generator": { + "version": "7.20.14", + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.20.14.tgz", + "integrity": "sha512-AEmuXHdcD3A52HHXxaTmYlb8q/xMEhoRP67B3T4Oq7lbmSoqroMZzjnGj3+i1io3pdnF8iBYVu4Ilj+c4hBxYg==", + "dev": true, + "dependencies": { + "@babel/types": "^7.20.7", + "@jridgewell/gen-mapping": "^0.3.2", + "jsesc": "^2.5.1" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/generator/node_modules/@jridgewell/gen-mapping": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.2.tgz", + "integrity": "sha512-mh65xKQAzI6iBcFzwv28KVWSmCkdRBWoOh+bYQGW3+6OZvbbN3TqMGo5hqYxQniRcH9F2VZIoJCm4pa3BPDK/A==", + "dev": true, + "dependencies": { + "@jridgewell/set-array": "^1.0.1", + "@jridgewell/sourcemap-codec": "^1.4.10", + "@jridgewell/trace-mapping": "^0.3.9" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@babel/helper-annotate-as-pure": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.18.6.tgz", + "integrity": "sha512-duORpUiYrEpzKIop6iNbjnwKLAKnJ47csTyRACyEmWj0QdUrm5aqNJGHSSEQSUAvNW0ojX0dOmK9dZduvkfeXA==", + "dev": true, + "dependencies": { + "@babel/types": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-builder-binary-assignment-operator-visitor": { + "version": "7.18.9", + "resolved": "https://registry.npmjs.org/@babel/helper-builder-binary-assignment-operator-visitor/-/helper-builder-binary-assignment-operator-visitor-7.18.9.tgz", + "integrity": "sha512-yFQ0YCHoIqarl8BCRwBL8ulYUaZpz3bNsA7oFepAzee+8/+ImtADXNOmO5vJvsPff3qi+hvpkY/NYBTrBQgdNw==", + "dev": true, + "dependencies": { + "@babel/helper-explode-assignable-expression": "^7.18.6", + "@babel/types": "^7.18.9" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-compilation-targets": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/helper-compilation-targets/-/helper-compilation-targets-7.20.7.tgz", + "integrity": "sha512-4tGORmfQcrc+bvrjb5y3dG9Mx1IOZjsHqQVUz7XCNHO+iTmqxWnVg3KRygjGmpRLJGdQSKuvFinbIb0CnZwHAQ==", + "dev": true, + "dependencies": { + "@babel/compat-data": "^7.20.5", + "@babel/helper-validator-option": "^7.18.6", + "browserslist": "^4.21.3", + "lru-cache": "^5.1.1", + "semver": "^6.3.0" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/helper-create-class-features-plugin": { + "version": "7.20.12", + "resolved": "https://registry.npmjs.org/@babel/helper-create-class-features-plugin/-/helper-create-class-features-plugin-7.20.12.tgz", + "integrity": "sha512-9OunRkbT0JQcednL0UFvbfXpAsUXiGjUk0a7sN8fUXX7Mue79cUSMjHGDRRi/Vz9vYlpIhLV5fMD5dKoMhhsNQ==", + "dev": true, + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.18.6", + "@babel/helper-environment-visitor": "^7.18.9", + "@babel/helper-function-name": "^7.19.0", + "@babel/helper-member-expression-to-functions": "^7.20.7", + "@babel/helper-optimise-call-expression": "^7.18.6", + "@babel/helper-replace-supers": "^7.20.7", + "@babel/helper-skip-transparent-expression-wrappers": "^7.20.0", + "@babel/helper-split-export-declaration": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/helper-create-regexp-features-plugin": { + "version": "7.20.5", + "resolved": "https://registry.npmjs.org/@babel/helper-create-regexp-features-plugin/-/helper-create-regexp-features-plugin-7.20.5.tgz", + "integrity": "sha512-m68B1lkg3XDGX5yCvGO0kPx3v9WIYLnzjKfPcQiwntEQa5ZeRkPmo2X/ISJc8qxWGfwUr+kvZAeEzAwLec2r2w==", + "dev": true, + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.18.6", + "regexpu-core": "^5.2.1" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/helper-define-polyfill-provider": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.3.3.tgz", + "integrity": "sha512-z5aQKU4IzbqCC1XH0nAqfsFLMVSo22SBKUc0BxGrLkolTdPTructy0ToNnlO2zA4j9Q/7pjMZf0DSY+DSTYzww==", + "dev": true, + "dependencies": { + "@babel/helper-compilation-targets": "^7.17.7", + "@babel/helper-plugin-utils": "^7.16.7", + "debug": "^4.1.1", + "lodash.debounce": "^4.0.8", + "resolve": "^1.14.2", + "semver": "^6.1.2" + }, + "peerDependencies": { + "@babel/core": "^7.4.0-0" + } + }, + "node_modules/@babel/helper-environment-visitor": { + "version": "7.18.9", + "resolved": "https://registry.npmjs.org/@babel/helper-environment-visitor/-/helper-environment-visitor-7.18.9.tgz", + "integrity": "sha512-3r/aACDJ3fhQ/EVgFy0hpj8oHyHpQc+LPtJoY9SzTThAsStm4Ptegq92vqKoE3vD706ZVFWITnMnxucw+S9Ipg==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-explode-assignable-expression": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/helper-explode-assignable-expression/-/helper-explode-assignable-expression-7.18.6.tgz", + "integrity": "sha512-eyAYAsQmB80jNfg4baAtLeWAQHfHFiR483rzFK+BhETlGZaQC9bsfrugfXDCbRHLQbIA7U5NxhhOxN7p/dWIcg==", + "dev": true, + "dependencies": { + "@babel/types": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-function-name": { + "version": "7.19.0", + "resolved": "https://registry.npmjs.org/@babel/helper-function-name/-/helper-function-name-7.19.0.tgz", + "integrity": "sha512-WAwHBINyrpqywkUH0nTnNgI5ina5TFn85HKS0pbPDfxFfhyR/aNQEn4hGi1P1JyT//I0t4OgXUlofzWILRvS5w==", + "dev": true, + "dependencies": { + "@babel/template": "^7.18.10", + "@babel/types": "^7.19.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-hoist-variables": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/helper-hoist-variables/-/helper-hoist-variables-7.18.6.tgz", + "integrity": "sha512-UlJQPkFqFULIcyW5sbzgbkxn2FKRgwWiRexcuaR8RNJRy8+LLveqPjwZV/bwrLZCN0eUHD/x8D0heK1ozuoo6Q==", + "dev": true, + "dependencies": { + "@babel/types": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-member-expression-to-functions": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/helper-member-expression-to-functions/-/helper-member-expression-to-functions-7.20.7.tgz", + "integrity": "sha512-9J0CxJLq315fEdi4s7xK5TQaNYjZw+nDVpVqr1axNGKzdrdwYBD5b4uKv3n75aABG0rCCTK8Im8Ww7eYfMrZgw==", + "dev": true, + "dependencies": { + "@babel/types": "^7.20.7" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-module-imports": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.18.6.tgz", + "integrity": "sha512-0NFvs3VkuSYbFi1x2Vd6tKrywq+z/cLeYC/RJNFrIX/30Bf5aiGYbtvGXolEktzJH8o5E5KJ3tT+nkxuuZFVlA==", + "dev": true, + "dependencies": { + "@babel/types": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-module-transforms": { + "version": "7.20.11", + "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.20.11.tgz", + "integrity": "sha512-uRy78kN4psmji1s2QtbtcCSaj/LILFDp0f/ymhpQH5QY3nljUZCaNWz9X1dEj/8MBdBEFECs7yRhKn8i7NjZgg==", + "dev": true, + "dependencies": { + "@babel/helper-environment-visitor": "^7.18.9", + "@babel/helper-module-imports": "^7.18.6", + "@babel/helper-simple-access": "^7.20.2", + "@babel/helper-split-export-declaration": "^7.18.6", + "@babel/helper-validator-identifier": "^7.19.1", + "@babel/template": "^7.20.7", + "@babel/traverse": "^7.20.10", + "@babel/types": "^7.20.7" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-optimise-call-expression": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/helper-optimise-call-expression/-/helper-optimise-call-expression-7.18.6.tgz", + "integrity": "sha512-HP59oD9/fEHQkdcbgFCnbmgH5vIQTJbxh2yf+CdM89/glUNnuzr87Q8GIjGEnOktTROemO0Pe0iPAYbqZuOUiA==", + "dev": true, + "dependencies": { + "@babel/types": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-plugin-utils": { + "version": "7.20.2", + "resolved": "https://registry.npmjs.org/@babel/helper-plugin-utils/-/helper-plugin-utils-7.20.2.tgz", + "integrity": "sha512-8RvlJG2mj4huQ4pZ+rU9lqKi9ZKiRmuvGuM2HlWmkmgOhbs6zEAw6IEiJ5cQqGbDzGZOhwuOQNtZMi/ENLjZoQ==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-remap-async-to-generator": { + "version": "7.18.9", + "resolved": "https://registry.npmjs.org/@babel/helper-remap-async-to-generator/-/helper-remap-async-to-generator-7.18.9.tgz", + "integrity": "sha512-dI7q50YKd8BAv3VEfgg7PS7yD3Rtbi2J1XMXaalXO0W0164hYLnh8zpjRS0mte9MfVp/tltvr/cfdXPvJr1opA==", + "dev": true, + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.18.6", + "@babel/helper-environment-visitor": "^7.18.9", + "@babel/helper-wrap-function": "^7.18.9", + "@babel/types": "^7.18.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/helper-replace-supers": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/helper-replace-supers/-/helper-replace-supers-7.20.7.tgz", + "integrity": "sha512-vujDMtB6LVfNW13jhlCrp48QNslK6JXi7lQG736HVbHz/mbf4Dc7tIRh1Xf5C0rF7BP8iiSxGMCmY6Ci1ven3A==", + "dev": true, + "dependencies": { + "@babel/helper-environment-visitor": "^7.18.9", + "@babel/helper-member-expression-to-functions": "^7.20.7", + "@babel/helper-optimise-call-expression": "^7.18.6", + "@babel/template": "^7.20.7", + "@babel/traverse": "^7.20.7", + "@babel/types": "^7.20.7" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-simple-access": { + "version": "7.20.2", + "resolved": "https://registry.npmjs.org/@babel/helper-simple-access/-/helper-simple-access-7.20.2.tgz", + "integrity": "sha512-+0woI/WPq59IrqDYbVGfshjT5Dmk/nnbdpcF8SnMhhXObpTq2KNBdLFRFrkVdbDOyUmHBCxzm5FHV1rACIkIbA==", + "dev": true, + "dependencies": { + "@babel/types": "^7.20.2" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-skip-transparent-expression-wrappers": { + "version": "7.20.0", + "resolved": "https://registry.npmjs.org/@babel/helper-skip-transparent-expression-wrappers/-/helper-skip-transparent-expression-wrappers-7.20.0.tgz", + "integrity": "sha512-5y1JYeNKfvnT8sZcK9DVRtpTbGiomYIHviSP3OQWmDPU3DeH4a1ZlT/N2lyQ5P8egjcRaT/Y9aNqUxK0WsnIIg==", + "dev": true, + "dependencies": { + "@babel/types": "^7.20.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-split-export-declaration": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.18.6.tgz", + "integrity": "sha512-bde1etTx6ZyTmobl9LLMMQsaizFVZrquTEHOqKeQESMKo4PlObf+8+JA25ZsIpZhT/WEd39+vOdLXAFG/nELpA==", + "dev": true, + "dependencies": { + "@babel/types": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-string-parser": { + "version": "7.19.4", + "resolved": "https://registry.npmjs.org/@babel/helper-string-parser/-/helper-string-parser-7.19.4.tgz", + "integrity": "sha512-nHtDoQcuqFmwYNYPz3Rah5ph2p8PFeFCsZk9A/48dPc/rGocJ5J3hAAZ7pb76VWX3fZKu+uEr/FhH5jLx7umrw==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-validator-identifier": { + "version": "7.19.1", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.19.1.tgz", + "integrity": "sha512-awrNfaMtnHUr653GgGEs++LlAvW6w+DcPrOliSMXWCKo597CwL5Acf/wWdNkf/tfEQE3mjkeD1YOVZOUV/od1w==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-validator-option": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-option/-/helper-validator-option-7.18.6.tgz", + "integrity": "sha512-XO7gESt5ouv/LRJdrVjkShckw6STTaB7l9BrpBaAHDeF5YZT+01PCwmR0SJHnkW6i8OwW/EVWRShfi4j2x+KQw==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-wrap-function": { + "version": "7.20.5", + "resolved": "https://registry.npmjs.org/@babel/helper-wrap-function/-/helper-wrap-function-7.20.5.tgz", + "integrity": "sha512-bYMxIWK5mh+TgXGVqAtnu5Yn1un+v8DDZtqyzKRLUzrh70Eal2O3aZ7aPYiMADO4uKlkzOiRiZ6GX5q3qxvW9Q==", + "dev": true, + "dependencies": { + "@babel/helper-function-name": "^7.19.0", + "@babel/template": "^7.18.10", + "@babel/traverse": "^7.20.5", + "@babel/types": "^7.20.5" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helpers": { + "version": "7.20.13", + "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.20.13.tgz", + "integrity": "sha512-nzJ0DWCL3gB5RCXbUO3KIMMsBY2Eqbx8mBpKGE/02PgyRQFcPQLbkQ1vyy596mZLaP+dAfD+R4ckASzNVmW3jg==", + "dev": true, + "peer": true, + "dependencies": { + "@babel/template": "^7.20.7", + "@babel/traverse": "^7.20.13", + "@babel/types": "^7.20.7" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/highlight": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.18.6.tgz", + "integrity": "sha512-u7stbOuYjaPezCuLj29hNW1v64M2Md2qupEKP1fHc7WdOA3DgLh37suiSrZYY7haUB7iBeQZ9P1uiRF359do3g==", + "dev": true, + "dependencies": { + "@babel/helper-validator-identifier": "^7.18.6", + "chalk": "^2.0.0", + "js-tokens": "^4.0.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/parser": { + "version": "7.20.15", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.20.15.tgz", + "integrity": "sha512-DI4a1oZuf8wC+oAJA9RW6ga3Zbe8RZFt7kD9i4qAspz3I/yHet1VvC3DiSy/fsUvv5pvJuNPh0LPOdCcqinDPg==", + "dev": true, + "bin": { + "parser": "bin/babel-parser.js" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression/-/plugin-bugfix-safari-id-destructuring-collision-in-function-expression-7.18.6.tgz", + "integrity": "sha512-Dgxsyg54Fx1d4Nge8UnvTrED63vrwOdPmyvPzlNN/boaliRP54pm3pGzZD1SJUwrBA+Cs/xdG8kXX6Mn/RfISQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining/-/plugin-bugfix-v8-spread-parameters-in-optional-chaining-7.20.7.tgz", + "integrity": "sha512-sbr9+wNE5aXMBBFBICk01tt7sBf2Oc9ikRFEcem/ZORup9IMUdNhW7/wVLEbbtlWOsEubJet46mHAL2C8+2jKQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/helper-skip-transparent-expression-wrappers": "^7.20.0", + "@babel/plugin-proposal-optional-chaining": "^7.20.7" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.13.0" + } + }, + "node_modules/@babel/plugin-proposal-async-generator-functions": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-async-generator-functions/-/plugin-proposal-async-generator-functions-7.20.7.tgz", + "integrity": "sha512-xMbiLsn/8RK7Wq7VeVytytS2L6qE69bXPB10YCmMdDZbKF4okCqY74pI/jJQ/8U0b/F6NrT2+14b8/P9/3AMGA==", + "dev": true, + "dependencies": { + "@babel/helper-environment-visitor": "^7.18.9", + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/helper-remap-async-to-generator": "^7.18.9", + "@babel/plugin-syntax-async-generators": "^7.8.4" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-class-properties": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-class-properties/-/plugin-proposal-class-properties-7.18.6.tgz", + "integrity": "sha512-cumfXOF0+nzZrrN8Rf0t7M+tF6sZc7vhQwYQck9q1/5w2OExlD+b4v4RpMJFaV1Z7WcDRgO6FqvxqxGlwo+RHQ==", + "dev": true, + "dependencies": { + "@babel/helper-create-class-features-plugin": "^7.18.6", + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-class-static-block": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-class-static-block/-/plugin-proposal-class-static-block-7.20.7.tgz", + "integrity": "sha512-AveGOoi9DAjUYYuUAG//Ig69GlazLnoyzMw68VCDux+c1tsnnH/OkYcpz/5xzMkEFC6UxjR5Gw1c+iY2wOGVeQ==", + "dev": true, + "dependencies": { + "@babel/helper-create-class-features-plugin": "^7.20.7", + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/plugin-syntax-class-static-block": "^7.14.5" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.12.0" + } + }, + "node_modules/@babel/plugin-proposal-dynamic-import": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-dynamic-import/-/plugin-proposal-dynamic-import-7.18.6.tgz", + "integrity": "sha512-1auuwmK+Rz13SJj36R+jqFPMJWyKEDd7lLSdOj4oJK0UTgGueSAtkrCvz9ewmgyU/P941Rv2fQwZJN8s6QruXw==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6", + "@babel/plugin-syntax-dynamic-import": "^7.8.3" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-export-namespace-from": { + "version": "7.18.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-export-namespace-from/-/plugin-proposal-export-namespace-from-7.18.9.tgz", + "integrity": "sha512-k1NtHyOMvlDDFeb9G5PhUXuGj8m/wiwojgQVEhJ/fsVsMCpLyOP4h0uGEjYJKrRI+EVPlb5Jk+Gt9P97lOGwtA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.9", + "@babel/plugin-syntax-export-namespace-from": "^7.8.3" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-json-strings": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-json-strings/-/plugin-proposal-json-strings-7.18.6.tgz", + "integrity": "sha512-lr1peyn9kOdbYc0xr0OdHTZ5FMqS6Di+H0Fz2I/JwMzGmzJETNeOFq2pBySw6X/KFL5EWDjlJuMsUGRFb8fQgQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6", + "@babel/plugin-syntax-json-strings": "^7.8.3" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-logical-assignment-operators": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-logical-assignment-operators/-/plugin-proposal-logical-assignment-operators-7.20.7.tgz", + "integrity": "sha512-y7C7cZgpMIjWlKE5T7eJwp+tnRYM89HmRvWM5EQuB5BoHEONjmQ8lSNmBUwOyy/GFRsohJED51YBF79hE1djug==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/plugin-syntax-logical-assignment-operators": "^7.10.4" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-nullish-coalescing-operator": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-nullish-coalescing-operator/-/plugin-proposal-nullish-coalescing-operator-7.18.6.tgz", + "integrity": "sha512-wQxQzxYeJqHcfppzBDnm1yAY0jSRkUXR2z8RePZYrKwMKgMlE8+Z6LUno+bd6LvbGh8Gltvy74+9pIYkr+XkKA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6", + "@babel/plugin-syntax-nullish-coalescing-operator": "^7.8.3" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-numeric-separator": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-numeric-separator/-/plugin-proposal-numeric-separator-7.18.6.tgz", + "integrity": "sha512-ozlZFogPqoLm8WBr5Z8UckIoE4YQ5KESVcNudyXOR8uqIkliTEgJ3RoketfG6pmzLdeZF0H/wjE9/cCEitBl7Q==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6", + "@babel/plugin-syntax-numeric-separator": "^7.10.4" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-object-rest-spread": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-object-rest-spread/-/plugin-proposal-object-rest-spread-7.20.7.tgz", + "integrity": "sha512-d2S98yCiLxDVmBmE8UjGcfPvNEUbA1U5q5WxaWFUGRzJSVAZqm5W6MbPct0jxnegUZ0niLeNX+IOzEs7wYg9Dg==", + "dev": true, + "dependencies": { + "@babel/compat-data": "^7.20.5", + "@babel/helper-compilation-targets": "^7.20.7", + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/plugin-syntax-object-rest-spread": "^7.8.3", + "@babel/plugin-transform-parameters": "^7.20.7" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-optional-catch-binding": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-optional-catch-binding/-/plugin-proposal-optional-catch-binding-7.18.6.tgz", + "integrity": "sha512-Q40HEhs9DJQyaZfUjjn6vE8Cv4GmMHCYuMGIWUnlxH6400VGxOuwWsPt4FxXxJkC/5eOzgn0z21M9gMT4MOhbw==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6", + "@babel/plugin-syntax-optional-catch-binding": "^7.8.3" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-optional-chaining": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-optional-chaining/-/plugin-proposal-optional-chaining-7.20.7.tgz", + "integrity": "sha512-T+A7b1kfjtRM51ssoOfS1+wbyCVqorfyZhT99TvxxLMirPShD8CzKMRepMlCBGM5RpHMbn8s+5MMHnPstJH6mQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/helper-skip-transparent-expression-wrappers": "^7.20.0", + "@babel/plugin-syntax-optional-chaining": "^7.8.3" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-private-methods": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-private-methods/-/plugin-proposal-private-methods-7.18.6.tgz", + "integrity": "sha512-nutsvktDItsNn4rpGItSNV2sz1XwS+nfU0Rg8aCx3W3NOKVzdMjJRu0O5OkgDp3ZGICSTbgRpxZoWsxoKRvbeA==", + "dev": true, + "dependencies": { + "@babel/helper-create-class-features-plugin": "^7.18.6", + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-private-property-in-object": { + "version": "7.20.5", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-private-property-in-object/-/plugin-proposal-private-property-in-object-7.20.5.tgz", + "integrity": "sha512-Vq7b9dUA12ByzB4EjQTPo25sFhY+08pQDBSZRtUAkj7lb7jahaHR5igera16QZ+3my1nYR4dKsNdYj5IjPHilQ==", + "dev": true, + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.18.6", + "@babel/helper-create-class-features-plugin": "^7.20.5", + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/plugin-syntax-private-property-in-object": "^7.14.5" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-proposal-unicode-property-regex": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-unicode-property-regex/-/plugin-proposal-unicode-property-regex-7.18.6.tgz", + "integrity": "sha512-2BShG/d5yoZyXZfVePH91urL5wTG6ASZU9M4o03lKK8u8UW1y08OMttBSOADTcJrnPMpvDXRG3G8fyLh4ovs8w==", + "dev": true, + "dependencies": { + "@babel/helper-create-regexp-features-plugin": "^7.18.6", + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=4" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-async-generators": { + "version": "7.8.4", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-async-generators/-/plugin-syntax-async-generators-7.8.4.tgz", + "integrity": "sha512-tycmZxkGfZaxhMRbXlPXuVFpdWlXpir2W4AMhSJgRKzk/eDlIXOhb2LHWoLpDF7TEHylV5zNhykX6KAgHJmTNw==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-class-properties": { + "version": "7.12.13", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-class-properties/-/plugin-syntax-class-properties-7.12.13.tgz", + "integrity": "sha512-fm4idjKla0YahUNgFNLCB0qySdsoPiZP3iQE3rky0mBUtMZ23yDJ9SJdg6dXTSDnulOVqiF3Hgr9nbXvXTQZYA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.12.13" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-class-static-block": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-class-static-block/-/plugin-syntax-class-static-block-7.14.5.tgz", + "integrity": "sha512-b+YyPmr6ldyNnM6sqYeMWE+bgJcJpO6yS4QD7ymxgH34GBPNDM/THBh8iunyvKIZztiwLH4CJZ0RxTk9emgpjw==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.14.5" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-dynamic-import": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-dynamic-import/-/plugin-syntax-dynamic-import-7.8.3.tgz", + "integrity": "sha512-5gdGbFon+PszYzqs83S3E5mpi7/y/8M9eC90MRTZfduQOYW76ig6SOSPNe41IG5LoP3FGBn2N0RjVDSQiS94kQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-export-namespace-from": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-export-namespace-from/-/plugin-syntax-export-namespace-from-7.8.3.tgz", + "integrity": "sha512-MXf5laXo6c1IbEbegDmzGPwGNTsHZmEy6QGznu5Sh2UCWvueywb2ee+CCE4zQiZstxU9BMoQO9i6zUFSY0Kj0Q==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.3" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-import-assertions": { + "version": "7.20.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-assertions/-/plugin-syntax-import-assertions-7.20.0.tgz", + "integrity": "sha512-IUh1vakzNoWalR8ch/areW7qFopR2AEw03JlG7BbrDqmQ4X3q9uuipQwSGrUn7oGiemKjtSLDhNtQHzMHr1JdQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.19.0" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-json-strings": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-json-strings/-/plugin-syntax-json-strings-7.8.3.tgz", + "integrity": "sha512-lY6kdGpWHvjoe2vk4WrAapEuBR69EMxZl+RoGRhrFGNYVK8mOPAW8VfbT/ZgrFbXlDNiiaxQnAtgVCZ6jv30EA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-logical-assignment-operators": { + "version": "7.10.4", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-logical-assignment-operators/-/plugin-syntax-logical-assignment-operators-7.10.4.tgz", + "integrity": "sha512-d8waShlpFDinQ5MtvGU9xDAOzKH47+FFoney2baFIoMr952hKOLp1HR7VszoZvOsV/4+RRszNY7D17ba0te0ig==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.10.4" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-nullish-coalescing-operator": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-nullish-coalescing-operator/-/plugin-syntax-nullish-coalescing-operator-7.8.3.tgz", + "integrity": "sha512-aSff4zPII1u2QD7y+F8oDsz19ew4IGEJg9SVW+bqwpwtfFleiQDMdzA/R+UlWDzfnHFCxxleFT0PMIrR36XLNQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-numeric-separator": { + "version": "7.10.4", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-numeric-separator/-/plugin-syntax-numeric-separator-7.10.4.tgz", + "integrity": "sha512-9H6YdfkcK/uOnY/K7/aA2xpzaAgkQn37yzWUMRK7OaPOqOpGS1+n0H5hxT9AUw9EsSjPW8SVyMJwYRtWs3X3ug==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.10.4" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-object-rest-spread": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-object-rest-spread/-/plugin-syntax-object-rest-spread-7.8.3.tgz", + "integrity": "sha512-XoqMijGZb9y3y2XskN+P1wUGiVwWZ5JmoDRwx5+3GmEplNyVM2s2Dg8ILFQm8rWM48orGy5YpI5Bl8U1y7ydlA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-optional-catch-binding": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-optional-catch-binding/-/plugin-syntax-optional-catch-binding-7.8.3.tgz", + "integrity": "sha512-6VPD0Pc1lpTqw0aKoeRTMiB+kWhAoT24PA+ksWSBrFtl5SIRVpZlwN3NNPQjehA2E/91FV3RjLWoVTglWcSV3Q==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-optional-chaining": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-optional-chaining/-/plugin-syntax-optional-chaining-7.8.3.tgz", + "integrity": "sha512-KoK9ErH1MBlCPxV0VANkXW2/dw4vlbGDrFgz8bmUsBGYkFRcbRwMh6cIJubdPrkxRwuGdtCk0v/wPTKbQgBjkg==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-private-property-in-object": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-private-property-in-object/-/plugin-syntax-private-property-in-object-7.14.5.tgz", + "integrity": "sha512-0wVnp9dxJ72ZUJDV27ZfbSj6iHLoytYZmh3rFcxNnvsJF3ktkzLDZPy/mA17HGsaQT3/DQsWYX1f1QGWkCoVUg==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.14.5" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-top-level-await": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-top-level-await/-/plugin-syntax-top-level-await-7.14.5.tgz", + "integrity": "sha512-hx++upLv5U1rgYfwe1xBQUhRmU41NEvpUvrp8jkrSCdvGSnM5/qdRMtylJ6PG5OFkBaHkbTAKTnd3/YyESRHFw==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.14.5" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-typescript": { + "version": "7.20.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-typescript/-/plugin-syntax-typescript-7.20.0.tgz", + "integrity": "sha512-rd9TkG+u1CExzS4SM1BlMEhMXwFLKVjOAFFCDx9PbX5ycJWDoWMcwdJH9RhkPu1dOgn5TrxLot/Gx6lWFuAUNQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.19.0" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-arrow-functions": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-arrow-functions/-/plugin-transform-arrow-functions-7.20.7.tgz", + "integrity": "sha512-3poA5E7dzDomxj9WXWwuD6A5F3kc7VXwIJO+E+J8qtDtS+pXPAhrgEyh+9GBwBgPq1Z+bB+/JD60lp5jsN7JPQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.20.2" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-async-to-generator": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-to-generator/-/plugin-transform-async-to-generator-7.20.7.tgz", + "integrity": "sha512-Uo5gwHPT9vgnSXQxqGtpdufUiWp96gk7yiP4Mp5bm1QMkEmLXBO7PAGYbKoJ6DhAwiNkcHFBol/x5zZZkL/t0Q==", + "dev": true, + "dependencies": { + "@babel/helper-module-imports": "^7.18.6", + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/helper-remap-async-to-generator": "^7.18.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-block-scoped-functions": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoped-functions/-/plugin-transform-block-scoped-functions-7.18.6.tgz", + "integrity": "sha512-ExUcOqpPWnliRcPqves5HJcJOvHvIIWfuS4sroBUenPuMdmW+SMHDakmtS7qOo13sVppmUijqeTv7qqGsvURpQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-block-scoping": { + "version": "7.20.15", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-block-scoping/-/plugin-transform-block-scoping-7.20.15.tgz", + "integrity": "sha512-Vv4DMZ6MiNOhu/LdaZsT/bsLRxgL94d269Mv4R/9sp6+Mp++X/JqypZYypJXLlM4mlL352/Egzbzr98iABH1CA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.20.2" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-classes": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-classes/-/plugin-transform-classes-7.20.7.tgz", + "integrity": "sha512-LWYbsiXTPKl+oBlXUGlwNlJZetXD5Am+CyBdqhPsDVjM9Jc8jwBJFrKhHf900Kfk2eZG1y9MAG3UNajol7A4VQ==", + "dev": true, + "dependencies": { + "@babel/helper-annotate-as-pure": "^7.18.6", + "@babel/helper-compilation-targets": "^7.20.7", + "@babel/helper-environment-visitor": "^7.18.9", + "@babel/helper-function-name": "^7.19.0", + "@babel/helper-optimise-call-expression": "^7.18.6", + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/helper-replace-supers": "^7.20.7", + "@babel/helper-split-export-declaration": "^7.18.6", + "globals": "^11.1.0" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-computed-properties": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-computed-properties/-/plugin-transform-computed-properties-7.20.7.tgz", + "integrity": "sha512-Lz7MvBK6DTjElHAmfu6bfANzKcxpyNPeYBGEafyA6E5HtRpjpZwU+u7Qrgz/2OR0z+5TvKYbPdphfSaAcZBrYQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/template": "^7.20.7" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-destructuring": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-destructuring/-/plugin-transform-destructuring-7.20.7.tgz", + "integrity": "sha512-Xwg403sRrZb81IVB79ZPqNQME23yhugYVqgTxAhT99h485F4f+GMELFhhOsscDUB7HCswepKeCKLn/GZvUKoBA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.20.2" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-dotall-regex": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-dotall-regex/-/plugin-transform-dotall-regex-7.18.6.tgz", + "integrity": "sha512-6S3jpun1eEbAxq7TdjLotAsl4WpQI9DxfkycRcKrjhQYzU87qpXdknpBg/e+TdcMehqGnLFi7tnFUBR02Vq6wg==", + "dev": true, + "dependencies": { + "@babel/helper-create-regexp-features-plugin": "^7.18.6", + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-duplicate-keys": { + "version": "7.18.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-duplicate-keys/-/plugin-transform-duplicate-keys-7.18.9.tgz", + "integrity": "sha512-d2bmXCtZXYc59/0SanQKbiWINadaJXqtvIQIzd4+hNwkWBgyCd5F/2t1kXoUdvPMrxzPvhK6EMQRROxsue+mfw==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-exponentiation-operator": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-exponentiation-operator/-/plugin-transform-exponentiation-operator-7.18.6.tgz", + "integrity": "sha512-wzEtc0+2c88FVR34aQmiz56dxEkxr2g8DQb/KfaFa1JYXOFVsbhvAonFN6PwVWj++fKmku8NP80plJ5Et4wqHw==", + "dev": true, + "dependencies": { + "@babel/helper-builder-binary-assignment-operator-visitor": "^7.18.6", + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-for-of": { + "version": "7.18.8", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.18.8.tgz", + "integrity": "sha512-yEfTRnjuskWYo0k1mHUqrVWaZwrdq8AYbfrpqULOJOaucGSp4mNMVps+YtA8byoevxS/urwU75vyhQIxcCgiBQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-function-name": { + "version": "7.18.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-function-name/-/plugin-transform-function-name-7.18.9.tgz", + "integrity": "sha512-WvIBoRPaJQ5yVHzcnJFor7oS5Ls0PYixlTYE63lCj2RtdQEl15M68FXQlxnG6wdraJIXRdR7KI+hQ7q/9QjrCQ==", + "dev": true, + "dependencies": { + "@babel/helper-compilation-targets": "^7.18.9", + "@babel/helper-function-name": "^7.18.9", + "@babel/helper-plugin-utils": "^7.18.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-literals": { + "version": "7.18.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-literals/-/plugin-transform-literals-7.18.9.tgz", + "integrity": "sha512-IFQDSRoTPnrAIrI5zoZv73IFeZu2dhu6irxQjY9rNjTT53VmKg9fenjvoiOWOkJ6mm4jKVPtdMzBY98Fp4Z4cg==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-member-expression-literals": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-member-expression-literals/-/plugin-transform-member-expression-literals-7.18.6.tgz", + "integrity": "sha512-qSF1ihLGO3q+/g48k85tUjD033C29TNTVB2paCwZPVmOsjn9pClvYYrM2VeJpBY2bcNkuny0YUyTNRyRxJ54KA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-modules-amd": { + "version": "7.20.11", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-amd/-/plugin-transform-modules-amd-7.20.11.tgz", + "integrity": "sha512-NuzCt5IIYOW0O30UvqktzHYR2ud5bOWbY0yaxWZ6G+aFzOMJvrs5YHNikrbdaT15+KNO31nPOy5Fim3ku6Zb5g==", + "dev": true, + "dependencies": { + "@babel/helper-module-transforms": "^7.20.11", + "@babel/helper-plugin-utils": "^7.20.2" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-modules-commonjs": { + "version": "7.20.11", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-commonjs/-/plugin-transform-modules-commonjs-7.20.11.tgz", + "integrity": "sha512-S8e1f7WQ7cimJQ51JkAaDrEtohVEitXjgCGAS2N8S31Y42E+kWwfSz83LYz57QdBm7q9diARVqanIaH2oVgQnw==", + "dev": true, + "dependencies": { + "@babel/helper-module-transforms": "^7.20.11", + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/helper-simple-access": "^7.20.2" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-modules-systemjs": { + "version": "7.20.11", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-systemjs/-/plugin-transform-modules-systemjs-7.20.11.tgz", + "integrity": "sha512-vVu5g9BPQKSFEmvt2TA4Da5N+QVS66EX21d8uoOihC+OCpUoGvzVsXeqFdtAEfVa5BILAeFt+U7yVmLbQnAJmw==", + "dev": true, + "dependencies": { + "@babel/helper-hoist-variables": "^7.18.6", + "@babel/helper-module-transforms": "^7.20.11", + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/helper-validator-identifier": "^7.19.1" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-modules-umd": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-modules-umd/-/plugin-transform-modules-umd-7.18.6.tgz", + "integrity": "sha512-dcegErExVeXcRqNtkRU/z8WlBLnvD4MRnHgNs3MytRO1Mn1sHRyhbcpYbVMGclAqOjdW+9cfkdZno9dFdfKLfQ==", + "dev": true, + "dependencies": { + "@babel/helper-module-transforms": "^7.18.6", + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-named-capturing-groups-regex": { + "version": "7.20.5", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-named-capturing-groups-regex/-/plugin-transform-named-capturing-groups-regex-7.20.5.tgz", + "integrity": "sha512-mOW4tTzi5iTLnw+78iEq3gr8Aoq4WNRGpmSlrogqaiCBoR1HFhpU4JkpQFOHfeYx3ReVIFWOQJS4aZBRvuZ6mA==", + "dev": true, + "dependencies": { + "@babel/helper-create-regexp-features-plugin": "^7.20.5", + "@babel/helper-plugin-utils": "^7.20.2" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/plugin-transform-new-target": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-new-target/-/plugin-transform-new-target-7.18.6.tgz", + "integrity": "sha512-DjwFA/9Iu3Z+vrAn+8pBUGcjhxKguSMlsFqeCKbhb9BAV756v0krzVK04CRDi/4aqmk8BsHb4a/gFcaA5joXRw==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-object-super": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-object-super/-/plugin-transform-object-super-7.18.6.tgz", + "integrity": "sha512-uvGz6zk+pZoS1aTZrOvrbj6Pp/kK2mp45t2B+bTDre2UgsZZ8EZLSJtUg7m/no0zOJUWgFONpB7Zv9W2tSaFlA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6", + "@babel/helper-replace-supers": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-parameters": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-parameters/-/plugin-transform-parameters-7.20.7.tgz", + "integrity": "sha512-WiWBIkeHKVOSYPO0pWkxGPfKeWrCJyD3NJ53+Lrp/QMSZbsVPovrVl2aWZ19D/LTVnaDv5Ap7GJ/B2CTOZdrfA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.20.2" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-property-literals": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-property-literals/-/plugin-transform-property-literals-7.18.6.tgz", + "integrity": "sha512-cYcs6qlgafTud3PAzrrRNbQtfpQ8+y/+M5tKmksS9+M1ckbH6kzY8MrexEM9mcA6JDsukE19iIRvAyYl463sMg==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-regenerator": { + "version": "7.20.5", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-regenerator/-/plugin-transform-regenerator-7.20.5.tgz", + "integrity": "sha512-kW/oO7HPBtntbsahzQ0qSE3tFvkFwnbozz3NWFhLGqH75vLEg+sCGngLlhVkePlCs3Jv0dBBHDzCHxNiFAQKCQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.20.2", + "regenerator-transform": "^0.15.1" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-reserved-words": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-reserved-words/-/plugin-transform-reserved-words-7.18.6.tgz", + "integrity": "sha512-oX/4MyMoypzHjFrT1CdivfKZ+XvIPMFXwwxHp/r0Ddy2Vuomt4HDFGmft1TAY2yiTKiNSsh3kjBAzcM8kSdsjA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-shorthand-properties": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-shorthand-properties/-/plugin-transform-shorthand-properties-7.18.6.tgz", + "integrity": "sha512-eCLXXJqv8okzg86ywZJbRn19YJHU4XUa55oz2wbHhaQVn/MM+XhukiT7SYqp/7o00dg52Rj51Ny+Ecw4oyoygw==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-spread": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-spread/-/plugin-transform-spread-7.20.7.tgz", + "integrity": "sha512-ewBbHQ+1U/VnH1fxltbJqDeWBU1oNLG8Dj11uIv3xVf7nrQu0bPGe5Rf716r7K5Qz+SqtAOVswoVunoiBtGhxw==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/helper-skip-transparent-expression-wrappers": "^7.20.0" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-sticky-regex": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-sticky-regex/-/plugin-transform-sticky-regex-7.18.6.tgz", + "integrity": "sha512-kfiDrDQ+PBsQDO85yj1icueWMfGfJFKN1KCkndygtu/C9+XUfydLC8Iv5UYJqRwy4zk8EcplRxEOeLyjq1gm6Q==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-template-literals": { + "version": "7.18.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-template-literals/-/plugin-transform-template-literals-7.18.9.tgz", + "integrity": "sha512-S8cOWfT82gTezpYOiVaGHrCbhlHgKhQt8XH5ES46P2XWmX92yisoZywf5km75wv5sYcXDUCLMmMxOLCtthDgMA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-typeof-symbol": { + "version": "7.18.9", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typeof-symbol/-/plugin-transform-typeof-symbol-7.18.9.tgz", + "integrity": "sha512-SRfwTtF11G2aemAZWivL7PD+C9z52v9EvMqH9BuYbabyPuKUvSWks3oCg6041pT925L4zVFqaVBeECwsmlguEw==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-typescript": { + "version": "7.20.13", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typescript/-/plugin-transform-typescript-7.20.13.tgz", + "integrity": "sha512-O7I/THxarGcDZxkgWKMUrk7NK1/WbHAg3Xx86gqS6x9MTrNL6AwIluuZ96ms4xeDe6AVx6rjHbWHP7x26EPQBA==", + "dev": true, + "dependencies": { + "@babel/helper-create-class-features-plugin": "^7.20.12", + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/plugin-syntax-typescript": "^7.20.0" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-unicode-escapes": { + "version": "7.18.10", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-escapes/-/plugin-transform-unicode-escapes-7.18.10.tgz", + "integrity": "sha512-kKAdAI+YzPgGY/ftStBFXTI1LZFju38rYThnfMykS+IXy8BVx+res7s2fxf1l8I35DV2T97ezo6+SGrXz6B3iQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.9" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-transform-unicode-regex": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-unicode-regex/-/plugin-transform-unicode-regex-7.18.6.tgz", + "integrity": "sha512-gE7A6Lt7YLnNOL3Pb9BNeZvi+d8l7tcRrG4+pwJjK9hD2xX4mEvjlQW60G9EEmfXVYRPv9VRQcyegIVHCql/AA==", + "dev": true, + "dependencies": { + "@babel/helper-create-regexp-features-plugin": "^7.18.6", + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/preset-env": { + "version": "7.20.2", + "resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.20.2.tgz", + "integrity": "sha512-1G0efQEWR1EHkKvKHqbG+IN/QdgwfByUpM5V5QroDzGV2t3S/WXNQd693cHiHTlCFMpr9B6FkPFXDA2lQcKoDg==", + "dev": true, + "dependencies": { + "@babel/compat-data": "^7.20.1", + "@babel/helper-compilation-targets": "^7.20.0", + "@babel/helper-plugin-utils": "^7.20.2", + "@babel/helper-validator-option": "^7.18.6", + "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": "^7.18.6", + "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": "^7.18.9", + "@babel/plugin-proposal-async-generator-functions": "^7.20.1", + "@babel/plugin-proposal-class-properties": "^7.18.6", + "@babel/plugin-proposal-class-static-block": "^7.18.6", + "@babel/plugin-proposal-dynamic-import": "^7.18.6", + "@babel/plugin-proposal-export-namespace-from": "^7.18.9", + "@babel/plugin-proposal-json-strings": "^7.18.6", + "@babel/plugin-proposal-logical-assignment-operators": "^7.18.9", + "@babel/plugin-proposal-nullish-coalescing-operator": "^7.18.6", + "@babel/plugin-proposal-numeric-separator": "^7.18.6", + "@babel/plugin-proposal-object-rest-spread": "^7.20.2", + "@babel/plugin-proposal-optional-catch-binding": "^7.18.6", + "@babel/plugin-proposal-optional-chaining": "^7.18.9", + "@babel/plugin-proposal-private-methods": "^7.18.6", + "@babel/plugin-proposal-private-property-in-object": "^7.18.6", + "@babel/plugin-proposal-unicode-property-regex": "^7.18.6", + "@babel/plugin-syntax-async-generators": "^7.8.4", + "@babel/plugin-syntax-class-properties": "^7.12.13", + "@babel/plugin-syntax-class-static-block": "^7.14.5", + "@babel/plugin-syntax-dynamic-import": "^7.8.3", + "@babel/plugin-syntax-export-namespace-from": "^7.8.3", + "@babel/plugin-syntax-import-assertions": "^7.20.0", + "@babel/plugin-syntax-json-strings": "^7.8.3", + "@babel/plugin-syntax-logical-assignment-operators": "^7.10.4", + "@babel/plugin-syntax-nullish-coalescing-operator": "^7.8.3", + "@babel/plugin-syntax-numeric-separator": "^7.10.4", + "@babel/plugin-syntax-object-rest-spread": "^7.8.3", + "@babel/plugin-syntax-optional-catch-binding": "^7.8.3", + "@babel/plugin-syntax-optional-chaining": "^7.8.3", + "@babel/plugin-syntax-private-property-in-object": "^7.14.5", + "@babel/plugin-syntax-top-level-await": "^7.14.5", + "@babel/plugin-transform-arrow-functions": "^7.18.6", + "@babel/plugin-transform-async-to-generator": "^7.18.6", + "@babel/plugin-transform-block-scoped-functions": "^7.18.6", + "@babel/plugin-transform-block-scoping": "^7.20.2", + "@babel/plugin-transform-classes": "^7.20.2", + "@babel/plugin-transform-computed-properties": "^7.18.9", + "@babel/plugin-transform-destructuring": "^7.20.2", + "@babel/plugin-transform-dotall-regex": "^7.18.6", + "@babel/plugin-transform-duplicate-keys": "^7.18.9", + "@babel/plugin-transform-exponentiation-operator": "^7.18.6", + "@babel/plugin-transform-for-of": "^7.18.8", + "@babel/plugin-transform-function-name": "^7.18.9", + "@babel/plugin-transform-literals": "^7.18.9", + "@babel/plugin-transform-member-expression-literals": "^7.18.6", + "@babel/plugin-transform-modules-amd": "^7.19.6", + "@babel/plugin-transform-modules-commonjs": "^7.19.6", + "@babel/plugin-transform-modules-systemjs": "^7.19.6", + "@babel/plugin-transform-modules-umd": "^7.18.6", + "@babel/plugin-transform-named-capturing-groups-regex": "^7.19.1", + "@babel/plugin-transform-new-target": "^7.18.6", + "@babel/plugin-transform-object-super": "^7.18.6", + "@babel/plugin-transform-parameters": "^7.20.1", + "@babel/plugin-transform-property-literals": "^7.18.6", + "@babel/plugin-transform-regenerator": "^7.18.6", + "@babel/plugin-transform-reserved-words": "^7.18.6", + "@babel/plugin-transform-shorthand-properties": "^7.18.6", + "@babel/plugin-transform-spread": "^7.19.0", + "@babel/plugin-transform-sticky-regex": "^7.18.6", + "@babel/plugin-transform-template-literals": "^7.18.9", + "@babel/plugin-transform-typeof-symbol": "^7.18.9", + "@babel/plugin-transform-unicode-escapes": "^7.18.10", + "@babel/plugin-transform-unicode-regex": "^7.18.6", + "@babel/preset-modules": "^0.1.5", + "@babel/types": "^7.20.2", + "babel-plugin-polyfill-corejs2": "^0.3.3", + "babel-plugin-polyfill-corejs3": "^0.6.0", + "babel-plugin-polyfill-regenerator": "^0.4.1", + "core-js-compat": "^3.25.1", + "semver": "^6.3.0" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/preset-modules": { + "version": "0.1.5", + "resolved": "https://registry.npmjs.org/@babel/preset-modules/-/preset-modules-0.1.5.tgz", + "integrity": "sha512-A57th6YRG7oR3cq/yt/Y84MvGgE0eJG2F1JLhKuyG+jFxEgrd/HAMJatiFtmOiZurz+0DkrvbheCLaV5f2JfjA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.0.0", + "@babel/plugin-proposal-unicode-property-regex": "^7.4.4", + "@babel/plugin-transform-dotall-regex": "^7.4.4", + "@babel/types": "^7.4.4", + "esutils": "^2.0.2" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/preset-typescript": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/preset-typescript/-/preset-typescript-7.18.6.tgz", + "integrity": "sha512-s9ik86kXBAnD760aybBucdpnLsAt0jK1xqJn2juOn9lkOvSHV60os5hxoVJsPzMQxvnUJFAlkont2DvvaYEBtQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6", + "@babel/helper-validator-option": "^7.18.6", + "@babel/plugin-transform-typescript": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/runtime": { + "version": "7.20.13", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.20.13.tgz", + "integrity": "sha512-gt3PKXs0DBoL9xCvOIIZ2NEqAGZqHjAnmVbfQtB620V0uReIQutpel14KcneZuer7UioY8ALKZ7iocavvzTNFA==", + "dev": true, + "dependencies": { + "regenerator-runtime": "^0.13.11" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/template": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.20.7.tgz", + "integrity": "sha512-8SegXApWe6VoNw0r9JHpSteLKTpTiLZ4rMlGIm9JQ18KiCtyQiAMEazujAHrUS5flrcqYZa75ukev3P6QmUwUw==", + "dev": true, + "dependencies": { + "@babel/code-frame": "^7.18.6", + "@babel/parser": "^7.20.7", + "@babel/types": "^7.20.7" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/traverse": { + "version": "7.20.13", + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.20.13.tgz", + "integrity": "sha512-kMJXfF0T6DIS9E8cgdLCSAL+cuCK+YEZHWiLK0SXpTo8YRj5lpJu3CDNKiIBCne4m9hhTIqUg6SYTAI39tAiVQ==", + "dev": true, + "dependencies": { + "@babel/code-frame": "^7.18.6", + "@babel/generator": "^7.20.7", + "@babel/helper-environment-visitor": "^7.18.9", + "@babel/helper-function-name": "^7.19.0", + "@babel/helper-hoist-variables": "^7.18.6", + "@babel/helper-split-export-declaration": "^7.18.6", + "@babel/parser": "^7.20.13", + "@babel/types": "^7.20.7", + "debug": "^4.1.0", + "globals": "^11.1.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/types": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.20.7.tgz", + "integrity": "sha512-69OnhBxSSgK0OzTJai4kyPDiKTIe3j+ctaHdIGVbRahTLAT7L3R9oeXHC2aVSuGYt3cVnoAMDmOCgJ2yaiLMvg==", + "dev": true, + "dependencies": { + "@babel/helper-string-parser": "^7.19.4", + "@babel/helper-validator-identifier": "^7.19.1", + "to-fast-properties": "^2.0.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@discoveryjs/json-ext": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/@discoveryjs/json-ext/-/json-ext-0.5.7.tgz", + "integrity": "sha512-dBVuXR082gk3jsFp7Rd/JI4kytwGHecnCoTtXFb7DB6CNHp4rg5k1bhg0nWdLGLnOV71lmDzGQaLMy8iPLY0pw==", + "dev": true, + "engines": { + "node": ">=10.0.0" + } + }, + "node_modules/@jridgewell/gen-mapping": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.1.1.tgz", + "integrity": "sha512-sQXCasFk+U8lWYEe66WxRDOE9PjVz4vSM51fTu3Hw+ClTpUSQb718772vH3pyS5pShp6lvQM7SxgIDXXXmOX7w==", + "dev": true, + "peer": true, + "dependencies": { + "@jridgewell/set-array": "^1.0.0", + "@jridgewell/sourcemap-codec": "^1.4.10" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/resolve-uri": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.0.tgz", + "integrity": "sha512-F2msla3tad+Mfht5cJq7LSXcdudKTWCVYUgw6pLFOOHSTtZlj6SWNYAp+AhuqLmWdBO2X5hPrLcu8cVP8fy28w==", + "dev": true, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/set-array": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.1.2.tgz", + "integrity": "sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==", + "dev": true, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/source-map": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.2.tgz", + "integrity": "sha512-m7O9o2uR8k2ObDysZYzdfhb08VuEml5oWGiosa1VdaPZ/A6QyPkAJuwN0Q1lhULOf6B7MtQmHENS743hWtCrgw==", + "dev": true, + "dependencies": { + "@jridgewell/gen-mapping": "^0.3.0", + "@jridgewell/trace-mapping": "^0.3.9" + } + }, + "node_modules/@jridgewell/source-map/node_modules/@jridgewell/gen-mapping": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.2.tgz", + "integrity": "sha512-mh65xKQAzI6iBcFzwv28KVWSmCkdRBWoOh+bYQGW3+6OZvbbN3TqMGo5hqYxQniRcH9F2VZIoJCm4pa3BPDK/A==", + "dev": true, + "dependencies": { + "@jridgewell/set-array": "^1.0.1", + "@jridgewell/sourcemap-codec": "^1.4.10", + "@jridgewell/trace-mapping": "^0.3.9" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/sourcemap-codec": { + "version": "1.4.14", + "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.14.tgz", + "integrity": "sha512-XPSJHWmi394fuUuzDnGz1wiKqWfo1yXecHQMRf2l6hztTO+nPru658AyDngaBe7isIxEkRsPR3FZh+s7iVa4Uw==", + "dev": true + }, + "node_modules/@jridgewell/trace-mapping": { + "version": "0.3.17", + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.17.tgz", + "integrity": "sha512-MCNzAp77qzKca9+W/+I0+sEpaUnZoeasnghNeVc41VZCEKaCH73Vq3BZZ/SzWIgrqE4H4ceI+p+b6C0mHf9T4g==", + "dev": true, + "dependencies": { + "@jridgewell/resolve-uri": "3.1.0", + "@jridgewell/sourcemap-codec": "1.4.14" + } + }, + "node_modules/@leichtgewicht/ip-codec": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/@leichtgewicht/ip-codec/-/ip-codec-2.0.4.tgz", + "integrity": "sha512-Hcv+nVC0kZnQ3tD9GVu5xSMR4VVYOteQIr/hwFPVEvPdlXqgGEuRjiheChHgdM+JyqdgNcmzZOX/tnl0JOiI7A==", + "dev": true + }, + "node_modules/@types/body-parser": { + "version": "1.19.2", + "resolved": "https://registry.npmjs.org/@types/body-parser/-/body-parser-1.19.2.tgz", + "integrity": "sha512-ALYone6pm6QmwZoAgeyNksccT9Q4AWZQ6PvfwR37GT6r6FWUPguq6sUmNGSMV2Wr761oQoBxwGGa6DR5o1DC9g==", + "dev": true, + "dependencies": { + "@types/connect": "*", + "@types/node": "*" + } + }, + "node_modules/@types/bonjour": { + "version": "3.5.10", + "resolved": "https://registry.npmjs.org/@types/bonjour/-/bonjour-3.5.10.tgz", + "integrity": "sha512-p7ienRMiS41Nu2/igbJxxLDWrSZ0WxM8UQgCeO9KhoVF7cOVFkrKsiDr1EsJIla8vV3oEEjGcz11jc5yimhzZw==", + "dev": true, + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@types/connect": { + "version": "3.4.35", + "resolved": "https://registry.npmjs.org/@types/connect/-/connect-3.4.35.tgz", + "integrity": "sha512-cdeYyv4KWoEgpBISTxWvqYsVy444DOqehiF3fM3ne10AmJ62RSyNkUnxMJXHQWRQQX2eR94m5y1IZyDwBjV9FQ==", + "dev": true, + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@types/connect-history-api-fallback": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/@types/connect-history-api-fallback/-/connect-history-api-fallback-1.3.5.tgz", + "integrity": "sha512-h8QJa8xSb1WD4fpKBDcATDNGXghFj6/3GRWG6dhmRcu0RX1Ubasur2Uvx5aeEwlf0MwblEC2bMzzMQntxnw/Cw==", + "dev": true, + "dependencies": { + "@types/express-serve-static-core": "*", + "@types/node": "*" + } + }, + "node_modules/@types/eslint": { + "version": "8.21.0", + "resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-8.21.0.tgz", + "integrity": "sha512-35EhHNOXgxnUgh4XCJsGhE7zdlDhYDN/aMG6UbkByCFFNgQ7b3U+uVoqBpicFydR8JEfgdjCF7SJ7MiJfzuiTA==", + "dev": true, + "dependencies": { + "@types/estree": "*", + "@types/json-schema": "*" + } + }, + "node_modules/@types/eslint-scope": { + "version": "3.7.4", + "resolved": "https://registry.npmjs.org/@types/eslint-scope/-/eslint-scope-3.7.4.tgz", + "integrity": "sha512-9K4zoImiZc3HlIp6AVUDE4CWYx22a+lhSZMYNpbjW04+YF0KWj4pJXnEMjdnFTiQibFFmElcsasJXDbdI/EPhA==", + "dev": true, + "dependencies": { + "@types/eslint": "*", + "@types/estree": "*" + } + }, + "node_modules/@types/estree": { + "version": "0.0.51", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-0.0.51.tgz", + "integrity": "sha512-CuPgU6f3eT/XgKKPqKd/gLZV1Xmvf1a2R5POBOGQa6uv82xpls89HU5zKeVoyR8XzHd1RGNOlQlvUe3CFkjWNQ==", + "dev": true + }, + "node_modules/@types/express": { + "version": "4.17.17", + "resolved": "https://registry.npmjs.org/@types/express/-/express-4.17.17.tgz", + "integrity": "sha512-Q4FmmuLGBG58btUnfS1c1r/NQdlp3DMfGDGig8WhfpA2YRUtEkxAjkZb0yvplJGYdF1fsQ81iMDcH24sSCNC/Q==", + "dev": true, + "dependencies": { + "@types/body-parser": "*", + "@types/express-serve-static-core": "^4.17.33", + "@types/qs": "*", + "@types/serve-static": "*" + } + }, + "node_modules/@types/express-serve-static-core": { + "version": "4.17.33", + "resolved": "https://registry.npmjs.org/@types/express-serve-static-core/-/express-serve-static-core-4.17.33.tgz", + "integrity": "sha512-TPBqmR/HRYI3eC2E5hmiivIzv+bidAfXofM+sbonAGvyDhySGw9/PQZFt2BLOrjUUR++4eJVpx6KnLQK1Fk9tA==", + "dev": true, + "dependencies": { + "@types/node": "*", + "@types/qs": "*", + "@types/range-parser": "*" + } + }, + "node_modules/@types/glob": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/@types/glob/-/glob-7.2.0.tgz", + "integrity": "sha512-ZUxbzKl0IfJILTS6t7ip5fQQM/J3TJYubDm3nMbgubNNYS62eXeUpoLUC8/7fJNiFYHTrGPQn7hspDUzIHX3UA==", + "dev": true, + "dependencies": { + "@types/minimatch": "*", + "@types/node": "*" + } + }, + "node_modules/@types/html-minifier-terser": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/@types/html-minifier-terser/-/html-minifier-terser-6.1.0.tgz", + "integrity": "sha512-oh/6byDPnL1zeNXFrDXFLyZjkr1MsBG667IM792caf1L2UPOOMf65NFzjUH/ltyfwjAGfs1rsX1eftK0jC/KIg==", + "dev": true + }, + "node_modules/@types/http-proxy": { + "version": "1.17.9", + "resolved": "https://registry.npmjs.org/@types/http-proxy/-/http-proxy-1.17.9.tgz", + "integrity": "sha512-QsbSjA/fSk7xB+UXlCT3wHBy5ai9wOcNDWwZAtud+jXhwOM3l+EYZh8Lng4+/6n8uar0J7xILzqftJdJ/Wdfkw==", + "dev": true, + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@types/json-schema": { + "version": "7.0.11", + "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.11.tgz", + "integrity": "sha512-wOuvG1SN4Us4rez+tylwwwCV1psiNVOkJeM3AUWUNWg/jDQY2+HE/444y5gc+jBmRqASOm2Oeh5c1axHobwRKQ==", + "dev": true + }, + "node_modules/@types/mime": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/@types/mime/-/mime-3.0.1.tgz", + "integrity": "sha512-Y4XFY5VJAuw0FgAqPNd6NNoV44jbq9Bz2L7Rh/J6jLTiHBSBJa9fxqQIvkIld4GsoDOcCbvzOUAbLPsSKKg+uA==", + "dev": true + }, + "node_modules/@types/minimatch": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/@types/minimatch/-/minimatch-5.1.2.tgz", + "integrity": "sha512-K0VQKziLUWkVKiRVrx4a40iPaxTUefQmjtkQofBkYRcoaaL/8rhwDWww9qWbrgicNOgnpIsMxyNIUM4+n6dUIA==", + "dev": true + }, "node_modules/@types/node": { "version": "18.11.18", "resolved": "https://registry.npmjs.org/@types/node/-/node-18.11.18.tgz", "integrity": "sha512-DHQpWGjyQKSHj3ebjFI/wRKcqQcdR+MoFBygntYOZytCqNfkd2ZC4ARDJ2DQqhjH5p85Nnd3jhUJIXrszFX/JA==", "dev": true }, + "node_modules/@types/parse-json": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/@types/parse-json/-/parse-json-4.0.0.tgz", + "integrity": "sha512-//oorEZjL6sbPcKUaCdIGlIUeH26mgzimjBB77G6XRgnDl/L5wOnpyBGRe/Mmf5CVW3PwEBE1NjiMZ/ssFh4wA==", + "dev": true + }, + "node_modules/@types/qs": { + "version": "6.9.7", + "resolved": "https://registry.npmjs.org/@types/qs/-/qs-6.9.7.tgz", + "integrity": "sha512-FGa1F62FT09qcrueBA6qYTrJPVDzah9a+493+o2PCXsesWHIn27G98TsSMs3WPNbZIEj4+VJf6saSFpvD+3Zsw==", + "dev": true + }, + "node_modules/@types/range-parser": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/@types/range-parser/-/range-parser-1.2.4.tgz", + "integrity": "sha512-EEhsLsD6UsDM1yFhAvy0Cjr6VwmpMWqFBCb9w07wVugF7w9nfajxLuVmngTIpgS6svCnm6Vaw+MZhoDCKnOfsw==", + "dev": true + }, + "node_modules/@types/retry": { + "version": "0.12.0", + "resolved": "https://registry.npmjs.org/@types/retry/-/retry-0.12.0.tgz", + "integrity": "sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA==", + "dev": true + }, + "node_modules/@types/serve-index": { + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/@types/serve-index/-/serve-index-1.9.1.tgz", + "integrity": "sha512-d/Hs3nWDxNL2xAczmOVZNj92YZCS6RGxfBPjKzuu/XirCgXdpKEb88dYNbrYGint6IVWLNP+yonwVAuRC0T2Dg==", + "dev": true, + "dependencies": { + "@types/express": "*" + } + }, + "node_modules/@types/serve-static": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/@types/serve-static/-/serve-static-1.15.0.tgz", + "integrity": "sha512-z5xyF6uh8CbjAu9760KDKsH2FcDxZ2tFCsA4HIMWE6IkiYMXfVoa+4f9KX+FN0ZLsaMw1WNG2ETLA6N+/YA+cg==", + "dev": true, + "dependencies": { + "@types/mime": "*", + "@types/node": "*" + } + }, + "node_modules/@types/sockjs": { + "version": "0.3.33", + "resolved": "https://registry.npmjs.org/@types/sockjs/-/sockjs-0.3.33.tgz", + "integrity": "sha512-f0KEEe05NvUnat+boPTZ0dgaLZ4SfSouXUgv5noUiefG2ajgKjmETo9ZJyuqsl7dfl2aHlLJUiki6B4ZYldiiw==", + "dev": true, + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@types/ws": { + "version": "8.5.4", + "resolved": "https://registry.npmjs.org/@types/ws/-/ws-8.5.4.tgz", + "integrity": "sha512-zdQDHKUgcX/zBc4GrwsE/7dVdAD8JR4EuiAXiiUhhfyIJXXb2+PrGshFyeXWQPMmmZ2XxgaqclgpIC7eTXc1mg==", + "dev": true, + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@webassemblyjs/ast": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.11.1.tgz", + "integrity": "sha512-ukBh14qFLjxTQNTXocdyksN5QdM28S1CxHt2rdskFyL+xFV7VremuBLVbmCePj+URalXBENx/9Lm7lnhihtCSw==", + "dev": true, + "dependencies": { + "@webassemblyjs/helper-numbers": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1" + } + }, + "node_modules/@webassemblyjs/floating-point-hex-parser": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.11.1.tgz", + "integrity": "sha512-iGRfyc5Bq+NnNuX8b5hwBrRjzf0ocrJPI6GWFodBFzmFnyvrQ83SHKhmilCU/8Jv67i4GJZBMhEzltxzcNagtQ==", + "dev": true + }, + "node_modules/@webassemblyjs/helper-api-error": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-api-error/-/helper-api-error-1.11.1.tgz", + "integrity": "sha512-RlhS8CBCXfRUR/cwo2ho9bkheSXG0+NwooXcc3PAILALf2QLdFyj7KGsKRbVc95hZnhnERon4kW/D3SZpp6Tcg==", + "dev": true + }, + "node_modules/@webassemblyjs/helper-buffer": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-buffer/-/helper-buffer-1.11.1.tgz", + "integrity": "sha512-gwikF65aDNeeXa8JxXa2BAk+REjSyhrNC9ZwdT0f8jc4dQQeDQ7G4m0f2QCLPJiMTTO6wfDmRmj/pW0PsUvIcA==", + "dev": true + }, + "node_modules/@webassemblyjs/helper-numbers": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-numbers/-/helper-numbers-1.11.1.tgz", + "integrity": "sha512-vDkbxiB8zfnPdNK9Rajcey5C0w+QJugEglN0of+kmO8l7lDb77AnlKYQF7aarZuCrv+l0UvqL+68gSDr3k9LPQ==", + "dev": true, + "dependencies": { + "@webassemblyjs/floating-point-hex-parser": "1.11.1", + "@webassemblyjs/helper-api-error": "1.11.1", + "@xtuc/long": "4.2.2" + } + }, + "node_modules/@webassemblyjs/helper-wasm-bytecode": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.11.1.tgz", + "integrity": "sha512-PvpoOGiJwXeTrSf/qfudJhwlvDQxFgelbMqtq52WWiXC6Xgg1IREdngmPN3bs4RoO83PnL/nFrxucXj1+BX62Q==", + "dev": true + }, + "node_modules/@webassemblyjs/helper-wasm-section": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.11.1.tgz", + "integrity": "sha512-10P9No29rYX1j7F3EVPX3JvGPQPae+AomuSTPiF9eBQeChHI6iqjMIwR9JmOJXwpnn/oVGDk7I5IlskuMwU/pg==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-buffer": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1", + "@webassemblyjs/wasm-gen": "1.11.1" + } + }, + "node_modules/@webassemblyjs/ieee754": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.11.1.tgz", + "integrity": "sha512-hJ87QIPtAMKbFq6CGTkZYJivEwZDbQUgYd3qKSadTNOhVY7p+gfP6Sr0lLRVTaG1JjFj+r3YchoqRYxNH3M0GQ==", + "dev": true, + "dependencies": { + "@xtuc/ieee754": "^1.2.0" + } + }, + "node_modules/@webassemblyjs/leb128": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.11.1.tgz", + "integrity": "sha512-BJ2P0hNZ0u+Th1YZXJpzW6miwqQUGcIHT1G/sf72gLVD9DZ5AdYTqPNbHZh6K1M5VmKvFXwGSWZADz+qBWxeRw==", + "dev": true, + "dependencies": { + "@xtuc/long": "4.2.2" + } + }, + "node_modules/@webassemblyjs/utf8": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.11.1.tgz", + "integrity": "sha512-9kqcxAEdMhiwQkHpkNiorZzqpGrodQQ2IGrHHxCy+Ozng0ofyMA0lTqiLkVs1uzTRejX+/O0EOT7KxqVPuXosQ==", + "dev": true + }, + "node_modules/@webassemblyjs/wasm-edit": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-edit/-/wasm-edit-1.11.1.tgz", + "integrity": "sha512-g+RsupUC1aTHfR8CDgnsVRVZFJqdkFHpsHMfJuWQzWU3tvnLC07UqHICfP+4XyL2tnr1amvl1Sdp06TnYCmVkA==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-buffer": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1", + "@webassemblyjs/helper-wasm-section": "1.11.1", + "@webassemblyjs/wasm-gen": "1.11.1", + "@webassemblyjs/wasm-opt": "1.11.1", + "@webassemblyjs/wasm-parser": "1.11.1", + "@webassemblyjs/wast-printer": "1.11.1" + } + }, + "node_modules/@webassemblyjs/wasm-gen": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-gen/-/wasm-gen-1.11.1.tgz", + "integrity": "sha512-F7QqKXwwNlMmsulj6+O7r4mmtAlCWfO/0HdgOxSklZfQcDu0TpLiD1mRt/zF25Bk59FIjEuGAIyn5ei4yMfLhA==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1", + "@webassemblyjs/ieee754": "1.11.1", + "@webassemblyjs/leb128": "1.11.1", + "@webassemblyjs/utf8": "1.11.1" + } + }, + "node_modules/@webassemblyjs/wasm-opt": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-opt/-/wasm-opt-1.11.1.tgz", + "integrity": "sha512-VqnkNqnZlU5EB64pp1l7hdm3hmQw7Vgqa0KF/KCNO9sIpI6Fk6brDEiX+iCOYrvMuBWDws0NkTOxYEb85XQHHw==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-buffer": "1.11.1", + "@webassemblyjs/wasm-gen": "1.11.1", + "@webassemblyjs/wasm-parser": "1.11.1" + } + }, + "node_modules/@webassemblyjs/wasm-parser": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.11.1.tgz", + "integrity": "sha512-rrBujw+dJu32gYB7/Lup6UhdkPx9S9SnobZzRVL7VcBH9Bt9bCBLEuX/YXOOtBsOZ4NQrRykKhffRWHvigQvOA==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-api-error": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1", + "@webassemblyjs/ieee754": "1.11.1", + "@webassemblyjs/leb128": "1.11.1", + "@webassemblyjs/utf8": "1.11.1" + } + }, + "node_modules/@webassemblyjs/wast-printer": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wast-printer/-/wast-printer-1.11.1.tgz", + "integrity": "sha512-IQboUWM4eKzWW+N/jij2sRatKMh99QEelo3Eb2q0qXkvPRISAj8Qxtmw5itwqK+TTkBuUIE45AxYPToqPtL5gg==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@xtuc/long": "4.2.2" + } + }, + "node_modules/@webpack-cli/configtest": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/@webpack-cli/configtest/-/configtest-2.0.1.tgz", + "integrity": "sha512-njsdJXJSiS2iNbQVS0eT8A/KPnmyH4pv1APj2K0d1wrZcBLw+yppxOy4CGqa0OxDJkzfL/XELDhD8rocnIwB5A==", + "dev": true, + "engines": { + "node": ">=14.15.0" + }, + "peerDependencies": { + "webpack": "5.x.x", + "webpack-cli": "5.x.x" + } + }, + "node_modules/@webpack-cli/info": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/@webpack-cli/info/-/info-2.0.1.tgz", + "integrity": "sha512-fE1UEWTwsAxRhrJNikE7v4EotYflkEhBL7EbajfkPlf6E37/2QshOy/D48Mw8G5XMFlQtS6YV42vtbG9zBpIQA==", + "dev": true, + "engines": { + "node": ">=14.15.0" + }, + "peerDependencies": { + "webpack": "5.x.x", + "webpack-cli": "5.x.x" + } + }, + "node_modules/@webpack-cli/serve": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/@webpack-cli/serve/-/serve-2.0.1.tgz", + "integrity": "sha512-0G7tNyS+yW8TdgHwZKlDWYXFA6OJQnoLCQvYKkQP0Q2X205PSQ6RNUj0M+1OB/9gRQaUZ/ccYfaxd0nhaWKfjw==", + "dev": true, + "engines": { + "node": ">=14.15.0" + }, + "peerDependencies": { + "webpack": "5.x.x", + "webpack-cli": "5.x.x" + }, + "peerDependenciesMeta": { + "webpack-dev-server": { + "optional": true + } + } + }, + "node_modules/@xtuc/ieee754": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/@xtuc/ieee754/-/ieee754-1.2.0.tgz", + "integrity": "sha512-DX8nKgqcGwsc0eJSqYt5lwP4DH5FlHnmuWWBRy7X0NcaGR0ZtuyeESgMwTYVEtxmsNGY+qit4QYT/MIYTOTPeA==", + "dev": true + }, + "node_modules/@xtuc/long": { + "version": "4.2.2", + "resolved": "https://registry.npmjs.org/@xtuc/long/-/long-4.2.2.tgz", + "integrity": "sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ==", + "dev": true + }, + "node_modules/accepts": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.8.tgz", + "integrity": "sha512-PYAthTa2m2VKxuvSD3DPC/Gy+U+sOA1LAuT8mkmRuvw+NACSaeXEQ+NHcVF7rONl6qcaxV3Uuemwawk+7+SJLw==", + "dev": true, + "dependencies": { + "mime-types": "~2.1.34", + "negotiator": "0.6.3" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/acorn": { + "version": "8.8.2", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.8.2.tgz", + "integrity": "sha512-xjIYgE8HBrkpd/sJqOGNspf8uHG+NOHGOw6a/Urj8taM2EXfdNAH2oFcPeIFfsv3+kz/mJrS5VuMqbNLjCa2vw==", + "dev": true, + "bin": { + "acorn": "bin/acorn" + }, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/acorn-import-assertions": { + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/acorn-import-assertions/-/acorn-import-assertions-1.8.0.tgz", + "integrity": "sha512-m7VZ3jwz4eK6A4Vtt8Ew1/mNbP24u0FhdyfA7fSvnJR6LMdfOYnmuIrrJAgrYfYJ10F/otaHTtrtrtmHdMNzEw==", + "dev": true, + "peerDependencies": { + "acorn": "^8" + } + }, + "node_modules/ajv": { + "version": "8.12.0", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.12.0.tgz", + "integrity": "sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "json-schema-traverse": "^1.0.0", + "require-from-string": "^2.0.2", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/ajv-formats": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ajv-formats/-/ajv-formats-2.1.1.tgz", + "integrity": "sha512-Wx0Kx52hxE7C18hkMEggYlEifqWZtYaRgouJor+WMdPnQyEK13vgEWyVNup7SoeeoLMsr4kf5h6dOW11I15MUA==", + "dev": true, + "dependencies": { + "ajv": "^8.0.0" + }, + "peerDependencies": { + "ajv": "^8.0.0" + }, + "peerDependenciesMeta": { + "ajv": { + "optional": true + } + } + }, + "node_modules/ajv-keywords": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-5.1.0.tgz", + "integrity": "sha512-YCS/JNFAUyr5vAuhk1DWm1CBxRHW9LbJ2ozWeemrIqpbsqKjHVxYPyi5GC0rjZIT5JxJ3virVTS8wk4i/Z+krw==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.3" + }, + "peerDependencies": { + "ajv": "^8.8.2" + } + }, + "node_modules/ansi-html-community": { + "version": "0.0.8", + "resolved": "https://registry.npmjs.org/ansi-html-community/-/ansi-html-community-0.0.8.tgz", + "integrity": "sha512-1APHAyr3+PCamwNw3bXCPp4HFLONZt/yIH0sZp0/469KWNTEy+qN5jQ3GVX6DMZ1UXAi34yVwtTeaG/HpBuuzw==", + "dev": true, + "engines": [ + "node >= 0.8.0" + ], + "bin": { + "ansi-html": "bin/ansi-html" + } + }, + "node_modules/ansi-regex": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", + "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/ansi-styles": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", + "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dev": true, + "dependencies": { + "color-convert": "^1.9.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/anymatch": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.3.tgz", + "integrity": "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==", + "dev": true, + "dependencies": { + "normalize-path": "^3.0.0", + "picomatch": "^2.0.4" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/array-flatten": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-2.1.2.tgz", + "integrity": "sha512-hNfzcOV8W4NdualtqBFPyVO+54DSJuZGY9qT4pRroB6S9e3iiido2ISIC5h9R2sPJ8H3FHCIiEnsv1lPXO3KtQ==", + "dev": true + }, + "node_modules/array-union": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/array-union/-/array-union-1.0.2.tgz", + "integrity": "sha512-Dxr6QJj/RdU/hCaBjOfxW+q6lyuVE6JFWIrAUpuOOhoJJoQ99cUn3igRaHVB5P9WrgFVN0FfArM3x0cueOU8ng==", + "dev": true, + "dependencies": { + "array-uniq": "^1.0.1" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/array-uniq": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/array-uniq/-/array-uniq-1.0.3.tgz", + "integrity": "sha512-MNha4BWQ6JbwhFhj03YK552f7cb3AzoE8SzeljgChvL1dl3IcvggXVz1DilzySZkCja+CXuZbdW7yATchWn8/Q==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/autoprefixer": { + "version": "10.4.13", + "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.13.tgz", + "integrity": "sha512-49vKpMqcZYsJjwotvt4+h/BCjJVnhGwcLpDt5xkcaOG3eLrG/HUYLagrihYsQ+qrIBgIzX1Rw7a6L8I/ZA1Atg==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/postcss/" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/autoprefixer" + } + ], + "dependencies": { + "browserslist": "^4.21.4", + "caniuse-lite": "^1.0.30001426", + "fraction.js": "^4.2.0", + "normalize-range": "^0.1.2", + "picocolors": "^1.0.0", + "postcss-value-parser": "^4.2.0" + }, + "bin": { + "autoprefixer": "bin/autoprefixer" + }, + "engines": { + "node": "^10 || ^12 || >=14" + }, + "peerDependencies": { + "postcss": "^8.1.0" + } + }, + "node_modules/babel-loader": { + "version": "9.1.2", + "resolved": "https://registry.npmjs.org/babel-loader/-/babel-loader-9.1.2.tgz", + "integrity": "sha512-mN14niXW43tddohGl8HPu5yfQq70iUThvFL/4QzESA7GcZoC0eVOhvWdQ8+3UlSjaDE9MVtsW9mxDY07W7VpVA==", + "dev": true, + "dependencies": { + "find-cache-dir": "^3.3.2", + "schema-utils": "^4.0.0" + }, + "engines": { + "node": ">= 14.15.0" + }, + "peerDependencies": { + "@babel/core": "^7.12.0", + "webpack": ">=5" + } + }, + "node_modules/babel-plugin-polyfill-corejs2": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs2/-/babel-plugin-polyfill-corejs2-0.3.3.tgz", + "integrity": "sha512-8hOdmFYFSZhqg2C/JgLUQ+t52o5nirNwaWM2B9LWteozwIvM14VSwdsCAUET10qT+kmySAlseadmfeeSWFCy+Q==", + "dev": true, + "dependencies": { + "@babel/compat-data": "^7.17.7", + "@babel/helper-define-polyfill-provider": "^0.3.3", + "semver": "^6.1.1" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/babel-plugin-polyfill-corejs3": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs3/-/babel-plugin-polyfill-corejs3-0.6.0.tgz", + "integrity": "sha512-+eHqR6OPcBhJOGgsIar7xoAB1GcSwVUA3XjAd7HJNzOXT4wv6/H7KIdA/Nc60cvUlDbKApmqNvD1B1bzOt4nyA==", + "dev": true, + "dependencies": { + "@babel/helper-define-polyfill-provider": "^0.3.3", + "core-js-compat": "^3.25.1" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/babel-plugin-polyfill-regenerator": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-regenerator/-/babel-plugin-polyfill-regenerator-0.4.1.tgz", + "integrity": "sha512-NtQGmyQDXjQqQ+IzRkBVwEOz9lQ4zxAQZgoAYEtU9dJjnl1Oc98qnN7jcp+bE7O7aYzVpavXE3/VKXNzUbh7aw==", + "dev": true, + "dependencies": { + "@babel/helper-define-polyfill-provider": "^0.3.3" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/balanced-match": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "dev": true + }, + "node_modules/batch": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/batch/-/batch-0.6.1.tgz", + "integrity": "sha512-x+VAiMRL6UPkx+kudNvxTl6hB2XNNCG2r+7wixVfIYwu/2HKRXimwQyaumLjMveWvT2Hkd/cAJw+QBMfJ/EKVw==", + "dev": true + }, + "node_modules/big.js": { + "version": "5.2.2", + "resolved": "https://registry.npmjs.org/big.js/-/big.js-5.2.2.tgz", + "integrity": "sha512-vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ==", + "dev": true, + "engines": { + "node": "*" + } + }, + "node_modules/binary-extensions": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.2.0.tgz", + "integrity": "sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/body-parser": { + "version": "1.20.1", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.20.1.tgz", + "integrity": "sha512-jWi7abTbYwajOytWCQc37VulmWiRae5RyTpaCyDcS5/lMdtwSz5lOpDE67srw/HYe35f1z3fDQw+3txg7gNtWw==", + "dev": true, + "dependencies": { + "bytes": "3.1.2", + "content-type": "~1.0.4", + "debug": "2.6.9", + "depd": "2.0.0", + "destroy": "1.2.0", + "http-errors": "2.0.0", + "iconv-lite": "0.4.24", + "on-finished": "2.4.1", + "qs": "6.11.0", + "raw-body": "2.5.1", + "type-is": "~1.6.18", + "unpipe": "1.0.0" + }, + "engines": { + "node": ">= 0.8", + "npm": "1.2.8000 || >= 1.4.16" + } + }, + "node_modules/body-parser/node_modules/bytes": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", + "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/body-parser/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/body-parser/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true + }, + "node_modules/bonjour-service": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/bonjour-service/-/bonjour-service-1.1.0.tgz", + "integrity": "sha512-LVRinRB3k1/K0XzZ2p58COnWvkQknIY6sf0zF2rpErvcJXpMBttEPQSxK+HEXSS9VmpZlDoDnQWv8ftJT20B0Q==", + "dev": true, + "dependencies": { + "array-flatten": "^2.1.2", + "dns-equal": "^1.0.0", + "fast-deep-equal": "^3.1.3", + "multicast-dns": "^7.2.5" + } + }, + "node_modules/boolbase": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/boolbase/-/boolbase-1.0.0.tgz", + "integrity": "sha512-JZOSA7Mo9sNGB8+UjSgzdLtokWAky1zbztM3WRLCbZ70/3cTANmQmOdR7y2g+J0e2WXywy1yS468tY+IruqEww==", + "dev": true + }, + "node_modules/brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dev": true, + "dependencies": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "node_modules/braces": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", + "integrity": "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==", + "dev": true, + "dependencies": { + "fill-range": "^7.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/browserslist": { + "version": "4.21.5", + "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.21.5.tgz", + "integrity": "sha512-tUkiguQGW7S3IhB7N+c2MV/HZPSCPAAiYBZXLsBhFB/PCy6ZKKsZrmBayHV9fdGV/ARIfJ14NkxKzRDjvp7L6w==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/browserslist" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/browserslist" + } + ], + "dependencies": { + "caniuse-lite": "^1.0.30001449", + "electron-to-chromium": "^1.4.284", + "node-releases": "^2.0.8", + "update-browserslist-db": "^1.0.10" + }, + "bin": { + "browserslist": "cli.js" + }, + "engines": { + "node": "^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7" + } + }, + "node_modules/buffer-from": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", + "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==", + "dev": true + }, + "node_modules/bytes": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", + "integrity": "sha512-pMhOfFDPiv9t5jjIXkHosWmkSyQbvsgEVNkz0ERHbuLh2T/7j4Mqqpz523Fe8MVY89KC6Sh/QfS2sM+SjgFDcw==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/call-bind": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.2.tgz", + "integrity": "sha512-7O+FbCihrB5WGbFYesctwmTKae6rOiIzmz1icreWJ+0aA7LJfuqhEso2T9ncpcFtzMQtzXf2QGGueWJGTYsqrA==", + "dev": true, + "dependencies": { + "function-bind": "^1.1.1", + "get-intrinsic": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/callsites": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", + "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/camel-case": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/camel-case/-/camel-case-4.1.2.tgz", + "integrity": "sha512-gxGWBrTT1JuMx6R+o5PTXMmUnhnVzLQ9SNutD4YqKtI6ap897t3tKECYla6gCWEkplXnlNybEkZg9GEGxKFCgw==", + "dev": true, + "dependencies": { + "pascal-case": "^3.1.2", + "tslib": "^2.0.3" + } + }, + "node_modules/caniuse-lite": { + "version": "1.0.30001450", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001450.tgz", + "integrity": "sha512-qMBmvmQmFXaSxexkjjfMvD5rnDL0+m+dUMZKoDYsGG8iZN29RuYh9eRoMvKsT6uMAWlyUUGDEQGJJYjzCIO9ew==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/browserslist" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/caniuse-lite" + } + ] + }, + "node_modules/chalk": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dev": true, + "dependencies": { + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/chokidar": { + "version": "3.5.3", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.5.3.tgz", + "integrity": "sha512-Dr3sfKRP6oTcjf2JmUmFJfeVMvXBdegxB0iVQ5eb2V10uFJUCAS8OByZdVAyVb8xXNz3GjjTgj9kLWsZTqE6kw==", + "dev": true, + "funding": [ + { + "type": "individual", + "url": "https://paulmillr.com/funding/" + } + ], + "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" + }, + "engines": { + "node": ">= 8.10.0" + }, + "optionalDependencies": { + "fsevents": "~2.3.2" + } + }, + "node_modules/chrome-trace-event": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/chrome-trace-event/-/chrome-trace-event-1.0.3.tgz", + "integrity": "sha512-p3KULyQg4S7NIHixdwbGX+nFHkoBiA4YQmyWtjb8XngSKV124nJmRysgAeujbUVb15vh+RvFUfCPqU7rXk+hZg==", + "dev": true, + "engines": { + "node": ">=6.0" + } + }, + "node_modules/clean-css": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/clean-css/-/clean-css-5.3.2.tgz", + "integrity": "sha512-JVJbM+f3d3Q704rF4bqQ5UUyTtuJ0JRKNbTKVEeujCCBoMdkEi+V+e8oktO9qGQNSvHrFTM6JZRXrUvGR1czww==", + "dev": true, + "dependencies": { + "source-map": "~0.6.0" + }, + "engines": { + "node": ">= 10.0" + } + }, + "node_modules/clean-webpack-plugin": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/clean-webpack-plugin/-/clean-webpack-plugin-4.0.0.tgz", + "integrity": "sha512-WuWE1nyTNAyW5T7oNyys2EN0cfP2fdRxhxnIQWiAp0bMabPdHhoGxM8A6YL2GhqwgrPnnaemVE7nv5XJ2Fhh2w==", + "dev": true, + "dependencies": { + "del": "^4.1.1" + }, + "engines": { + "node": ">=10.0.0" + }, + "peerDependencies": { + "webpack": ">=4.0.0 <6.0.0" + } + }, + "node_modules/clone-deep": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/clone-deep/-/clone-deep-4.0.1.tgz", + "integrity": "sha512-neHB9xuzh/wk0dIHweyAXv2aPGZIVk3pLMe+/RNzINf17fe0OG96QroktYAUm7SM1PBnzTabaLboqqxDyMU+SQ==", + "dev": true, + "dependencies": { + "is-plain-object": "^2.0.4", + "kind-of": "^6.0.2", + "shallow-clone": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/color-convert": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", + "dev": true, + "dependencies": { + "color-name": "1.1.3" + } + }, + "node_modules/color-name": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", + "integrity": "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==", + "dev": true + }, + "node_modules/colorette": { + "version": "2.0.19", + "resolved": "https://registry.npmjs.org/colorette/-/colorette-2.0.19.tgz", + "integrity": "sha512-3tlv/dIP7FWvj3BsbHrGLJ6l/oKh1O3TcgBqMn+yyCagOxc23fyzDS6HypQbgxWbkpDnf52p1LuR4eWDQ/K9WQ==", + "dev": true + }, + "node_modules/commander": { + "version": "8.3.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-8.3.0.tgz", + "integrity": "sha512-OkTL9umf+He2DZkUq8f8J9of7yL6RJKI24dVITBmNfZBmri9zYZQrKkuXiKhyfPSu8tUhnVBB1iKXevvnlR4Ww==", + "dev": true, + "engines": { + "node": ">= 12" + } + }, + "node_modules/commondir": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/commondir/-/commondir-1.0.1.tgz", + "integrity": "sha512-W9pAhw0ja1Edb5GVdIF1mjZw/ASI0AlShXM83UUGe2DVr5TdAPEA1OA8m/g8zWp9x6On7gqufY+FatDbC3MDQg==", + "dev": true + }, + "node_modules/compressible": { + "version": "2.0.18", + "resolved": "https://registry.npmjs.org/compressible/-/compressible-2.0.18.tgz", + "integrity": "sha512-AF3r7P5dWxL8MxyITRMlORQNaOA2IkAFaTr4k7BUumjPtRpGDTZpl0Pb1XCO6JeDCBdp126Cgs9sMxqSjgYyRg==", + "dev": true, + "dependencies": { + "mime-db": ">= 1.43.0 < 2" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/compression": { + "version": "1.7.4", + "resolved": "https://registry.npmjs.org/compression/-/compression-1.7.4.tgz", + "integrity": "sha512-jaSIDzP9pZVS4ZfQ+TzvtiWhdpFhE2RDHz8QJkpX9SIpLq88VueF5jJw6t+6CUQcAoA6t+x89MLrWAqpfDE8iQ==", + "dev": true, + "dependencies": { + "accepts": "~1.3.5", + "bytes": "3.0.0", + "compressible": "~2.0.16", + "debug": "2.6.9", + "on-headers": "~1.0.2", + "safe-buffer": "5.1.2", + "vary": "~1.1.2" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/compression/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/compression/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true + }, + "node_modules/compression/node_modules/safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true + }, + "node_modules/concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", + "dev": true + }, + "node_modules/connect-history-api-fallback": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/connect-history-api-fallback/-/connect-history-api-fallback-2.0.0.tgz", + "integrity": "sha512-U73+6lQFmfiNPrYbXqr6kZ1i1wiRqXnp2nhMsINseWXO8lDau0LGEffJ8kQi4EjLZympVgRdvqjAgiZ1tgzDDA==", + "dev": true, + "engines": { + "node": ">=0.8" + } + }, + "node_modules/content-disposition": { + "version": "0.5.4", + "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.4.tgz", + "integrity": "sha512-FveZTNuGw04cxlAiWbzi6zTAL/lhehaWbTtgluJh4/E95DqMwTmha3KZN1aAWA8cFIhHzMZUvLevkw5Rqk+tSQ==", + "dev": true, + "dependencies": { + "safe-buffer": "5.2.1" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/content-type": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.5.tgz", + "integrity": "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/convert-source-map": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.9.0.tgz", + "integrity": "sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A==", + "dev": true, + "peer": true + }, + "node_modules/cookie": { + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.5.0.tgz", + "integrity": "sha512-YZ3GUyn/o8gfKJlnlX7g7xq4gyO6OSuhGPKaaGssGB2qgDUS0gPgtTvoyZLTt9Ab6dC4hfc9dV5arkvc/OCmrw==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/cookie-signature": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", + "integrity": "sha512-QADzlaHc8icV8I7vbaJXJwod9HWYp8uCqf1xa4OfNu1T7JVxQIrUgOWtHdNDtPiywmFbiS12VjotIXLrKM3orQ==", + "dev": true + }, + "node_modules/core-js-compat": { + "version": "3.27.2", + "resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.27.2.tgz", + "integrity": "sha512-welaYuF7ZtbYKGrIy7y3eb40d37rG1FvzEOfe7hSLd2iD6duMDqUhRfSvCGyC46HhR6Y8JXXdZ2lnRUMkPBpvg==", + "dev": true, + "dependencies": { + "browserslist": "^4.21.4" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/core-js" + } + }, + "node_modules/core-util-is": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz", + "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==", + "dev": true + }, + "node_modules/cosmiconfig": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-7.1.0.tgz", + "integrity": "sha512-AdmX6xUzdNASswsFtmwSt7Vj8po9IuqXm0UXz7QKPuEUmPB4XyjGfaAr2PSuELMwkRMVH1EpIkX5bTZGRB3eCA==", + "dev": true, + "dependencies": { + "@types/parse-json": "^4.0.0", + "import-fresh": "^3.2.1", + "parse-json": "^5.0.0", + "path-type": "^4.0.0", + "yaml": "^1.10.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/cross-spawn": { + "version": "7.0.3", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz", + "integrity": "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==", + "dev": true, + "dependencies": { + "path-key": "^3.1.0", + "shebang-command": "^2.0.0", + "which": "^2.0.1" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/css-loader": { + "version": "6.7.3", + "resolved": "https://registry.npmjs.org/css-loader/-/css-loader-6.7.3.tgz", + "integrity": "sha512-qhOH1KlBMnZP8FzRO6YCH9UHXQhVMcEGLyNdb7Hv2cpcmJbW0YrddO+tG1ab5nT41KpHIYGsbeHqxB9xPu1pKQ==", + "dev": true, + "dependencies": { + "icss-utils": "^5.1.0", + "postcss": "^8.4.19", + "postcss-modules-extract-imports": "^3.0.0", + "postcss-modules-local-by-default": "^4.0.0", + "postcss-modules-scope": "^3.0.0", + "postcss-modules-values": "^4.0.0", + "postcss-value-parser": "^4.2.0", + "semver": "^7.3.8" + }, + "engines": { + "node": ">= 12.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependencies": { + "webpack": "^5.0.0" + } + }, + "node_modules/css-loader/node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dev": true, + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/css-loader/node_modules/semver": { + "version": "7.3.8", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.8.tgz", + "integrity": "sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/css-loader/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, + "node_modules/css-select": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/css-select/-/css-select-4.3.0.tgz", + "integrity": "sha512-wPpOYtnsVontu2mODhA19JrqWxNsfdatRKd64kmpRbQgh1KtItko5sTnEpPdpSaJszTOhEMlF/RPz28qj4HqhQ==", + "dev": true, + "dependencies": { + "boolbase": "^1.0.0", + "css-what": "^6.0.1", + "domhandler": "^4.3.1", + "domutils": "^2.8.0", + "nth-check": "^2.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/fb55" + } + }, + "node_modules/css-what": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/css-what/-/css-what-6.1.0.tgz", + "integrity": "sha512-HTUrgRJ7r4dsZKU6GjmpfRK1O76h97Z8MfS1G0FozR+oF2kG6Vfe8JE6zwrkbxigziPHinCJ+gCPjA9EaBDtRw==", + "dev": true, + "engines": { + "node": ">= 6" + }, + "funding": { + "url": "https://github.com/sponsors/fb55" + } + }, + "node_modules/cssesc": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/cssesc/-/cssesc-3.0.0.tgz", + "integrity": "sha512-/Tb/JcjK111nNScGob5MNtsntNM1aCNUDipB/TkwZFhyDrrE47SOx/18wF2bbjgc3ZzCSKW1T5nt5EbFoAz/Vg==", + "dev": true, + "bin": { + "cssesc": "bin/cssesc" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/debug": { + "version": "4.3.4", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.4.tgz", + "integrity": "sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ==", + "dev": true, + "dependencies": { + "ms": "2.1.2" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/default-gateway": { + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/default-gateway/-/default-gateway-6.0.3.tgz", + "integrity": "sha512-fwSOJsbbNzZ/CUFpqFBqYfYNLj1NbMPm8MMCIzHjC83iSJRBEGmDUxU+WP661BaBQImeC2yHwXtz+P/O9o+XEg==", + "dev": true, + "dependencies": { + "execa": "^5.0.0" + }, + "engines": { + "node": ">= 10" + } + }, + "node_modules/define-lazy-prop": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/define-lazy-prop/-/define-lazy-prop-2.0.0.tgz", + "integrity": "sha512-Ds09qNh8yw3khSjiJjiUInaGX9xlqZDY7JVryGxdxV7NPeuqQfplOpQ66yJFZut3jLa5zOwkXw1g9EI2uKh4Og==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/del": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/del/-/del-4.1.1.tgz", + "integrity": "sha512-QwGuEUouP2kVwQenAsOof5Fv8K9t3D8Ca8NxcXKrIpEHjTXK5J2nXLdP+ALI1cgv8wj7KuwBhTwBkOZSJKM5XQ==", + "dev": true, + "dependencies": { + "@types/glob": "^7.1.1", + "globby": "^6.1.0", + "is-path-cwd": "^2.0.0", + "is-path-in-cwd": "^2.0.0", + "p-map": "^2.0.0", + "pify": "^4.0.1", + "rimraf": "^2.6.3" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/depd": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", + "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/destroy": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.2.0.tgz", + "integrity": "sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==", + "dev": true, + "engines": { + "node": ">= 0.8", + "npm": "1.2.8000 || >= 1.4.16" + } + }, + "node_modules/detect-node": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/detect-node/-/detect-node-2.1.0.tgz", + "integrity": "sha512-T0NIuQpnTvFDATNuHN5roPwSBG83rFsuO+MXXH9/3N1eFbn4wcPjttvjMLEPWJ0RGUYgQE7cGgS3tNxbqCGM7g==", + "dev": true + }, + "node_modules/dns-equal": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/dns-equal/-/dns-equal-1.0.0.tgz", + "integrity": "sha512-z+paD6YUQsk+AbGCEM4PrOXSss5gd66QfcVBFTKR/HpFL9jCqikS94HYwKww6fQyO7IxrIIyUu+g0Ka9tUS2Cg==", + "dev": true + }, + "node_modules/dns-packet": { + "version": "5.4.0", + "resolved": "https://registry.npmjs.org/dns-packet/-/dns-packet-5.4.0.tgz", + "integrity": "sha512-EgqGeaBB8hLiHLZtp/IbaDQTL8pZ0+IvwzSHA6d7VyMDM+B9hgddEMa9xjK5oYnw0ci0JQ6g2XCD7/f6cafU6g==", + "dev": true, + "dependencies": { + "@leichtgewicht/ip-codec": "^2.0.1" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/dom-converter": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/dom-converter/-/dom-converter-0.2.0.tgz", + "integrity": "sha512-gd3ypIPfOMr9h5jIKq8E3sHOTCjeirnl0WK5ZdS1AW0Odt0b1PaWaHdJ4Qk4klv+YB9aJBS7mESXjFoDQPu6DA==", + "dev": true, + "dependencies": { + "utila": "~0.4" + } + }, + "node_modules/dom-serializer": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-1.4.1.tgz", + "integrity": "sha512-VHwB3KfrcOOkelEG2ZOfxqLZdfkil8PtJi4P8N2MMXucZq2yLp75ClViUlOVwyoHEDjYU433Aq+5zWP61+RGag==", + "dev": true, + "dependencies": { + "domelementtype": "^2.0.1", + "domhandler": "^4.2.0", + "entities": "^2.0.0" + }, + "funding": { + "url": "https://github.com/cheeriojs/dom-serializer?sponsor=1" + } + }, + "node_modules/domelementtype": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-2.3.0.tgz", + "integrity": "sha512-OLETBj6w0OsagBwdXnPdN0cnMfF9opN69co+7ZrbfPGrdpPVNBUj02spi6B1N7wChLQiPn4CSH/zJvXw56gmHw==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/fb55" + } + ] + }, + "node_modules/domhandler": { + "version": "4.3.1", + "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-4.3.1.tgz", + "integrity": "sha512-GrwoxYN+uWlzO8uhUXRl0P+kHE4GtVPfYzVLcUxPL7KNdHKj66vvlhiweIHqYYXWlw+T8iLMp42Lm67ghw4WMQ==", + "dev": true, + "dependencies": { + "domelementtype": "^2.2.0" + }, + "engines": { + "node": ">= 4" + }, + "funding": { + "url": "https://github.com/fb55/domhandler?sponsor=1" + } + }, + "node_modules/domutils": { + "version": "2.8.0", + "resolved": "https://registry.npmjs.org/domutils/-/domutils-2.8.0.tgz", + "integrity": "sha512-w96Cjofp72M5IIhpjgobBimYEfoPjx1Vx0BSX9P30WBdZW2WIKU0T1Bd0kz2eNZ9ikjKgHbEyKx8BB6H1L3h3A==", + "dev": true, + "dependencies": { + "dom-serializer": "^1.0.1", + "domelementtype": "^2.2.0", + "domhandler": "^4.2.0" + }, + "funding": { + "url": "https://github.com/fb55/domutils?sponsor=1" + } + }, + "node_modules/dot-case": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/dot-case/-/dot-case-3.0.4.tgz", + "integrity": "sha512-Kv5nKlh6yRrdrGvxeJ2e5y2eRUpkUosIW4A2AS38zwSz27zu7ufDwQPi5Jhs3XAlGNetl3bmnGhQsMtkKJnj3w==", + "dev": true, + "dependencies": { + "no-case": "^3.0.4", + "tslib": "^2.0.3" + } + }, + "node_modules/ee-first": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", + "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==", + "dev": true + }, + "node_modules/electron-to-chromium": { + "version": "1.4.286", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.286.tgz", + "integrity": "sha512-Vp3CVhmYpgf4iXNKAucoQUDcCrBQX3XLBtwgFqP9BUXuucgvAV9zWp1kYU7LL9j4++s9O+12cb3wMtN4SJy6UQ==", + "dev": true + }, + "node_modules/emojis-list": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz", + "integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==", + "dev": true, + "engines": { + "node": ">= 4" + } + }, + "node_modules/encodeurl": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", + "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/enhanced-resolve": { + "version": "5.12.0", + "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.12.0.tgz", + "integrity": "sha512-QHTXI/sZQmko1cbDoNAa3mJ5qhWUUNAq3vR0/YiD379fWQrcfuoX1+HW2S0MTt7XmoPLapdaDKUtelUSPic7hQ==", + "dev": true, + "dependencies": { + "graceful-fs": "^4.2.4", + "tapable": "^2.2.0" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/entities": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-2.2.0.tgz", + "integrity": "sha512-p92if5Nz619I0w+akJrLZH0MX0Pb5DX39XOwQTtXSdQQOaYH03S1uIQp4mhOZtAXrxq4ViO67YTiLBo2638o9A==", + "dev": true, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" + } + }, + "node_modules/envinfo": { + "version": "7.8.1", + "resolved": "https://registry.npmjs.org/envinfo/-/envinfo-7.8.1.tgz", + "integrity": "sha512-/o+BXHmB7ocbHEAs6F2EnG0ogybVVUdkRunTT2glZU9XAaGmhqskrvKwqXuDfNjEO0LZKWdejEEpnq8aM0tOaw==", + "dev": true, + "bin": { + "envinfo": "dist/cli.js" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/error-ex": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", + "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", + "dev": true, + "dependencies": { + "is-arrayish": "^0.2.1" + } + }, + "node_modules/es-module-lexer": { + "version": "0.9.3", + "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-0.9.3.tgz", + "integrity": "sha512-1HQ2M2sPtxwnvOvT1ZClHyQDiggdNjURWpY2we6aMKCQiUVxTmVs2UYPLIrD84sS+kMdUwfBSylbJPwNnBrnHQ==", + "dev": true + }, + "node_modules/escalade": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", + "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/escape-html": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", + "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==", + "dev": true + }, + "node_modules/escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", + "dev": true, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/eslint-scope": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", + "integrity": "sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==", + "dev": true, + "dependencies": { + "esrecurse": "^4.3.0", + "estraverse": "^4.1.1" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/esrecurse": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", + "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", + "dev": true, + "dependencies": { + "estraverse": "^5.2.0" + }, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/esrecurse/node_modules/estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/estraverse": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.3.0.tgz", + "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==", + "dev": true, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/esutils": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", + "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/etag": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", + "integrity": "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/eventemitter3": { + "version": "4.0.7", + "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-4.0.7.tgz", + "integrity": "sha512-8guHBZCwKnFhYdHr2ysuRWErTwhoN2X8XELRlrRwpmfeY2jjuUN4taQMsULKUVo1K4DvZl+0pgfyoysHxvmvEw==", + "dev": true + }, + "node_modules/events": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/events/-/events-3.3.0.tgz", + "integrity": "sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==", + "dev": true, + "engines": { + "node": ">=0.8.x" + } + }, + "node_modules/execa": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/execa/-/execa-5.1.1.tgz", + "integrity": "sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==", + "dev": true, + "dependencies": { + "cross-spawn": "^7.0.3", + "get-stream": "^6.0.0", + "human-signals": "^2.1.0", + "is-stream": "^2.0.0", + "merge-stream": "^2.0.0", + "npm-run-path": "^4.0.1", + "onetime": "^5.1.2", + "signal-exit": "^3.0.3", + "strip-final-newline": "^2.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sindresorhus/execa?sponsor=1" + } + }, + "node_modules/express": { + "version": "4.18.2", + "resolved": "https://registry.npmjs.org/express/-/express-4.18.2.tgz", + "integrity": "sha512-5/PsL6iGPdfQ/lKM1UuielYgv3BUoJfz1aUwU9vHZ+J7gyvwdQXFEBIEIaxeGf0GIcreATNyBExtalisDbuMqQ==", + "dev": true, + "dependencies": { + "accepts": "~1.3.8", + "array-flatten": "1.1.1", + "body-parser": "1.20.1", + "content-disposition": "0.5.4", + "content-type": "~1.0.4", + "cookie": "0.5.0", + "cookie-signature": "1.0.6", + "debug": "2.6.9", + "depd": "2.0.0", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "finalhandler": "1.2.0", + "fresh": "0.5.2", + "http-errors": "2.0.0", + "merge-descriptors": "1.0.1", + "methods": "~1.1.2", + "on-finished": "2.4.1", + "parseurl": "~1.3.3", + "path-to-regexp": "0.1.7", + "proxy-addr": "~2.0.7", + "qs": "6.11.0", + "range-parser": "~1.2.1", + "safe-buffer": "5.2.1", + "send": "0.18.0", + "serve-static": "1.15.0", + "setprototypeof": "1.2.0", + "statuses": "2.0.1", + "type-is": "~1.6.18", + "utils-merge": "1.0.1", + "vary": "~1.1.2" + }, + "engines": { + "node": ">= 0.10.0" + } + }, + "node_modules/express/node_modules/array-flatten": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", + "integrity": "sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==", + "dev": true + }, + "node_modules/express/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/express/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true + }, + "node_modules/fast-deep-equal": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", + "dev": true + }, + "node_modules/fast-json-stable-stringify": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", + "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", + "dev": true + }, + "node_modules/fastest-levenshtein": { + "version": "1.0.16", + "resolved": "https://registry.npmjs.org/fastest-levenshtein/-/fastest-levenshtein-1.0.16.tgz", + "integrity": "sha512-eRnCtTTtGZFpQCwhJiUOuxPQWRXVKYDn0b2PeHfXL6/Zi53SLAzAHfVhVWK2AryC/WH05kGfxhFIPvTF0SXQzg==", + "dev": true, + "engines": { + "node": ">= 4.9.1" + } + }, + "node_modules/faye-websocket": { + "version": "0.11.4", + "resolved": "https://registry.npmjs.org/faye-websocket/-/faye-websocket-0.11.4.tgz", + "integrity": "sha512-CzbClwlXAuiRQAlUyfqPgvPoNKTckTPGfwZV4ZdAhVcP2lh9KUxJg2b5GkE7XbjKQ3YJnQ9z6D9ntLAlB+tP8g==", + "dev": true, + "dependencies": { + "websocket-driver": ">=0.5.1" + }, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/fill-range": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz", + "integrity": "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==", + "dev": true, + "dependencies": { + "to-regex-range": "^5.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/finalhandler": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.2.0.tgz", + "integrity": "sha512-5uXcUVftlQMFnWC9qu/svkWv3GTd2PfUhK/3PLkYNAe7FbqJMt3515HaxE6eRL74GdsriiwujiawdaB1BpEISg==", + "dev": true, + "dependencies": { + "debug": "2.6.9", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "on-finished": "2.4.1", + "parseurl": "~1.3.3", + "statuses": "2.0.1", + "unpipe": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/finalhandler/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/finalhandler/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true + }, + "node_modules/find-cache-dir": { + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/find-cache-dir/-/find-cache-dir-3.3.2.tgz", + "integrity": "sha512-wXZV5emFEjrridIgED11OoUKLxiYjAcqot/NJdAkOhlJ+vGzwhOAfcG5OX1jP+S0PcjEn8bdMJv+g2jwQ3Onig==", + "dev": true, + "dependencies": { + "commondir": "^1.0.1", + "make-dir": "^3.0.2", + "pkg-dir": "^4.1.0" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/avajs/find-cache-dir?sponsor=1" + } + }, + "node_modules/find-up": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", + "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", + "dev": true, + "dependencies": { + "locate-path": "^5.0.0", + "path-exists": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/follow-redirects": { + "version": "1.15.2", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.2.tgz", + "integrity": "sha512-VQLG33o04KaQ8uYi2tVNbdrWp1QWxNNea+nmIB4EVM28v0hmP17z7aG1+wAkNzVq4KeXTq3221ye5qTJP91JwA==", + "dev": true, + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/RubenVerborgh" + } + ], + "engines": { + "node": ">=4.0" + }, + "peerDependenciesMeta": { + "debug": { + "optional": true + } + } + }, + "node_modules/forwarded": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", + "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/fraction.js": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/fraction.js/-/fraction.js-4.2.0.tgz", + "integrity": "sha512-MhLuK+2gUcnZe8ZHlaaINnQLl0xRIGRfcGk2yl8xoQAfHrSsL3rYu6FCmBdkdbhc9EPlwyGHewaRsvwRMJtAlA==", + "dev": true, + "engines": { + "node": "*" + }, + "funding": { + "type": "patreon", + "url": "https://www.patreon.com/infusion" + } + }, + "node_modules/fresh": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", + "integrity": "sha512-zJ2mQYM18rEFOudeV4GShTGIQ7RbzA7ozbU9I/XBpm7kqgMywgmylMwXHxZJmkVoYkna9d2pVXVXPdYTP9ej8Q==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/fs-monkey": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/fs-monkey/-/fs-monkey-1.0.3.tgz", + "integrity": "sha512-cybjIfiiE+pTWicSCLFHSrXZ6EilF30oh91FDP9S2B051prEa7QWfrVTQm10/dDpswBDXZugPa1Ogu8Yh+HV0Q==", + "dev": true + }, + "node_modules/fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", + "dev": true + }, + "node_modules/fsevents": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", + "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", + "dev": true, + "hasInstallScript": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, + "node_modules/function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", + "dev": true + }, + "node_modules/gensync": { + "version": "1.0.0-beta.2", + "resolved": "https://registry.npmjs.org/gensync/-/gensync-1.0.0-beta.2.tgz", + "integrity": "sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==", + "dev": true, + "peer": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/get-intrinsic": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.0.tgz", + "integrity": "sha512-L049y6nFOuom5wGyRc3/gdTLO94dySVKRACj1RmJZBQXlbTMhtNIgkWkUHq+jYmZvKf14EW1EoJnnjbmoHij0Q==", + "dev": true, + "dependencies": { + "function-bind": "^1.1.1", + "has": "^1.0.3", + "has-symbols": "^1.0.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/get-stream": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-6.0.1.tgz", + "integrity": "sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/glob": { + "version": "7.2.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", + "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", + "dev": true, + "dependencies": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.1.1", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + }, + "engines": { + "node": "*" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/glob-parent": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", + "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", + "dev": true, + "dependencies": { + "is-glob": "^4.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/glob-to-regexp": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/glob-to-regexp/-/glob-to-regexp-0.4.1.tgz", + "integrity": "sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==", + "dev": true + }, + "node_modules/globals": { + "version": "11.12.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-11.12.0.tgz", + "integrity": "sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/globby": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/globby/-/globby-6.1.0.tgz", + "integrity": "sha512-KVbFv2TQtbzCoxAnfD6JcHZTYCzyliEaaeM/gH8qQdkKr5s0OP9scEgvdcngyk7AVdY6YVW/TJHd+lQ/Df3Daw==", + "dev": true, + "dependencies": { + "array-union": "^1.0.1", + "glob": "^7.0.3", + "object-assign": "^4.0.1", + "pify": "^2.0.0", + "pinkie-promise": "^2.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/globby/node_modules/pify": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", + "integrity": "sha512-udgsAY+fTnvv7kI7aaxbqwWNb0AHiB0qBO89PZKPkoTmGOgdbrHDKD+0B2X4uTfJ/FT1R09r9gTsjUjNJotuog==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/graceful-fs": { + "version": "4.2.10", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.10.tgz", + "integrity": "sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==", + "dev": true + }, + "node_modules/handle-thing": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/handle-thing/-/handle-thing-2.0.1.tgz", + "integrity": "sha512-9Qn4yBxelxoh2Ow62nP+Ka/kMnOXRi8BXnRaUwezLNhqelnN49xKz4F/dPP8OYLxLxq6JDtZb2i9XznUQbNPTg==", + "dev": true + }, + "node_modules/has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "dev": true, + "dependencies": { + "function-bind": "^1.1.1" + }, + "engines": { + "node": ">= 0.4.0" + } + }, + "node_modules/has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/has-symbols": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", + "integrity": "sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/he": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/he/-/he-1.2.0.tgz", + "integrity": "sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw==", + "dev": true, + "bin": { + "he": "bin/he" + } + }, + "node_modules/hpack.js": { + "version": "2.1.6", + "resolved": "https://registry.npmjs.org/hpack.js/-/hpack.js-2.1.6.tgz", + "integrity": "sha512-zJxVehUdMGIKsRaNt7apO2Gqp0BdqW5yaiGHXXmbpvxgBYVZnAql+BJb4RO5ad2MgpbZKn5G6nMnegrH1FcNYQ==", + "dev": true, + "dependencies": { + "inherits": "^2.0.1", + "obuf": "^1.0.0", + "readable-stream": "^2.0.1", + "wbuf": "^1.1.0" + } + }, + "node_modules/hpack.js/node_modules/readable-stream": { + "version": "2.3.7", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.7.tgz", + "integrity": "sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==", + "dev": true, + "dependencies": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" + } + }, + "node_modules/hpack.js/node_modules/safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true + }, + "node_modules/hpack.js/node_modules/string_decoder": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "dev": true, + "dependencies": { + "safe-buffer": "~5.1.0" + } + }, + "node_modules/html-entities": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/html-entities/-/html-entities-2.3.3.tgz", + "integrity": "sha512-DV5Ln36z34NNTDgnz0EWGBLZENelNAtkiFA4kyNOG2tDI6Mz1uSWiq1wAKdyjnJwyDiDO7Fa2SO1CTxPXL8VxA==", + "dev": true + }, + "node_modules/html-minifier-terser": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/html-minifier-terser/-/html-minifier-terser-6.1.0.tgz", + "integrity": "sha512-YXxSlJBZTP7RS3tWnQw74ooKa6L9b9i9QYXY21eUEvhZ3u9XLfv6OnFsQq6RxkhHygsaUMvYsZRV5rU/OVNZxw==", + "dev": true, + "dependencies": { + "camel-case": "^4.1.2", + "clean-css": "^5.2.2", + "commander": "^8.3.0", + "he": "^1.2.0", + "param-case": "^3.0.4", + "relateurl": "^0.2.7", + "terser": "^5.10.0" + }, + "bin": { + "html-minifier-terser": "cli.js" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/html-webpack-plugin": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/html-webpack-plugin/-/html-webpack-plugin-5.5.0.tgz", + "integrity": "sha512-sy88PC2cRTVxvETRgUHFrL4No3UxvcH8G1NepGhqaTT+GXN2kTamqasot0inS5hXeg1cMbFDt27zzo9p35lZVw==", + "dev": true, + "dependencies": { + "@types/html-minifier-terser": "^6.0.0", + "html-minifier-terser": "^6.0.2", + "lodash": "^4.17.21", + "pretty-error": "^4.0.0", + "tapable": "^2.0.0" + }, + "engines": { + "node": ">=10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/html-webpack-plugin" + }, + "peerDependencies": { + "webpack": "^5.20.0" + } + }, + "node_modules/htmlparser2": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/htmlparser2/-/htmlparser2-6.1.0.tgz", + "integrity": "sha512-gyyPk6rgonLFEDGoeRgQNaEUvdJ4ktTmmUh/h2t7s+M8oPpIPxgNACWa+6ESR57kXstwqPiCut0V8NRpcwgU7A==", + "dev": true, + "funding": [ + "https://github.com/fb55/htmlparser2?sponsor=1", + { + "type": "github", + "url": "https://github.com/sponsors/fb55" + } + ], + "dependencies": { + "domelementtype": "^2.0.1", + "domhandler": "^4.0.0", + "domutils": "^2.5.2", + "entities": "^2.0.0" + } + }, + "node_modules/http-deceiver": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/http-deceiver/-/http-deceiver-1.2.7.tgz", + "integrity": "sha512-LmpOGxTfbpgtGVxJrj5k7asXHCgNZp5nLfp+hWc8QQRqtb7fUy6kRY3BO1h9ddF6yIPYUARgxGOwB42DnxIaNw==", + "dev": true + }, + "node_modules/http-errors": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.0.tgz", + "integrity": "sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==", + "dev": true, + "dependencies": { + "depd": "2.0.0", + "inherits": "2.0.4", + "setprototypeof": "1.2.0", + "statuses": "2.0.1", + "toidentifier": "1.0.1" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/http-parser-js": { + "version": "0.5.8", + "resolved": "https://registry.npmjs.org/http-parser-js/-/http-parser-js-0.5.8.tgz", + "integrity": "sha512-SGeBX54F94Wgu5RH3X5jsDtf4eHyRogWX1XGT3b4HuW3tQPM4AaBzoUji/4AAJNXCEOWZ5O0DgZmJw1947gD5Q==", + "dev": true + }, + "node_modules/http-proxy": { + "version": "1.18.1", + "resolved": "https://registry.npmjs.org/http-proxy/-/http-proxy-1.18.1.tgz", + "integrity": "sha512-7mz/721AbnJwIVbnaSv1Cz3Am0ZLT/UBwkC92VlxhXv/k/BBQfM2fXElQNC27BVGr0uwUpplYPQM9LnaBMR5NQ==", + "dev": true, + "dependencies": { + "eventemitter3": "^4.0.0", + "follow-redirects": "^1.0.0", + "requires-port": "^1.0.0" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/http-proxy-middleware": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/http-proxy-middleware/-/http-proxy-middleware-2.0.6.tgz", + "integrity": "sha512-ya/UeJ6HVBYxrgYotAZo1KvPWlgB48kUJLDePFeneHsVujFaW5WNj2NgWCAE//B1Dl02BIfYlpNgBy8Kf8Rjmw==", + "dev": true, + "dependencies": { + "@types/http-proxy": "^1.17.8", + "http-proxy": "^1.18.1", + "is-glob": "^4.0.1", + "is-plain-obj": "^3.0.0", + "micromatch": "^4.0.2" + }, + "engines": { + "node": ">=12.0.0" + }, + "peerDependencies": { + "@types/express": "^4.17.13" + }, + "peerDependenciesMeta": { + "@types/express": { + "optional": true + } + } + }, + "node_modules/human-signals": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/human-signals/-/human-signals-2.1.0.tgz", + "integrity": "sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw==", + "dev": true, + "engines": { + "node": ">=10.17.0" + } + }, + "node_modules/iconv-lite": { + "version": "0.4.24", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", + "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", + "dev": true, + "dependencies": { + "safer-buffer": ">= 2.1.2 < 3" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/icss-utils": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/icss-utils/-/icss-utils-5.1.0.tgz", + "integrity": "sha512-soFhflCVWLfRNOPU3iv5Z9VUdT44xFRbzjLsEzSr5AQmgqPMTHdU3PMT1Cf1ssx8fLNJDA1juftYl+PUcv3MqA==", + "dev": true, + "engines": { + "node": "^10 || ^12 || >= 14" + }, + "peerDependencies": { + "postcss": "^8.1.0" + } + }, + "node_modules/immutable": { + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/immutable/-/immutable-4.2.3.tgz", + "integrity": "sha512-IHpmvaOIX4VLJwPOuQr1NpeBr2ZG6vpIj3blsLVxXRWJscLioaJRStqC+NcBsLeCDsnGlPpXd5/WZmnE7MbsKA==", + "dev": true + }, + "node_modules/import-fresh": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz", + "integrity": "sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw==", + "dev": true, + "dependencies": { + "parent-module": "^1.0.0", + "resolve-from": "^4.0.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/import-local": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/import-local/-/import-local-3.1.0.tgz", + "integrity": "sha512-ASB07uLtnDs1o6EHjKpX34BKYDSqnFerfTOJL2HvMqF70LnxpjkzDB8J44oT9pu4AMPkQwf8jl6szgvNd2tRIg==", + "dev": true, + "dependencies": { + "pkg-dir": "^4.2.0", + "resolve-cwd": "^3.0.0" + }, + "bin": { + "import-local-fixture": "fixtures/cli.js" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==", + "dev": true, + "dependencies": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "node_modules/inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true + }, + "node_modules/interpret": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/interpret/-/interpret-3.1.1.tgz", + "integrity": "sha512-6xwYfHbajpoF0xLW+iwLkhwgvLoZDfjYfoFNu8ftMoXINzwuymNLd9u/KmwtdT2GbR+/Cz66otEGEVVUHX9QLQ==", + "dev": true, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/ipaddr.js": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-2.0.1.tgz", + "integrity": "sha512-1qTgH9NG+IIJ4yfKs2e6Pp1bZg8wbDbKHT21HrLIeYBTRLgMYKnMTPAuI3Lcs61nfx5h1xlXnbJtH1kX5/d/ng==", + "dev": true, + "engines": { + "node": ">= 10" + } + }, + "node_modules/is-arrayish": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", + "integrity": "sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg==", + "dev": true + }, + "node_modules/is-binary-path": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz", + "integrity": "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==", + "dev": true, + "dependencies": { + "binary-extensions": "^2.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/is-core-module": { + "version": "2.11.0", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.11.0.tgz", + "integrity": "sha512-RRjxlvLDkD1YJwDbroBHMb+cukurkDWNyHx7D3oNB5x9rb5ogcksMC5wHCadcXoo67gVr/+3GFySh3134zi6rw==", + "dev": true, + "dependencies": { + "has": "^1.0.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-docker": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/is-docker/-/is-docker-2.2.1.tgz", + "integrity": "sha512-F+i2BKsFrH66iaUFc0woD8sLy8getkwTwtOBjvs56Cx4CgJDeKQeqfz8wAYiSb8JOprWhHH5p77PbmYCvvUuXQ==", + "dev": true, + "bin": { + "is-docker": "cli.js" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-glob": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", + "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", + "dev": true, + "dependencies": { + "is-extglob": "^2.1.1" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-number": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", + "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", + "dev": true, + "engines": { + "node": ">=0.12.0" + } + }, + "node_modules/is-path-cwd": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/is-path-cwd/-/is-path-cwd-2.2.0.tgz", + "integrity": "sha512-w942bTcih8fdJPJmQHFzkS76NEP8Kzzvmw92cXsazb8intwLqPibPPdXf4ANdKV3rYMuuQYGIWtvz9JilB3NFQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/is-path-in-cwd": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-path-in-cwd/-/is-path-in-cwd-2.1.0.tgz", + "integrity": "sha512-rNocXHgipO+rvnP6dk3zI20RpOtrAM/kzbB258Uw5BWr3TpXi861yzjo16Dn4hUox07iw5AyeMLHWsujkjzvRQ==", + "dev": true, + "dependencies": { + "is-path-inside": "^2.1.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/is-path-inside": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-2.1.0.tgz", + "integrity": "sha512-wiyhTzfDWsvwAW53OBWF5zuvaOGlZ6PwYxAbPVDhpm+gM09xKQGjBq/8uYN12aDvMxnAnq3dxTyoSoRNmg5YFg==", + "dev": true, + "dependencies": { + "path-is-inside": "^1.0.2" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/is-plain-obj": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-3.0.0.tgz", + "integrity": "sha512-gwsOE28k+23GP1B6vFl1oVh/WOzmawBrKwo5Ev6wMKzPkaXaCDIQKzLnvsA42DRlbVTWorkgTKIviAKCWkfUwA==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/is-plain-object": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", + "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", + "dev": true, + "dependencies": { + "isobject": "^3.0.1" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-stream": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", + "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/is-wsl": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/is-wsl/-/is-wsl-2.2.0.tgz", + "integrity": "sha512-fKzAra0rGJUUBwGBgNkHZuToZcn+TtXHpeCgmkMJMMYx1sQDYaCSyjJBSCa2nH1DGm7s3n1oBnohoVTBaN7Lww==", + "dev": true, + "dependencies": { + "is-docker": "^2.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==", + "dev": true + }, + "node_modules/isexe": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", + "dev": true + }, + "node_modules/isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha512-WhB9zCku7EGTj/HQQRz5aUQEUeoQZH2bWcltRErOpymJ4boYE6wL9Tbr23krRPSZ+C5zqNSrSw+Cc7sZZ4b7vg==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/jest-worker": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", + "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", + "dev": true, + "dependencies": { + "@types/node": "*", + "merge-stream": "^2.0.0", + "supports-color": "^8.0.0" + }, + "engines": { + "node": ">= 10.13.0" + } + }, + "node_modules/jest-worker/node_modules/has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/jest-worker/node_modules/supports-color": { + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", + "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "dev": true, + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/supports-color?sponsor=1" + } + }, + "node_modules/js-tokens": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", + "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", + "dev": true + }, + "node_modules/jsesc": { + "version": "2.5.2", + "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-2.5.2.tgz", + "integrity": "sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==", + "dev": true, + "bin": { + "jsesc": "bin/jsesc" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/json-parse-even-better-errors": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz", + "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==", + "dev": true + }, + "node_modules/json-schema-traverse": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", + "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==", + "dev": true + }, + "node_modules/json5": { + "version": "2.2.3", + "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", + "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==", + "dev": true, + "bin": { + "json5": "lib/cli.js" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/kind-of": { + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.3.tgz", + "integrity": "sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/klona": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/klona/-/klona-2.0.6.tgz", + "integrity": "sha512-dhG34DXATL5hSxJbIexCft8FChFXtmskoZYnoPWjXQuebWYCNkVeV3KkGegCK9CP1oswI/vQibS2GY7Em/sJJA==", + "dev": true, + "engines": { + "node": ">= 8" + } + }, + "node_modules/lines-and-columns": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/lines-and-columns/-/lines-and-columns-1.2.4.tgz", + "integrity": "sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==", + "dev": true + }, + "node_modules/loader-runner": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.3.0.tgz", + "integrity": "sha512-3R/1M+yS3j5ou80Me59j7F9IMs4PXs3VqRrm0TU3AbKPxlmpoY1TNscJV/oGJXo8qCatFGTfDbY6W6ipGOYXfg==", + "dev": true, + "engines": { + "node": ">=6.11.5" + } + }, + "node_modules/loader-utils": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-2.0.4.tgz", + "integrity": "sha512-xXqpXoINfFhgua9xiqD8fPFHgkoq1mmmpE92WlDbm9rNRd/EbRb+Gqf908T2DMfuHjjJlksiK2RbHVOdD/MqSw==", + "dev": true, + "dependencies": { + "big.js": "^5.2.2", + "emojis-list": "^3.0.0", + "json5": "^2.1.2" + }, + "engines": { + "node": ">=8.9.0" + } + }, + "node_modules/locate-path": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", + "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", + "dev": true, + "dependencies": { + "p-locate": "^4.1.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/lodash": { + "version": "4.17.21", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", + "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==", + "dev": true + }, + "node_modules/lodash.debounce": { + "version": "4.0.8", + "resolved": "https://registry.npmjs.org/lodash.debounce/-/lodash.debounce-4.0.8.tgz", + "integrity": "sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==", + "dev": true + }, + "node_modules/lower-case": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/lower-case/-/lower-case-2.0.2.tgz", + "integrity": "sha512-7fm3l3NAF9WfN6W3JOmf5drwpVqX78JtoGJ3A6W0a6ZnldM41w2fV5D490psKFTpMds8TJse/eHLFFsNHHjHgg==", + "dev": true, + "dependencies": { + "tslib": "^2.0.3" + } + }, + "node_modules/lru-cache": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", + "integrity": "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==", + "dev": true, + "dependencies": { + "yallist": "^3.0.2" + } + }, + "node_modules/make-dir": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-3.1.0.tgz", + "integrity": "sha512-g3FeP20LNwhALb/6Cz6Dd4F2ngze0jz7tbzrD2wAV+o9FeNHe4rL+yK2md0J/fiSf1sa1ADhXqi5+oVwOM/eGw==", + "dev": true, + "dependencies": { + "semver": "^6.0.0" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/media-typer": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", + "integrity": "sha512-dq+qelQ9akHpcOl/gUVRTxVIOkAJ1wR3QAvb4RsVjS8oVoFjDGTc679wJYmUmknUF5HwMLOgb5O+a3KxfWapPQ==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/memfs": { + "version": "3.4.13", + "resolved": "https://registry.npmjs.org/memfs/-/memfs-3.4.13.tgz", + "integrity": "sha512-omTM41g3Skpvx5dSYeZIbXKcXoAVc/AoMNwn9TKx++L/gaen/+4TTttmu8ZSch5vfVJ8uJvGbroTsIlslRg6lg==", + "dev": true, + "dependencies": { + "fs-monkey": "^1.0.3" + }, + "engines": { + "node": ">= 4.0.0" + } + }, + "node_modules/merge-descriptors": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", + "integrity": "sha512-cCi6g3/Zr1iqQi6ySbseM1Xvooa98N0w31jzUYrXPX2xqObmFGHJ0tQ5u74H3mVh7wLouTseZyYIq39g8cNp1w==", + "dev": true + }, + "node_modules/merge-stream": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", + "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==", + "dev": true + }, + "node_modules/methods": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", + "integrity": "sha512-iclAHeNqNm68zFtnZ0e+1L2yUIdvzNoauKU4WBA3VvH/vPFieF7qfRlwUZU+DA9P9bPXIS90ulxoUoCH23sV2w==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/micromatch": { + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.5.tgz", + "integrity": "sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA==", + "dev": true, + "dependencies": { + "braces": "^3.0.2", + "picomatch": "^2.3.1" + }, + "engines": { + "node": ">=8.6" + } + }, + "node_modules/mime": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", + "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", + "dev": true, + "bin": { + "mime": "cli.js" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dev": true, + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mimic-fn": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-2.1.0.tgz", + "integrity": "sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/mini-css-extract-plugin": { + "version": "2.7.2", + "resolved": "https://registry.npmjs.org/mini-css-extract-plugin/-/mini-css-extract-plugin-2.7.2.tgz", + "integrity": "sha512-EdlUizq13o0Pd+uCp+WO/JpkLvHRVGt97RqfeGhXqAcorYo1ypJSpkV+WDT0vY/kmh/p7wRdJNJtuyK540PXDw==", + "dev": true, + "dependencies": { + "schema-utils": "^4.0.0" + }, + "engines": { + "node": ">= 12.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependencies": { + "webpack": "^5.0.0" + } + }, + "node_modules/minimalistic-assert": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz", + "integrity": "sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A==", + "dev": true + }, + "node_modules/minimatch": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", + "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", + "dev": true, + "dependencies": { + "brace-expansion": "^1.1.7" + }, + "engines": { + "node": "*" + } + }, + "node_modules/ms": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", + "dev": true + }, + "node_modules/multicast-dns": { + "version": "7.2.5", + "resolved": "https://registry.npmjs.org/multicast-dns/-/multicast-dns-7.2.5.tgz", + "integrity": "sha512-2eznPJP8z2BFLX50tf0LuODrpINqP1RVIm/CObbTcBRITQgmC/TjcREF1NeTBzIcR5XO/ukWo+YHOjBbFwIupg==", + "dev": true, + "dependencies": { + "dns-packet": "^5.2.2", + "thunky": "^1.0.2" + }, + "bin": { + "multicast-dns": "cli.js" + } + }, + "node_modules/nanoid": { + "version": "3.3.4", + "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.4.tgz", + "integrity": "sha512-MqBkQh/OHTS2egovRtLk45wEyNXwF+cokD+1YPf9u5VfJiRdAiRwB2froX5Co9Rh20xs4siNPm8naNotSD6RBw==", + "dev": true, + "bin": { + "nanoid": "bin/nanoid.cjs" + }, + "engines": { + "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" + } + }, + "node_modules/negotiator": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz", + "integrity": "sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/neo-async": { + "version": "2.6.2", + "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.2.tgz", + "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==", + "dev": true + }, + "node_modules/no-case": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/no-case/-/no-case-3.0.4.tgz", + "integrity": "sha512-fgAN3jGAh+RoxUGZHTSOLJIqUc2wmoBwGR4tbpNAKmmovFoWq0OdRkb0VkldReO2a2iBT/OEulG9XSUc10r3zg==", + "dev": true, + "dependencies": { + "lower-case": "^2.0.2", + "tslib": "^2.0.3" + } + }, + "node_modules/node-forge": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/node-forge/-/node-forge-1.3.1.tgz", + "integrity": "sha512-dPEtOeMvF9VMcYV/1Wb8CPoVAXtp6MKMlcbAt4ddqmGqUJ6fQZFXkNZNkNlfevtNkGtaSoXf/vNNNSvgrdXwtA==", + "dev": true, + "engines": { + "node": ">= 6.13.0" + } + }, + "node_modules/node-releases": { + "version": "2.0.9", + "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.9.tgz", + "integrity": "sha512-2xfmOrRkGogbTK9R6Leda0DGiXeY3p2NJpy4+gNCffdUvV6mdEJnaDEic1i3Ec2djAo8jWYoJMR5PB0MSMpxUA==", + "dev": true + }, + "node_modules/normalize-path": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", + "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/normalize-range": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/normalize-range/-/normalize-range-0.1.2.tgz", + "integrity": "sha512-bdok/XvKII3nUpklnV6P2hxtMNrCboOjAcyBuQnWEhO665FwrSNRxU+AqpsyvO6LgGYPspN+lu5CLtw4jPRKNA==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/npm-run-path": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-4.0.1.tgz", + "integrity": "sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw==", + "dev": true, + "dependencies": { + "path-key": "^3.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/nth-check": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/nth-check/-/nth-check-2.1.1.tgz", + "integrity": "sha512-lqjrjmaOoAnWfMmBPL+XNnynZh2+swxiX3WUE0s4yEHI6m+AwrK2UZOimIRl3X/4QctVqS8AiZjFqyOGrMXb/w==", + "dev": true, + "dependencies": { + "boolbase": "^1.0.0" + }, + "funding": { + "url": "https://github.com/fb55/nth-check?sponsor=1" + } + }, + "node_modules/object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/object-inspect": { + "version": "1.12.3", + "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.3.tgz", + "integrity": "sha512-geUvdk7c+eizMNUDkRpW1wJwgfOiOeHbxBR/hLXK1aT6zmVSO0jsQcs7fj6MGw89jC/cjGfLcNOrtMYtGqm81g==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/obuf": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/obuf/-/obuf-1.1.2.tgz", + "integrity": "sha512-PX1wu0AmAdPqOL1mWhqmlOd8kOIZQwGZw6rh7uby9fTc5lhaOWFLX3I6R1hrF9k3zUY40e6igsLGkDXK92LJNg==", + "dev": true + }, + "node_modules/on-finished": { + "version": "2.4.1", + "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.4.1.tgz", + "integrity": "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==", + "dev": true, + "dependencies": { + "ee-first": "1.1.1" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/on-headers": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/on-headers/-/on-headers-1.0.2.tgz", + "integrity": "sha512-pZAE+FJLoyITytdqK0U5s+FIpjN0JP3OzFi/u8Rx+EV5/W+JTWGXG8xFzevE7AjBfDqHv/8vL8qQsIhHnqRkrA==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==", + "dev": true, + "dependencies": { + "wrappy": "1" + } + }, + "node_modules/onetime": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/onetime/-/onetime-5.1.2.tgz", + "integrity": "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==", + "dev": true, + "dependencies": { + "mimic-fn": "^2.1.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/open": { + "version": "8.4.0", + "resolved": "https://registry.npmjs.org/open/-/open-8.4.0.tgz", + "integrity": "sha512-XgFPPM+B28FtCCgSb9I+s9szOC1vZRSwgWsRUA5ylIxRTgKozqjOCrVOqGsYABPYK5qnfqClxZTFBa8PKt2v6Q==", + "dev": true, + "dependencies": { + "define-lazy-prop": "^2.0.0", + "is-docker": "^2.1.1", + "is-wsl": "^2.2.0" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/p-limit": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", + "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", + "dev": true, + "dependencies": { + "p-try": "^2.0.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/p-locate": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", + "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", + "dev": true, + "dependencies": { + "p-limit": "^2.2.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/p-map": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/p-map/-/p-map-2.1.0.tgz", + "integrity": "sha512-y3b8Kpd8OAN444hxfBbFfj1FY/RjtTd8tzYwhUqNYXx0fXx2iX4maP4Qr6qhIKbQXI02wTLAda4fYUbDagTUFw==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/p-retry": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/p-retry/-/p-retry-4.6.2.tgz", + "integrity": "sha512-312Id396EbJdvRONlngUx0NydfrIQ5lsYu0znKVUzVvArzEIt08V1qhtyESbGVd1FGX7UKtiFp5uwKZdM8wIuQ==", + "dev": true, + "dependencies": { + "@types/retry": "0.12.0", + "retry": "^0.13.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/p-try": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz", + "integrity": "sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/param-case": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/param-case/-/param-case-3.0.4.tgz", + "integrity": "sha512-RXlj7zCYokReqWpOPH9oYivUzLYZ5vAPIfEmCTNViosC78F8F0H9y7T7gG2M39ymgutxF5gcFEsyZQSph9Bp3A==", + "dev": true, + "dependencies": { + "dot-case": "^3.0.4", + "tslib": "^2.0.3" + } + }, + "node_modules/parent-module": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", + "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==", + "dev": true, + "dependencies": { + "callsites": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/parse-json": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-5.2.0.tgz", + "integrity": "sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==", + "dev": true, + "dependencies": { + "@babel/code-frame": "^7.0.0", + "error-ex": "^1.3.1", + "json-parse-even-better-errors": "^2.3.0", + "lines-and-columns": "^1.1.6" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/parseurl": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", + "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/pascal-case": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/pascal-case/-/pascal-case-3.1.2.tgz", + "integrity": "sha512-uWlGT3YSnK9x3BQJaOdcZwrnV6hPpd8jFH1/ucpiLRPh/2zCVJKS19E4GvYHvaCcACn3foXZ0cLB9Wrx1KGe5g==", + "dev": true, + "dependencies": { + "no-case": "^3.0.4", + "tslib": "^2.0.3" + } + }, + "node_modules/path-exists": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", + "integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/path-is-inside": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/path-is-inside/-/path-is-inside-1.0.2.tgz", + "integrity": "sha512-DUWJr3+ULp4zXmol/SZkFf3JGsS9/SIv+Y3Rt93/UjPpDpklB5f1er4O3POIbUuUJ3FXgqte2Q7SrU6zAqwk8w==", + "dev": true + }, + "node_modules/path-key": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", + "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/path-parse": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", + "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==", + "dev": true + }, + "node_modules/path-to-regexp": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", + "integrity": "sha512-5DFkuoqlv1uYQKxy8omFBeJPQcdoE07Kv2sferDCrAq1ohOU+MSDswDIbnx3YAM60qIOnYa53wBhXW0EbMonrQ==", + "dev": true + }, + "node_modules/path-type": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz", + "integrity": "sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/picocolors": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.0.0.tgz", + "integrity": "sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==", + "dev": true + }, + "node_modules/picomatch": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", + "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", + "dev": true, + "engines": { + "node": ">=8.6" + }, + "funding": { + "url": "https://github.com/sponsors/jonschlinkert" + } + }, + "node_modules/pify": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/pify/-/pify-4.0.1.tgz", + "integrity": "sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/pinkie": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/pinkie/-/pinkie-2.0.4.tgz", + "integrity": "sha512-MnUuEycAemtSaeFSjXKW/aroV7akBbY+Sv+RkyqFjgAe73F+MR0TBWKBRDkmfWq/HiFmdavfZ1G7h4SPZXaCSg==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/pinkie-promise": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", + "integrity": "sha512-0Gni6D4UcLTbv9c57DfxDGdr41XfgUjqWZu492f0cIGr16zDU06BWP/RAEvOuo7CQ0CNjHaLlM59YJJFm3NWlw==", + "dev": true, + "dependencies": { + "pinkie": "^2.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/pkg-dir": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-4.2.0.tgz", + "integrity": "sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ==", + "dev": true, + "dependencies": { + "find-up": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/postcss": { + "version": "8.4.21", + "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.4.21.tgz", + "integrity": "sha512-tP7u/Sn/dVxK2NnruI4H9BG+x+Wxz6oeZ1cJ8P6G/PZY0IKk4k/63TDsQf2kQq3+qoJeLm2kIBUNlZe3zgb4Zg==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/postcss/" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/postcss" + } + ], + "dependencies": { + "nanoid": "^3.3.4", + "picocolors": "^1.0.0", + "source-map-js": "^1.0.2" + }, + "engines": { + "node": "^10 || ^12 || >=14" + } + }, + "node_modules/postcss-loader": { + "version": "7.0.2", + "resolved": "https://registry.npmjs.org/postcss-loader/-/postcss-loader-7.0.2.tgz", + "integrity": "sha512-fUJzV/QH7NXUAqV8dWJ9Lg4aTkDCezpTS5HgJ2DvqznexTbSTxgi/dTECvTZ15BwKTtk8G/bqI/QTu2HPd3ZCg==", + "dev": true, + "dependencies": { + "cosmiconfig": "^7.0.0", + "klona": "^2.0.5", + "semver": "^7.3.8" + }, + "engines": { + "node": ">= 14.15.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependencies": { + "postcss": "^7.0.0 || ^8.0.1", + "webpack": "^5.0.0" + } + }, + "node_modules/postcss-loader/node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dev": true, + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/postcss-loader/node_modules/semver": { + "version": "7.3.8", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.8.tgz", + "integrity": "sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/postcss-loader/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, + "node_modules/postcss-modules-extract-imports": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/postcss-modules-extract-imports/-/postcss-modules-extract-imports-3.0.0.tgz", + "integrity": "sha512-bdHleFnP3kZ4NYDhuGlVK+CMrQ/pqUm8bx/oGL93K6gVwiclvX5x0n76fYMKuIGKzlABOy13zsvqjb0f92TEXw==", + "dev": true, + "engines": { + "node": "^10 || ^12 || >= 14" + }, + "peerDependencies": { + "postcss": "^8.1.0" + } + }, + "node_modules/postcss-modules-local-by-default": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/postcss-modules-local-by-default/-/postcss-modules-local-by-default-4.0.0.tgz", + "integrity": "sha512-sT7ihtmGSF9yhm6ggikHdV0hlziDTX7oFoXtuVWeDd3hHObNkcHRo9V3yg7vCAY7cONyxJC/XXCmmiHHcvX7bQ==", + "dev": true, + "dependencies": { + "icss-utils": "^5.0.0", + "postcss-selector-parser": "^6.0.2", + "postcss-value-parser": "^4.1.0" + }, + "engines": { + "node": "^10 || ^12 || >= 14" + }, + "peerDependencies": { + "postcss": "^8.1.0" + } + }, + "node_modules/postcss-modules-scope": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/postcss-modules-scope/-/postcss-modules-scope-3.0.0.tgz", + "integrity": "sha512-hncihwFA2yPath8oZ15PZqvWGkWf+XUfQgUGamS4LqoP1anQLOsOJw0vr7J7IwLpoY9fatA2qiGUGmuZL0Iqlg==", + "dev": true, + "dependencies": { + "postcss-selector-parser": "^6.0.4" + }, + "engines": { + "node": "^10 || ^12 || >= 14" + }, + "peerDependencies": { + "postcss": "^8.1.0" + } + }, + "node_modules/postcss-modules-values": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/postcss-modules-values/-/postcss-modules-values-4.0.0.tgz", + "integrity": "sha512-RDxHkAiEGI78gS2ofyvCsu7iycRv7oqw5xMWn9iMoR0N/7mf9D50ecQqUo5BZ9Zh2vH4bCUR/ktCqbB9m8vJjQ==", + "dev": true, + "dependencies": { + "icss-utils": "^5.0.0" + }, + "engines": { + "node": "^10 || ^12 || >= 14" + }, + "peerDependencies": { + "postcss": "^8.1.0" + } + }, + "node_modules/postcss-selector-parser": { + "version": "6.0.11", + "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-6.0.11.tgz", + "integrity": "sha512-zbARubNdogI9j7WY4nQJBiNqQf3sLS3wCP4WfOidu+p28LofJqDH1tcXypGrcmMHhDk2t9wGhCsYe/+szLTy1g==", + "dev": true, + "dependencies": { + "cssesc": "^3.0.0", + "util-deprecate": "^1.0.2" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/postcss-value-parser": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/postcss-value-parser/-/postcss-value-parser-4.2.0.tgz", + "integrity": "sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ==", + "dev": true + }, + "node_modules/pretty-error": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/pretty-error/-/pretty-error-4.0.0.tgz", + "integrity": "sha512-AoJ5YMAcXKYxKhuJGdcvse+Voc6v1RgnsR3nWcYU7q4t6z0Q6T86sv5Zq8VIRbOWWFpvdGE83LtdSMNd+6Y0xw==", + "dev": true, + "dependencies": { + "lodash": "^4.17.20", + "renderkid": "^3.0.0" + } + }, + "node_modules/process-nextick-args": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", + "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==", + "dev": true + }, + "node_modules/proxy-addr": { + "version": "2.0.7", + "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", + "integrity": "sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==", + "dev": true, + "dependencies": { + "forwarded": "0.2.0", + "ipaddr.js": "1.9.1" + }, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/proxy-addr/node_modules/ipaddr.js": { + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", + "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==", + "dev": true, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/punycode": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.0.tgz", + "integrity": "sha512-rRV+zQD8tVFys26lAGR9WUuS4iUAngJScM+ZRSKtvl5tKeZ2t5bvdNFdNHBW9FWR4guGHlgmsZ1G7BSm2wTbuA==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/qs": { + "version": "6.11.0", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.11.0.tgz", + "integrity": "sha512-MvjoMCJwEarSbUYk5O+nmoSzSutSsTwF85zcHPQ9OrlFoZOYIjaqBAJIqIXjptyD5vThxGq52Xu/MaJzRkIk4Q==", + "dev": true, + "dependencies": { + "side-channel": "^1.0.4" + }, + "engines": { + "node": ">=0.6" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/randombytes": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", + "integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==", + "dev": true, + "dependencies": { + "safe-buffer": "^5.1.0" + } + }, + "node_modules/range-parser": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", + "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/raw-body": { + "version": "2.5.1", + "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.5.1.tgz", + "integrity": "sha512-qqJBtEyVgS0ZmPGdCFPWJ3FreoqvG4MVQln/kCgF7Olq95IbOp0/BWyMwbdtn4VTvkM8Y7khCQ2Xgk/tcrCXig==", + "dev": true, + "dependencies": { + "bytes": "3.1.2", + "http-errors": "2.0.0", + "iconv-lite": "0.4.24", + "unpipe": "1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/raw-body/node_modules/bytes": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", + "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/readable-stream": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", + "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", + "dev": true, + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/readdirp": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", + "integrity": "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==", + "dev": true, + "dependencies": { + "picomatch": "^2.2.1" + }, + "engines": { + "node": ">=8.10.0" + } + }, + "node_modules/rechoir": { + "version": "0.8.0", + "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.8.0.tgz", + "integrity": "sha512-/vxpCXddiX8NGfGO/mTafwjq4aFa/71pvamip0++IQk3zG8cbCj0fifNPrjjF1XMXUne91jL9OoxmdykoEtifQ==", + "dev": true, + "dependencies": { + "resolve": "^1.20.0" + }, + "engines": { + "node": ">= 10.13.0" + } + }, + "node_modules/regenerate": { + "version": "1.4.2", + "resolved": "https://registry.npmjs.org/regenerate/-/regenerate-1.4.2.tgz", + "integrity": "sha512-zrceR/XhGYU/d/opr2EKO7aRHUeiBI8qjtfHqADTwZd6Szfy16la6kqD0MIUs5z5hx6AaKa+PixpPrR289+I0A==", + "dev": true + }, + "node_modules/regenerate-unicode-properties": { + "version": "10.1.0", + "resolved": "https://registry.npmjs.org/regenerate-unicode-properties/-/regenerate-unicode-properties-10.1.0.tgz", + "integrity": "sha512-d1VudCLoIGitcU/hEg2QqvyGZQmdC0Lf8BqdOMXGFSvJP4bNV1+XqbPQeHHLD51Jh4QJJ225dlIFvY4Ly6MXmQ==", + "dev": true, + "dependencies": { + "regenerate": "^1.4.2" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/regenerator-runtime": { + "version": "0.13.11", + "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.11.tgz", + "integrity": "sha512-kY1AZVr2Ra+t+piVaJ4gxaFaReZVH40AKNo7UCX6W+dEwBo/2oZJzqfuN1qLq1oL45o56cPaTXELwrTh8Fpggg==", + "dev": true + }, + "node_modules/regenerator-transform": { + "version": "0.15.1", + "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.15.1.tgz", + "integrity": "sha512-knzmNAcuyxV+gQCufkYcvOqX/qIIfHLv0u5x79kRxuGojfYVky1f15TzZEu2Avte8QGepvUNTnLskf8E6X6Vyg==", + "dev": true, + "dependencies": { + "@babel/runtime": "^7.8.4" + } + }, + "node_modules/regexpu-core": { + "version": "5.2.2", + "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-5.2.2.tgz", + "integrity": "sha512-T0+1Zp2wjF/juXMrMxHxidqGYn8U4R+zleSJhX9tQ1PUsS8a9UtYfbsF9LdiVgNX3kiX8RNaKM42nfSgvFJjmw==", + "dev": true, + "dependencies": { + "regenerate": "^1.4.2", + "regenerate-unicode-properties": "^10.1.0", + "regjsgen": "^0.7.1", + "regjsparser": "^0.9.1", + "unicode-match-property-ecmascript": "^2.0.0", + "unicode-match-property-value-ecmascript": "^2.1.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/regjsgen": { + "version": "0.7.1", + "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.7.1.tgz", + "integrity": "sha512-RAt+8H2ZEzHeYWxZ3H2z6tF18zyyOnlcdaafLrm21Bguj7uZy6ULibiAFdXEtKQY4Sy7wDTwDiOazasMLc4KPA==", + "dev": true + }, + "node_modules/regjsparser": { + "version": "0.9.1", + "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.9.1.tgz", + "integrity": "sha512-dQUtn90WanSNl+7mQKcXAgZxvUe7Z0SqXlgzv0za4LwiUhyzBC58yQO3liFoUgu8GiJVInAhJjkj1N0EtQ5nkQ==", + "dev": true, + "dependencies": { + "jsesc": "~0.5.0" + }, + "bin": { + "regjsparser": "bin/parser" + } + }, + "node_modules/regjsparser/node_modules/jsesc": { + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-0.5.0.tgz", + "integrity": "sha512-uZz5UnB7u4T9LvwmFqXii7pZSouaRPorGs5who1Ip7VO0wxanFvBL7GkM6dTHlgX+jhBApRetaWpnDabOeTcnA==", + "dev": true, + "bin": { + "jsesc": "bin/jsesc" + } + }, + "node_modules/relateurl": { + "version": "0.2.7", + "resolved": "https://registry.npmjs.org/relateurl/-/relateurl-0.2.7.tgz", + "integrity": "sha512-G08Dxvm4iDN3MLM0EsP62EDV9IuhXPR6blNz6Utcp7zyV3tr4HVNINt6MpaRWbxoOHT3Q7YN2P+jaHX8vUbgog==", + "dev": true, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/renderkid": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/renderkid/-/renderkid-3.0.0.tgz", + "integrity": "sha512-q/7VIQA8lmM1hF+jn+sFSPWGlMkSAeNYcPLmDQx2zzuiDfaLrOmumR8iaUKlenFgh0XRPIUeSPlH3A+AW3Z5pg==", + "dev": true, + "dependencies": { + "css-select": "^4.1.3", + "dom-converter": "^0.2.0", + "htmlparser2": "^6.1.0", + "lodash": "^4.17.21", + "strip-ansi": "^6.0.1" + } + }, + "node_modules/require-from-string": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", + "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/requires-port": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/requires-port/-/requires-port-1.0.0.tgz", + "integrity": "sha512-KigOCHcocU3XODJxsu8i/j8T9tzT4adHiecwORRQ0ZZFcp7ahwXuRU1m+yuO90C5ZUyGeGfocHDI14M3L3yDAQ==", + "dev": true + }, + "node_modules/resolve": { + "version": "1.22.1", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.1.tgz", + "integrity": "sha512-nBpuuYuY5jFsli/JIs1oldw6fOQCBioohqWZg/2hiaOybXOft4lonv85uDOKXdf8rhyK159cxU5cDcK/NKk8zw==", + "dev": true, + "dependencies": { + "is-core-module": "^2.9.0", + "path-parse": "^1.0.7", + "supports-preserve-symlinks-flag": "^1.0.0" + }, + "bin": { + "resolve": "bin/resolve" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/resolve-cwd": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/resolve-cwd/-/resolve-cwd-3.0.0.tgz", + "integrity": "sha512-OrZaX2Mb+rJCpH/6CpSqt9xFVpN++x01XnN2ie9g6P5/3xelLAkXWVADpdz1IHD/KFfEXyE6V0U01OQ3UO2rEg==", + "dev": true, + "dependencies": { + "resolve-from": "^5.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/resolve-cwd/node_modules/resolve-from": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz", + "integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/resolve-from": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", + "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/retry": { + "version": "0.13.1", + "resolved": "https://registry.npmjs.org/retry/-/retry-0.13.1.tgz", + "integrity": "sha512-XQBQ3I8W1Cge0Seh+6gjj03LbmRFWuoszgK9ooCpwYIrhhoO80pfq4cUkU5DkknwfOfFteRwlZ56PYOGYyFWdg==", + "dev": true, + "engines": { + "node": ">= 4" + } + }, + "node_modules/rimraf": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.7.1.tgz", + "integrity": "sha512-uWjbaKIK3T1OSVptzX7Nl6PvQ3qAGtKEtVRjRuazjfL3Bx5eI409VZSqgND+4UNnmzLVdPj9FqFJNPqBZFve4w==", + "dev": true, + "dependencies": { + "glob": "^7.1.3" + }, + "bin": { + "rimraf": "bin.js" + } + }, + "node_modules/safe-buffer": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", + "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ] + }, + "node_modules/safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", + "dev": true + }, + "node_modules/sass": { + "version": "1.58.0", + "resolved": "https://registry.npmjs.org/sass/-/sass-1.58.0.tgz", + "integrity": "sha512-PiMJcP33DdKtZ/1jSjjqVIKihoDc6yWmYr9K/4r3fVVIEDAluD0q7XZiRKrNJcPK3qkLRF/79DND1H5q1LBjgg==", + "dev": true, + "dependencies": { + "chokidar": ">=3.0.0 <4.0.0", + "immutable": "^4.0.0", + "source-map-js": ">=0.6.2 <2.0.0" + }, + "bin": { + "sass": "sass.js" + }, + "engines": { + "node": ">=12.0.0" + } + }, + "node_modules/sass-loader": { + "version": "13.2.0", + "resolved": "https://registry.npmjs.org/sass-loader/-/sass-loader-13.2.0.tgz", + "integrity": "sha512-JWEp48djQA4nbZxmgC02/Wh0eroSUutulROUusYJO9P9zltRbNN80JCBHqRGzjd4cmZCa/r88xgfkjGD0TXsHg==", + "dev": true, + "dependencies": { + "klona": "^2.0.4", + "neo-async": "^2.6.2" + }, + "engines": { + "node": ">= 14.15.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependencies": { + "fibers": ">= 3.1.0", + "node-sass": "^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0", + "sass": "^1.3.0", + "sass-embedded": "*", + "webpack": "^5.0.0" + }, + "peerDependenciesMeta": { + "fibers": { + "optional": true + }, + "node-sass": { + "optional": true + }, + "sass": { + "optional": true + }, + "sass-embedded": { + "optional": true + } + } + }, + "node_modules/schema-utils": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-4.0.0.tgz", + "integrity": "sha512-1edyXKgh6XnJsJSQ8mKWXnN/BVaIbFMLpouRUrXgVq7WYne5kw3MW7UPhO44uRXQSIpTSXoJbmrR2X0w9kUTyg==", + "dev": true, + "dependencies": { + "@types/json-schema": "^7.0.9", + "ajv": "^8.8.0", + "ajv-formats": "^2.1.1", + "ajv-keywords": "^5.0.0" + }, + "engines": { + "node": ">= 12.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + } + }, + "node_modules/select-hose": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/select-hose/-/select-hose-2.0.0.tgz", + "integrity": "sha512-mEugaLK+YfkijB4fx0e6kImuJdCIt2LxCRcbEYPqRGCs4F2ogyfZU5IAZRdjCP8JPq2AtdNoC/Dux63d9Kiryg==", + "dev": true + }, + "node_modules/selfsigned": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/selfsigned/-/selfsigned-2.1.1.tgz", + "integrity": "sha512-GSL3aowiF7wa/WtSFwnUrludWFoNhftq8bUkH9pkzjpN2XSPOAYEgg6e0sS9s0rZwgJzJiQRPU18A6clnoW5wQ==", + "dev": true, + "dependencies": { + "node-forge": "^1" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/semver": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "dev": true, + "bin": { + "semver": "bin/semver.js" + } + }, + "node_modules/send": { + "version": "0.18.0", + "resolved": "https://registry.npmjs.org/send/-/send-0.18.0.tgz", + "integrity": "sha512-qqWzuOjSFOuqPjFe4NOsMLafToQQwBSOEpS+FwEt3A2V3vKubTquT3vmLTQpFgMXp8AlFWFuP1qKaJZOtPpVXg==", + "dev": true, + "dependencies": { + "debug": "2.6.9", + "depd": "2.0.0", + "destroy": "1.2.0", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "fresh": "0.5.2", + "http-errors": "2.0.0", + "mime": "1.6.0", + "ms": "2.1.3", + "on-finished": "2.4.1", + "range-parser": "~1.2.1", + "statuses": "2.0.1" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/send/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/send/node_modules/debug/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true + }, + "node_modules/send/node_modules/ms": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", + "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", + "dev": true + }, + "node_modules/serialize-javascript": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-6.0.1.tgz", + "integrity": "sha512-owoXEFjWRllis8/M1Q+Cw5k8ZH40e3zhp/ovX+Xr/vi1qj6QesbyXXViFbpNvWvPNAD62SutwEXavefrLJWj7w==", + "dev": true, + "dependencies": { + "randombytes": "^2.1.0" + } + }, + "node_modules/serve-index": { + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/serve-index/-/serve-index-1.9.1.tgz", + "integrity": "sha512-pXHfKNP4qujrtteMrSBb0rc8HJ9Ms/GrXwcUtUtD5s4ewDJI8bT3Cz2zTVRMKtri49pLx2e0Ya8ziP5Ya2pZZw==", + "dev": true, + "dependencies": { + "accepts": "~1.3.4", + "batch": "0.6.1", + "debug": "2.6.9", + "escape-html": "~1.0.3", + "http-errors": "~1.6.2", + "mime-types": "~2.1.17", + "parseurl": "~1.3.2" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/serve-index/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/serve-index/node_modules/depd": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", + "integrity": "sha512-7emPTl6Dpo6JRXOXjLRxck+FlLRX5847cLKEn00PLAgc3g2hTZZgr+e4c2v6QpSmLeFP3n5yUo7ft6avBK/5jQ==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/serve-index/node_modules/http-errors": { + "version": "1.6.3", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", + "integrity": "sha512-lks+lVC8dgGyh97jxvxeYTWQFvh4uw4yC12gVl63Cg30sjPX4wuGcdkICVXDAESr6OJGjqGA8Iz5mkeN6zlD7A==", + "dev": true, + "dependencies": { + "depd": "~1.1.2", + "inherits": "2.0.3", + "setprototypeof": "1.1.0", + "statuses": ">= 1.4.0 < 2" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/serve-index/node_modules/inherits": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", + "integrity": "sha512-x00IRNXNy63jwGkJmzPigoySHbaqpNuzKbBOmzK+g2OdZpQ9w+sxCN+VSB3ja7IAge2OP2qpfxTjeNcyjmW1uw==", + "dev": true + }, + "node_modules/serve-index/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true + }, + "node_modules/serve-index/node_modules/setprototypeof": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", + "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==", + "dev": true + }, + "node_modules/serve-index/node_modules/statuses": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", + "integrity": "sha512-OpZ3zP+jT1PI7I8nemJX4AKmAX070ZkYPVWV/AaKTJl+tXCTGyVdC1a4SL8RUQYEwk/f34ZX8UTykN68FwrqAA==", + "dev": true, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/serve-static": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.15.0.tgz", + "integrity": "sha512-XGuRDNjXUijsUL0vl6nSD7cwURuzEgglbOaFuZM9g3kwDXOWVTck0jLzjPzGD+TazWbboZYu52/9/XPdUgne9g==", + "dev": true, + "dependencies": { + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "parseurl": "~1.3.3", + "send": "0.18.0" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/setprototypeof": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", + "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==", + "dev": true + }, + "node_modules/shallow-clone": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/shallow-clone/-/shallow-clone-3.0.1.tgz", + "integrity": "sha512-/6KqX+GVUdqPuPPd2LxDDxzX6CAbjJehAAOKlNpqqUpAqPM6HeL8f+o3a+JsyGjn2lv0WY8UsTgUJjU9Ok55NA==", + "dev": true, + "dependencies": { + "kind-of": "^6.0.2" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/shebang-command": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", + "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", + "dev": true, + "dependencies": { + "shebang-regex": "^3.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/shebang-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", + "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/side-channel": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.4.tgz", + "integrity": "sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.0", + "get-intrinsic": "^1.0.2", + "object-inspect": "^1.9.0" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/signal-exit": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", + "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==", + "dev": true + }, + "node_modules/sockjs": { + "version": "0.3.24", + "resolved": "https://registry.npmjs.org/sockjs/-/sockjs-0.3.24.tgz", + "integrity": "sha512-GJgLTZ7vYb/JtPSSZ10hsOYIvEYsjbNU+zPdIHcUaWVNUEPivzxku31865sSSud0Da0W4lEeOPlmw93zLQchuQ==", + "dev": true, + "dependencies": { + "faye-websocket": "^0.11.3", + "uuid": "^8.3.2", + "websocket-driver": "^0.7.4" + } + }, + "node_modules/source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/source-map-js": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.0.2.tgz", + "integrity": "sha512-R0XvVJ9WusLiqTCEiGCmICCMplcCkIwwR11mOSD9CR5u+IXYdiseeEuXCVAjS54zqwkLcPNnmU4OeJ6tUrWhDw==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/source-map-support": { + "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==", + "dev": true, + "dependencies": { + "buffer-from": "^1.0.0", + "source-map": "^0.6.0" + } + }, + "node_modules/spdy": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/spdy/-/spdy-4.0.2.tgz", + "integrity": "sha512-r46gZQZQV+Kl9oItvl1JZZqJKGr+oEkB08A6BzkiR7593/7IbtuncXHd2YoYeTsG4157ZssMu9KYvUHLcjcDoA==", + "dev": true, + "dependencies": { + "debug": "^4.1.0", + "handle-thing": "^2.0.0", + "http-deceiver": "^1.2.7", + "select-hose": "^2.0.0", + "spdy-transport": "^3.0.0" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/spdy-transport": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/spdy-transport/-/spdy-transport-3.0.0.tgz", + "integrity": "sha512-hsLVFE5SjA6TCisWeJXFKniGGOpBgMLmerfO2aCyCU5s7nJ/rpAepqmFifv/GCbSbueEeAJJnmSQ2rKC/g8Fcw==", + "dev": true, + "dependencies": { + "debug": "^4.1.0", + "detect-node": "^2.0.4", + "hpack.js": "^2.1.6", + "obuf": "^1.1.2", + "readable-stream": "^3.0.6", + "wbuf": "^1.7.3" + } + }, + "node_modules/statuses": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", + "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/string_decoder": { + "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==", + "dev": true, + "dependencies": { + "safe-buffer": "~5.2.0" + } + }, + "node_modules/strip-ansi": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", + "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", + "dev": true, + "dependencies": { + "ansi-regex": "^5.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/strip-final-newline": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/strip-final-newline/-/strip-final-newline-2.0.0.tgz", + "integrity": "sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, + "dependencies": { + "has-flag": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/supports-preserve-symlinks-flag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", + "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/tapable": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz", + "integrity": "sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/terser": { + "version": "5.16.3", + "resolved": "https://registry.npmjs.org/terser/-/terser-5.16.3.tgz", + "integrity": "sha512-v8wWLaS/xt3nE9dgKEWhNUFP6q4kngO5B8eYFUuebsu7Dw/UNAnpUod6UHo04jSSkv8TzKHjZDSd7EXdDQAl8Q==", + "dev": true, + "dependencies": { + "@jridgewell/source-map": "^0.3.2", + "acorn": "^8.5.0", + "commander": "^2.20.0", + "source-map-support": "~0.5.20" + }, + "bin": { + "terser": "bin/terser" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/terser-webpack-plugin": { + "version": "5.3.6", + "resolved": "https://registry.npmjs.org/terser-webpack-plugin/-/terser-webpack-plugin-5.3.6.tgz", + "integrity": "sha512-kfLFk+PoLUQIbLmB1+PZDMRSZS99Mp+/MHqDNmMA6tOItzRt+Npe3E+fsMs5mfcM0wCtrrdU387UnV+vnSffXQ==", + "dev": true, + "dependencies": { + "@jridgewell/trace-mapping": "^0.3.14", + "jest-worker": "^27.4.5", + "schema-utils": "^3.1.1", + "serialize-javascript": "^6.0.0", + "terser": "^5.14.1" + }, + "engines": { + "node": ">= 10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependencies": { + "webpack": "^5.1.0" + }, + "peerDependenciesMeta": { + "@swc/core": { + "optional": true + }, + "esbuild": { + "optional": true + }, + "uglify-js": { + "optional": true + } + } + }, + "node_modules/terser-webpack-plugin/node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/terser-webpack-plugin/node_modules/ajv-keywords": { + "version": "3.5.2", + "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", + "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", + "dev": true, + "peerDependencies": { + "ajv": "^6.9.1" + } + }, + "node_modules/terser-webpack-plugin/node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "node_modules/terser-webpack-plugin/node_modules/schema-utils": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.1.1.tgz", + "integrity": "sha512-Y5PQxS4ITlC+EahLuXaY86TXfR7Dc5lw294alXOq86JAHCihAIZfqv8nNCWvaEJvaC51uN9hbLGeV0cFBdH+Fw==", + "dev": true, + "dependencies": { + "@types/json-schema": "^7.0.8", + "ajv": "^6.12.5", + "ajv-keywords": "^3.5.2" + }, + "engines": { + "node": ">= 10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + } + }, + "node_modules/terser/node_modules/commander": { + "version": "2.20.3", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", + "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==", + "dev": true + }, + "node_modules/thunky": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/thunky/-/thunky-1.1.0.tgz", + "integrity": "sha512-eHY7nBftgThBqOyHGVN+l8gF0BucP09fMo0oO/Lb0w1OF80dJv+lDVpXG60WMQvkcxAkNybKsrEIE3ZtKGmPrA==", + "dev": true + }, + "node_modules/to-fast-properties": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-2.0.0.tgz", + "integrity": "sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/to-regex-range": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", + "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", + "dev": true, + "dependencies": { + "is-number": "^7.0.0" + }, + "engines": { + "node": ">=8.0" + } + }, + "node_modules/toidentifier": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", + "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==", + "dev": true, + "engines": { + "node": ">=0.6" + } + }, + "node_modules/tslib": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.5.0.tgz", + "integrity": "sha512-336iVw3rtn2BUK7ORdIAHTyxHGRIHVReokCR3XjbckJMK7ms8FysBfhLR8IXnAgy7T0PTPNBWKiH514FOW/WSg==", + "dev": true + }, + "node_modules/type-is": { + "version": "1.6.18", + "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", + "integrity": "sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==", + "dev": true, + "dependencies": { + "media-typer": "0.3.0", + "mime-types": "~2.1.24" + }, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/typescript": { "version": "4.9.5", "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.9.5.tgz", @@ -31,6 +6131,578 @@ "engines": { "node": ">=4.2.0" } + }, + "node_modules/unicode-canonical-property-names-ecmascript": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/unicode-canonical-property-names-ecmascript/-/unicode-canonical-property-names-ecmascript-2.0.0.tgz", + "integrity": "sha512-yY5PpDlfVIU5+y/BSCxAJRBIS1Zc2dDG3Ujq+sR0U+JjUevW2JhocOF+soROYDSaAezOzOKuyyixhD6mBknSmQ==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/unicode-match-property-ecmascript": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/unicode-match-property-ecmascript/-/unicode-match-property-ecmascript-2.0.0.tgz", + "integrity": "sha512-5kaZCrbp5mmbz5ulBkDkbY0SsPOjKqVS35VpL9ulMPfSl0J0Xsm+9Evphv9CoIZFwre7aJoa94AY6seMKGVN5Q==", + "dev": true, + "dependencies": { + "unicode-canonical-property-names-ecmascript": "^2.0.0", + "unicode-property-aliases-ecmascript": "^2.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/unicode-match-property-value-ecmascript": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/unicode-match-property-value-ecmascript/-/unicode-match-property-value-ecmascript-2.1.0.tgz", + "integrity": "sha512-qxkjQt6qjg/mYscYMC0XKRn3Rh0wFPlfxB0xkt9CfyTvpX1Ra0+rAmdX2QyAobptSEvuy4RtpPRui6XkV+8wjA==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/unicode-property-aliases-ecmascript": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/unicode-property-aliases-ecmascript/-/unicode-property-aliases-ecmascript-2.1.0.tgz", + "integrity": "sha512-6t3foTQI9qne+OZoVQB/8x8rk2k1eVy1gRXhV3oFQ5T6R1dqQ1xtin3XqSlx3+ATBkliTaR/hHyJBm+LVPNM8w==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/unpipe": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", + "integrity": "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/update-browserslist-db": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.0.10.tgz", + "integrity": "sha512-OztqDenkfFkbSG+tRxBeAnCVPckDBcvibKd35yDONx6OU8N7sqgwc7rCbkJ/WcYtVRZ4ba68d6byhC21GFh7sQ==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/browserslist" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/browserslist" + } + ], + "dependencies": { + "escalade": "^3.1.1", + "picocolors": "^1.0.0" + }, + "bin": { + "browserslist-lint": "cli.js" + }, + "peerDependencies": { + "browserslist": ">= 4.21.0" + } + }, + "node_modules/uri-js": { + "version": "4.4.1", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", + "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", + "dev": true, + "dependencies": { + "punycode": "^2.1.0" + } + }, + "node_modules/url-loader": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/url-loader/-/url-loader-4.1.1.tgz", + "integrity": "sha512-3BTV812+AVHHOJQO8O5MkWgZ5aosP7GnROJwvzLS9hWDj00lZ6Z0wNak423Lp9PBZN05N+Jk/N5Si8jRAlGyWA==", + "dev": true, + "dependencies": { + "loader-utils": "^2.0.0", + "mime-types": "^2.1.27", + "schema-utils": "^3.0.0" + }, + "engines": { + "node": ">= 10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependencies": { + "file-loader": "*", + "webpack": "^4.0.0 || ^5.0.0" + }, + "peerDependenciesMeta": { + "file-loader": { + "optional": true + } + } + }, + "node_modules/url-loader/node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/url-loader/node_modules/ajv-keywords": { + "version": "3.5.2", + "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", + "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", + "dev": true, + "peerDependencies": { + "ajv": "^6.9.1" + } + }, + "node_modules/url-loader/node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "node_modules/url-loader/node_modules/schema-utils": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.1.1.tgz", + "integrity": "sha512-Y5PQxS4ITlC+EahLuXaY86TXfR7Dc5lw294alXOq86JAHCihAIZfqv8nNCWvaEJvaC51uN9hbLGeV0cFBdH+Fw==", + "dev": true, + "dependencies": { + "@types/json-schema": "^7.0.8", + "ajv": "^6.12.5", + "ajv-keywords": "^3.5.2" + }, + "engines": { + "node": ">= 10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + } + }, + "node_modules/util-deprecate": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", + "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", + "dev": true + }, + "node_modules/utila": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/utila/-/utila-0.4.0.tgz", + "integrity": "sha512-Z0DbgELS9/L/75wZbro8xAnT50pBVFQZ+hUEueGDU5FN51YSCYM+jdxsfCiHjwNP/4LCDD0i/graKpeBnOXKRA==", + "dev": true + }, + "node_modules/utils-merge": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", + "integrity": "sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA==", + "dev": true, + "engines": { + "node": ">= 0.4.0" + } + }, + "node_modules/uuid": { + "version": "8.3.2", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz", + "integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==", + "dev": true, + "bin": { + "uuid": "dist/bin/uuid" + } + }, + "node_modules/vary": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", + "integrity": "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/watchpack": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.4.0.tgz", + "integrity": "sha512-Lcvm7MGST/4fup+ifyKi2hjyIAwcdI4HRgtvTpIUxBRhB+RFtUh8XtDOxUfctVCnhVi+QQj49i91OyvzkJl6cg==", + "dev": true, + "dependencies": { + "glob-to-regexp": "^0.4.1", + "graceful-fs": "^4.1.2" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/wbuf": { + "version": "1.7.3", + "resolved": "https://registry.npmjs.org/wbuf/-/wbuf-1.7.3.tgz", + "integrity": "sha512-O84QOnr0icsbFGLS0O3bI5FswxzRr8/gHwWkDlQFskhSPryQXvrTMxjxGP4+iWYoauLoBvfDpkrOauZ+0iZpDA==", + "dev": true, + "dependencies": { + "minimalistic-assert": "^1.0.0" + } + }, + "node_modules/webpack": { + "version": "5.75.0", + "resolved": "https://registry.npmjs.org/webpack/-/webpack-5.75.0.tgz", + "integrity": "sha512-piaIaoVJlqMsPtX/+3KTTO6jfvrSYgauFVdt8cr9LTHKmcq/AMd4mhzsiP7ZF/PGRNPGA8336jldh9l2Kt2ogQ==", + "dev": true, + "dependencies": { + "@types/eslint-scope": "^3.7.3", + "@types/estree": "^0.0.51", + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/wasm-edit": "1.11.1", + "@webassemblyjs/wasm-parser": "1.11.1", + "acorn": "^8.7.1", + "acorn-import-assertions": "^1.7.6", + "browserslist": "^4.14.5", + "chrome-trace-event": "^1.0.2", + "enhanced-resolve": "^5.10.0", + "es-module-lexer": "^0.9.0", + "eslint-scope": "5.1.1", + "events": "^3.2.0", + "glob-to-regexp": "^0.4.1", + "graceful-fs": "^4.2.9", + "json-parse-even-better-errors": "^2.3.1", + "loader-runner": "^4.2.0", + "mime-types": "^2.1.27", + "neo-async": "^2.6.2", + "schema-utils": "^3.1.0", + "tapable": "^2.1.1", + "terser-webpack-plugin": "^5.1.3", + "watchpack": "^2.4.0", + "webpack-sources": "^3.2.3" + }, + "bin": { + "webpack": "bin/webpack.js" + }, + "engines": { + "node": ">=10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependenciesMeta": { + "webpack-cli": { + "optional": true + } + } + }, + "node_modules/webpack-cli": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/webpack-cli/-/webpack-cli-5.0.1.tgz", + "integrity": "sha512-S3KVAyfwUqr0Mo/ur3NzIp6jnerNpo7GUO6so51mxLi1spqsA17YcMXy0WOIJtBSnj748lthxC6XLbNKh/ZC+A==", + "dev": true, + "dependencies": { + "@discoveryjs/json-ext": "^0.5.0", + "@webpack-cli/configtest": "^2.0.1", + "@webpack-cli/info": "^2.0.1", + "@webpack-cli/serve": "^2.0.1", + "colorette": "^2.0.14", + "commander": "^9.4.1", + "cross-spawn": "^7.0.3", + "envinfo": "^7.7.3", + "fastest-levenshtein": "^1.0.12", + "import-local": "^3.0.2", + "interpret": "^3.1.1", + "rechoir": "^0.8.0", + "webpack-merge": "^5.7.3" + }, + "bin": { + "webpack-cli": "bin/cli.js" + }, + "engines": { + "node": ">=14.15.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependencies": { + "webpack": "5.x.x" + }, + "peerDependenciesMeta": { + "@webpack-cli/generators": { + "optional": true + }, + "webpack-bundle-analyzer": { + "optional": true + }, + "webpack-dev-server": { + "optional": true + } + } + }, + "node_modules/webpack-cli/node_modules/commander": { + "version": "9.5.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-9.5.0.tgz", + "integrity": "sha512-KRs7WVDKg86PWiuAqhDrAQnTXZKraVcCc6vFdL14qrZ/DcWwuRo7VoiYXalXO7S5GKpqYiVEwCbgFDfxNHKJBQ==", + "dev": true, + "engines": { + "node": "^12.20.0 || >=14" + } + }, + "node_modules/webpack-dev-middleware": { + "version": "5.3.3", + "resolved": "https://registry.npmjs.org/webpack-dev-middleware/-/webpack-dev-middleware-5.3.3.tgz", + "integrity": "sha512-hj5CYrY0bZLB+eTO+x/j67Pkrquiy7kWepMHmUMoPsmcUaeEnQJqFzHJOyxgWlq746/wUuA64p9ta34Kyb01pA==", + "dev": true, + "dependencies": { + "colorette": "^2.0.10", + "memfs": "^3.4.3", + "mime-types": "^2.1.31", + "range-parser": "^1.2.1", + "schema-utils": "^4.0.0" + }, + "engines": { + "node": ">= 12.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependencies": { + "webpack": "^4.0.0 || ^5.0.0" + } + }, + "node_modules/webpack-dev-server": { + "version": "4.11.1", + "resolved": "https://registry.npmjs.org/webpack-dev-server/-/webpack-dev-server-4.11.1.tgz", + "integrity": "sha512-lILVz9tAUy1zGFwieuaQtYiadImb5M3d+H+L1zDYalYoDl0cksAB1UNyuE5MMWJrG6zR1tXkCP2fitl7yoUJiw==", + "dev": true, + "dependencies": { + "@types/bonjour": "^3.5.9", + "@types/connect-history-api-fallback": "^1.3.5", + "@types/express": "^4.17.13", + "@types/serve-index": "^1.9.1", + "@types/serve-static": "^1.13.10", + "@types/sockjs": "^0.3.33", + "@types/ws": "^8.5.1", + "ansi-html-community": "^0.0.8", + "bonjour-service": "^1.0.11", + "chokidar": "^3.5.3", + "colorette": "^2.0.10", + "compression": "^1.7.4", + "connect-history-api-fallback": "^2.0.0", + "default-gateway": "^6.0.3", + "express": "^4.17.3", + "graceful-fs": "^4.2.6", + "html-entities": "^2.3.2", + "http-proxy-middleware": "^2.0.3", + "ipaddr.js": "^2.0.1", + "open": "^8.0.9", + "p-retry": "^4.5.0", + "rimraf": "^3.0.2", + "schema-utils": "^4.0.0", + "selfsigned": "^2.1.1", + "serve-index": "^1.9.1", + "sockjs": "^0.3.24", + "spdy": "^4.0.2", + "webpack-dev-middleware": "^5.3.1", + "ws": "^8.4.2" + }, + "bin": { + "webpack-dev-server": "bin/webpack-dev-server.js" + }, + "engines": { + "node": ">= 12.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependencies": { + "webpack": "^4.37.0 || ^5.0.0" + }, + "peerDependenciesMeta": { + "webpack-cli": { + "optional": true + } + } + }, + "node_modules/webpack-dev-server/node_modules/rimraf": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", + "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", + "dev": true, + "dependencies": { + "glob": "^7.1.3" + }, + "bin": { + "rimraf": "bin.js" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/webpack-merge": { + "version": "5.8.0", + "resolved": "https://registry.npmjs.org/webpack-merge/-/webpack-merge-5.8.0.tgz", + "integrity": "sha512-/SaI7xY0831XwP6kzuwhKWVKDP9t1QY1h65lAFLbZqMPIuYcD9QAW4u9STIbU9kaJbPBB/geU/gLr1wDjOhQ+Q==", + "dev": true, + "dependencies": { + "clone-deep": "^4.0.1", + "wildcard": "^2.0.0" + }, + "engines": { + "node": ">=10.0.0" + } + }, + "node_modules/webpack-sources": { + "version": "3.2.3", + "resolved": "https://registry.npmjs.org/webpack-sources/-/webpack-sources-3.2.3.tgz", + "integrity": "sha512-/DyMEOrDgLKKIG0fmvtz+4dUX/3Ghozwgm6iPp8KRhvn+eQf9+Q7GWxVNMk3+uCPWfdXYC4ExGBckIXdFEfH1w==", + "dev": true, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/webpack/node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/webpack/node_modules/ajv-keywords": { + "version": "3.5.2", + "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", + "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", + "dev": true, + "peerDependencies": { + "ajv": "^6.9.1" + } + }, + "node_modules/webpack/node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "node_modules/webpack/node_modules/schema-utils": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.1.1.tgz", + "integrity": "sha512-Y5PQxS4ITlC+EahLuXaY86TXfR7Dc5lw294alXOq86JAHCihAIZfqv8nNCWvaEJvaC51uN9hbLGeV0cFBdH+Fw==", + "dev": true, + "dependencies": { + "@types/json-schema": "^7.0.8", + "ajv": "^6.12.5", + "ajv-keywords": "^3.5.2" + }, + "engines": { + "node": ">= 10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + } + }, + "node_modules/websocket-driver": { + "version": "0.7.4", + "resolved": "https://registry.npmjs.org/websocket-driver/-/websocket-driver-0.7.4.tgz", + "integrity": "sha512-b17KeDIQVjvb0ssuSDF2cYXSg2iztliJ4B9WdsuB6J952qCPKmnVq4DyW5motImXHDC1cBT/1UezrJVsKw5zjg==", + "dev": true, + "dependencies": { + "http-parser-js": ">=0.5.1", + "safe-buffer": ">=5.1.0", + "websocket-extensions": ">=0.1.1" + }, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/websocket-extensions": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/websocket-extensions/-/websocket-extensions-0.1.4.tgz", + "integrity": "sha512-OqedPIGOfsDlo31UNwYbCFMSaO9m9G/0faIHj5/dZFDMFqPTcx6UwqyOy3COEaEOg/9VsGIpdqn62W5KhoKSpg==", + "dev": true, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/which": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", + "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", + "dev": true, + "dependencies": { + "isexe": "^2.0.0" + }, + "bin": { + "node-which": "bin/node-which" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/wildcard": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/wildcard/-/wildcard-2.0.0.tgz", + "integrity": "sha512-JcKqAHLPxcdb9KM49dufGXn2x3ssnfjbcaQdLlfZsL9rH9wgDQjUtDxbo8NE0F6SFvydeu1VhZe7hZuHsB2/pw==", + "dev": true + }, + "node_modules/wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", + "dev": true + }, + "node_modules/ws": { + "version": "8.12.0", + "resolved": "https://registry.npmjs.org/ws/-/ws-8.12.0.tgz", + "integrity": "sha512-kU62emKIdKVeEIOIKVegvqpXMSTAMLJozpHZaJNDYqBjzlSYXQGviYwN1osDLJ9av68qHd4a2oSjd7yD4pacig==", + "dev": true, + "engines": { + "node": ">=10.0.0" + }, + "peerDependencies": { + "bufferutil": "^4.0.1", + "utf-8-validate": ">=5.0.2" + }, + "peerDependenciesMeta": { + "bufferutil": { + "optional": true + }, + "utf-8-validate": { + "optional": true + } + } + }, + "node_modules/yallist": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.1.1.tgz", + "integrity": "sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==", + "dev": true + }, + "node_modules/yaml": { + "version": "1.10.2", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-1.10.2.tgz", + "integrity": "sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==", + "dev": true, + "engines": { + "node": ">= 6" + } } } } diff --git a/client/package.json b/client/package.json index 0826ec4..454620d 100644 --- a/client/package.json +++ b/client/package.json @@ -2,12 +2,34 @@ "name": "rs-clone-client", "version": "0.0.1", "private": true, - "scripts": {}, + "scripts": { + "build": "webpack --mode production", + "build:dev": "webpack --mode development", + "build:watch": "webpack --mode development --watch", + "start": "webpack-dev-server --mode production --hot", + "start:dev": "webpack-dev-server --mode development --hot" + }, "keywords": [], "author": "HardManDev , VasaSkor, Alexey Zhuchkov", "license": "MIT", "devDependencies": { + "@babel/preset-env": "^7.20.2", + "@babel/preset-typescript": "^7.18.6", "@types/node": "^18.11.18", - "typescript": "^4.9.5" + "autoprefixer": "^10.4.13", + "babel-loader": "^9.1.2", + "clean-webpack-plugin": "^4.0.0", + "css-loader": "^6.7.3", + "html-webpack-plugin": "^5.5.0", + "mini-css-extract-plugin": "^2.7.2", + "postcss": "^8.4.21", + "postcss-loader": "^7.0.2", + "sass": "^1.58.0", + "sass-loader": "^13.2.0", + "typescript": "^4.9.5", + "url-loader": "^4.1.1", + "webpack": "^5.75.0", + "webpack-cli": "^5.0.1", + "webpack-dev-server": "^4.11.1" } } diff --git a/client/webpack.config.js b/client/webpack.config.js new file mode 100644 index 0000000..222b219 --- /dev/null +++ b/client/webpack.config.js @@ -0,0 +1,133 @@ +const path = require('path'); +const HtmlWebpackPlugin = require('html-webpack-plugin'); +const MiniCssExtractPlugin = require('mini-css-extract-plugin'); +const { CleanWebpackPlugin } = require('clean-webpack-plugin'); + +const sourcePath = path.resolve(__dirname, 'src'); +const destinationPath = path.resolve(__dirname, 'dist'); + +/** + * Generates a filename string for webpack given the given parameters. + * @param {boolean} isDevelopment true if needed name for development mode. + * @param {boolean} isBundled true if needed name with '.bundle' postfix. + * @param {string} ext target file extension. + * @returns {string} a string representing the filename for the webpack + * configuration. + */ +const resolveFilename = ( + isDevelopment, + isBundled = false, + ext = 'js', +) => `${isDevelopment ? '[name]' : '[contenthash]'}` + + `${isBundled ? '.bundle' : ''}.${ext}`; + +/** + * Generate webpack styles loaders chain. + * @param {any | undefined} extra extra loaders (pushed into start of chain). + * @returns {Array} a string representing the webpack styles loaders chain. + */ +const resolveStyleLoaders = ( + extra = undefined +) => { + const result = [ + MiniCssExtractPlugin.loader, + 'css-loader', + { + loader: 'postcss-loader', + options: { + postcssOptions: { + plugins: ['autoprefixer'], + }, + }, + }, + ]; + + if (extra) result.push(extra); + + return result; +}; + +module.exports = async (env, argv) => { + const isDevelopment = argv.mode === 'development' + || process.env.NODE_ENV === 'development'; + + return { + context: sourcePath, + entry: { + main: './index.ts', + }, + output: { + path: destinationPath, + filename: resolveFilename(isDevelopment, true, 'js'), + }, + resolve: { + extensions: ['.html', '.js', '.ts', '.css', 'sass', '.scss'], + alias: { + '@': sourcePath, + '@types': path.resolve(sourcePath, 'types'), + '@assets': path.resolve(sourcePath, 'assets'), + '@styles': path.resolve(sourcePath, 'styles'), + '@scripts': path.resolve(sourcePath, 'scripts'), + }, + }, + devtool: isDevelopment ? 'source-map' : false, + devServer: { + hot: true, + port: 8080, + }, + plugins: [ + new HtmlWebpackPlugin({ + filename: './index.html', + template: './index.html', + chunks: ['main'], + minify: !isDevelopment, + }), + new MiniCssExtractPlugin({ + filename: resolveFilename(isDevelopment, true, 'css'), + }), + new CleanWebpackPlugin() + ], + module: { + rules: [ + { + test: /\.(ts)$/i, + use: [ + { + loader: "babel-loader", + options: { + presets: [ + "@babel/preset-env", + "@babel/preset-typescript" + ] + } + } + ], + exclude: /node_modules/ + }, + { + test: /\.(css)$/i, + use: resolveStyleLoaders(), + }, + { + test: /\.(s[ac]ss)$/i, + use: resolveStyleLoaders('sass-loader'), + }, + { + test: /\.(png|jpe?g|gif|svg|ttf|woff|woff2)$/i, + dependency: { + not: ['url'] + }, + use: [ + { + loader: 'url-loader', + options: { + limit: 8192, + name: '[path][name].[ext]' + }, + }, + ], + }, + ] + } + } +} From 4e7dc7018730290a5ae5eef79f0295bf09d91983 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 00:24:28 +0300 Subject: [PATCH 004/196] feat: create base project --- client/.idea/watcherTasks.xml | 4 ++++ client/src/assets/.gitkeep | 0 client/src/index.html | 11 +++++++++++ client/src/index.ts | 1 + client/src/scripts/components/.gitkeep | 0 client/src/scripts/controllers/.gitkeep | 0 client/src/scripts/models/.gitkeep | 0 client/src/styles/main.scss | 5 +++++ client/src/types/index.d.ts | 8 ++++++++ client/webpack.config.js | 3 +++ 10 files changed, 32 insertions(+) create mode 100644 client/.idea/watcherTasks.xml create mode 100644 client/src/assets/.gitkeep create mode 100644 client/src/index.html create mode 100644 client/src/index.ts create mode 100644 client/src/scripts/components/.gitkeep create mode 100644 client/src/scripts/controllers/.gitkeep create mode 100644 client/src/scripts/models/.gitkeep create mode 100644 client/src/styles/main.scss create mode 100644 client/src/types/index.d.ts diff --git a/client/.idea/watcherTasks.xml b/client/.idea/watcherTasks.xml new file mode 100644 index 0000000..fb0d65a --- /dev/null +++ b/client/.idea/watcherTasks.xml @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/client/src/assets/.gitkeep b/client/src/assets/.gitkeep new file mode 100644 index 0000000..e69de29 diff --git a/client/src/index.html b/client/src/index.html new file mode 100644 index 0000000..53c4655 --- /dev/null +++ b/client/src/index.html @@ -0,0 +1,11 @@ + + + + + + + RS Clone + + + + diff --git a/client/src/index.ts b/client/src/index.ts new file mode 100644 index 0000000..d1bc7ca --- /dev/null +++ b/client/src/index.ts @@ -0,0 +1 @@ +import '@styles/main' diff --git a/client/src/scripts/components/.gitkeep b/client/src/scripts/components/.gitkeep new file mode 100644 index 0000000..e69de29 diff --git a/client/src/scripts/controllers/.gitkeep b/client/src/scripts/controllers/.gitkeep new file mode 100644 index 0000000..e69de29 diff --git a/client/src/scripts/models/.gitkeep b/client/src/scripts/models/.gitkeep new file mode 100644 index 0000000..e69de29 diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss new file mode 100644 index 0000000..cca57b3 --- /dev/null +++ b/client/src/styles/main.scss @@ -0,0 +1,5 @@ +* { + margin: 0; + padding: 0; + box-sizing: border-box; +} diff --git a/client/src/types/index.d.ts b/client/src/types/index.d.ts new file mode 100644 index 0000000..ed4e496 --- /dev/null +++ b/client/src/types/index.d.ts @@ -0,0 +1,8 @@ +declare module '*.jpg'; +declare module '*.jpeg'; +declare module '*.png'; +declare module '*.gif'; +declare module '*.svg'; +declare module '*.ttf'; +declare module '*.woff'; +declare module '*.woff2'; diff --git a/client/webpack.config.js b/client/webpack.config.js index 222b219..dc2258f 100644 --- a/client/webpack.config.js +++ b/client/webpack.config.js @@ -68,6 +68,9 @@ module.exports = async (env, argv) => { '@assets': path.resolve(sourcePath, 'assets'), '@styles': path.resolve(sourcePath, 'styles'), '@scripts': path.resolve(sourcePath, 'scripts'), + '@models': path.resolve(sourcePath, 'scripts/models'), + '@components': path.resolve(sourcePath, 'scripts/components'), + '@controllers': path.resolve(sourcePath, 'scripts/controllers'), }, }, devtool: isDevelopment ? 'source-map' : false, From a00571d9cce5761d078710773dff1b1f370a7c75 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 01:34:42 +0300 Subject: [PATCH 005/196] feat: add eslint with airbnb config and typescript --- client/.eslintrc.json | 50 + .../inspectionProfiles/Project_Default.xml | 6 + client/.idea/jsLinters/eslint.xml | 6 + client/package-lock.json | 2556 +++++++++++++++-- client/package.json | 8 +- client/src/index.ts | 2 +- client/tsconfig.eslint.json | 6 + 7 files changed, 2396 insertions(+), 238 deletions(-) create mode 100644 client/.eslintrc.json create mode 100644 client/.idea/inspectionProfiles/Project_Default.xml create mode 100644 client/.idea/jsLinters/eslint.xml create mode 100644 client/tsconfig.eslint.json diff --git a/client/.eslintrc.json b/client/.eslintrc.json new file mode 100644 index 0000000..b3341e7 --- /dev/null +++ b/client/.eslintrc.json @@ -0,0 +1,50 @@ +{ + "env": { + "browser": true, + "es2021": true + }, + "extends": [ + "airbnb-base", + "airbnb-typescript/base", + "eslint:recommended", + "plugin:@typescript-eslint/recommended" + ], + "overrides": [ + ], + "parser": "@typescript-eslint/parser", + "parserOptions": { + "ecmaVersion": "latest", + "sourceType": "module", + "project": "tsconfig.eslint.json" + }, + "plugins": [ + "@typescript-eslint" + ], + "rules": { + "no-param-reassign": "off", + "@typescript-eslint/no-explicit-any": "error", + "@typescript-eslint/explicit-function-return-type": "error", + "max-len": [ + "error", + { + "code": 80, + "tabWidth": 2, + "ignoreComments": true, + "ignoreTrailingComments": true, + "ignoreUrls": true, + "ignoreStrings": true, + "ignoreTemplateLiterals": true, + "ignoreRegExpLiterals": true + } + ], + "max-lines-per-function": [ + "warn", + { + "max": 40, + "skipBlankLines": true, + "skipComments": true, + "IIFEs": true + } + ] + } +} diff --git a/client/.idea/inspectionProfiles/Project_Default.xml b/client/.idea/inspectionProfiles/Project_Default.xml new file mode 100644 index 0000000..03d9549 --- /dev/null +++ b/client/.idea/inspectionProfiles/Project_Default.xml @@ -0,0 +1,6 @@ + + + + \ No newline at end of file diff --git a/client/.idea/jsLinters/eslint.xml b/client/.idea/jsLinters/eslint.xml new file mode 100644 index 0000000..541945b --- /dev/null +++ b/client/.idea/jsLinters/eslint.xml @@ -0,0 +1,6 @@ + + + + + \ No newline at end of file diff --git a/client/package-lock.json b/client/package-lock.json index 5077bee..f6612d8 100644 --- a/client/package-lock.json +++ b/client/package-lock.json @@ -12,10 +12,14 @@ "@babel/preset-env": "^7.20.2", "@babel/preset-typescript": "^7.18.6", "@types/node": "^18.11.18", + "@typescript-eslint/eslint-plugin": "^5.50.0", + "@typescript-eslint/parser": "^5.50.0", "autoprefixer": "^10.4.13", "babel-loader": "^9.1.2", "clean-webpack-plugin": "^4.0.0", "css-loader": "^6.7.3", + "eslint": "^8.33.0", + "eslint-config-airbnb-typescript": "^17.0.0", "html-webpack-plugin": "^5.5.0", "mini-css-extract-plugin": "^2.7.2", "postcss": "^8.4.21", @@ -1690,6 +1694,99 @@ "node": ">=10.0.0" } }, + "node_modules/@eslint/eslintrc": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.4.1.tgz", + "integrity": "sha512-XXrH9Uarn0stsyldqDYq8r++mROmWRI1xKMXa640Bb//SY1+ECYX6VzT6Lcx5frD0V30XieqJ0oX9I2Xj5aoMA==", + "dev": true, + "dependencies": { + "ajv": "^6.12.4", + "debug": "^4.3.2", + "espree": "^9.4.0", + "globals": "^13.19.0", + "ignore": "^5.2.0", + "import-fresh": "^3.2.1", + "js-yaml": "^4.1.0", + "minimatch": "^3.1.2", + "strip-json-comments": "^3.1.1" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/@eslint/eslintrc/node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/@eslint/eslintrc/node_modules/globals": { + "version": "13.20.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-13.20.0.tgz", + "integrity": "sha512-Qg5QtVkCy/kv3FUSlu4ukeZDVf9ee0iXLAUYX13gbR17bnejFTzr4iS9bY7kwCf1NztRNm1t91fjOiyx4CSwPQ==", + "dev": true, + "dependencies": { + "type-fest": "^0.20.2" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/@eslint/eslintrc/node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "node_modules/@humanwhocodes/config-array": { + "version": "0.11.8", + "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.11.8.tgz", + "integrity": "sha512-UybHIJzJnR5Qc/MsD9Kr+RpO2h+/P1GhOwdiLPXK5TWk5sgTdu88bTD9UP+CKbPPh5Rni1u0GjAdYQLemG8g+g==", + "dev": true, + "dependencies": { + "@humanwhocodes/object-schema": "^1.2.1", + "debug": "^4.1.1", + "minimatch": "^3.0.5" + }, + "engines": { + "node": ">=10.10.0" + } + }, + "node_modules/@humanwhocodes/module-importer": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz", + "integrity": "sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==", + "dev": true, + "engines": { + "node": ">=12.22" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/nzakas" + } + }, + "node_modules/@humanwhocodes/object-schema": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@humanwhocodes/object-schema/-/object-schema-1.2.1.tgz", + "integrity": "sha512-ZnQMnLV4e7hDlUvw8H+U8ASL02SS2Gn6+9Ac3wGGLIe7+je2AeAOxPY+izIPJDfFDb7eDjev0Us8MO1iFRN8hA==", + "dev": true + }, "node_modules/@jridgewell/gen-mapping": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.1.1.tgz", @@ -1768,6 +1865,41 @@ "integrity": "sha512-Hcv+nVC0kZnQ3tD9GVu5xSMR4VVYOteQIr/hwFPVEvPdlXqgGEuRjiheChHgdM+JyqdgNcmzZOX/tnl0JOiI7A==", "dev": true }, + "node_modules/@nodelib/fs.scandir": { + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", + "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", + "dev": true, + "dependencies": { + "@nodelib/fs.stat": "2.0.5", + "run-parallel": "^1.1.9" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/@nodelib/fs.stat": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", + "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", + "dev": true, + "engines": { + "node": ">= 8" + } + }, + "node_modules/@nodelib/fs.walk": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", + "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", + "dev": true, + "dependencies": { + "@nodelib/fs.scandir": "2.1.5", + "fastq": "^1.6.0" + }, + "engines": { + "node": ">= 8" + } + }, "node_modules/@types/body-parser": { "version": "1.19.2", "resolved": "https://registry.npmjs.org/@types/body-parser/-/body-parser-1.19.2.tgz", @@ -1886,6 +2018,13 @@ "integrity": "sha512-wOuvG1SN4Us4rez+tylwwwCV1psiNVOkJeM3AUWUNWg/jDQY2+HE/444y5gc+jBmRqASOm2Oeh5c1axHobwRKQ==", "dev": true }, + "node_modules/@types/json5": { + "version": "0.0.29", + "resolved": "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz", + "integrity": "sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==", + "dev": true, + "peer": true + }, "node_modules/@types/mime": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/@types/mime/-/mime-3.0.1.tgz", @@ -1928,6 +2067,12 @@ "integrity": "sha512-wWKOClTTiizcZhXnPY4wikVAwmdYHp8q6DmC+EJUzAMsycb7HB32Kh9RN4+0gExjmPmZSAQjgURXIGATPegAvA==", "dev": true }, + "node_modules/@types/semver": { + "version": "7.3.13", + "resolved": "https://registry.npmjs.org/@types/semver/-/semver-7.3.13.tgz", + "integrity": "sha512-21cFJr9z3g5dW8B0CVI9g2O9beqaThGQ6ZFBqHfwhzLDKUxaqTIy3vnfah/UPkfOiF2pLq+tGz+W8RyCskuslw==", + "dev": true + }, "node_modules/@types/serve-index": { "version": "1.9.1", "resolved": "https://registry.npmjs.org/@types/serve-index/-/serve-index-1.9.1.tgz", @@ -1965,138 +2110,454 @@ "@types/node": "*" } }, - "node_modules/@webassemblyjs/ast": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.11.1.tgz", - "integrity": "sha512-ukBh14qFLjxTQNTXocdyksN5QdM28S1CxHt2rdskFyL+xFV7VremuBLVbmCePj+URalXBENx/9Lm7lnhihtCSw==", + "node_modules/@typescript-eslint/eslint-plugin": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.50.0.tgz", + "integrity": "sha512-vwksQWSFZiUhgq3Kv7o1Jcj0DUNylwnIlGvKvLLYsq8pAWha6/WCnXUeaSoNNha/K7QSf2+jvmkxggC1u3pIwQ==", "dev": true, "dependencies": { - "@webassemblyjs/helper-numbers": "1.11.1", - "@webassemblyjs/helper-wasm-bytecode": "1.11.1" + "@typescript-eslint/scope-manager": "5.50.0", + "@typescript-eslint/type-utils": "5.50.0", + "@typescript-eslint/utils": "5.50.0", + "debug": "^4.3.4", + "grapheme-splitter": "^1.0.4", + "ignore": "^5.2.0", + "natural-compare-lite": "^1.4.0", + "regexpp": "^3.2.0", + "semver": "^7.3.7", + "tsutils": "^3.21.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "@typescript-eslint/parser": "^5.0.0", + "eslint": "^6.0.0 || ^7.0.0 || ^8.0.0" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } } }, - "node_modules/@webassemblyjs/floating-point-hex-parser": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.11.1.tgz", - "integrity": "sha512-iGRfyc5Bq+NnNuX8b5hwBrRjzf0ocrJPI6GWFodBFzmFnyvrQ83SHKhmilCU/8Jv67i4GJZBMhEzltxzcNagtQ==", - "dev": true - }, - "node_modules/@webassemblyjs/helper-api-error": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-api-error/-/helper-api-error-1.11.1.tgz", - "integrity": "sha512-RlhS8CBCXfRUR/cwo2ho9bkheSXG0+NwooXcc3PAILALf2QLdFyj7KGsKRbVc95hZnhnERon4kW/D3SZpp6Tcg==", - "dev": true - }, - "node_modules/@webassemblyjs/helper-buffer": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-buffer/-/helper-buffer-1.11.1.tgz", - "integrity": "sha512-gwikF65aDNeeXa8JxXa2BAk+REjSyhrNC9ZwdT0f8jc4dQQeDQ7G4m0f2QCLPJiMTTO6wfDmRmj/pW0PsUvIcA==", - "dev": true + "node_modules/@typescript-eslint/eslint-plugin/node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dev": true, + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } }, - "node_modules/@webassemblyjs/helper-numbers": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-numbers/-/helper-numbers-1.11.1.tgz", - "integrity": "sha512-vDkbxiB8zfnPdNK9Rajcey5C0w+QJugEglN0of+kmO8l7lDb77AnlKYQF7aarZuCrv+l0UvqL+68gSDr3k9LPQ==", + "node_modules/@typescript-eslint/eslint-plugin/node_modules/semver": { + "version": "7.3.8", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.8.tgz", + "integrity": "sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==", "dev": true, "dependencies": { - "@webassemblyjs/floating-point-hex-parser": "1.11.1", - "@webassemblyjs/helper-api-error": "1.11.1", - "@xtuc/long": "4.2.2" + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" } }, - "node_modules/@webassemblyjs/helper-wasm-bytecode": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.11.1.tgz", - "integrity": "sha512-PvpoOGiJwXeTrSf/qfudJhwlvDQxFgelbMqtq52WWiXC6Xgg1IREdngmPN3bs4RoO83PnL/nFrxucXj1+BX62Q==", + "node_modules/@typescript-eslint/eslint-plugin/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", "dev": true }, - "node_modules/@webassemblyjs/helper-wasm-section": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.11.1.tgz", - "integrity": "sha512-10P9No29rYX1j7F3EVPX3JvGPQPae+AomuSTPiF9eBQeChHI6iqjMIwR9JmOJXwpnn/oVGDk7I5IlskuMwU/pg==", + "node_modules/@typescript-eslint/parser": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.50.0.tgz", + "integrity": "sha512-KCcSyNaogUDftK2G9RXfQyOCt51uB5yqC6pkUYqhYh8Kgt+DwR5M0EwEAxGPy/+DH6hnmKeGsNhiZRQxjH71uQ==", "dev": true, "dependencies": { - "@webassemblyjs/ast": "1.11.1", - "@webassemblyjs/helper-buffer": "1.11.1", - "@webassemblyjs/helper-wasm-bytecode": "1.11.1", - "@webassemblyjs/wasm-gen": "1.11.1" + "@typescript-eslint/scope-manager": "5.50.0", + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/typescript-estree": "5.50.0", + "debug": "^4.3.4" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^6.0.0 || ^7.0.0 || ^8.0.0" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } } }, - "node_modules/@webassemblyjs/ieee754": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.11.1.tgz", - "integrity": "sha512-hJ87QIPtAMKbFq6CGTkZYJivEwZDbQUgYd3qKSadTNOhVY7p+gfP6Sr0lLRVTaG1JjFj+r3YchoqRYxNH3M0GQ==", + "node_modules/@typescript-eslint/scope-manager": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.50.0.tgz", + "integrity": "sha512-rt03kaX+iZrhssaT974BCmoUikYtZI24Vp/kwTSy841XhiYShlqoshRFDvN1FKKvU2S3gK+kcBW1EA7kNUrogg==", "dev": true, "dependencies": { - "@xtuc/ieee754": "^1.2.0" + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/visitor-keys": "5.50.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" } }, - "node_modules/@webassemblyjs/leb128": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.11.1.tgz", - "integrity": "sha512-BJ2P0hNZ0u+Th1YZXJpzW6miwqQUGcIHT1G/sf72gLVD9DZ5AdYTqPNbHZh6K1M5VmKvFXwGSWZADz+qBWxeRw==", + "node_modules/@typescript-eslint/type-utils": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.50.0.tgz", + "integrity": "sha512-dcnXfZ6OGrNCO7E5UY/i0ktHb7Yx1fV6fnQGGrlnfDhilcs6n19eIRcvLBqx6OQkrPaFlDPk3OJ0WlzQfrV0bQ==", "dev": true, "dependencies": { - "@xtuc/long": "4.2.2" + "@typescript-eslint/typescript-estree": "5.50.0", + "@typescript-eslint/utils": "5.50.0", + "debug": "^4.3.4", + "tsutils": "^3.21.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "*" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } } }, - "node_modules/@webassemblyjs/utf8": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.11.1.tgz", - "integrity": "sha512-9kqcxAEdMhiwQkHpkNiorZzqpGrodQQ2IGrHHxCy+Ozng0ofyMA0lTqiLkVs1uzTRejX+/O0EOT7KxqVPuXosQ==", - "dev": true - }, - "node_modules/@webassemblyjs/wasm-edit": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-edit/-/wasm-edit-1.11.1.tgz", - "integrity": "sha512-g+RsupUC1aTHfR8CDgnsVRVZFJqdkFHpsHMfJuWQzWU3tvnLC07UqHICfP+4XyL2tnr1amvl1Sdp06TnYCmVkA==", + "node_modules/@typescript-eslint/types": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.50.0.tgz", + "integrity": "sha512-atruOuJpir4OtyNdKahiHZobPKFvZnBnfDiyEaBf6d9vy9visE7gDjlmhl+y29uxZ2ZDgvXijcungGFjGGex7w==", "dev": true, - "dependencies": { - "@webassemblyjs/ast": "1.11.1", - "@webassemblyjs/helper-buffer": "1.11.1", - "@webassemblyjs/helper-wasm-bytecode": "1.11.1", - "@webassemblyjs/helper-wasm-section": "1.11.1", - "@webassemblyjs/wasm-gen": "1.11.1", - "@webassemblyjs/wasm-opt": "1.11.1", - "@webassemblyjs/wasm-parser": "1.11.1", - "@webassemblyjs/wast-printer": "1.11.1" + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" } }, - "node_modules/@webassemblyjs/wasm-gen": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-gen/-/wasm-gen-1.11.1.tgz", - "integrity": "sha512-F7QqKXwwNlMmsulj6+O7r4mmtAlCWfO/0HdgOxSklZfQcDu0TpLiD1mRt/zF25Bk59FIjEuGAIyn5ei4yMfLhA==", + "node_modules/@typescript-eslint/typescript-estree": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.50.0.tgz", + "integrity": "sha512-Gq4zapso+OtIZlv8YNAStFtT6d05zyVCK7Fx3h5inlLBx2hWuc/0465C2mg/EQDDU2LKe52+/jN4f0g9bd+kow==", "dev": true, "dependencies": { - "@webassemblyjs/ast": "1.11.1", - "@webassemblyjs/helper-wasm-bytecode": "1.11.1", - "@webassemblyjs/ieee754": "1.11.1", - "@webassemblyjs/leb128": "1.11.1", - "@webassemblyjs/utf8": "1.11.1" + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/visitor-keys": "5.50.0", + "debug": "^4.3.4", + "globby": "^11.1.0", + "is-glob": "^4.0.3", + "semver": "^7.3.7", + "tsutils": "^3.21.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } } }, - "node_modules/@webassemblyjs/wasm-opt": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-opt/-/wasm-opt-1.11.1.tgz", - "integrity": "sha512-VqnkNqnZlU5EB64pp1l7hdm3hmQw7Vgqa0KF/KCNO9sIpI6Fk6brDEiX+iCOYrvMuBWDws0NkTOxYEb85XQHHw==", + "node_modules/@typescript-eslint/typescript-estree/node_modules/array-union": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/array-union/-/array-union-2.1.0.tgz", + "integrity": "sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw==", "dev": true, - "dependencies": { - "@webassemblyjs/ast": "1.11.1", - "@webassemblyjs/helper-buffer": "1.11.1", - "@webassemblyjs/wasm-gen": "1.11.1", - "@webassemblyjs/wasm-parser": "1.11.1" + "engines": { + "node": ">=8" } }, - "node_modules/@webassemblyjs/wasm-parser": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.11.1.tgz", - "integrity": "sha512-rrBujw+dJu32gYB7/Lup6UhdkPx9S9SnobZzRVL7VcBH9Bt9bCBLEuX/YXOOtBsOZ4NQrRykKhffRWHvigQvOA==", + "node_modules/@typescript-eslint/typescript-estree/node_modules/globby": { + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/globby/-/globby-11.1.0.tgz", + "integrity": "sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g==", "dev": true, "dependencies": { - "@webassemblyjs/ast": "1.11.1", - "@webassemblyjs/helper-api-error": "1.11.1", - "@webassemblyjs/helper-wasm-bytecode": "1.11.1", - "@webassemblyjs/ieee754": "1.11.1", + "array-union": "^2.1.0", + "dir-glob": "^3.0.1", + "fast-glob": "^3.2.9", + "ignore": "^5.2.0", + "merge2": "^1.4.1", + "slash": "^3.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/@typescript-eslint/typescript-estree/node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dev": true, + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@typescript-eslint/typescript-estree/node_modules/semver": { + "version": "7.3.8", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.8.tgz", + "integrity": "sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@typescript-eslint/typescript-estree/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, + "node_modules/@typescript-eslint/utils": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.50.0.tgz", + "integrity": "sha512-v/AnUFImmh8G4PH0NDkf6wA8hujNNcrwtecqW4vtQ1UOSNBaZl49zP1SHoZ/06e+UiwzHpgb5zP5+hwlYYWYAw==", + "dev": true, + "dependencies": { + "@types/json-schema": "^7.0.9", + "@types/semver": "^7.3.12", + "@typescript-eslint/scope-manager": "5.50.0", + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/typescript-estree": "5.50.0", + "eslint-scope": "^5.1.1", + "eslint-utils": "^3.0.0", + "semver": "^7.3.7" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^6.0.0 || ^7.0.0 || ^8.0.0" + } + }, + "node_modules/@typescript-eslint/utils/node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dev": true, + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@typescript-eslint/utils/node_modules/semver": { + "version": "7.3.8", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.8.tgz", + "integrity": "sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@typescript-eslint/utils/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, + "node_modules/@typescript-eslint/visitor-keys": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.50.0.tgz", + "integrity": "sha512-cdMeD9HGu6EXIeGOh2yVW6oGf9wq8asBgZx7nsR/D36gTfQ0odE5kcRYe5M81vjEFAcPeugXrHg78Imu55F6gg==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.50.0", + "eslint-visitor-keys": "^3.3.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@webassemblyjs/ast": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.11.1.tgz", + "integrity": "sha512-ukBh14qFLjxTQNTXocdyksN5QdM28S1CxHt2rdskFyL+xFV7VremuBLVbmCePj+URalXBENx/9Lm7lnhihtCSw==", + "dev": true, + "dependencies": { + "@webassemblyjs/helper-numbers": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1" + } + }, + "node_modules/@webassemblyjs/floating-point-hex-parser": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.11.1.tgz", + "integrity": "sha512-iGRfyc5Bq+NnNuX8b5hwBrRjzf0ocrJPI6GWFodBFzmFnyvrQ83SHKhmilCU/8Jv67i4GJZBMhEzltxzcNagtQ==", + "dev": true + }, + "node_modules/@webassemblyjs/helper-api-error": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-api-error/-/helper-api-error-1.11.1.tgz", + "integrity": "sha512-RlhS8CBCXfRUR/cwo2ho9bkheSXG0+NwooXcc3PAILALf2QLdFyj7KGsKRbVc95hZnhnERon4kW/D3SZpp6Tcg==", + "dev": true + }, + "node_modules/@webassemblyjs/helper-buffer": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-buffer/-/helper-buffer-1.11.1.tgz", + "integrity": "sha512-gwikF65aDNeeXa8JxXa2BAk+REjSyhrNC9ZwdT0f8jc4dQQeDQ7G4m0f2QCLPJiMTTO6wfDmRmj/pW0PsUvIcA==", + "dev": true + }, + "node_modules/@webassemblyjs/helper-numbers": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-numbers/-/helper-numbers-1.11.1.tgz", + "integrity": "sha512-vDkbxiB8zfnPdNK9Rajcey5C0w+QJugEglN0of+kmO8l7lDb77AnlKYQF7aarZuCrv+l0UvqL+68gSDr3k9LPQ==", + "dev": true, + "dependencies": { + "@webassemblyjs/floating-point-hex-parser": "1.11.1", + "@webassemblyjs/helper-api-error": "1.11.1", + "@xtuc/long": "4.2.2" + } + }, + "node_modules/@webassemblyjs/helper-wasm-bytecode": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.11.1.tgz", + "integrity": "sha512-PvpoOGiJwXeTrSf/qfudJhwlvDQxFgelbMqtq52WWiXC6Xgg1IREdngmPN3bs4RoO83PnL/nFrxucXj1+BX62Q==", + "dev": true + }, + "node_modules/@webassemblyjs/helper-wasm-section": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.11.1.tgz", + "integrity": "sha512-10P9No29rYX1j7F3EVPX3JvGPQPae+AomuSTPiF9eBQeChHI6iqjMIwR9JmOJXwpnn/oVGDk7I5IlskuMwU/pg==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-buffer": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1", + "@webassemblyjs/wasm-gen": "1.11.1" + } + }, + "node_modules/@webassemblyjs/ieee754": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.11.1.tgz", + "integrity": "sha512-hJ87QIPtAMKbFq6CGTkZYJivEwZDbQUgYd3qKSadTNOhVY7p+gfP6Sr0lLRVTaG1JjFj+r3YchoqRYxNH3M0GQ==", + "dev": true, + "dependencies": { + "@xtuc/ieee754": "^1.2.0" + } + }, + "node_modules/@webassemblyjs/leb128": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.11.1.tgz", + "integrity": "sha512-BJ2P0hNZ0u+Th1YZXJpzW6miwqQUGcIHT1G/sf72gLVD9DZ5AdYTqPNbHZh6K1M5VmKvFXwGSWZADz+qBWxeRw==", + "dev": true, + "dependencies": { + "@xtuc/long": "4.2.2" + } + }, + "node_modules/@webassemblyjs/utf8": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.11.1.tgz", + "integrity": "sha512-9kqcxAEdMhiwQkHpkNiorZzqpGrodQQ2IGrHHxCy+Ozng0ofyMA0lTqiLkVs1uzTRejX+/O0EOT7KxqVPuXosQ==", + "dev": true + }, + "node_modules/@webassemblyjs/wasm-edit": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-edit/-/wasm-edit-1.11.1.tgz", + "integrity": "sha512-g+RsupUC1aTHfR8CDgnsVRVZFJqdkFHpsHMfJuWQzWU3tvnLC07UqHICfP+4XyL2tnr1amvl1Sdp06TnYCmVkA==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-buffer": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1", + "@webassemblyjs/helper-wasm-section": "1.11.1", + "@webassemblyjs/wasm-gen": "1.11.1", + "@webassemblyjs/wasm-opt": "1.11.1", + "@webassemblyjs/wasm-parser": "1.11.1", + "@webassemblyjs/wast-printer": "1.11.1" + } + }, + "node_modules/@webassemblyjs/wasm-gen": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-gen/-/wasm-gen-1.11.1.tgz", + "integrity": "sha512-F7QqKXwwNlMmsulj6+O7r4mmtAlCWfO/0HdgOxSklZfQcDu0TpLiD1mRt/zF25Bk59FIjEuGAIyn5ei4yMfLhA==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1", + "@webassemblyjs/ieee754": "1.11.1", + "@webassemblyjs/leb128": "1.11.1", + "@webassemblyjs/utf8": "1.11.1" + } + }, + "node_modules/@webassemblyjs/wasm-opt": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-opt/-/wasm-opt-1.11.1.tgz", + "integrity": "sha512-VqnkNqnZlU5EB64pp1l7hdm3hmQw7Vgqa0KF/KCNO9sIpI6Fk6brDEiX+iCOYrvMuBWDws0NkTOxYEb85XQHHw==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-buffer": "1.11.1", + "@webassemblyjs/wasm-gen": "1.11.1", + "@webassemblyjs/wasm-parser": "1.11.1" + } + }, + "node_modules/@webassemblyjs/wasm-parser": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.11.1.tgz", + "integrity": "sha512-rrBujw+dJu32gYB7/Lup6UhdkPx9S9SnobZzRVL7VcBH9Bt9bCBLEuX/YXOOtBsOZ4NQrRykKhffRWHvigQvOA==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-api-error": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1", + "@webassemblyjs/ieee754": "1.11.1", "@webassemblyjs/leb128": "1.11.1", "@webassemblyjs/utf8": "1.11.1" } @@ -2201,6 +2662,15 @@ "acorn": "^8" } }, + "node_modules/acorn-jsx": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", + "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", + "dev": true, + "peerDependencies": { + "acorn": "^6.0.0 || ^7.0.0 || ^8.0.0" + } + }, "node_modules/ajv": { "version": "8.12.0", "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.12.0.tgz", @@ -2292,12 +2762,38 @@ "node": ">= 8" } }, + "node_modules/argparse": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", + "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==", + "dev": true + }, "node_modules/array-flatten": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-2.1.2.tgz", "integrity": "sha512-hNfzcOV8W4NdualtqBFPyVO+54DSJuZGY9qT4pRroB6S9e3iiido2ISIC5h9R2sPJ8H3FHCIiEnsv1lPXO3KtQ==", "dev": true }, + "node_modules/array-includes": { + "version": "3.1.6", + "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.6.tgz", + "integrity": "sha512-sgTbLvL6cNnw24FnbaDyjmvddQ2ML8arZsgaJhoABMoplz/4QRhtrYS+alr1BUM1Bwp6dhx8vVCBSLG+StwOFw==", + "dev": true, + "peer": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4", + "get-intrinsic": "^1.1.3", + "is-string": "^1.0.7" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/array-union": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/array-union/-/array-union-1.0.2.tgz", @@ -2319,21 +2815,59 @@ "node": ">=0.10.0" } }, - "node_modules/autoprefixer": { - "version": "10.4.13", - "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.13.tgz", - "integrity": "sha512-49vKpMqcZYsJjwotvt4+h/BCjJVnhGwcLpDt5xkcaOG3eLrG/HUYLagrihYsQ+qrIBgIzX1Rw7a6L8I/ZA1Atg==", + "node_modules/array.prototype.flat": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/array.prototype.flat/-/array.prototype.flat-1.3.1.tgz", + "integrity": "sha512-roTU0KWIOmJ4DRLmwKd19Otg0/mT3qPNt0Qb3GWW8iObuZXxrjB/pzn0R3hqpRSWg4HCwqx+0vwOnWnvlOyeIA==", "dev": true, - "funding": [ - { - "type": "opencollective", - "url": "https://opencollective.com/postcss/" - }, - { - "type": "tidelift", - "url": "https://tidelift.com/funding/github/npm/autoprefixer" - } - ], + "peer": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4", + "es-shim-unscopables": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/array.prototype.flatmap": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/array.prototype.flatmap/-/array.prototype.flatmap-1.3.1.tgz", + "integrity": "sha512-8UGn9O1FDVvMNB0UlLv4voxRMze7+FpHyF5mSMRjWHUMlpoDViniy05870VlxhfgTnLbpuwTzvD76MTtWxB/mQ==", + "dev": true, + "peer": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4", + "es-shim-unscopables": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/autoprefixer": { + "version": "10.4.13", + "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.13.tgz", + "integrity": "sha512-49vKpMqcZYsJjwotvt4+h/BCjJVnhGwcLpDt5xkcaOG3eLrG/HUYLagrihYsQ+qrIBgIzX1Rw7a6L8I/ZA1Atg==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/postcss/" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/autoprefixer" + } + ], "dependencies": { "browserslist": "^4.21.4", "caniuse-lite": "^1.0.30001426", @@ -2352,6 +2886,18 @@ "postcss": "^8.1.0" } }, + "node_modules/available-typed-arrays": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.5.tgz", + "integrity": "sha512-DMD0KiN46eipeziST1LPP/STfDU0sufISXmjSgvVsoU2tqxctQeASejWcfNtxYKqETM1UxQ8sp2OrSBWpHY6sw==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/babel-loader": { "version": "9.1.2", "resolved": "https://registry.npmjs.org/babel-loader/-/babel-loader-9.1.2.tgz", @@ -2801,6 +3347,12 @@ "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", "dev": true }, + "node_modules/confusing-browser-globals": { + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/confusing-browser-globals/-/confusing-browser-globals-1.0.11.tgz", + "integrity": "sha512-JsPKdmh8ZkmnHxDk55FZ1TqVLvEQTvoByJZRN9jzI0UjxK/QgAmsphz7PGtqgPieQZ/CQcHWXCR7ATDNhGe+YA==", + "dev": true + }, "node_modules/connect-history-api-fallback": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/connect-history-api-fallback/-/connect-history-api-fallback-2.0.0.tgz", @@ -3018,6 +3570,12 @@ } } }, + "node_modules/deep-is": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.4.tgz", + "integrity": "sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==", + "dev": true + }, "node_modules/default-gateway": { "version": "6.0.3", "resolved": "https://registry.npmjs.org/default-gateway/-/default-gateway-6.0.3.tgz", @@ -3039,6 +3597,22 @@ "node": ">=8" } }, + "node_modules/define-properties": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.1.4.tgz", + "integrity": "sha512-uckOqKcfaVvtBdsVkdPv3XjveQJsNQqmhXgRi8uhvWWuPYZCNlzT8qAyblUgNoXdHdjMTzAqeGjAoli8f+bzPA==", + "dev": true, + "dependencies": { + "has-property-descriptors": "^1.0.0", + "object-keys": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/del": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/del/-/del-4.1.1.tgz", @@ -3082,6 +3656,18 @@ "integrity": "sha512-T0NIuQpnTvFDATNuHN5roPwSBG83rFsuO+MXXH9/3N1eFbn4wcPjttvjMLEPWJ0RGUYgQE7cGgS3tNxbqCGM7g==", "dev": true }, + "node_modules/dir-glob": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-3.0.1.tgz", + "integrity": "sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA==", + "dev": true, + "dependencies": { + "path-type": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, "node_modules/dns-equal": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/dns-equal/-/dns-equal-1.0.0.tgz", @@ -3100,194 +3686,784 @@ "node": ">=6" } }, + "node_modules/doctrine": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", + "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", + "dev": true, + "dependencies": { + "esutils": "^2.0.2" + }, + "engines": { + "node": ">=6.0.0" + } + }, "node_modules/dom-converter": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/dom-converter/-/dom-converter-0.2.0.tgz", "integrity": "sha512-gd3ypIPfOMr9h5jIKq8E3sHOTCjeirnl0WK5ZdS1AW0Odt0b1PaWaHdJ4Qk4klv+YB9aJBS7mESXjFoDQPu6DA==", "dev": true, - "dependencies": { - "utila": "~0.4" + "dependencies": { + "utila": "~0.4" + } + }, + "node_modules/dom-serializer": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-1.4.1.tgz", + "integrity": "sha512-VHwB3KfrcOOkelEG2ZOfxqLZdfkil8PtJi4P8N2MMXucZq2yLp75ClViUlOVwyoHEDjYU433Aq+5zWP61+RGag==", + "dev": true, + "dependencies": { + "domelementtype": "^2.0.1", + "domhandler": "^4.2.0", + "entities": "^2.0.0" + }, + "funding": { + "url": "https://github.com/cheeriojs/dom-serializer?sponsor=1" + } + }, + "node_modules/domelementtype": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-2.3.0.tgz", + "integrity": "sha512-OLETBj6w0OsagBwdXnPdN0cnMfF9opN69co+7ZrbfPGrdpPVNBUj02spi6B1N7wChLQiPn4CSH/zJvXw56gmHw==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/fb55" + } + ] + }, + "node_modules/domhandler": { + "version": "4.3.1", + "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-4.3.1.tgz", + "integrity": "sha512-GrwoxYN+uWlzO8uhUXRl0P+kHE4GtVPfYzVLcUxPL7KNdHKj66vvlhiweIHqYYXWlw+T8iLMp42Lm67ghw4WMQ==", + "dev": true, + "dependencies": { + "domelementtype": "^2.2.0" + }, + "engines": { + "node": ">= 4" + }, + "funding": { + "url": "https://github.com/fb55/domhandler?sponsor=1" + } + }, + "node_modules/domutils": { + "version": "2.8.0", + "resolved": "https://registry.npmjs.org/domutils/-/domutils-2.8.0.tgz", + "integrity": "sha512-w96Cjofp72M5IIhpjgobBimYEfoPjx1Vx0BSX9P30WBdZW2WIKU0T1Bd0kz2eNZ9ikjKgHbEyKx8BB6H1L3h3A==", + "dev": true, + "dependencies": { + "dom-serializer": "^1.0.1", + "domelementtype": "^2.2.0", + "domhandler": "^4.2.0" + }, + "funding": { + "url": "https://github.com/fb55/domutils?sponsor=1" + } + }, + "node_modules/dot-case": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/dot-case/-/dot-case-3.0.4.tgz", + "integrity": "sha512-Kv5nKlh6yRrdrGvxeJ2e5y2eRUpkUosIW4A2AS38zwSz27zu7ufDwQPi5Jhs3XAlGNetl3bmnGhQsMtkKJnj3w==", + "dev": true, + "dependencies": { + "no-case": "^3.0.4", + "tslib": "^2.0.3" + } + }, + "node_modules/ee-first": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", + "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==", + "dev": true + }, + "node_modules/electron-to-chromium": { + "version": "1.4.286", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.286.tgz", + "integrity": "sha512-Vp3CVhmYpgf4iXNKAucoQUDcCrBQX3XLBtwgFqP9BUXuucgvAV9zWp1kYU7LL9j4++s9O+12cb3wMtN4SJy6UQ==", + "dev": true + }, + "node_modules/emojis-list": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz", + "integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==", + "dev": true, + "engines": { + "node": ">= 4" + } + }, + "node_modules/encodeurl": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", + "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w==", + "dev": true, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/enhanced-resolve": { + "version": "5.12.0", + "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.12.0.tgz", + "integrity": "sha512-QHTXI/sZQmko1cbDoNAa3mJ5qhWUUNAq3vR0/YiD379fWQrcfuoX1+HW2S0MTt7XmoPLapdaDKUtelUSPic7hQ==", + "dev": true, + "dependencies": { + "graceful-fs": "^4.2.4", + "tapable": "^2.2.0" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/entities": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-2.2.0.tgz", + "integrity": "sha512-p92if5Nz619I0w+akJrLZH0MX0Pb5DX39XOwQTtXSdQQOaYH03S1uIQp4mhOZtAXrxq4ViO67YTiLBo2638o9A==", + "dev": true, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" + } + }, + "node_modules/envinfo": { + "version": "7.8.1", + "resolved": "https://registry.npmjs.org/envinfo/-/envinfo-7.8.1.tgz", + "integrity": "sha512-/o+BXHmB7ocbHEAs6F2EnG0ogybVVUdkRunTT2glZU9XAaGmhqskrvKwqXuDfNjEO0LZKWdejEEpnq8aM0tOaw==", + "dev": true, + "bin": { + "envinfo": "dist/cli.js" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/error-ex": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", + "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", + "dev": true, + "dependencies": { + "is-arrayish": "^0.2.1" + } + }, + "node_modules/es-abstract": { + "version": "1.21.1", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.21.1.tgz", + "integrity": "sha512-QudMsPOz86xYz/1dG1OuGBKOELjCh99IIWHLzy5znUB6j8xG2yMA7bfTV86VSqKF+Y/H08vQPR+9jyXpuC6hfg==", + "dev": true, + "dependencies": { + "available-typed-arrays": "^1.0.5", + "call-bind": "^1.0.2", + "es-set-tostringtag": "^2.0.1", + "es-to-primitive": "^1.2.1", + "function-bind": "^1.1.1", + "function.prototype.name": "^1.1.5", + "get-intrinsic": "^1.1.3", + "get-symbol-description": "^1.0.0", + "globalthis": "^1.0.3", + "gopd": "^1.0.1", + "has": "^1.0.3", + "has-property-descriptors": "^1.0.0", + "has-proto": "^1.0.1", + "has-symbols": "^1.0.3", + "internal-slot": "^1.0.4", + "is-array-buffer": "^3.0.1", + "is-callable": "^1.2.7", + "is-negative-zero": "^2.0.2", + "is-regex": "^1.1.4", + "is-shared-array-buffer": "^1.0.2", + "is-string": "^1.0.7", + "is-typed-array": "^1.1.10", + "is-weakref": "^1.0.2", + "object-inspect": "^1.12.2", + "object-keys": "^1.1.1", + "object.assign": "^4.1.4", + "regexp.prototype.flags": "^1.4.3", + "safe-regex-test": "^1.0.0", + "string.prototype.trimend": "^1.0.6", + "string.prototype.trimstart": "^1.0.6", + "typed-array-length": "^1.0.4", + "unbox-primitive": "^1.0.2", + "which-typed-array": "^1.1.9" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/es-module-lexer": { + "version": "0.9.3", + "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-0.9.3.tgz", + "integrity": "sha512-1HQ2M2sPtxwnvOvT1ZClHyQDiggdNjURWpY2we6aMKCQiUVxTmVs2UYPLIrD84sS+kMdUwfBSylbJPwNnBrnHQ==", + "dev": true + }, + "node_modules/es-set-tostringtag": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.0.1.tgz", + "integrity": "sha512-g3OMbtlwY3QewlqAiMLI47KywjWZoEytKr8pf6iTC8uJq5bIAH52Z9pnQ8pVL6whrCto53JZDuUIsifGeLorTg==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.1.3", + "has": "^1.0.3", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-shim-unscopables": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/es-shim-unscopables/-/es-shim-unscopables-1.0.0.tgz", + "integrity": "sha512-Jm6GPcCdC30eMLbZ2x8z2WuRwAws3zTBBKuusffYVUrNj/GVSUAZ+xKMaUpfNDR5IbyNA5LJbaecoUVbmUcB1w==", + "dev": true, + "peer": true, + "dependencies": { + "has": "^1.0.3" + } + }, + "node_modules/es-to-primitive": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.1.tgz", + "integrity": "sha512-QCOllgZJtaUo9miYBcLChTUaHNjJF3PYs1VidD7AwiEj1kYxKeQTctLAezAOH5ZKRH0g2IgPn6KwB4IT8iRpvA==", + "dev": true, + "dependencies": { + "is-callable": "^1.1.4", + "is-date-object": "^1.0.1", + "is-symbol": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/escalade": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", + "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/escape-html": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", + "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==", + "dev": true + }, + "node_modules/escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", + "dev": true, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/eslint": { + "version": "8.33.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.33.0.tgz", + "integrity": "sha512-WjOpFQgKK8VrCnAtl8We0SUOy/oVZ5NHykyMiagV1M9r8IFpIJX7DduK6n1mpfhlG7T1NLWm2SuD8QB7KFySaA==", + "dev": true, + "dependencies": { + "@eslint/eslintrc": "^1.4.1", + "@humanwhocodes/config-array": "^0.11.8", + "@humanwhocodes/module-importer": "^1.0.1", + "@nodelib/fs.walk": "^1.2.8", + "ajv": "^6.10.0", + "chalk": "^4.0.0", + "cross-spawn": "^7.0.2", + "debug": "^4.3.2", + "doctrine": "^3.0.0", + "escape-string-regexp": "^4.0.0", + "eslint-scope": "^7.1.1", + "eslint-utils": "^3.0.0", + "eslint-visitor-keys": "^3.3.0", + "espree": "^9.4.0", + "esquery": "^1.4.0", + "esutils": "^2.0.2", + "fast-deep-equal": "^3.1.3", + "file-entry-cache": "^6.0.1", + "find-up": "^5.0.0", + "glob-parent": "^6.0.2", + "globals": "^13.19.0", + "grapheme-splitter": "^1.0.4", + "ignore": "^5.2.0", + "import-fresh": "^3.0.0", + "imurmurhash": "^0.1.4", + "is-glob": "^4.0.0", + "is-path-inside": "^3.0.3", + "js-sdsl": "^4.1.4", + "js-yaml": "^4.1.0", + "json-stable-stringify-without-jsonify": "^1.0.1", + "levn": "^0.4.1", + "lodash.merge": "^4.6.2", + "minimatch": "^3.1.2", + "natural-compare": "^1.4.0", + "optionator": "^0.9.1", + "regexpp": "^3.2.0", + "strip-ansi": "^6.0.1", + "strip-json-comments": "^3.1.0", + "text-table": "^0.2.0" + }, + "bin": { + "eslint": "bin/eslint.js" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/eslint-config-airbnb-base": { + "version": "15.0.0", + "resolved": "https://registry.npmjs.org/eslint-config-airbnb-base/-/eslint-config-airbnb-base-15.0.0.tgz", + "integrity": "sha512-xaX3z4ZZIcFLvh2oUNvcX5oEofXda7giYmuplVxoOg5A7EXJMrUyqRgR+mhDhPK8LZ4PttFOBvCYDbX3sUoUig==", + "dev": true, + "dependencies": { + "confusing-browser-globals": "^1.0.10", + "object.assign": "^4.1.2", + "object.entries": "^1.1.5", + "semver": "^6.3.0" + }, + "engines": { + "node": "^10.12.0 || >=12.0.0" + }, + "peerDependencies": { + "eslint": "^7.32.0 || ^8.2.0", + "eslint-plugin-import": "^2.25.2" + } + }, + "node_modules/eslint-config-airbnb-typescript": { + "version": "17.0.0", + "resolved": "https://registry.npmjs.org/eslint-config-airbnb-typescript/-/eslint-config-airbnb-typescript-17.0.0.tgz", + "integrity": "sha512-elNiuzD0kPAPTXjFWg+lE24nMdHMtuxgYoD30OyMD6yrW1AhFZPAg27VX7d3tzOErw+dgJTNWfRSDqEcXb4V0g==", + "dev": true, + "dependencies": { + "eslint-config-airbnb-base": "^15.0.0" + }, + "peerDependencies": { + "@typescript-eslint/eslint-plugin": "^5.13.0", + "@typescript-eslint/parser": "^5.0.0", + "eslint": "^7.32.0 || ^8.2.0", + "eslint-plugin-import": "^2.25.3" + } + }, + "node_modules/eslint-import-resolver-node": { + "version": "0.3.7", + "resolved": "https://registry.npmjs.org/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.7.tgz", + "integrity": "sha512-gozW2blMLJCeFpBwugLTGyvVjNoeo1knonXAcatC6bjPBZitotxdWf7Gimr25N4c0AAOo4eOUfaG82IJPDpqCA==", + "dev": true, + "peer": true, + "dependencies": { + "debug": "^3.2.7", + "is-core-module": "^2.11.0", + "resolve": "^1.22.1" + } + }, + "node_modules/eslint-import-resolver-node/node_modules/debug": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", + "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "dev": true, + "peer": true, + "dependencies": { + "ms": "^2.1.1" + } + }, + "node_modules/eslint-module-utils": { + "version": "2.7.4", + "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.7.4.tgz", + "integrity": "sha512-j4GT+rqzCoRKHwURX7pddtIPGySnX9Si/cgMI5ztrcqOPtk5dDEeZ34CQVPphnqkJytlc97Vuk05Um2mJ3gEQA==", + "dev": true, + "peer": true, + "dependencies": { + "debug": "^3.2.7" + }, + "engines": { + "node": ">=4" + }, + "peerDependenciesMeta": { + "eslint": { + "optional": true + } + } + }, + "node_modules/eslint-module-utils/node_modules/debug": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", + "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "dev": true, + "peer": true, + "dependencies": { + "ms": "^2.1.1" + } + }, + "node_modules/eslint-plugin-import": { + "version": "2.27.5", + "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.27.5.tgz", + "integrity": "sha512-LmEt3GVofgiGuiE+ORpnvP+kAm3h6MLZJ4Q5HCyHADofsb4VzXFsRiWj3c0OFiV+3DWFh0qg3v9gcPlfc3zRow==", + "dev": true, + "peer": true, + "dependencies": { + "array-includes": "^3.1.6", + "array.prototype.flat": "^1.3.1", + "array.prototype.flatmap": "^1.3.1", + "debug": "^3.2.7", + "doctrine": "^2.1.0", + "eslint-import-resolver-node": "^0.3.7", + "eslint-module-utils": "^2.7.4", + "has": "^1.0.3", + "is-core-module": "^2.11.0", + "is-glob": "^4.0.3", + "minimatch": "^3.1.2", + "object.values": "^1.1.6", + "resolve": "^1.22.1", + "semver": "^6.3.0", + "tsconfig-paths": "^3.14.1" + }, + "engines": { + "node": ">=4" + }, + "peerDependencies": { + "eslint": "^2 || ^3 || ^4 || ^5 || ^6 || ^7.2.0 || ^8" + } + }, + "node_modules/eslint-plugin-import/node_modules/debug": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", + "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "dev": true, + "peer": true, + "dependencies": { + "ms": "^2.1.1" + } + }, + "node_modules/eslint-plugin-import/node_modules/doctrine": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", + "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", + "dev": true, + "peer": true, + "dependencies": { + "esutils": "^2.0.2" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/eslint-scope": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", + "integrity": "sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==", + "dev": true, + "dependencies": { + "esrecurse": "^4.3.0", + "estraverse": "^4.1.1" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/eslint-utils": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/eslint-utils/-/eslint-utils-3.0.0.tgz", + "integrity": "sha512-uuQC43IGctw68pJA1RgbQS8/NP7rch6Cwd4j3ZBtgo4/8Flj4eGE7ZYSZRN3iq5pVUv6GPdW5Z1RFleo84uLDA==", + "dev": true, + "dependencies": { + "eslint-visitor-keys": "^2.0.0" + }, + "engines": { + "node": "^10.0.0 || ^12.0.0 || >= 14.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/mysticatea" + }, + "peerDependencies": { + "eslint": ">=5" + } + }, + "node_modules/eslint-utils/node_modules/eslint-visitor-keys": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-2.1.0.tgz", + "integrity": "sha512-0rSmRBzXgDzIsD6mGdJgevzgezI534Cer5L/vyMX0kHzT/jiB43jRhd9YUlMGYLQy2zprNmoT8qasCGtY+QaKw==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/eslint-visitor-keys": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.3.0.tgz", + "integrity": "sha512-mQ+suqKJVyeuwGYHAdjMFqjCyfl8+Ldnxuyp3ldiMBFKkvytrXUZWaiPCEav8qDHKty44bD+qV1IP4T+w+xXRA==", + "dev": true, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + } + }, + "node_modules/eslint/node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/eslint/node_modules/ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, + "dependencies": { + "color-convert": "^2.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/eslint/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/eslint/node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/eslint/node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true + }, + "node_modules/eslint/node_modules/escape-string-regexp": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", + "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/dom-serializer": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-1.4.1.tgz", - "integrity": "sha512-VHwB3KfrcOOkelEG2ZOfxqLZdfkil8PtJi4P8N2MMXucZq2yLp75ClViUlOVwyoHEDjYU433Aq+5zWP61+RGag==", + "node_modules/eslint/node_modules/eslint-scope": { + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-7.1.1.tgz", + "integrity": "sha512-QKQM/UXpIiHcLqJ5AOyIW7XZmzjkzQXYE54n1++wb0u9V/abW3l9uQnxX8Z5Xd18xyKIMTUAyQ0k1e8pz6LUrw==", "dev": true, "dependencies": { - "domelementtype": "^2.0.1", - "domhandler": "^4.2.0", - "entities": "^2.0.0" + "esrecurse": "^4.3.0", + "estraverse": "^5.2.0" }, - "funding": { - "url": "https://github.com/cheeriojs/dom-serializer?sponsor=1" + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" } }, - "node_modules/domelementtype": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-2.3.0.tgz", - "integrity": "sha512-OLETBj6w0OsagBwdXnPdN0cnMfF9opN69co+7ZrbfPGrdpPVNBUj02spi6B1N7wChLQiPn4CSH/zJvXw56gmHw==", + "node_modules/eslint/node_modules/estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", "dev": true, - "funding": [ - { - "type": "github", - "url": "https://github.com/sponsors/fb55" - } - ] + "engines": { + "node": ">=4.0" + } }, - "node_modules/domhandler": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-4.3.1.tgz", - "integrity": "sha512-GrwoxYN+uWlzO8uhUXRl0P+kHE4GtVPfYzVLcUxPL7KNdHKj66vvlhiweIHqYYXWlw+T8iLMp42Lm67ghw4WMQ==", + "node_modules/eslint/node_modules/find-up": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", + "integrity": "sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==", "dev": true, "dependencies": { - "domelementtype": "^2.2.0" + "locate-path": "^6.0.0", + "path-exists": "^4.0.0" }, "engines": { - "node": ">= 4" + "node": ">=10" }, "funding": { - "url": "https://github.com/fb55/domhandler?sponsor=1" + "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/domutils": { - "version": "2.8.0", - "resolved": "https://registry.npmjs.org/domutils/-/domutils-2.8.0.tgz", - "integrity": "sha512-w96Cjofp72M5IIhpjgobBimYEfoPjx1Vx0BSX9P30WBdZW2WIKU0T1Bd0kz2eNZ9ikjKgHbEyKx8BB6H1L3h3A==", + "node_modules/eslint/node_modules/glob-parent": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-6.0.2.tgz", + "integrity": "sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==", "dev": true, "dependencies": { - "dom-serializer": "^1.0.1", - "domelementtype": "^2.2.0", - "domhandler": "^4.2.0" + "is-glob": "^4.0.3" }, - "funding": { - "url": "https://github.com/fb55/domutils?sponsor=1" + "engines": { + "node": ">=10.13.0" } }, - "node_modules/dot-case": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/dot-case/-/dot-case-3.0.4.tgz", - "integrity": "sha512-Kv5nKlh6yRrdrGvxeJ2e5y2eRUpkUosIW4A2AS38zwSz27zu7ufDwQPi5Jhs3XAlGNetl3bmnGhQsMtkKJnj3w==", + "node_modules/eslint/node_modules/globals": { + "version": "13.20.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-13.20.0.tgz", + "integrity": "sha512-Qg5QtVkCy/kv3FUSlu4ukeZDVf9ee0iXLAUYX13gbR17bnejFTzr4iS9bY7kwCf1NztRNm1t91fjOiyx4CSwPQ==", "dev": true, "dependencies": { - "no-case": "^3.0.4", - "tslib": "^2.0.3" + "type-fest": "^0.20.2" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/ee-first": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", - "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==", - "dev": true - }, - "node_modules/electron-to-chromium": { - "version": "1.4.286", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.286.tgz", - "integrity": "sha512-Vp3CVhmYpgf4iXNKAucoQUDcCrBQX3XLBtwgFqP9BUXuucgvAV9zWp1kYU7LL9j4++s9O+12cb3wMtN4SJy6UQ==", - "dev": true - }, - "node_modules/emojis-list": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz", - "integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==", + "node_modules/eslint/node_modules/has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", "dev": true, "engines": { - "node": ">= 4" + "node": ">=8" } }, - "node_modules/encodeurl": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", - "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w==", + "node_modules/eslint/node_modules/is-path-inside": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-3.0.3.tgz", + "integrity": "sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ==", "dev": true, "engines": { - "node": ">= 0.8" + "node": ">=8" } }, - "node_modules/enhanced-resolve": { - "version": "5.12.0", - "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.12.0.tgz", - "integrity": "sha512-QHTXI/sZQmko1cbDoNAa3mJ5qhWUUNAq3vR0/YiD379fWQrcfuoX1+HW2S0MTt7XmoPLapdaDKUtelUSPic7hQ==", + "node_modules/eslint/node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "node_modules/eslint/node_modules/locate-path": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz", + "integrity": "sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==", "dev": true, "dependencies": { - "graceful-fs": "^4.2.4", - "tapable": "^2.2.0" + "p-locate": "^5.0.0" }, "engines": { - "node": ">=10.13.0" + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/entities": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/entities/-/entities-2.2.0.tgz", - "integrity": "sha512-p92if5Nz619I0w+akJrLZH0MX0Pb5DX39XOwQTtXSdQQOaYH03S1uIQp4mhOZtAXrxq4ViO67YTiLBo2638o9A==", + "node_modules/eslint/node_modules/p-limit": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-3.1.0.tgz", + "integrity": "sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==", "dev": true, + "dependencies": { + "yocto-queue": "^0.1.0" + }, + "engines": { + "node": ">=10" + }, "funding": { - "url": "https://github.com/fb55/entities?sponsor=1" + "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/envinfo": { - "version": "7.8.1", - "resolved": "https://registry.npmjs.org/envinfo/-/envinfo-7.8.1.tgz", - "integrity": "sha512-/o+BXHmB7ocbHEAs6F2EnG0ogybVVUdkRunTT2glZU9XAaGmhqskrvKwqXuDfNjEO0LZKWdejEEpnq8aM0tOaw==", + "node_modules/eslint/node_modules/p-locate": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-5.0.0.tgz", + "integrity": "sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==", "dev": true, - "bin": { - "envinfo": "dist/cli.js" + "dependencies": { + "p-limit": "^3.0.2" }, "engines": { - "node": ">=4" + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/error-ex": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", - "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", + "node_modules/eslint/node_modules/supports-color": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", + "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", "dev": true, "dependencies": { - "is-arrayish": "^0.2.1" + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=8" } }, - "node_modules/es-module-lexer": { - "version": "0.9.3", - "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-0.9.3.tgz", - "integrity": "sha512-1HQ2M2sPtxwnvOvT1ZClHyQDiggdNjURWpY2we6aMKCQiUVxTmVs2UYPLIrD84sS+kMdUwfBSylbJPwNnBrnHQ==", - "dev": true - }, - "node_modules/escalade": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", - "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==", + "node_modules/espree": { + "version": "9.4.1", + "resolved": "https://registry.npmjs.org/espree/-/espree-9.4.1.tgz", + "integrity": "sha512-XwctdmTO6SIvCzd9810yyNzIrOrqNYV9Koizx4C/mRhf9uq0o4yHoCEU/670pOxOL/MSraektvSAji79kX90Vg==", "dev": true, + "dependencies": { + "acorn": "^8.8.0", + "acorn-jsx": "^5.3.2", + "eslint-visitor-keys": "^3.3.0" + }, "engines": { - "node": ">=6" + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" } }, - "node_modules/escape-html": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", - "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==", - "dev": true - }, - "node_modules/escape-string-regexp": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", - "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", + "node_modules/esquery": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.4.0.tgz", + "integrity": "sha512-cCDispWt5vHHtwMY2YrAQ4ibFkAL8RbH5YGBnZBc90MolvvfkkQcJro/aZiAQUlQ3qgrYS6D6v8Gc5G5CQsc9w==", "dev": true, + "dependencies": { + "estraverse": "^5.1.0" + }, "engines": { - "node": ">=0.8.0" + "node": ">=0.10" } }, - "node_modules/eslint-scope": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", - "integrity": "sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==", + "node_modules/esquery/node_modules/estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", "dev": true, - "dependencies": { - "esrecurse": "^4.3.0", - "estraverse": "^4.1.1" - }, "engines": { - "node": ">=8.0.0" + "node": ">=4.0" } }, "node_modules/esrecurse": { @@ -3445,12 +4621,34 @@ "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", "dev": true }, + "node_modules/fast-glob": { + "version": "3.2.12", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.12.tgz", + "integrity": "sha512-DVj4CQIYYow0BlaelwK1pHl5n5cRSJfM60UA0zK891sVInoPri2Ekj7+e1CT3/3qxXenpI+nBBmQAcJPJgaj4w==", + "dev": true, + "dependencies": { + "@nodelib/fs.stat": "^2.0.2", + "@nodelib/fs.walk": "^1.2.3", + "glob-parent": "^5.1.2", + "merge2": "^1.3.0", + "micromatch": "^4.0.4" + }, + "engines": { + "node": ">=8.6.0" + } + }, "node_modules/fast-json-stable-stringify": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", "dev": true }, + "node_modules/fast-levenshtein": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", + "integrity": "sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==", + "dev": true + }, "node_modules/fastest-levenshtein": { "version": "1.0.16", "resolved": "https://registry.npmjs.org/fastest-levenshtein/-/fastest-levenshtein-1.0.16.tgz", @@ -3460,6 +4658,15 @@ "node": ">= 4.9.1" } }, + "node_modules/fastq": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.15.0.tgz", + "integrity": "sha512-wBrocU2LCXXa+lWBt8RoIRD89Fi8OdABODa/kEnyeyjS5aZO5/GNvI5sEINADqP/h8M29UHTHUb53sUu5Ihqdw==", + "dev": true, + "dependencies": { + "reusify": "^1.0.4" + } + }, "node_modules/faye-websocket": { "version": "0.11.4", "resolved": "https://registry.npmjs.org/faye-websocket/-/faye-websocket-0.11.4.tgz", @@ -3472,6 +4679,18 @@ "node": ">=0.8.0" } }, + "node_modules/file-entry-cache": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-6.0.1.tgz", + "integrity": "sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg==", + "dev": true, + "dependencies": { + "flat-cache": "^3.0.4" + }, + "engines": { + "node": "^10.12.0 || >=12.0.0" + } + }, "node_modules/fill-range": { "version": "7.0.1", "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz", @@ -3547,6 +4766,40 @@ "node": ">=8" } }, + "node_modules/flat-cache": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-3.0.4.tgz", + "integrity": "sha512-dm9s5Pw7Jc0GvMYbshN6zchCA9RgQlzzEZX3vylR9IqFfS8XciblUXOKfW6SiuJ0e13eDYZoZV5wdrev7P3Nwg==", + "dev": true, + "dependencies": { + "flatted": "^3.1.0", + "rimraf": "^3.0.2" + }, + "engines": { + "node": "^10.12.0 || >=12.0.0" + } + }, + "node_modules/flat-cache/node_modules/rimraf": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", + "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", + "dev": true, + "dependencies": { + "glob": "^7.1.3" + }, + "bin": { + "rimraf": "bin.js" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/flatted": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/flatted/-/flatted-3.2.7.tgz", + "integrity": "sha512-5nqDSxl8nn5BSNxyR3n4I6eDmbolI6WT+QqR547RwxQapgjQBmtktdP+HTBb/a/zLsbzERTONyUB5pefh5TtjQ==", + "dev": true + }, "node_modules/follow-redirects": { "version": "1.15.2", "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.2.tgz", @@ -3567,6 +4820,15 @@ } } }, + "node_modules/for-each": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", + "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", + "dev": true, + "dependencies": { + "is-callable": "^1.1.3" + } + }, "node_modules/forwarded": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", @@ -3624,11 +4886,38 @@ "node": "^8.16.0 || ^10.6.0 || >=11.0.0" } }, - "node_modules/function-bind": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", - "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", - "dev": true + "node_modules/function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", + "dev": true + }, + "node_modules/function.prototype.name": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/function.prototype.name/-/function.prototype.name-1.1.5.tgz", + "integrity": "sha512-uN7m/BzVKQnCUF/iW8jYea67v++2u7m5UgENbHRtdDVclOUP+FMPlCNdmk0h/ysGyo2tavMJEDqJAkJdRa1vMA==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.3", + "es-abstract": "^1.19.0", + "functions-have-names": "^1.2.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/functions-have-names": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/functions-have-names/-/functions-have-names-1.2.3.tgz", + "integrity": "sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } }, "node_modules/gensync": { "version": "1.0.0-beta.2", @@ -3666,6 +4955,22 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/get-symbol-description": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/get-symbol-description/-/get-symbol-description-1.0.0.tgz", + "integrity": "sha512-2EmdH1YvIQiZpltCNgkuiUnyukzxM/R6NDJX31Ke3BG1Nq5b0S2PhX59UKi9vZpPDQVdqn+1IcaAwnzTT5vCjw==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/glob": { "version": "7.2.3", "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", @@ -3713,6 +5018,21 @@ "node": ">=4" } }, + "node_modules/globalthis": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/globalthis/-/globalthis-1.0.3.tgz", + "integrity": "sha512-sFdI5LyBiNTHjRd7cGPWapiHWMOXKyuBNX/cWJ3NfzrZQVa8GI/8cofCl74AOVqq9W5kNmguTIzJ/1s2gyI9wA==", + "dev": true, + "dependencies": { + "define-properties": "^1.1.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/globby": { "version": "6.1.0", "resolved": "https://registry.npmjs.org/globby/-/globby-6.1.0.tgz", @@ -3738,12 +5058,30 @@ "node": ">=0.10.0" } }, + "node_modules/gopd": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.0.1.tgz", + "integrity": "sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.1.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/graceful-fs": { "version": "4.2.10", "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.10.tgz", "integrity": "sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==", "dev": true }, + "node_modules/grapheme-splitter": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/grapheme-splitter/-/grapheme-splitter-1.0.4.tgz", + "integrity": "sha512-bzh50DW9kTPM00T8y4o8vQg89Di9oLJVLW/KaOGIXJWP/iqCN6WKYkbNOF04vFLJhwcpYUh9ydh/+5vpOqV4YQ==", + "dev": true + }, "node_modules/handle-thing": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/handle-thing/-/handle-thing-2.0.1.tgz", @@ -3762,6 +5100,15 @@ "node": ">= 0.4.0" } }, + "node_modules/has-bigints": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.0.2.tgz", + "integrity": "sha512-tSvCKtBr9lkF0Ex0aQiP9N+OpV4zi2r/Nee5VkRDbaqv35RLYMzbwQfFSZZH0kR+Rd6302UJZ2p/bJCEoR3VoQ==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/has-flag": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", @@ -3771,6 +5118,30 @@ "node": ">=4" } }, + "node_modules/has-property-descriptors": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.0.tgz", + "integrity": "sha512-62DVLZGoiEBDHQyqG4w9xCuZ7eJEwNmJRWw2VY84Oedb7WFcA27fiEVe8oUQx9hAUJ4ekurquucTGwsyO1XGdQ==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.1.1" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-proto": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.0.1.tgz", + "integrity": "sha512-7qE+iP+O+bgF9clE5+UoBFzE65mlBiVj3tKCrlNQ0Ogwm0BjpT/gK4SlLYDMybDh5I3TCTKnPPa0oMG7JDYrhg==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/has-symbols": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", @@ -3783,6 +5154,21 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/has-tostringtag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.0.tgz", + "integrity": "sha512-kFjcSNhnlGV1kyoGk7OXKSawH5JOb/LzUc5w9B02hOTO0dfFRjbHQKvg1d6cf3HbeUmtU9VbbV3qzZ2Teh97WQ==", + "dev": true, + "dependencies": { + "has-symbols": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/he": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/he/-/he-1.2.0.tgz", @@ -4002,6 +5388,15 @@ "postcss": "^8.1.0" } }, + "node_modules/ignore": { + "version": "5.2.4", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.2.4.tgz", + "integrity": "sha512-MAb38BcSbH0eHNBxn7ql2NH/kX33OkB3lZ1BNdh7ENeRChHTYsTvWrMubiIAMNS2llXEEgZ1MUOBtXChP3kaFQ==", + "dev": true, + "engines": { + "node": ">= 4" + } + }, "node_modules/immutable": { "version": "4.2.3", "resolved": "https://registry.npmjs.org/immutable/-/immutable-4.2.3.tgz", @@ -4043,6 +5438,15 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==", + "dev": true, + "engines": { + "node": ">=0.8.19" + } + }, "node_modules/inflight": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", @@ -4059,6 +5463,20 @@ "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", "dev": true }, + "node_modules/internal-slot": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.0.4.tgz", + "integrity": "sha512-tA8URYccNzMo94s5MQZgH8NB/XTa6HsOo0MLfXTKKEnHVVdegzaQoFZ7Jp44bdvLvY2waT5dc+j5ICEswhi7UQ==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.1.3", + "has": "^1.0.3", + "side-channel": "^1.0.4" + }, + "engines": { + "node": ">= 0.4" + } + }, "node_modules/interpret": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/interpret/-/interpret-3.1.1.tgz", @@ -4077,12 +5495,38 @@ "node": ">= 10" } }, + "node_modules/is-array-buffer": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-3.0.1.tgz", + "integrity": "sha512-ASfLknmY8Xa2XtB4wmbz13Wu202baeA18cJBCeCy0wXUHZF0IPyVEXqKEcd+t2fNSLLL1vC6k7lxZEojNbISXQ==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.1.3", + "is-typed-array": "^1.1.10" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/is-arrayish": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", "integrity": "sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg==", "dev": true }, + "node_modules/is-bigint": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-bigint/-/is-bigint-1.0.4.tgz", + "integrity": "sha512-zB9CruMamjym81i2JZ3UMn54PKGsQzsJeo6xvN3HJJ4CAsQNB6iRutp2To77OfCNuoxspsIhzaPoO1zyCEhFOg==", + "dev": true, + "dependencies": { + "has-bigints": "^1.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/is-binary-path": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz", @@ -4095,6 +5539,34 @@ "node": ">=8" } }, + "node_modules/is-boolean-object": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/is-boolean-object/-/is-boolean-object-1.1.2.tgz", + "integrity": "sha512-gDYaKHJmnj4aWxyj6YHyXVpdQawtVLHU5cb+eztPGczf6cjuTdwve5ZIEfgXqH4e57An1D1AKf8CZ3kYrQRqYA==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-callable": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz", + "integrity": "sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/is-core-module": { "version": "2.11.0", "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.11.0.tgz", @@ -4107,6 +5579,21 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/is-date-object": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.5.tgz", + "integrity": "sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ==", + "dev": true, + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/is-docker": { "version": "2.2.1", "resolved": "https://registry.npmjs.org/is-docker/-/is-docker-2.2.1.tgz", @@ -4143,6 +5630,18 @@ "node": ">=0.10.0" } }, + "node_modules/is-negative-zero": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.2.tgz", + "integrity": "sha512-dqJvarLawXsFbNDeJW7zAz8ItJ9cd28YufuuFzh0G8pNHjJMnY08Dv7sYX2uF5UpQOwieAeOExEYAWWfu7ZZUA==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/is-number": { "version": "7.0.0", "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", @@ -4152,6 +5651,21 @@ "node": ">=0.12.0" } }, + "node_modules/is-number-object": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.0.7.tgz", + "integrity": "sha512-k1U0IRzLMo7ZlYIfzRu23Oh6MiIFasgpb9X76eqfFZAqwH44UI4KTBvBYIZ1dSL9ZzChTB9ShHfLkR4pdW5krQ==", + "dev": true, + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/is-path-cwd": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/is-path-cwd/-/is-path-cwd-2.2.0.tgz", @@ -4209,6 +5723,34 @@ "node": ">=0.10.0" } }, + "node_modules/is-regex": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.1.4.tgz", + "integrity": "sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-shared-array-buffer": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-shared-array-buffer/-/is-shared-array-buffer-1.0.2.tgz", + "integrity": "sha512-sqN2UDu1/0y6uvXyStCOzyhAjCSlHceFoMKJW8W9EU9cvic/QdsZ0kEU93HEy3IUEFZIiH/3w+AH/UQbPHNdhA==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/is-stream": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", @@ -4221,6 +5763,67 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/is-string": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/is-string/-/is-string-1.0.7.tgz", + "integrity": "sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg==", + "dev": true, + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-symbol": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.4.tgz", + "integrity": "sha512-C/CPBqKWnvdcxqIARxyOh4v1UUEOCHpgDa0WYgpKDFMszcrPcffg5uhwSgPCLD2WWxmq6isisz87tzT01tuGhg==", + "dev": true, + "dependencies": { + "has-symbols": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-typed-array": { + "version": "1.1.10", + "resolved": "https://registry.npmjs.org/is-typed-array/-/is-typed-array-1.1.10.tgz", + "integrity": "sha512-PJqgEHiWZvMpaFZ3uTc8kHPM4+4ADTlDniuQL7cU/UDA0Ql7F70yGfHph3cLNe+c9toaigv+DFzTJKhc2CtO6A==", + "dev": true, + "dependencies": { + "available-typed-arrays": "^1.0.5", + "call-bind": "^1.0.2", + "for-each": "^0.3.3", + "gopd": "^1.0.1", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-weakref": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-weakref/-/is-weakref-1.0.2.tgz", + "integrity": "sha512-qctsuLZmIQ0+vSSMfoVvyFe2+GSEvnmZ2ezTup1SBse9+twCCeial6EEi3Nc2KFcf6+qz2FBPnjXsk8xhKSaPQ==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/is-wsl": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/is-wsl/-/is-wsl-2.2.0.tgz", @@ -4292,12 +5895,34 @@ "url": "https://github.com/chalk/supports-color?sponsor=1" } }, + "node_modules/js-sdsl": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/js-sdsl/-/js-sdsl-4.3.0.tgz", + "integrity": "sha512-mifzlm2+5nZ+lEcLJMoBK0/IH/bDg8XnJfd/Wq6IP+xoCjLZsTOnV2QpxlVbX9bMnkl5PdEjNtBJ9Cj1NjifhQ==", + "dev": true, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/js-sdsl" + } + }, "node_modules/js-tokens": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", "dev": true }, + "node_modules/js-yaml": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", + "integrity": "sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==", + "dev": true, + "dependencies": { + "argparse": "^2.0.1" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" + } + }, "node_modules/jsesc": { "version": "2.5.2", "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-2.5.2.tgz", @@ -4322,6 +5947,12 @@ "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==", "dev": true }, + "node_modules/json-stable-stringify-without-jsonify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz", + "integrity": "sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==", + "dev": true + }, "node_modules/json5": { "version": "2.2.3", "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", @@ -4352,6 +5983,19 @@ "node": ">= 8" } }, + "node_modules/levn": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", + "integrity": "sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==", + "dev": true, + "dependencies": { + "prelude-ls": "^1.2.1", + "type-check": "~0.4.0" + }, + "engines": { + "node": ">= 0.8.0" + } + }, "node_modules/lines-and-columns": { "version": "1.2.4", "resolved": "https://registry.npmjs.org/lines-and-columns/-/lines-and-columns-1.2.4.tgz", @@ -4405,6 +6049,12 @@ "integrity": "sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==", "dev": true }, + "node_modules/lodash.merge": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", + "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", + "dev": true + }, "node_modules/lower-case": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/lower-case/-/lower-case-2.0.2.tgz", @@ -4471,6 +6121,15 @@ "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==", "dev": true }, + "node_modules/merge2": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", + "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", + "dev": true, + "engines": { + "node": ">= 8" + } + }, "node_modules/methods": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", @@ -4572,6 +6231,16 @@ "node": "*" } }, + "node_modules/minimist": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.7.tgz", + "integrity": "sha512-bzfL1YUZsP41gmu/qjrEk0Q6i2ix/cVeAhbCbqH9u3zYutS1cLg00qhrD0M2MVdCcx4Sc0UpP2eBWo9rotpq6g==", + "dev": true, + "peer": true, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/ms": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", @@ -4603,6 +6272,18 @@ "node": "^10 || ^12 || ^13.7 || ^14 || >=15.0.1" } }, + "node_modules/natural-compare": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", + "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", + "dev": true + }, + "node_modules/natural-compare-lite": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare-lite/-/natural-compare-lite-1.4.0.tgz", + "integrity": "sha512-Tj+HTDSJJKaZnfiuw+iaF9skdPpTo2GtEly5JHnWV/hfv2Qj/9RKsGISQtLh2ox3l5EAGw487hnBee0sIJ6v2g==", + "dev": true + }, "node_modules/negotiator": { "version": "0.6.3", "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz", @@ -4703,6 +6384,65 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/object-keys": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", + "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==", + "dev": true, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/object.assign": { + "version": "4.1.4", + "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.4.tgz", + "integrity": "sha512-1mxKf0e58bvyjSCtKYY4sRe9itRk3PJpquJOjeIkz885CczcI4IvJJDLPS72oowuSh+pBxUFROpX+TU++hxhZQ==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "has-symbols": "^1.0.3", + "object-keys": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/object.entries": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/object.entries/-/object.entries-1.1.6.tgz", + "integrity": "sha512-leTPzo4Zvg3pmbQ3rDK69Rl8GQvIqMWubrkxONG9/ojtFE2rD9fjMKfSI5BxW3osRH1m6VdzmqK8oAY9aT4x5w==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/object.values": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/object.values/-/object.values-1.1.6.tgz", + "integrity": "sha512-FVVTkD1vENCsAcwNs9k6jea2uHC/X0+JcjG8YA60FN5CMaJmG95wT9jek/xX9nornqGRrBkKtzuAu2wuHpKqvw==", + "dev": true, + "peer": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/obuf": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/obuf/-/obuf-1.1.2.tgz", @@ -4771,6 +6511,23 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/optionator": { + "version": "0.9.1", + "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.1.tgz", + "integrity": "sha512-74RlY5FCnhq4jRxVUPKDaRwrVNXMqsGsiW6AJw4XK8hmtm10wC0ypZBLw5IIp85NZMr91+qd1RvvENwg7jjRFw==", + "dev": true, + "dependencies": { + "deep-is": "^0.1.3", + "fast-levenshtein": "^2.0.6", + "levn": "^0.4.1", + "prelude-ls": "^1.2.1", + "type-check": "^0.4.0", + "word-wrap": "^1.2.3" + }, + "engines": { + "node": ">= 0.8.0" + } + }, "node_modules/p-limit": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", @@ -5159,6 +6916,15 @@ "integrity": "sha512-1NNCs6uurfkVbeXG4S8JFT9t19m45ICnif8zWLd5oPSZ50QnwMfK+H3jv408d4jw/7Bttv5axS5IiHoLaVNHeQ==", "dev": true }, + "node_modules/prelude-ls": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz", + "integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==", + "dev": true, + "engines": { + "node": ">= 0.8.0" + } + }, "node_modules/pretty-error": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/pretty-error/-/pretty-error-4.0.0.tgz", @@ -5221,6 +6987,26 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/queue-microtask": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", + "integrity": "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ] + }, "node_modules/randombytes": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", @@ -5334,6 +7120,35 @@ "@babel/runtime": "^7.8.4" } }, + "node_modules/regexp.prototype.flags": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.4.3.tgz", + "integrity": "sha512-fjggEOO3slI6Wvgjwflkc4NFRCTZAu5CnNfBd5qOMYhWdn67nJBBu34/TkD++eeFmd8C9r9jfXJ27+nSiRkSUA==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.3", + "functions-have-names": "^1.2.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/regexpp": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-3.2.0.tgz", + "integrity": "sha512-pq2bWo9mVD43nbts2wGv17XLiNLya+GklZ8kaDLV2Z08gDCsGpnKn9BFMepvWuHCbyVvY7J5o5+BVvoQbmlJLg==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/mysticatea" + } + }, "node_modules/regexpu-core": { "version": "5.2.2", "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-5.2.2.tgz", @@ -5471,6 +7286,16 @@ "node": ">= 4" } }, + "node_modules/reusify": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.0.4.tgz", + "integrity": "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==", + "dev": true, + "engines": { + "iojs": ">=1.0.0", + "node": ">=0.10.0" + } + }, "node_modules/rimraf": { "version": "2.7.1", "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.7.1.tgz", @@ -5483,6 +7308,29 @@ "rimraf": "bin.js" } }, + "node_modules/run-parallel": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", + "integrity": "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "dependencies": { + "queue-microtask": "^1.2.2" + } + }, "node_modules/safe-buffer": { "version": "5.2.1", "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", @@ -5503,6 +7351,20 @@ } ] }, + "node_modules/safe-regex-test": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.0.0.tgz", + "integrity": "sha512-JBUUzyOgEwXQY1NuPtvcj/qcBDbDmEvWufhlnXZIm75DEHp+afM1r1ujJpJsV/gSM4t59tpDyPi1sd6ZaPFfsA==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.1.3", + "is-regex": "^1.1.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/safer-buffer": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", @@ -5816,6 +7678,15 @@ "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==", "dev": true }, + "node_modules/slash": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/slash/-/slash-3.0.0.tgz", + "integrity": "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==", + "dev": true, + "engines": { + "node": ">=8" + } + }, "node_modules/sockjs": { "version": "0.3.24", "resolved": "https://registry.npmjs.org/sockjs/-/sockjs-0.3.24.tgz", @@ -5903,6 +7774,34 @@ "safe-buffer": "~5.2.0" } }, + "node_modules/string.prototype.trimend": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.6.tgz", + "integrity": "sha512-JySq+4mrPf9EsDBEDYMOb/lM7XQLulwg5R/m1r0PXEFqrV0qHvl58sdTilSXtKOflCsK2E8jxf+GKC0T07RWwQ==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/string.prototype.trimstart": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.6.tgz", + "integrity": "sha512-omqjMDaY92pbn5HOX7f9IccLA+U1tA9GvtU4JrodiXFfYB7jPzzHpRzpglLAjtUV6bB557zwClJezTqnAiYnQA==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/strip-ansi": { "version": "6.0.1", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", @@ -5915,6 +7814,16 @@ "node": ">=8" } }, + "node_modules/strip-bom": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", + "integrity": "sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==", + "dev": true, + "peer": true, + "engines": { + "node": ">=4" + } + }, "node_modules/strip-final-newline": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/strip-final-newline/-/strip-final-newline-2.0.0.tgz", @@ -5924,6 +7833,18 @@ "node": ">=6" } }, + "node_modules/strip-json-comments": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz", + "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/supports-color": { "version": "5.5.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", @@ -6064,6 +7985,12 @@ "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==", "dev": true }, + "node_modules/text-table": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", + "integrity": "sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw==", + "dev": true + }, "node_modules/thunky": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/thunky/-/thunky-1.1.0.tgz", @@ -6100,12 +8027,83 @@ "node": ">=0.6" } }, + "node_modules/tsconfig-paths": { + "version": "3.14.1", + "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.14.1.tgz", + "integrity": "sha512-fxDhWnFSLt3VuTwtvJt5fpwxBHg5AdKWMsgcPOOIilyjymcYVZoCQF8fvFRezCNfblEXmi+PcM1eYHeOAgXCOQ==", + "dev": true, + "peer": true, + "dependencies": { + "@types/json5": "^0.0.29", + "json5": "^1.0.1", + "minimist": "^1.2.6", + "strip-bom": "^3.0.0" + } + }, + "node_modules/tsconfig-paths/node_modules/json5": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/json5/-/json5-1.0.2.tgz", + "integrity": "sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA==", + "dev": true, + "peer": true, + "dependencies": { + "minimist": "^1.2.0" + }, + "bin": { + "json5": "lib/cli.js" + } + }, "node_modules/tslib": { "version": "2.5.0", "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.5.0.tgz", "integrity": "sha512-336iVw3rtn2BUK7ORdIAHTyxHGRIHVReokCR3XjbckJMK7ms8FysBfhLR8IXnAgy7T0PTPNBWKiH514FOW/WSg==", "dev": true }, + "node_modules/tsutils": { + "version": "3.21.0", + "resolved": "https://registry.npmjs.org/tsutils/-/tsutils-3.21.0.tgz", + "integrity": "sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA==", + "dev": true, + "dependencies": { + "tslib": "^1.8.1" + }, + "engines": { + "node": ">= 6" + }, + "peerDependencies": { + "typescript": ">=2.8.0 || >= 3.2.0-dev || >= 3.3.0-dev || >= 3.4.0-dev || >= 3.5.0-dev || >= 3.6.0-dev || >= 3.6.0-beta || >= 3.7.0-dev || >= 3.7.0-beta" + } + }, + "node_modules/tsutils/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "dev": true + }, + "node_modules/type-check": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.4.0.tgz", + "integrity": "sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==", + "dev": true, + "dependencies": { + "prelude-ls": "^1.2.1" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/type-fest": { + "version": "0.20.2", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.20.2.tgz", + "integrity": "sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/type-is": { "version": "1.6.18", "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", @@ -6119,6 +8117,20 @@ "node": ">= 0.6" } }, + "node_modules/typed-array-length": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/typed-array-length/-/typed-array-length-1.0.4.tgz", + "integrity": "sha512-KjZypGq+I/H7HI5HlOoGHkWUUGq+Q0TPhQurLbyrVrvnKTBgzLhIJ7j6J/XTQOi0d1RjyZ0wdas8bKs2p0x3Ng==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "for-each": "^0.3.3", + "is-typed-array": "^1.1.9" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/typescript": { "version": "4.9.5", "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.9.5.tgz", @@ -6132,6 +8144,21 @@ "node": ">=4.2.0" } }, + "node_modules/unbox-primitive": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.0.2.tgz", + "integrity": "sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "has-bigints": "^1.0.2", + "has-symbols": "^1.0.3", + "which-boxed-primitive": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/unicode-canonical-property-names-ecmascript": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/unicode-canonical-property-names-ecmascript/-/unicode-canonical-property-names-ecmascript-2.0.0.tgz", @@ -6656,12 +8683,57 @@ "node": ">= 8" } }, + "node_modules/which-boxed-primitive": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/which-boxed-primitive/-/which-boxed-primitive-1.0.2.tgz", + "integrity": "sha512-bwZdv0AKLpplFY2KZRX6TvyuN7ojjr7lwkg6ml0roIy9YeuSr7JS372qlNW18UQYzgYK9ziGcerWqZOmEn9VNg==", + "dev": true, + "dependencies": { + "is-bigint": "^1.0.1", + "is-boolean-object": "^1.1.0", + "is-number-object": "^1.0.4", + "is-string": "^1.0.5", + "is-symbol": "^1.0.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/which-typed-array": { + "version": "1.1.9", + "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.9.tgz", + "integrity": "sha512-w9c4xkx6mPidwp7180ckYWfMmvxpjlZuIudNtDf4N/tTAUB8VJbX25qZoAsrtGuYNnGw3pa0AXgbGKRB8/EceA==", + "dev": true, + "dependencies": { + "available-typed-arrays": "^1.0.5", + "call-bind": "^1.0.2", + "for-each": "^0.3.3", + "gopd": "^1.0.1", + "has-tostringtag": "^1.0.0", + "is-typed-array": "^1.1.10" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, "node_modules/wildcard": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/wildcard/-/wildcard-2.0.0.tgz", "integrity": "sha512-JcKqAHLPxcdb9KM49dufGXn2x3ssnfjbcaQdLlfZsL9rH9wgDQjUtDxbo8NE0F6SFvydeu1VhZe7hZuHsB2/pw==", "dev": true }, + "node_modules/word-wrap": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/word-wrap/-/word-wrap-1.2.3.tgz", + "integrity": "sha512-Hz/mrNwitNRh/HUAtM/VT/5VH+ygD6DV7mYKZAtHOrbs8U7lvPS6xf7EJKMF0uW1KJCl0H701g3ZGus+muE5vQ==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/wrappy": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", @@ -6703,6 +8775,18 @@ "engines": { "node": ">= 6" } + }, + "node_modules/yocto-queue": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz", + "integrity": "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } } } } diff --git a/client/package.json b/client/package.json index 454620d..eb352ba 100644 --- a/client/package.json +++ b/client/package.json @@ -7,7 +7,9 @@ "build:dev": "webpack --mode development", "build:watch": "webpack --mode development --watch", "start": "webpack-dev-server --mode production --hot", - "start:dev": "webpack-dev-server --mode development --hot" + "start:dev": "webpack-dev-server --mode development --hot", + "eslint": "eslint ./src --ext .ts", + "eslint:fix": "eslint ./src --ext .ts --fix" }, "keywords": [], "author": "HardManDev , VasaSkor, Alexey Zhuchkov", @@ -16,10 +18,14 @@ "@babel/preset-env": "^7.20.2", "@babel/preset-typescript": "^7.18.6", "@types/node": "^18.11.18", + "@typescript-eslint/eslint-plugin": "^5.50.0", + "@typescript-eslint/parser": "^5.50.0", "autoprefixer": "^10.4.13", "babel-loader": "^9.1.2", "clean-webpack-plugin": "^4.0.0", "css-loader": "^6.7.3", + "eslint": "^8.33.0", + "eslint-config-airbnb-typescript": "^17.0.0", "html-webpack-plugin": "^5.5.0", "mini-css-extract-plugin": "^2.7.2", "postcss": "^8.4.21", diff --git a/client/src/index.ts b/client/src/index.ts index d1bc7ca..6625124 100644 --- a/client/src/index.ts +++ b/client/src/index.ts @@ -1 +1 @@ -import '@styles/main' +import '@styles/main'; diff --git a/client/tsconfig.eslint.json b/client/tsconfig.eslint.json new file mode 100644 index 0000000..2510bea --- /dev/null +++ b/client/tsconfig.eslint.json @@ -0,0 +1,6 @@ +{ + "extends": "./tsconfig.json", + "include": [ + "src/**/*.ts" + ] +} From 266a261a91c94bd845d6880373cfba54ad1f8d93 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 01:39:30 +0300 Subject: [PATCH 006/196] feat: add stylelint with sass config --- .../inspectionProfiles/Project_Default.xml | 1 + client/.idea/stylesheetLinters/stylelint.xml | 6 + client/.stylelintrc.json | 9 + client/package-lock.json | 993 +++++++++++++++++- client/package.json | 8 +- 5 files changed, 1000 insertions(+), 17 deletions(-) create mode 100644 client/.idea/stylesheetLinters/stylelint.xml create mode 100644 client/.stylelintrc.json diff --git a/client/.idea/inspectionProfiles/Project_Default.xml b/client/.idea/inspectionProfiles/Project_Default.xml index 03d9549..7c4836f 100644 --- a/client/.idea/inspectionProfiles/Project_Default.xml +++ b/client/.idea/inspectionProfiles/Project_Default.xml @@ -2,5 +2,6 @@ \ No newline at end of file diff --git a/client/.idea/stylesheetLinters/stylelint.xml b/client/.idea/stylesheetLinters/stylelint.xml new file mode 100644 index 0000000..be1ca11 --- /dev/null +++ b/client/.idea/stylesheetLinters/stylelint.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/client/.stylelintrc.json b/client/.stylelintrc.json new file mode 100644 index 0000000..12ae177 --- /dev/null +++ b/client/.stylelintrc.json @@ -0,0 +1,9 @@ +{ + "extends": "stylelint-config-standard-scss", + "rules": { + "max-line-length": null, + "selector-class-pattern": null, + "scss/no-global-function-names": null, + "scss/at-extend-no-missing-placeholder": null + } +} diff --git a/client/package-lock.json b/client/package-lock.json index f6612d8..69c86fb 100644 --- a/client/package-lock.json +++ b/client/package-lock.json @@ -26,6 +26,8 @@ "postcss-loader": "^7.0.2", "sass": "^1.58.0", "sass-loader": "^13.2.0", + "stylelint": "^14.16.1", + "stylelint-config-standard-scss": "^6.1.0", "typescript": "^4.9.5", "url-loader": "^4.1.1", "webpack": "^5.75.0", @@ -1685,6 +1687,23 @@ "node": ">=6.9.0" } }, + "node_modules/@csstools/selector-specificity": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/@csstools/selector-specificity/-/selector-specificity-2.1.1.tgz", + "integrity": "sha512-jwx+WCqszn53YHOfvFMJJRd/B2GqkCBt+1MJSG6o5/s8+ytHMvDZXsJgUEWLk12UnLd7HYKac4BYU5i/Ron1Cw==", + "dev": true, + "engines": { + "node": "^14 || ^16 || >=18" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/csstools" + }, + "peerDependencies": { + "postcss": "^8.4", + "postcss-selector-parser": "^6.0.10" + } + }, "node_modules/@discoveryjs/json-ext": { "version": "0.5.7", "resolved": "https://registry.npmjs.org/@discoveryjs/json-ext/-/json-ext-0.5.7.tgz", @@ -2037,12 +2056,24 @@ "integrity": "sha512-K0VQKziLUWkVKiRVrx4a40iPaxTUefQmjtkQofBkYRcoaaL/8rhwDWww9qWbrgicNOgnpIsMxyNIUM4+n6dUIA==", "dev": true }, + "node_modules/@types/minimist": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/@types/minimist/-/minimist-1.2.2.tgz", + "integrity": "sha512-jhuKLIRrhvCPLqwPcx6INqmKeiA5EWrsCOPhrlFSrbrmU4ZMPjj5Ul/oLCMDO98XRUIwVm78xICz4EPCektzeQ==", + "dev": true + }, "node_modules/@types/node": { "version": "18.11.18", "resolved": "https://registry.npmjs.org/@types/node/-/node-18.11.18.tgz", "integrity": "sha512-DHQpWGjyQKSHj3ebjFI/wRKcqQcdR+MoFBygntYOZytCqNfkd2ZC4ARDJ2DQqhjH5p85Nnd3jhUJIXrszFX/JA==", "dev": true }, + "node_modules/@types/normalize-package-data": { + "version": "2.4.1", + "resolved": "https://registry.npmjs.org/@types/normalize-package-data/-/normalize-package-data-2.4.1.tgz", + "integrity": "sha512-Gj7cI7z+98M282Tqmp2K5EIsoouUEzbBJhQQzDE3jSIRk6r9gsz0oUokqIUR4u1R3dMHo0pDHM7sNOHyhulypw==", + "dev": true + }, "node_modules/@types/parse-json": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/@types/parse-json/-/parse-json-4.0.0.tgz", @@ -2853,6 +2884,24 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/arrify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", + "integrity": "sha512-3CYzex9M9FGQjCGMGyi6/31c8GJbgb0qGyrx5HWxPd0aCwh4cB2YjMb2Xf9UuoogrMrlO9cTqnB5rI5GHZTcUA==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/astral-regex": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/astral-regex/-/astral-regex-2.0.0.tgz", + "integrity": "sha512-Z7tMw1ytTXt5jqMcOP+OQteU1VuNK9Y02uuJtKQ1Sv69jXQKKg5cibLwGJow8yzZP+eAc18EmLGPal0bp36rvQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, "node_modules/autoprefixer": { "version": "10.4.13", "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.4.13.tgz", @@ -3147,6 +3196,32 @@ "tslib": "^2.0.3" } }, + "node_modules/camelcase": { + "version": "5.3.1", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-5.3.1.tgz", + "integrity": "sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/camelcase-keys": { + "version": "6.2.2", + "resolved": "https://registry.npmjs.org/camelcase-keys/-/camelcase-keys-6.2.2.tgz", + "integrity": "sha512-YrwaA0vEKazPBkn0ipTiMpSajYDSe+KjQfrjhcBMxJt/znbvlHd8Pw/Vamaz5EB4Wfhs3SUR3Z9mwRu/P3s3Yg==", + "dev": true, + "dependencies": { + "camelcase": "^5.3.1", + "map-obj": "^4.0.0", + "quick-lru": "^4.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/caniuse-lite": { "version": "1.0.30001450", "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001450.tgz", @@ -3269,6 +3344,12 @@ "integrity": "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==", "dev": true }, + "node_modules/colord": { + "version": "2.9.3", + "resolved": "https://registry.npmjs.org/colord/-/colord-2.9.3.tgz", + "integrity": "sha512-jeC1axXpnb0/2nn/Y1LPuLdgXBLH7aDcHu4KEKfqw3CUhX7ZpfBSlPKyqXE6btIgEzfWtrX3/tyBCaCvXvMkOw==", + "dev": true + }, "node_modules/colorette": { "version": "2.0.19", "resolved": "https://registry.npmjs.org/colorette/-/colorette-2.0.19.tgz", @@ -3454,6 +3535,15 @@ "node": ">= 8" } }, + "node_modules/css-functions-list": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/css-functions-list/-/css-functions-list-3.1.0.tgz", + "integrity": "sha512-/9lCvYZaUbBGvYUgYGFJ4dcYiyqdhSjG7IPVluoV8A1ILjkF7ilmhp1OGUz8n+nmBcu0RNrQAzgD8B6FJbrt2w==", + "dev": true, + "engines": { + "node": ">=12.22" + } + }, "node_modules/css-loader": { "version": "6.7.3", "resolved": "https://registry.npmjs.org/css-loader/-/css-loader-6.7.3.tgz", @@ -3570,6 +3660,40 @@ } } }, + "node_modules/decamelize": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", + "integrity": "sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/decamelize-keys": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/decamelize-keys/-/decamelize-keys-1.1.1.tgz", + "integrity": "sha512-WiPxgEirIV0/eIOMcnFBA3/IJZAZqKnwAwWyvvdi4lsr1WCN22nhdf/3db3DoZcUjTV2SqfzIwNyp6y2xs3nmg==", + "dev": true, + "dependencies": { + "decamelize": "^1.1.0", + "map-obj": "^1.0.0" + }, + "engines": { + "node": ">=0.10.0" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/decamelize-keys/node_modules/map-obj": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/map-obj/-/map-obj-1.0.1.tgz", + "integrity": "sha512-7N/q3lyZ+LVCp7PzuxrJr4KMbBE2hW7BT7YNia330OFxIf4d3r5zVpicP2650l7CPN6RM9zOJRl3NGpqSiw3Eg==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/deep-is": { "version": "0.1.4", "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.4.tgz", @@ -3784,6 +3908,12 @@ "integrity": "sha512-Vp3CVhmYpgf4iXNKAucoQUDcCrBQX3XLBtwgFqP9BUXuucgvAV9zWp1kYU7LL9j4++s9O+12cb3wMtN4SJy6UQ==", "dev": true }, + "node_modules/emoji-regex": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", + "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", + "dev": true + }, "node_modules/emojis-list": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz", @@ -5009,6 +5139,44 @@ "integrity": "sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==", "dev": true }, + "node_modules/global-modules": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/global-modules/-/global-modules-2.0.0.tgz", + "integrity": "sha512-NGbfmJBp9x8IxyJSd1P+otYK8vonoJactOogrVfFRIAEY1ukil8RSKDz2Yo7wh1oihl51l/r6W4epkeKJHqL8A==", + "dev": true, + "dependencies": { + "global-prefix": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/global-prefix": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/global-prefix/-/global-prefix-3.0.0.tgz", + "integrity": "sha512-awConJSVCHVGND6x3tmMaKcQvwXLhjdkmomy2W+Goaui8YPgYgXJZewhg3fWC+DlfqqQuWg8AwqjGTD2nAPVWg==", + "dev": true, + "dependencies": { + "ini": "^1.3.5", + "kind-of": "^6.0.2", + "which": "^1.3.1" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/global-prefix/node_modules/which": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", + "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", + "dev": true, + "dependencies": { + "isexe": "^2.0.0" + }, + "bin": { + "which": "bin/which" + } + }, "node_modules/globals": { "version": "11.12.0", "resolved": "https://registry.npmjs.org/globals/-/globals-11.12.0.tgz", @@ -5058,6 +5226,12 @@ "node": ">=0.10.0" } }, + "node_modules/globjoin": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/globjoin/-/globjoin-0.1.4.tgz", + "integrity": "sha512-xYfnw62CKG8nLkZBfWbhWwDw02CHty86jfPcc2cr3ZfeuK9ysoVPPEUxf21bAD/rWAgk52SuBrLJlefNy8mvFg==", + "dev": true + }, "node_modules/gopd": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.0.1.tgz", @@ -5088,6 +5262,15 @@ "integrity": "sha512-9Qn4yBxelxoh2Ow62nP+Ka/kMnOXRi8BXnRaUwezLNhqelnN49xKz4F/dPP8OYLxLxq6JDtZb2i9XznUQbNPTg==", "dev": true }, + "node_modules/hard-rejection": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/hard-rejection/-/hard-rejection-2.1.0.tgz", + "integrity": "sha512-VIZB+ibDhx7ObhAe7OVtoEbuP4h/MuOTHJ+J8h/eBXotJYl0fBgR72xDFCKgIh22OJZIOVNxBMWuhAr10r8HdA==", + "dev": true, + "engines": { + "node": ">=6" + } + }, "node_modules/has": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", @@ -5178,6 +5361,36 @@ "he": "bin/he" } }, + "node_modules/hosted-git-info": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-4.1.0.tgz", + "integrity": "sha512-kyCuEOWjJqZuDbRHzL8V93NzQhwIB71oFWSyzVo+KPZI+pnQPPxucdkrOZvkLRnrf5URsQM+IJ09Dw29cRALIA==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/hosted-git-info/node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dev": true, + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/hosted-git-info/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, "node_modules/hpack.js": { "version": "2.1.6", "resolved": "https://registry.npmjs.org/hpack.js/-/hpack.js-2.1.6.tgz", @@ -5247,6 +5460,18 @@ "node": ">=12" } }, + "node_modules/html-tags": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/html-tags/-/html-tags-3.2.0.tgz", + "integrity": "sha512-vy7ClnArOZwCnqZgvv+ddgHgJiAFXe3Ge9ML5/mBctVJoUoYPCdxVucOywjDARn6CVoh3dRSFdPHy2sX80L0Wg==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/html-webpack-plugin": { "version": "5.5.0", "resolved": "https://registry.npmjs.org/html-webpack-plugin/-/html-webpack-plugin-5.5.0.tgz", @@ -5419,6 +5644,15 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/import-lazy": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/import-lazy/-/import-lazy-4.0.0.tgz", + "integrity": "sha512-rKtvo6a868b5Hu3heneU+L4yEQ4jYKLtjpnPeUdK7h0yzXGmyBTypknlkCvHFBqfX9YlorEiMM6Dnq/5atfHkw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, "node_modules/import-local": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/import-local/-/import-local-3.1.0.tgz", @@ -5447,6 +5681,15 @@ "node": ">=0.8.19" } }, + "node_modules/indent-string": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-4.0.0.tgz", + "integrity": "sha512-EdDDZu4A2OyIK7Lr/2zG+w5jmbuk1DVBnEwREQvBzspBJkCEbRa8GxU1lghYcaGJCnRWibjDXlq779X1/y5xwg==", + "dev": true, + "engines": { + "node": ">=8" + } + }, "node_modules/inflight": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", @@ -5463,6 +5706,12 @@ "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", "dev": true }, + "node_modules/ini": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz", + "integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==", + "dev": true + }, "node_modules/internal-slot": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.0.4.tgz", @@ -5618,6 +5867,15 @@ "node": ">=0.10.0" } }, + "node_modules/is-fullwidth-code-point": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz", + "integrity": "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==", + "dev": true, + "engines": { + "node": ">=8" + } + }, "node_modules/is-glob": { "version": "4.0.3", "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", @@ -5983,6 +6241,12 @@ "node": ">= 8" } }, + "node_modules/known-css-properties": { + "version": "0.26.0", + "resolved": "https://registry.npmjs.org/known-css-properties/-/known-css-properties-0.26.0.tgz", + "integrity": "sha512-5FZRzrZzNTBruuurWpvZnvP9pum+fe0HcK8z/ooo+U+Hmp4vtbyp1/QDsqmufirXy4egGzbaH/y2uCZf+6W5Kg==", + "dev": true + }, "node_modules/levn": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", @@ -6055,6 +6319,12 @@ "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", "dev": true }, + "node_modules/lodash.truncate": { + "version": "4.4.2", + "resolved": "https://registry.npmjs.org/lodash.truncate/-/lodash.truncate-4.4.2.tgz", + "integrity": "sha512-jttmRe7bRse52OsWIMDLaXxWqRAmtIUccAQ3garviCqJjafXOfNMO0yMfNpdD6zbGaTU0P5Nz7e7gAT6cKmJRw==", + "dev": true + }, "node_modules/lower-case": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/lower-case/-/lower-case-2.0.2.tgz", @@ -6088,6 +6358,28 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/map-obj": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/map-obj/-/map-obj-4.3.0.tgz", + "integrity": "sha512-hdN1wVrZbb29eBGiGjJbeP8JbKjq1urkHJ/LIP/NY48MZ1QVXUsQBV1G1zvYFHn1XE06cwjBsOI2K3Ulnj1YXQ==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/mathml-tag-names": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/mathml-tag-names/-/mathml-tag-names-2.1.3.tgz", + "integrity": "sha512-APMBEanjybaPzUrfqU0IMU5I0AswKMH7k8OTLs0vvV4KZpExkTkY87nR/zpbuTPj+gARop7aGUbl11pnDfW6xg==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/media-typer": { "version": "0.3.0", "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", @@ -6109,6 +6401,44 @@ "node": ">= 4.0.0" } }, + "node_modules/meow": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/meow/-/meow-9.0.0.tgz", + "integrity": "sha512-+obSblOQmRhcyBt62furQqRAQpNyWXo8BuQ5bN7dG8wmwQ+vwHKp/rCFD4CrTP8CsDQD1sjoZ94K417XEUk8IQ==", + "dev": true, + "dependencies": { + "@types/minimist": "^1.2.0", + "camelcase-keys": "^6.2.2", + "decamelize": "^1.2.0", + "decamelize-keys": "^1.1.0", + "hard-rejection": "^2.1.0", + "minimist-options": "4.1.0", + "normalize-package-data": "^3.0.0", + "read-pkg-up": "^7.0.1", + "redent": "^3.0.0", + "trim-newlines": "^3.0.0", + "type-fest": "^0.18.0", + "yargs-parser": "^20.2.3" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/meow/node_modules/type-fest": { + "version": "0.18.1", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.18.1.tgz", + "integrity": "sha512-OIAYXk8+ISY+qTOwkHtKqzAuxchoMiD9Udx+FSGQDuiRR+PJKJHc2NJAXlbhkGwTt/4/nKZxELY1w3ReWOL8mw==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/merge-descriptors": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", @@ -6194,6 +6524,15 @@ "node": ">=6" } }, + "node_modules/min-indent": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/min-indent/-/min-indent-1.0.1.tgz", + "integrity": "sha512-I9jwMn07Sy/IwOj3zVkVik2JTvgpaykDZEigL6Rx6N9LbMywwUSMtxET+7lVoDLLd3O3IXwJwvuuns8UB/HeAg==", + "dev": true, + "engines": { + "node": ">=4" + } + }, "node_modules/mini-css-extract-plugin": { "version": "2.7.2", "resolved": "https://registry.npmjs.org/mini-css-extract-plugin/-/mini-css-extract-plugin-2.7.2.tgz", @@ -6241,6 +6580,29 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/minimist-options": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/minimist-options/-/minimist-options-4.1.0.tgz", + "integrity": "sha512-Q4r8ghd80yhO/0j1O3B2BjweX3fiHg9cdOwjJd2J76Q135c+NDxGCqdYKQ1SKBuFfgWbAUzBfvYjPUEeNgqN1A==", + "dev": true, + "dependencies": { + "arrify": "^1.0.1", + "is-plain-obj": "^1.1.0", + "kind-of": "^6.0.3" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/minimist-options/node_modules/is-plain-obj": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-1.1.0.tgz", + "integrity": "sha512-yvkRyxmFKEOQ4pNXCmJG5AEQNlXJS5LaONXo5/cLdTZdWvsZ1ioJEonLGAosKlMWE8lwUy/bJzMjcw8az73+Fg==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/ms": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", @@ -6324,34 +6686,82 @@ "integrity": "sha512-2xfmOrRkGogbTK9R6Leda0DGiXeY3p2NJpy4+gNCffdUvV6mdEJnaDEic1i3Ec2djAo8jWYoJMR5PB0MSMpxUA==", "dev": true }, - "node_modules/normalize-path": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", - "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", + "node_modules/normalize-package-data": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-3.0.3.tgz", + "integrity": "sha512-p2W1sgqij3zMMyRC067Dg16bfzVH+w7hyegmpIvZ4JNjqtGOVAIvLmjBx3yP7YTe9vKJgkoNOPjwQGogDoMXFA==", "dev": true, + "dependencies": { + "hosted-git-info": "^4.0.1", + "is-core-module": "^2.5.0", + "semver": "^7.3.4", + "validate-npm-package-license": "^3.0.1" + }, "engines": { - "node": ">=0.10.0" + "node": ">=10" } }, - "node_modules/normalize-range": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/normalize-range/-/normalize-range-0.1.2.tgz", - "integrity": "sha512-bdok/XvKII3nUpklnV6P2hxtMNrCboOjAcyBuQnWEhO665FwrSNRxU+AqpsyvO6LgGYPspN+lu5CLtw4jPRKNA==", + "node_modules/normalize-package-data/node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", "dev": true, + "dependencies": { + "yallist": "^4.0.0" + }, "engines": { - "node": ">=0.10.0" + "node": ">=10" } }, - "node_modules/npm-run-path": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-4.0.1.tgz", - "integrity": "sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw==", + "node_modules/normalize-package-data/node_modules/semver": { + "version": "7.3.8", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.8.tgz", + "integrity": "sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==", "dev": true, "dependencies": { - "path-key": "^3.0.0" + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" }, "engines": { - "node": ">=8" + "node": ">=10" + } + }, + "node_modules/normalize-package-data/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, + "node_modules/normalize-path": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", + "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/normalize-range": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/normalize-range/-/normalize-range-0.1.2.tgz", + "integrity": "sha512-bdok/XvKII3nUpklnV6P2hxtMNrCboOjAcyBuQnWEhO665FwrSNRxU+AqpsyvO6LgGYPspN+lu5CLtw4jPRKNA==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/npm-run-path": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-4.0.1.tgz", + "integrity": "sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw==", + "dev": true, + "dependencies": { + "path-key": "^3.0.0" + }, + "engines": { + "node": ">=8" } }, "node_modules/nth-check": { @@ -6838,6 +7248,12 @@ "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", "dev": true }, + "node_modules/postcss-media-query-parser": { + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/postcss-media-query-parser/-/postcss-media-query-parser-0.2.3.tgz", + "integrity": "sha512-3sOlxmbKcSHMjlUXQZKQ06jOswE7oVkXPxmZdoB1r5l0q6gTFTQSHxNxOrCccElbW7dxNytifNEo8qidX2Vsig==", + "dev": true + }, "node_modules/postcss-modules-extract-imports": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/postcss-modules-extract-imports/-/postcss-modules-extract-imports-3.0.0.tgz", @@ -6897,6 +7313,50 @@ "postcss": "^8.1.0" } }, + "node_modules/postcss-resolve-nested-selector": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/postcss-resolve-nested-selector/-/postcss-resolve-nested-selector-0.1.1.tgz", + "integrity": "sha512-HvExULSwLqHLgUy1rl3ANIqCsvMS0WHss2UOsXhXnQaZ9VCc2oBvIpXrl00IUFT5ZDITME0o6oiXeiHr2SAIfw==", + "dev": true + }, + "node_modules/postcss-safe-parser": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/postcss-safe-parser/-/postcss-safe-parser-6.0.0.tgz", + "integrity": "sha512-FARHN8pwH+WiS2OPCxJI8FuRJpTVnn6ZNFiqAM2aeW2LwTHWWmWgIyKC6cUo0L8aeKiF/14MNvnpls6R2PBeMQ==", + "dev": true, + "engines": { + "node": ">=12.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/postcss/" + }, + "peerDependencies": { + "postcss": "^8.3.3" + } + }, + "node_modules/postcss-scss": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/postcss-scss/-/postcss-scss-4.0.6.tgz", + "integrity": "sha512-rLDPhJY4z/i4nVFZ27j9GqLxj1pwxE80eAzUNRMXtcpipFYIeowerzBgG3yJhMtObGEXidtIgbUpQ3eLDsf5OQ==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/postcss/" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/postcss-scss" + } + ], + "engines": { + "node": ">=12.0" + }, + "peerDependencies": { + "postcss": "^8.4.19" + } + }, "node_modules/postcss-selector-parser": { "version": "6.0.11", "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-6.0.11.tgz", @@ -7007,6 +7467,15 @@ } ] }, + "node_modules/quick-lru": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/quick-lru/-/quick-lru-4.0.1.tgz", + "integrity": "sha512-ARhCpm70fzdcvNQfPoy49IaanKkTlRWF2JMzqhcJbhSFRZv7nPTvZJdcY7301IPmvW+/p0RgIWnQDLJxifsQ7g==", + "dev": true, + "engines": { + "node": ">=8" + } + }, "node_modules/randombytes": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", @@ -7049,6 +7518,83 @@ "node": ">= 0.8" } }, + "node_modules/read-pkg": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-5.2.0.tgz", + "integrity": "sha512-Ug69mNOpfvKDAc2Q8DRpMjjzdtrnv9HcSMX+4VsZxD1aZ6ZzrIE7rlzXBtWTyhULSMKg076AW6WR5iZpD0JiOg==", + "dev": true, + "dependencies": { + "@types/normalize-package-data": "^2.4.0", + "normalize-package-data": "^2.5.0", + "parse-json": "^5.0.0", + "type-fest": "^0.6.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/read-pkg-up": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-7.0.1.tgz", + "integrity": "sha512-zK0TB7Xd6JpCLmlLmufqykGE+/TlOePD6qKClNW7hHDKFh/J7/7gCWGR7joEQEW1bKq3a3yUZSObOoWLFQ4ohg==", + "dev": true, + "dependencies": { + "find-up": "^4.1.0", + "read-pkg": "^5.2.0", + "type-fest": "^0.8.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/read-pkg-up/node_modules/type-fest": { + "version": "0.8.1", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.8.1.tgz", + "integrity": "sha512-4dbzIzqvjtgiM5rw1k5rEHtBANKmdudhGyBEajN01fEyhaAIhsoKNy6y7+IN93IfpFtwY9iqi7kD+xwKhQsNJA==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/read-pkg/node_modules/hosted-git-info": { + "version": "2.8.9", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.8.9.tgz", + "integrity": "sha512-mxIDAb9Lsm6DoOJ7xH+5+X4y1LU/4Hi50L9C5sIswK3JzULS4bwk1FvjdBgvYR4bzT4tuUQiC15FE2f5HbLvYw==", + "dev": true + }, + "node_modules/read-pkg/node_modules/normalize-package-data": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.5.0.tgz", + "integrity": "sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==", + "dev": true, + "dependencies": { + "hosted-git-info": "^2.1.4", + "resolve": "^1.10.0", + "semver": "2 || 3 || 4 || 5", + "validate-npm-package-license": "^3.0.1" + } + }, + "node_modules/read-pkg/node_modules/semver": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz", + "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==", + "dev": true, + "bin": { + "semver": "bin/semver" + } + }, + "node_modules/read-pkg/node_modules/type-fest": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.6.0.tgz", + "integrity": "sha512-q+MB8nYR1KDLrgr4G5yemftpMC7/QLqVndBmEEdqzmNj5dcFOO4Oo8qlwZE3ULT3+Zim1F8Kq4cBnikNhlCMlg==", + "dev": true, + "engines": { + "node": ">=8" + } + }, "node_modules/readable-stream": { "version": "3.6.0", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", @@ -7087,6 +7633,19 @@ "node": ">= 10.13.0" } }, + "node_modules/redent": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/redent/-/redent-3.0.0.tgz", + "integrity": "sha512-6tDA8g98We0zd0GvVeMT9arEOnTw9qM03L9cJXaCjrip1OO764RDBLBfrB4cwzNGDj5OA5ioymC9GkizgWJDUg==", + "dev": true, + "dependencies": { + "indent-string": "^4.0.0", + "strip-indent": "^3.0.0" + }, + "engines": { + "node": ">=8" + } + }, "node_modules/regenerate": { "version": "1.4.2", "resolved": "https://registry.npmjs.org/regenerate/-/regenerate-1.4.2.tgz", @@ -7687,6 +8246,56 @@ "node": ">=8" } }, + "node_modules/slice-ansi": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-4.0.0.tgz", + "integrity": "sha512-qMCMfhY040cVHT43K9BFygqYbUPFZKHOg7K73mtTWJRb8pyP3fzf4Ixd5SzdEJQ6MRUg/WBnOLxghZtKKurENQ==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.0.0", + "astral-regex": "^2.0.0", + "is-fullwidth-code-point": "^3.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/slice-ansi?sponsor=1" + } + }, + "node_modules/slice-ansi/node_modules/ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, + "dependencies": { + "color-convert": "^2.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/slice-ansi/node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/slice-ansi/node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true + }, "node_modules/sockjs": { "version": "0.3.24", "resolved": "https://registry.npmjs.org/sockjs/-/sockjs-0.3.24.tgz", @@ -7726,6 +8335,38 @@ "source-map": "^0.6.0" } }, + "node_modules/spdx-correct": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.1.tgz", + "integrity": "sha512-cOYcUWwhCuHCXi49RhFRCyJEK3iPj1Ziz9DpViV3tbZOwXD49QzIN3MpOLJNxh2qwq2lJJZaKMVw9qNi4jTC0w==", + "dev": true, + "dependencies": { + "spdx-expression-parse": "^3.0.0", + "spdx-license-ids": "^3.0.0" + } + }, + "node_modules/spdx-exceptions": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.3.0.tgz", + "integrity": "sha512-/tTrYOC7PPI1nUAgx34hUpqXuyJG+DTHJTnIULG4rDygi4xu/tfgmq1e1cIRwRzwZgo4NLySi+ricLkZkw4i5A==", + "dev": true + }, + "node_modules/spdx-expression-parse": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-3.0.1.tgz", + "integrity": "sha512-cbqHunsQWnJNE6KhVSMsMeH5H/L9EpymbzqTQ3uLwNCLZ1Q481oWaofqH7nO6V07xlXwY6PhQdQ2IedWx/ZK4Q==", + "dev": true, + "dependencies": { + "spdx-exceptions": "^2.1.0", + "spdx-license-ids": "^3.0.0" + } + }, + "node_modules/spdx-license-ids": { + "version": "3.0.12", + "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.12.tgz", + "integrity": "sha512-rr+VVSXtRhO4OHbXUiAF7xW3Bo9DuuF6C5jH+q/x15j2jniycgKbxU09Hr0WqlSLUs4i4ltHGXqTe7VHclYWyA==", + "dev": true + }, "node_modules/spdy": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/spdy/-/spdy-4.0.2.tgz", @@ -7774,6 +8415,20 @@ "safe-buffer": "~5.2.0" } }, + "node_modules/string-width": { + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", + "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", + "dev": true, + "dependencies": { + "emoji-regex": "^8.0.0", + "is-fullwidth-code-point": "^3.0.0", + "strip-ansi": "^6.0.1" + }, + "engines": { + "node": ">=8" + } + }, "node_modules/string.prototype.trimend": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.6.tgz", @@ -7833,6 +8488,18 @@ "node": ">=6" } }, + "node_modules/strip-indent": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/strip-indent/-/strip-indent-3.0.0.tgz", + "integrity": "sha512-laJTa3Jb+VQpaC6DseHhF7dXVqHTfJPCRDaEbid/drOhgitgYku/letMUqOXFoWV0zIIUbjpdH2t+tYj4bQMRQ==", + "dev": true, + "dependencies": { + "min-indent": "^1.0.0" + }, + "engines": { + "node": ">=8" + } + }, "node_modules/strip-json-comments": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz", @@ -7845,6 +8512,197 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/style-search": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/style-search/-/style-search-0.1.0.tgz", + "integrity": "sha512-Dj1Okke1C3uKKwQcetra4jSuk0DqbzbYtXipzFlFMZtowbF1x7BKJwB9AayVMyFARvU8EDrZdcax4At/452cAg==", + "dev": true + }, + "node_modules/stylelint": { + "version": "14.16.1", + "resolved": "https://registry.npmjs.org/stylelint/-/stylelint-14.16.1.tgz", + "integrity": "sha512-ErlzR/T3hhbV+a925/gbfc3f3Fep9/bnspMiJPorfGEmcBbXdS+oo6LrVtoUZ/w9fqD6o6k7PtUlCOsCRdjX/A==", + "dev": true, + "dependencies": { + "@csstools/selector-specificity": "^2.0.2", + "balanced-match": "^2.0.0", + "colord": "^2.9.3", + "cosmiconfig": "^7.1.0", + "css-functions-list": "^3.1.0", + "debug": "^4.3.4", + "fast-glob": "^3.2.12", + "fastest-levenshtein": "^1.0.16", + "file-entry-cache": "^6.0.1", + "global-modules": "^2.0.0", + "globby": "^11.1.0", + "globjoin": "^0.1.4", + "html-tags": "^3.2.0", + "ignore": "^5.2.1", + "import-lazy": "^4.0.0", + "imurmurhash": "^0.1.4", + "is-plain-object": "^5.0.0", + "known-css-properties": "^0.26.0", + "mathml-tag-names": "^2.1.3", + "meow": "^9.0.0", + "micromatch": "^4.0.5", + "normalize-path": "^3.0.0", + "picocolors": "^1.0.0", + "postcss": "^8.4.19", + "postcss-media-query-parser": "^0.2.3", + "postcss-resolve-nested-selector": "^0.1.1", + "postcss-safe-parser": "^6.0.0", + "postcss-selector-parser": "^6.0.11", + "postcss-value-parser": "^4.2.0", + "resolve-from": "^5.0.0", + "string-width": "^4.2.3", + "strip-ansi": "^6.0.1", + "style-search": "^0.1.0", + "supports-hyperlinks": "^2.3.0", + "svg-tags": "^1.0.0", + "table": "^6.8.1", + "v8-compile-cache": "^2.3.0", + "write-file-atomic": "^4.0.2" + }, + "bin": { + "stylelint": "bin/stylelint.js" + }, + "engines": { + "node": "^12.20.0 || ^14.13.1 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/stylelint" + } + }, + "node_modules/stylelint-config-recommended": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/stylelint-config-recommended/-/stylelint-config-recommended-9.0.0.tgz", + "integrity": "sha512-9YQSrJq4NvvRuTbzDsWX3rrFOzOlYBmZP+o513BJN/yfEmGSr0AxdvrWs0P/ilSpVV/wisamAHu5XSk8Rcf4CQ==", + "dev": true, + "peerDependencies": { + "stylelint": "^14.10.0" + } + }, + "node_modules/stylelint-config-recommended-scss": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/stylelint-config-recommended-scss/-/stylelint-config-recommended-scss-8.0.0.tgz", + "integrity": "sha512-BxjxEzRaZoQb7Iinc3p92GS6zRdRAkIuEu2ZFLTxJK2e1AIcCb5B5MXY9KOXdGTnYFZ+KKx6R4Fv9zU6CtMYPQ==", + "dev": true, + "dependencies": { + "postcss-scss": "^4.0.2", + "stylelint-config-recommended": "^9.0.0", + "stylelint-scss": "^4.0.0" + }, + "peerDependencies": { + "postcss": "^8.3.3", + "stylelint": "^14.10.0" + }, + "peerDependenciesMeta": { + "postcss": { + "optional": true + } + } + }, + "node_modules/stylelint-config-standard": { + "version": "29.0.0", + "resolved": "https://registry.npmjs.org/stylelint-config-standard/-/stylelint-config-standard-29.0.0.tgz", + "integrity": "sha512-uy8tZLbfq6ZrXy4JKu3W+7lYLgRQBxYTUUB88vPgQ+ZzAxdrvcaSUW9hOMNLYBnwH+9Kkj19M2DHdZ4gKwI7tg==", + "dev": true, + "dependencies": { + "stylelint-config-recommended": "^9.0.0" + }, + "peerDependencies": { + "stylelint": "^14.14.0" + } + }, + "node_modules/stylelint-config-standard-scss": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/stylelint-config-standard-scss/-/stylelint-config-standard-scss-6.1.0.tgz", + "integrity": "sha512-iZ2B5kQT2G3rUzx+437cEpdcnFOQkwnwqXuY8Z0QUwIHQVE8mnYChGAquyKFUKZRZ0pRnrciARlPaR1RBtPb0Q==", + "dev": true, + "dependencies": { + "stylelint-config-recommended-scss": "^8.0.0", + "stylelint-config-standard": "^29.0.0" + }, + "peerDependencies": { + "postcss": "^8.3.3", + "stylelint": "^14.14.0" + }, + "peerDependenciesMeta": { + "postcss": { + "optional": true + } + } + }, + "node_modules/stylelint-scss": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/stylelint-scss/-/stylelint-scss-4.3.0.tgz", + "integrity": "sha512-GvSaKCA3tipzZHoz+nNO7S02ZqOsdBzMiCx9poSmLlb3tdJlGddEX/8QzCOD8O7GQan9bjsvLMsO5xiw6IhhIQ==", + "dev": true, + "dependencies": { + "lodash": "^4.17.21", + "postcss-media-query-parser": "^0.2.3", + "postcss-resolve-nested-selector": "^0.1.1", + "postcss-selector-parser": "^6.0.6", + "postcss-value-parser": "^4.1.0" + }, + "peerDependencies": { + "stylelint": "^14.5.1" + } + }, + "node_modules/stylelint/node_modules/array-union": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/array-union/-/array-union-2.1.0.tgz", + "integrity": "sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/stylelint/node_modules/balanced-match": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-2.0.0.tgz", + "integrity": "sha512-1ugUSr8BHXRnK23KfuYS+gVMC3LB8QGH9W1iGtDPsNWoQbgtXSExkBu2aDR4epiGWZOjZsj6lDl/N/AqqTC3UA==", + "dev": true + }, + "node_modules/stylelint/node_modules/globby": { + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/globby/-/globby-11.1.0.tgz", + "integrity": "sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g==", + "dev": true, + "dependencies": { + "array-union": "^2.1.0", + "dir-glob": "^3.0.1", + "fast-glob": "^3.2.9", + "ignore": "^5.2.0", + "merge2": "^1.4.1", + "slash": "^3.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/stylelint/node_modules/is-plain-object": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-5.0.0.tgz", + "integrity": "sha512-VRSzKkbMm5jMDoKLbltAkFQ5Qr7VDiTFGXxYFXXowVj387GeGNOCsOH6Msy00SGZ3Fp84b1Naa1psqgcCIEP5Q==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/stylelint/node_modules/resolve-from": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz", + "integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, "node_modules/supports-color": { "version": "5.5.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", @@ -7857,6 +8715,40 @@ "node": ">=4" } }, + "node_modules/supports-hyperlinks": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/supports-hyperlinks/-/supports-hyperlinks-2.3.0.tgz", + "integrity": "sha512-RpsAZlpWcDwOPQA22aCH4J0t7L8JmAvsCxfOSEwm7cQs3LshN36QaTkwd70DnBOXDWGssw2eUoc8CaRWT0XunA==", + "dev": true, + "dependencies": { + "has-flag": "^4.0.0", + "supports-color": "^7.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/supports-hyperlinks/node_modules/has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/supports-hyperlinks/node_modules/supports-color": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", + "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, "node_modules/supports-preserve-symlinks-flag": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", @@ -7869,6 +8761,28 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/svg-tags": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/svg-tags/-/svg-tags-1.0.0.tgz", + "integrity": "sha512-ovssysQTa+luh7A5Weu3Rta6FJlFBBbInjOh722LIt6klpU2/HtdUbszju/G4devcvk8PGt7FCLv5wftu3THUA==", + "dev": true + }, + "node_modules/table": { + "version": "6.8.1", + "resolved": "https://registry.npmjs.org/table/-/table-6.8.1.tgz", + "integrity": "sha512-Y4X9zqrCftUhMeH2EptSSERdVKt/nEdijTOacGD/97EKjhQ/Qs8RTlEGABSJNNN8lac9kheH+af7yAkEWlgneA==", + "dev": true, + "dependencies": { + "ajv": "^8.0.1", + "lodash.truncate": "^4.4.2", + "slice-ansi": "^4.0.0", + "string-width": "^4.2.3", + "strip-ansi": "^6.0.1" + }, + "engines": { + "node": ">=10.0.0" + } + }, "node_modules/tapable": { "version": "2.2.1", "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz", @@ -8027,6 +8941,15 @@ "node": ">=0.6" } }, + "node_modules/trim-newlines": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/trim-newlines/-/trim-newlines-3.0.1.tgz", + "integrity": "sha512-c1PTsA3tYrIsLGkJkzHF+w9F2EyxfXGo4UyJc4pFL++FMjnq0HJS69T3M7d//gKrFKwy429bouPescbjecU+Zw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, "node_modules/tsconfig-paths": { "version": "3.14.1", "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.14.1.tgz", @@ -8349,6 +9272,22 @@ "uuid": "dist/bin/uuid" } }, + "node_modules/v8-compile-cache": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz", + "integrity": "sha512-l8lCEmLcLYZh4nbunNZvQCJc5pv7+RCwa8q/LdUx8u7lsWvPDKmpodJAJNwkAhJC//dFY48KuIEmjtd4RViDrA==", + "dev": true + }, + "node_modules/validate-npm-package-license": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.4.tgz", + "integrity": "sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==", + "dev": true, + "dependencies": { + "spdx-correct": "^3.0.0", + "spdx-expression-parse": "^3.0.0" + } + }, "node_modules/vary": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", @@ -8740,6 +9679,19 @@ "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", "dev": true }, + "node_modules/write-file-atomic": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-4.0.2.tgz", + "integrity": "sha512-7KxauUdBmSdWnmpaGFg+ppNjKF8uNLry8LyzjauQDOVONfFLNKrKvQOxZ/VuTIcS/gge/YNahf5RIIQWTSarlg==", + "dev": true, + "dependencies": { + "imurmurhash": "^0.1.4", + "signal-exit": "^3.0.7" + }, + "engines": { + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" + } + }, "node_modules/ws": { "version": "8.12.0", "resolved": "https://registry.npmjs.org/ws/-/ws-8.12.0.tgz", @@ -8776,6 +9728,15 @@ "node": ">= 6" } }, + "node_modules/yargs-parser": { + "version": "20.2.9", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-20.2.9.tgz", + "integrity": "sha512-y11nGElTIV+CT3Zv9t7VKl+Q3hTQoT9a1Qzezhhl6Rp21gJ/IVTW7Z3y9EWXhuUBC2Shnf+DX0antecpAwSP8w==", + "dev": true, + "engines": { + "node": ">=10" + } + }, "node_modules/yocto-queue": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz", diff --git a/client/package.json b/client/package.json index eb352ba..1cda9ce 100644 --- a/client/package.json +++ b/client/package.json @@ -8,8 +8,12 @@ "build:watch": "webpack --mode development --watch", "start": "webpack-dev-server --mode production --hot", "start:dev": "webpack-dev-server --mode development --hot", + "lint": "npm run eslint && npm run stylelint", + "lint:fix": "npm run eslint:fix && npm run stylelint:fix", "eslint": "eslint ./src --ext .ts", - "eslint:fix": "eslint ./src --ext .ts --fix" + "eslint:fix": "eslint ./src --ext .ts --fix", + "stylelint": "stylelint ./src/**/*.scss", + "stylelint:fix": "stylelint ./src/**/*.scss --fix" }, "keywords": [], "author": "HardManDev , VasaSkor, Alexey Zhuchkov", @@ -32,6 +36,8 @@ "postcss-loader": "^7.0.2", "sass": "^1.58.0", "sass-loader": "^13.2.0", + "stylelint": "^14.16.1", + "stylelint-config-standard-scss": "^6.1.0", "typescript": "^4.9.5", "url-loader": "^4.1.1", "webpack": "^5.75.0", From bd2261bb5f8a8e4ba7136b2ed87d840c222318ec Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 02:20:43 +0300 Subject: [PATCH 007/196] init: nest new server project --- client/.idea/misc.xml | 7 + client/.idea/workspace.xml | 142 + server/.eslintrc.json | 51 + server/.idea/.gitignore | 6 + .../inspectionProfiles/Project_Default.xml | 6 + server/.idea/jsLinters/eslint.xml | 6 + server/.idea/modules.xml | 8 + server/.idea/server.iml | 12 + server/.idea/vcs.xml | 6 + server/nest-cli.json | 8 + server/package-lock.json | 9209 +++++++++++++++++ server/package.json | 67 + server/src/app.controller.ts | 14 + server/src/app.module.ts | 12 + server/src/app.service.ts | 10 + server/src/main.ts | 11 + server/tsconfig.build.json | 4 + server/tsconfig.json | 21 + 18 files changed, 9600 insertions(+) create mode 100644 client/.idea/misc.xml create mode 100644 client/.idea/workspace.xml create mode 100644 server/.eslintrc.json create mode 100644 server/.idea/.gitignore create mode 100644 server/.idea/inspectionProfiles/Project_Default.xml create mode 100644 server/.idea/jsLinters/eslint.xml create mode 100644 server/.idea/modules.xml create mode 100644 server/.idea/server.iml create mode 100644 server/.idea/vcs.xml create mode 100644 server/nest-cli.json create mode 100644 server/package-lock.json create mode 100644 server/package.json create mode 100644 server/src/app.controller.ts create mode 100644 server/src/app.module.ts create mode 100644 server/src/app.service.ts create mode 100644 server/src/main.ts create mode 100644 server/tsconfig.build.json create mode 100644 server/tsconfig.json diff --git a/client/.idea/misc.xml b/client/.idea/misc.xml new file mode 100644 index 0000000..30bab2a --- /dev/null +++ b/client/.idea/misc.xml @@ -0,0 +1,7 @@ + + + + + \ No newline at end of file diff --git a/client/.idea/workspace.xml b/client/.idea/workspace.xml new file mode 100644 index 0000000..88b81cb --- /dev/null +++ b/client/.idea/workspace.xml @@ -0,0 +1,142 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + 1675540728000 + + + 1675540954239 + + + 1675541118737 + + + 1675541696041 + + + 1675545875673 + + + 1675547769856 + + + 1675550093677 + + + 1675550371091 + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/server/.eslintrc.json b/server/.eslintrc.json new file mode 100644 index 0000000..fa62d77 --- /dev/null +++ b/server/.eslintrc.json @@ -0,0 +1,51 @@ +{ + "root": true, + "env": { + "node": true, + "jest": true + }, + "plugins": [ + "@typescript-eslint/eslint-plugin" + ], + "extends": [ + "airbnb-base", + "airbnb-typescript/base", + "eslint:recommended", + "plugin:@typescript-eslint/recommended" + ], + "parser": "@typescript-eslint/parser", + "parserOptions": { + "project": "tsconfig.json", + "sourceType": "module" + }, + "rules": { + "no-param-reassign": "off", + "class-methods-use-this": "warn", + "@typescript-eslint/interface-name-prefix": "off", + "@typescript-eslint/explicit-function-return-type": "off", + "@typescript-eslint/explicit-module-boundary-types": "off", + "@typescript-eslint/no-explicit-any": "off", + "max-len": [ + "error", + { + "code": 80, + "tabWidth": 2, + "ignoreComments": true, + "ignoreTrailingComments": true, + "ignoreUrls": true, + "ignoreStrings": true, + "ignoreTemplateLiterals": true, + "ignoreRegExpLiterals": true + } + ], + "max-lines-per-function": [ + "warn", + { + "max": 40, + "skipBlankLines": true, + "skipComments": true, + "IIFEs": true + } + ] + } +} diff --git a/server/.idea/.gitignore b/server/.idea/.gitignore new file mode 100644 index 0000000..df8562c --- /dev/null +++ b/server/.idea/.gitignore @@ -0,0 +1,6 @@ +# Default ignored files +/shelf/ +/workspace.xml +misc.xml +# Editor-based HTTP Client requests +/httpRequests/ diff --git a/server/.idea/inspectionProfiles/Project_Default.xml b/server/.idea/inspectionProfiles/Project_Default.xml new file mode 100644 index 0000000..03d9549 --- /dev/null +++ b/server/.idea/inspectionProfiles/Project_Default.xml @@ -0,0 +1,6 @@ + + + + \ No newline at end of file diff --git a/server/.idea/jsLinters/eslint.xml b/server/.idea/jsLinters/eslint.xml new file mode 100644 index 0000000..541945b --- /dev/null +++ b/server/.idea/jsLinters/eslint.xml @@ -0,0 +1,6 @@ + + + + + \ No newline at end of file diff --git a/server/.idea/modules.xml b/server/.idea/modules.xml new file mode 100644 index 0000000..fbd90b4 --- /dev/null +++ b/server/.idea/modules.xml @@ -0,0 +1,8 @@ + + + + + + + + \ No newline at end of file diff --git a/server/.idea/server.iml b/server/.idea/server.iml new file mode 100644 index 0000000..0c8867d --- /dev/null +++ b/server/.idea/server.iml @@ -0,0 +1,12 @@ + + + + + + + + + + + + \ No newline at end of file diff --git a/server/.idea/vcs.xml b/server/.idea/vcs.xml new file mode 100644 index 0000000..6c0b863 --- /dev/null +++ b/server/.idea/vcs.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/server/nest-cli.json b/server/nest-cli.json new file mode 100644 index 0000000..f9aa683 --- /dev/null +++ b/server/nest-cli.json @@ -0,0 +1,8 @@ +{ + "$schema": "https://json.schemastore.org/nest-cli", + "collection": "@nestjs/schematics", + "sourceRoot": "src", + "compilerOptions": { + "deleteOutDir": true + } +} diff --git a/server/package-lock.json b/server/package-lock.json new file mode 100644 index 0000000..8db2af1 --- /dev/null +++ b/server/package-lock.json @@ -0,0 +1,9209 @@ +{ + "name": "rs-clone-server", + "version": "0.0.1", + "lockfileVersion": 3, + "requires": true, + "packages": { + "": { + "name": "rs-clone-server", + "version": "0.0.1", + "license": "MIT", + "dependencies": { + "@nestjs/common": "^9.0.0", + "@nestjs/core": "^9.0.0", + "@nestjs/platform-express": "^9.0.0", + "reflect-metadata": "^0.1.13", + "rxjs": "^7.2.0" + }, + "devDependencies": { + "@nestjs/cli": "^9.0.0", + "@nestjs/schematics": "^9.0.0", + "@nestjs/testing": "^9.0.0", + "@types/express": "^4.17.13", + "@types/jest": "29.2.4", + "@types/node": "18.11.18", + "@types/supertest": "^2.0.11", + "@typescript-eslint/eslint-plugin": "^5.50.0", + "@typescript-eslint/parser": "^5.50.0", + "eslint": "^8.2.0", + "eslint-config-airbnb-base": "^15.0.0", + "eslint-config-airbnb-typescript": "^17.0.0", + "jest": "29.3.1", + "source-map-support": "^0.5.20", + "supertest": "^6.1.3", + "ts-jest": "29.0.3", + "ts-loader": "^9.2.3", + "ts-node": "^10.0.0", + "tsconfig-paths": "4.1.1", + "typescript": "^4.7.4" + } + }, + "node_modules/@ampproject/remapping": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@ampproject/remapping/-/remapping-2.2.0.tgz", + "integrity": "sha512-qRmjj8nj9qmLTQXXmaR1cck3UXSRMPrbsLJAasZpF+t3riI71BXed5ebIOYwQntykeZuhjsdweEc9BxH5Jc26w==", + "dev": true, + "dependencies": { + "@jridgewell/gen-mapping": "^0.1.0", + "@jridgewell/trace-mapping": "^0.3.9" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@angular-devkit/core": { + "version": "15.1.4", + "resolved": "https://registry.npmjs.org/@angular-devkit/core/-/core-15.1.4.tgz", + "integrity": "sha512-PW5MRmd9DHJR4FaXchwQtj9pXnsghSTnwRvfZeCRNYgU2sv0DKyTV+YTSJB+kNXnoPNG1Je6amDEkiXecpspXg==", + "dev": true, + "dependencies": { + "ajv": "8.12.0", + "ajv-formats": "2.1.1", + "jsonc-parser": "3.2.0", + "rxjs": "6.6.7", + "source-map": "0.7.4" + }, + "engines": { + "node": "^14.20.0 || ^16.13.0 || >=18.10.0", + "npm": "^6.11.0 || ^7.5.6 || >=8.0.0", + "yarn": ">= 1.13.0" + }, + "peerDependencies": { + "chokidar": "^3.5.2" + }, + "peerDependenciesMeta": { + "chokidar": { + "optional": true + } + } + }, + "node_modules/@angular-devkit/core/node_modules/rxjs": { + "version": "6.6.7", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.6.7.tgz", + "integrity": "sha512-hTdwr+7yYNIT5n4AMYp85KA6yw2Va0FLa3Rguvbpa4W3I5xynaBZo41cM3XM+4Q6fRMj3sBYIR1VAmZMXYJvRQ==", + "dev": true, + "dependencies": { + "tslib": "^1.9.0" + }, + "engines": { + "npm": ">=2.0.0" + } + }, + "node_modules/@angular-devkit/core/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "dev": true + }, + "node_modules/@angular-devkit/schematics": { + "version": "15.1.4", + "resolved": "https://registry.npmjs.org/@angular-devkit/schematics/-/schematics-15.1.4.tgz", + "integrity": "sha512-jpddxo9Qd2yRQ1t9FLhAx5S+luz6HkyhDytq0LFKbxf9ikf1J4oy9riPBFl4pRmrNARWcHZ6GbD20/Ky8PjmXQ==", + "dev": true, + "dependencies": { + "@angular-devkit/core": "15.1.4", + "jsonc-parser": "3.2.0", + "magic-string": "0.27.0", + "ora": "5.4.1", + "rxjs": "6.6.7" + }, + "engines": { + "node": "^14.20.0 || ^16.13.0 || >=18.10.0", + "npm": "^6.11.0 || ^7.5.6 || >=8.0.0", + "yarn": ">= 1.13.0" + } + }, + "node_modules/@angular-devkit/schematics-cli": { + "version": "15.1.4", + "resolved": "https://registry.npmjs.org/@angular-devkit/schematics-cli/-/schematics-cli-15.1.4.tgz", + "integrity": "sha512-qkM5Mfs28jZzNcJnSM6RlyrKkYvzhQmWFTxBXnn15k5T4EnSs1gI6O054Xn7jo/senfwNNt7h2Mlz2OmBLo6+w==", + "dev": true, + "dependencies": { + "@angular-devkit/core": "15.1.4", + "@angular-devkit/schematics": "15.1.4", + "ansi-colors": "4.1.3", + "inquirer": "8.2.4", + "symbol-observable": "4.0.0", + "yargs-parser": "21.1.1" + }, + "bin": { + "schematics": "bin/schematics.js" + }, + "engines": { + "node": "^14.20.0 || ^16.13.0 || >=18.10.0", + "npm": "^6.11.0 || ^7.5.6 || >=8.0.0", + "yarn": ">= 1.13.0" + } + }, + "node_modules/@angular-devkit/schematics-cli/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/@angular-devkit/schematics-cli/node_modules/inquirer": { + "version": "8.2.4", + "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-8.2.4.tgz", + "integrity": "sha512-nn4F01dxU8VeKfq192IjLsxu0/OmMZ4Lg3xKAns148rCaXP6ntAoEkVYZThWjwON8AlzdZZi6oqnhNbxUG9hVg==", + "dev": true, + "dependencies": { + "ansi-escapes": "^4.2.1", + "chalk": "^4.1.1", + "cli-cursor": "^3.1.0", + "cli-width": "^3.0.0", + "external-editor": "^3.0.3", + "figures": "^3.0.0", + "lodash": "^4.17.21", + "mute-stream": "0.0.8", + "ora": "^5.4.1", + "run-async": "^2.4.0", + "rxjs": "^7.5.5", + "string-width": "^4.1.0", + "strip-ansi": "^6.0.0", + "through": "^2.3.6", + "wrap-ansi": "^7.0.0" + }, + "engines": { + "node": ">=12.0.0" + } + }, + "node_modules/@angular-devkit/schematics/node_modules/rxjs": { + "version": "6.6.7", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.6.7.tgz", + "integrity": "sha512-hTdwr+7yYNIT5n4AMYp85KA6yw2Va0FLa3Rguvbpa4W3I5xynaBZo41cM3XM+4Q6fRMj3sBYIR1VAmZMXYJvRQ==", + "dev": true, + "dependencies": { + "tslib": "^1.9.0" + }, + "engines": { + "npm": ">=2.0.0" + } + }, + "node_modules/@angular-devkit/schematics/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "dev": true + }, + "node_modules/@babel/code-frame": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.18.6.tgz", + "integrity": "sha512-TDCmlK5eOvH+eH7cdAFlNXeVJqWIQ7gW9tY1GJIpUtFb6CmjVyq2VM3u71bOyR8CRihcCgMUYoDNyLXao3+70Q==", + "dev": true, + "dependencies": { + "@babel/highlight": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/compat-data": { + "version": "7.20.14", + "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.20.14.tgz", + "integrity": "sha512-0YpKHD6ImkWMEINCyDAD0HLLUH/lPCefG8ld9it8DJB2wnApraKuhgYTvTY1z7UFIfBTGy5LwncZ+5HWWGbhFw==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/core": { + "version": "7.20.12", + "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.20.12.tgz", + "integrity": "sha512-XsMfHovsUYHFMdrIHkZphTN/2Hzzi78R08NuHfDBehym2VsPDL6Zn/JAD/JQdnRvbSsbQc4mVaU1m6JgtTEElg==", + "dev": true, + "dependencies": { + "@ampproject/remapping": "^2.1.0", + "@babel/code-frame": "^7.18.6", + "@babel/generator": "^7.20.7", + "@babel/helper-compilation-targets": "^7.20.7", + "@babel/helper-module-transforms": "^7.20.11", + "@babel/helpers": "^7.20.7", + "@babel/parser": "^7.20.7", + "@babel/template": "^7.20.7", + "@babel/traverse": "^7.20.12", + "@babel/types": "^7.20.7", + "convert-source-map": "^1.7.0", + "debug": "^4.1.0", + "gensync": "^1.0.0-beta.2", + "json5": "^2.2.2", + "semver": "^6.3.0" + }, + "engines": { + "node": ">=6.9.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/babel" + } + }, + "node_modules/@babel/core/node_modules/convert-source-map": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.9.0.tgz", + "integrity": "sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A==", + "dev": true + }, + "node_modules/@babel/core/node_modules/semver": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "dev": true, + "bin": { + "semver": "bin/semver.js" + } + }, + "node_modules/@babel/generator": { + "version": "7.20.14", + "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.20.14.tgz", + "integrity": "sha512-AEmuXHdcD3A52HHXxaTmYlb8q/xMEhoRP67B3T4Oq7lbmSoqroMZzjnGj3+i1io3pdnF8iBYVu4Ilj+c4hBxYg==", + "dev": true, + "dependencies": { + "@babel/types": "^7.20.7", + "@jridgewell/gen-mapping": "^0.3.2", + "jsesc": "^2.5.1" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/generator/node_modules/@jridgewell/gen-mapping": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.2.tgz", + "integrity": "sha512-mh65xKQAzI6iBcFzwv28KVWSmCkdRBWoOh+bYQGW3+6OZvbbN3TqMGo5hqYxQniRcH9F2VZIoJCm4pa3BPDK/A==", + "dev": true, + "dependencies": { + "@jridgewell/set-array": "^1.0.1", + "@jridgewell/sourcemap-codec": "^1.4.10", + "@jridgewell/trace-mapping": "^0.3.9" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@babel/helper-compilation-targets": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/helper-compilation-targets/-/helper-compilation-targets-7.20.7.tgz", + "integrity": "sha512-4tGORmfQcrc+bvrjb5y3dG9Mx1IOZjsHqQVUz7XCNHO+iTmqxWnVg3KRygjGmpRLJGdQSKuvFinbIb0CnZwHAQ==", + "dev": true, + "dependencies": { + "@babel/compat-data": "^7.20.5", + "@babel/helper-validator-option": "^7.18.6", + "browserslist": "^4.21.3", + "lru-cache": "^5.1.1", + "semver": "^6.3.0" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/@babel/helper-compilation-targets/node_modules/semver": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "dev": true, + "bin": { + "semver": "bin/semver.js" + } + }, + "node_modules/@babel/helper-environment-visitor": { + "version": "7.18.9", + "resolved": "https://registry.npmjs.org/@babel/helper-environment-visitor/-/helper-environment-visitor-7.18.9.tgz", + "integrity": "sha512-3r/aACDJ3fhQ/EVgFy0hpj8oHyHpQc+LPtJoY9SzTThAsStm4Ptegq92vqKoE3vD706ZVFWITnMnxucw+S9Ipg==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-function-name": { + "version": "7.19.0", + "resolved": "https://registry.npmjs.org/@babel/helper-function-name/-/helper-function-name-7.19.0.tgz", + "integrity": "sha512-WAwHBINyrpqywkUH0nTnNgI5ina5TFn85HKS0pbPDfxFfhyR/aNQEn4hGi1P1JyT//I0t4OgXUlofzWILRvS5w==", + "dev": true, + "dependencies": { + "@babel/template": "^7.18.10", + "@babel/types": "^7.19.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-hoist-variables": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/helper-hoist-variables/-/helper-hoist-variables-7.18.6.tgz", + "integrity": "sha512-UlJQPkFqFULIcyW5sbzgbkxn2FKRgwWiRexcuaR8RNJRy8+LLveqPjwZV/bwrLZCN0eUHD/x8D0heK1ozuoo6Q==", + "dev": true, + "dependencies": { + "@babel/types": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-module-imports": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.18.6.tgz", + "integrity": "sha512-0NFvs3VkuSYbFi1x2Vd6tKrywq+z/cLeYC/RJNFrIX/30Bf5aiGYbtvGXolEktzJH8o5E5KJ3tT+nkxuuZFVlA==", + "dev": true, + "dependencies": { + "@babel/types": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-module-transforms": { + "version": "7.20.11", + "resolved": "https://registry.npmjs.org/@babel/helper-module-transforms/-/helper-module-transforms-7.20.11.tgz", + "integrity": "sha512-uRy78kN4psmji1s2QtbtcCSaj/LILFDp0f/ymhpQH5QY3nljUZCaNWz9X1dEj/8MBdBEFECs7yRhKn8i7NjZgg==", + "dev": true, + "dependencies": { + "@babel/helper-environment-visitor": "^7.18.9", + "@babel/helper-module-imports": "^7.18.6", + "@babel/helper-simple-access": "^7.20.2", + "@babel/helper-split-export-declaration": "^7.18.6", + "@babel/helper-validator-identifier": "^7.19.1", + "@babel/template": "^7.20.7", + "@babel/traverse": "^7.20.10", + "@babel/types": "^7.20.7" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-plugin-utils": { + "version": "7.20.2", + "resolved": "https://registry.npmjs.org/@babel/helper-plugin-utils/-/helper-plugin-utils-7.20.2.tgz", + "integrity": "sha512-8RvlJG2mj4huQ4pZ+rU9lqKi9ZKiRmuvGuM2HlWmkmgOhbs6zEAw6IEiJ5cQqGbDzGZOhwuOQNtZMi/ENLjZoQ==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-simple-access": { + "version": "7.20.2", + "resolved": "https://registry.npmjs.org/@babel/helper-simple-access/-/helper-simple-access-7.20.2.tgz", + "integrity": "sha512-+0woI/WPq59IrqDYbVGfshjT5Dmk/nnbdpcF8SnMhhXObpTq2KNBdLFRFrkVdbDOyUmHBCxzm5FHV1rACIkIbA==", + "dev": true, + "dependencies": { + "@babel/types": "^7.20.2" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-split-export-declaration": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.18.6.tgz", + "integrity": "sha512-bde1etTx6ZyTmobl9LLMMQsaizFVZrquTEHOqKeQESMKo4PlObf+8+JA25ZsIpZhT/WEd39+vOdLXAFG/nELpA==", + "dev": true, + "dependencies": { + "@babel/types": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-string-parser": { + "version": "7.19.4", + "resolved": "https://registry.npmjs.org/@babel/helper-string-parser/-/helper-string-parser-7.19.4.tgz", + "integrity": "sha512-nHtDoQcuqFmwYNYPz3Rah5ph2p8PFeFCsZk9A/48dPc/rGocJ5J3hAAZ7pb76VWX3fZKu+uEr/FhH5jLx7umrw==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-validator-identifier": { + "version": "7.19.1", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.19.1.tgz", + "integrity": "sha512-awrNfaMtnHUr653GgGEs++LlAvW6w+DcPrOliSMXWCKo597CwL5Acf/wWdNkf/tfEQE3mjkeD1YOVZOUV/od1w==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helper-validator-option": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/helper-validator-option/-/helper-validator-option-7.18.6.tgz", + "integrity": "sha512-XO7gESt5ouv/LRJdrVjkShckw6STTaB7l9BrpBaAHDeF5YZT+01PCwmR0SJHnkW6i8OwW/EVWRShfi4j2x+KQw==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/helpers": { + "version": "7.20.13", + "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.20.13.tgz", + "integrity": "sha512-nzJ0DWCL3gB5RCXbUO3KIMMsBY2Eqbx8mBpKGE/02PgyRQFcPQLbkQ1vyy596mZLaP+dAfD+R4ckASzNVmW3jg==", + "dev": true, + "dependencies": { + "@babel/template": "^7.20.7", + "@babel/traverse": "^7.20.13", + "@babel/types": "^7.20.7" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/highlight": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.18.6.tgz", + "integrity": "sha512-u7stbOuYjaPezCuLj29hNW1v64M2Md2qupEKP1fHc7WdOA3DgLh37suiSrZYY7haUB7iBeQZ9P1uiRF359do3g==", + "dev": true, + "dependencies": { + "@babel/helper-validator-identifier": "^7.18.6", + "chalk": "^2.0.0", + "js-tokens": "^4.0.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/highlight/node_modules/ansi-styles": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", + "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dev": true, + "dependencies": { + "color-convert": "^1.9.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/highlight/node_modules/chalk": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dev": true, + "dependencies": { + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/highlight/node_modules/color-convert": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", + "dev": true, + "dependencies": { + "color-name": "1.1.3" + } + }, + "node_modules/@babel/highlight/node_modules/color-name": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", + "integrity": "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==", + "dev": true + }, + "node_modules/@babel/highlight/node_modules/escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", + "dev": true, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/@babel/highlight/node_modules/has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/highlight/node_modules/supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, + "dependencies": { + "has-flag": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/parser": { + "version": "7.20.15", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.20.15.tgz", + "integrity": "sha512-DI4a1oZuf8wC+oAJA9RW6ga3Zbe8RZFt7kD9i4qAspz3I/yHet1VvC3DiSy/fsUvv5pvJuNPh0LPOdCcqinDPg==", + "dev": true, + "bin": { + "parser": "bin/babel-parser.js" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@babel/plugin-syntax-async-generators": { + "version": "7.8.4", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-async-generators/-/plugin-syntax-async-generators-7.8.4.tgz", + "integrity": "sha512-tycmZxkGfZaxhMRbXlPXuVFpdWlXpir2W4AMhSJgRKzk/eDlIXOhb2LHWoLpDF7TEHylV5zNhykX6KAgHJmTNw==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-bigint": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-bigint/-/plugin-syntax-bigint-7.8.3.tgz", + "integrity": "sha512-wnTnFlG+YxQm3vDxpGE57Pj0srRU4sHE/mDkt1qv2YJJSeUAec2ma4WLUnUPeKjyrfntVwe/N6dCXpU+zL3Npg==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-class-properties": { + "version": "7.12.13", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-class-properties/-/plugin-syntax-class-properties-7.12.13.tgz", + "integrity": "sha512-fm4idjKla0YahUNgFNLCB0qySdsoPiZP3iQE3rky0mBUtMZ23yDJ9SJdg6dXTSDnulOVqiF3Hgr9nbXvXTQZYA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.12.13" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-import-meta": { + "version": "7.10.4", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-meta/-/plugin-syntax-import-meta-7.10.4.tgz", + "integrity": "sha512-Yqfm+XDx0+Prh3VSeEQCPU81yC+JWZ2pDPFSS4ZdpfZhp4MkFMaDC1UqseovEKwSUpnIL7+vK+Clp7bfh0iD7g==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.10.4" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-json-strings": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-json-strings/-/plugin-syntax-json-strings-7.8.3.tgz", + "integrity": "sha512-lY6kdGpWHvjoe2vk4WrAapEuBR69EMxZl+RoGRhrFGNYVK8mOPAW8VfbT/ZgrFbXlDNiiaxQnAtgVCZ6jv30EA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-jsx": { + "version": "7.18.6", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-jsx/-/plugin-syntax-jsx-7.18.6.tgz", + "integrity": "sha512-6mmljtAedFGTWu2p/8WIORGwy+61PLgOMPOdazc7YoJ9ZCWUyFy3A6CpPkRKLKD1ToAesxX8KGEViAiLo9N+7Q==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.18.6" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-logical-assignment-operators": { + "version": "7.10.4", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-logical-assignment-operators/-/plugin-syntax-logical-assignment-operators-7.10.4.tgz", + "integrity": "sha512-d8waShlpFDinQ5MtvGU9xDAOzKH47+FFoney2baFIoMr952hKOLp1HR7VszoZvOsV/4+RRszNY7D17ba0te0ig==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.10.4" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-nullish-coalescing-operator": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-nullish-coalescing-operator/-/plugin-syntax-nullish-coalescing-operator-7.8.3.tgz", + "integrity": "sha512-aSff4zPII1u2QD7y+F8oDsz19ew4IGEJg9SVW+bqwpwtfFleiQDMdzA/R+UlWDzfnHFCxxleFT0PMIrR36XLNQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-numeric-separator": { + "version": "7.10.4", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-numeric-separator/-/plugin-syntax-numeric-separator-7.10.4.tgz", + "integrity": "sha512-9H6YdfkcK/uOnY/K7/aA2xpzaAgkQn37yzWUMRK7OaPOqOpGS1+n0H5hxT9AUw9EsSjPW8SVyMJwYRtWs3X3ug==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.10.4" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-object-rest-spread": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-object-rest-spread/-/plugin-syntax-object-rest-spread-7.8.3.tgz", + "integrity": "sha512-XoqMijGZb9y3y2XskN+P1wUGiVwWZ5JmoDRwx5+3GmEplNyVM2s2Dg8ILFQm8rWM48orGy5YpI5Bl8U1y7ydlA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-optional-catch-binding": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-optional-catch-binding/-/plugin-syntax-optional-catch-binding-7.8.3.tgz", + "integrity": "sha512-6VPD0Pc1lpTqw0aKoeRTMiB+kWhAoT24PA+ksWSBrFtl5SIRVpZlwN3NNPQjehA2E/91FV3RjLWoVTglWcSV3Q==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-optional-chaining": { + "version": "7.8.3", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-optional-chaining/-/plugin-syntax-optional-chaining-7.8.3.tgz", + "integrity": "sha512-KoK9ErH1MBlCPxV0VANkXW2/dw4vlbGDrFgz8bmUsBGYkFRcbRwMh6cIJubdPrkxRwuGdtCk0v/wPTKbQgBjkg==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.8.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-top-level-await": { + "version": "7.14.5", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-top-level-await/-/plugin-syntax-top-level-await-7.14.5.tgz", + "integrity": "sha512-hx++upLv5U1rgYfwe1xBQUhRmU41NEvpUvrp8jkrSCdvGSnM5/qdRMtylJ6PG5OFkBaHkbTAKTnd3/YyESRHFw==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.14.5" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/plugin-syntax-typescript": { + "version": "7.20.0", + "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-typescript/-/plugin-syntax-typescript-7.20.0.tgz", + "integrity": "sha512-rd9TkG+u1CExzS4SM1BlMEhMXwFLKVjOAFFCDx9PbX5ycJWDoWMcwdJH9RhkPu1dOgn5TrxLot/Gx6lWFuAUNQ==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.19.0" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/template": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.20.7.tgz", + "integrity": "sha512-8SegXApWe6VoNw0r9JHpSteLKTpTiLZ4rMlGIm9JQ18KiCtyQiAMEazujAHrUS5flrcqYZa75ukev3P6QmUwUw==", + "dev": true, + "dependencies": { + "@babel/code-frame": "^7.18.6", + "@babel/parser": "^7.20.7", + "@babel/types": "^7.20.7" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/traverse": { + "version": "7.20.13", + "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.20.13.tgz", + "integrity": "sha512-kMJXfF0T6DIS9E8cgdLCSAL+cuCK+YEZHWiLK0SXpTo8YRj5lpJu3CDNKiIBCne4m9hhTIqUg6SYTAI39tAiVQ==", + "dev": true, + "dependencies": { + "@babel/code-frame": "^7.18.6", + "@babel/generator": "^7.20.7", + "@babel/helper-environment-visitor": "^7.18.9", + "@babel/helper-function-name": "^7.19.0", + "@babel/helper-hoist-variables": "^7.18.6", + "@babel/helper-split-export-declaration": "^7.18.6", + "@babel/parser": "^7.20.13", + "@babel/types": "^7.20.7", + "debug": "^4.1.0", + "globals": "^11.1.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@babel/traverse/node_modules/globals": { + "version": "11.12.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-11.12.0.tgz", + "integrity": "sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/types": { + "version": "7.20.7", + "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.20.7.tgz", + "integrity": "sha512-69OnhBxSSgK0OzTJai4kyPDiKTIe3j+ctaHdIGVbRahTLAT7L3R9oeXHC2aVSuGYt3cVnoAMDmOCgJ2yaiLMvg==", + "dev": true, + "dependencies": { + "@babel/helper-string-parser": "^7.19.4", + "@babel/helper-validator-identifier": "^7.19.1", + "to-fast-properties": "^2.0.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/@bcoe/v8-coverage": { + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/@bcoe/v8-coverage/-/v8-coverage-0.2.3.tgz", + "integrity": "sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw==", + "dev": true + }, + "node_modules/@colors/colors": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/@colors/colors/-/colors-1.5.0.tgz", + "integrity": "sha512-ooWCrlZP11i8GImSjTHYHLkvFDP48nS4+204nGb1RiX/WXYHmJA2III9/e2DWVabCESdW7hBAEzHRqUn9OUVvQ==", + "dev": true, + "optional": true, + "engines": { + "node": ">=0.1.90" + } + }, + "node_modules/@cspotcode/source-map-support": { + "version": "0.8.1", + "resolved": "https://registry.npmjs.org/@cspotcode/source-map-support/-/source-map-support-0.8.1.tgz", + "integrity": "sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw==", + "dev": true, + "dependencies": { + "@jridgewell/trace-mapping": "0.3.9" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/@cspotcode/source-map-support/node_modules/@jridgewell/trace-mapping": { + "version": "0.3.9", + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.9.tgz", + "integrity": "sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==", + "dev": true, + "dependencies": { + "@jridgewell/resolve-uri": "^3.0.3", + "@jridgewell/sourcemap-codec": "^1.4.10" + } + }, + "node_modules/@eslint/eslintrc": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.4.1.tgz", + "integrity": "sha512-XXrH9Uarn0stsyldqDYq8r++mROmWRI1xKMXa640Bb//SY1+ECYX6VzT6Lcx5frD0V30XieqJ0oX9I2Xj5aoMA==", + "dev": true, + "dependencies": { + "ajv": "^6.12.4", + "debug": "^4.3.2", + "espree": "^9.4.0", + "globals": "^13.19.0", + "ignore": "^5.2.0", + "import-fresh": "^3.2.1", + "js-yaml": "^4.1.0", + "minimatch": "^3.1.2", + "strip-json-comments": "^3.1.1" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/@eslint/eslintrc/node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/@eslint/eslintrc/node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "node_modules/@humanwhocodes/config-array": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.6.0.tgz", + "integrity": "sha512-JQlEKbcgEUjBFhLIF4iqM7u/9lwgHRBcpHrmUNCALK0Q3amXN6lxdoXLnF0sm11E9VqTmBALR87IlUg1bZ8A9A==", + "dev": true, + "dependencies": { + "@humanwhocodes/object-schema": "^1.2.0", + "debug": "^4.1.1", + "minimatch": "^3.0.4" + }, + "engines": { + "node": ">=10.10.0" + } + }, + "node_modules/@humanwhocodes/object-schema": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@humanwhocodes/object-schema/-/object-schema-1.2.1.tgz", + "integrity": "sha512-ZnQMnLV4e7hDlUvw8H+U8ASL02SS2Gn6+9Ac3wGGLIe7+je2AeAOxPY+izIPJDfFDb7eDjev0Us8MO1iFRN8hA==", + "dev": true + }, + "node_modules/@istanbuljs/load-nyc-config": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/@istanbuljs/load-nyc-config/-/load-nyc-config-1.1.0.tgz", + "integrity": "sha512-VjeHSlIzpv/NyD3N0YuHfXOPDIixcA1q2ZV98wsMqcYlPmv2n3Yb2lYP9XMElnaFVXg5A7YLTeLu6V84uQDjmQ==", + "dev": true, + "dependencies": { + "camelcase": "^5.3.1", + "find-up": "^4.1.0", + "get-package-type": "^0.1.0", + "js-yaml": "^3.13.1", + "resolve-from": "^5.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/@istanbuljs/load-nyc-config/node_modules/argparse": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", + "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", + "dev": true, + "dependencies": { + "sprintf-js": "~1.0.2" + } + }, + "node_modules/@istanbuljs/load-nyc-config/node_modules/find-up": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", + "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", + "dev": true, + "dependencies": { + "locate-path": "^5.0.0", + "path-exists": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/@istanbuljs/load-nyc-config/node_modules/js-yaml": { + "version": "3.14.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.14.1.tgz", + "integrity": "sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==", + "dev": true, + "dependencies": { + "argparse": "^1.0.7", + "esprima": "^4.0.0" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" + } + }, + "node_modules/@istanbuljs/load-nyc-config/node_modules/locate-path": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", + "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", + "dev": true, + "dependencies": { + "p-locate": "^4.1.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/@istanbuljs/load-nyc-config/node_modules/p-limit": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", + "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", + "dev": true, + "dependencies": { + "p-try": "^2.0.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/@istanbuljs/load-nyc-config/node_modules/p-locate": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", + "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", + "dev": true, + "dependencies": { + "p-limit": "^2.2.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/@istanbuljs/load-nyc-config/node_modules/resolve-from": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz", + "integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/@istanbuljs/schema": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/@istanbuljs/schema/-/schema-0.1.3.tgz", + "integrity": "sha512-ZXRY4jNvVgSVQ8DL3LTcakaAtXwTVUxE81hslsyD2AtoXW/wVob10HkOJ1X/pAlcI7D+2YoZKg5do8G/w6RYgA==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/@jest/console": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/@jest/console/-/console-29.4.1.tgz", + "integrity": "sha512-m+XpwKSi3PPM9znm5NGS8bBReeAJJpSkL1OuFCqaMaJL2YX9YXLkkI+MBchMPwu+ZuM2rynL51sgfkQteQ1CKQ==", + "dev": true, + "dependencies": { + "@jest/types": "^29.4.1", + "@types/node": "*", + "chalk": "^4.0.0", + "jest-message-util": "^29.4.1", + "jest-util": "^29.4.1", + "slash": "^3.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/console/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/@jest/core": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/@jest/core/-/core-29.4.1.tgz", + "integrity": "sha512-RXFTohpBqpaTebNdg5l3I5yadnKo9zLBajMT0I38D0tDhreVBYv3fA8kywthI00sWxPztWLD3yjiUkewwu/wKA==", + "dev": true, + "dependencies": { + "@jest/console": "^29.4.1", + "@jest/reporters": "^29.4.1", + "@jest/test-result": "^29.4.1", + "@jest/transform": "^29.4.1", + "@jest/types": "^29.4.1", + "@types/node": "*", + "ansi-escapes": "^4.2.1", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "exit": "^0.1.2", + "graceful-fs": "^4.2.9", + "jest-changed-files": "^29.4.0", + "jest-config": "^29.4.1", + "jest-haste-map": "^29.4.1", + "jest-message-util": "^29.4.1", + "jest-regex-util": "^29.2.0", + "jest-resolve": "^29.4.1", + "jest-resolve-dependencies": "^29.4.1", + "jest-runner": "^29.4.1", + "jest-runtime": "^29.4.1", + "jest-snapshot": "^29.4.1", + "jest-util": "^29.4.1", + "jest-validate": "^29.4.1", + "jest-watcher": "^29.4.1", + "micromatch": "^4.0.4", + "pretty-format": "^29.4.1", + "slash": "^3.0.0", + "strip-ansi": "^6.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + }, + "peerDependencies": { + "node-notifier": "^8.0.1 || ^9.0.0 || ^10.0.0" + }, + "peerDependenciesMeta": { + "node-notifier": { + "optional": true + } + } + }, + "node_modules/@jest/core/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/@jest/environment": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/@jest/environment/-/environment-29.4.1.tgz", + "integrity": "sha512-pJ14dHGSQke7Q3mkL/UZR9ZtTOxqskZaC91NzamEH4dlKRt42W+maRBXiw/LWkdJe+P0f/zDR37+SPMplMRlPg==", + "dev": true, + "dependencies": { + "@jest/fake-timers": "^29.4.1", + "@jest/types": "^29.4.1", + "@types/node": "*", + "jest-mock": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/expect": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/@jest/expect/-/expect-29.4.1.tgz", + "integrity": "sha512-ZxKJP5DTUNF2XkpJeZIzvnzF1KkfrhEF6Rz0HGG69fHl6Bgx5/GoU3XyaeFYEjuuKSOOsbqD/k72wFvFxc3iTw==", + "dev": true, + "dependencies": { + "expect": "^29.4.1", + "jest-snapshot": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/expect-utils": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/@jest/expect-utils/-/expect-utils-29.4.1.tgz", + "integrity": "sha512-w6YJMn5DlzmxjO00i9wu2YSozUYRBhIoJ6nQwpMYcBMtiqMGJm1QBzOf6DDgRao8dbtpDoaqLg6iiQTvv0UHhQ==", + "dev": true, + "dependencies": { + "jest-get-type": "^29.2.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/fake-timers": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/@jest/fake-timers/-/fake-timers-29.4.1.tgz", + "integrity": "sha512-/1joI6rfHFmmm39JxNfmNAO3Nwm6Y0VoL5fJDy7H1AtWrD1CgRtqJbN9Ld6rhAkGO76qqp4cwhhxJ9o9kYjQMw==", + "dev": true, + "dependencies": { + "@jest/types": "^29.4.1", + "@sinonjs/fake-timers": "^10.0.2", + "@types/node": "*", + "jest-message-util": "^29.4.1", + "jest-mock": "^29.4.1", + "jest-util": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/globals": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/@jest/globals/-/globals-29.4.1.tgz", + "integrity": "sha512-znoK2EuFytbHH0ZSf2mQK2K1xtIgmaw4Da21R2C/NE/+NnItm5mPEFQmn8gmF3f0rfOlmZ3Y3bIf7bFj7DHxAA==", + "dev": true, + "dependencies": { + "@jest/environment": "^29.4.1", + "@jest/expect": "^29.4.1", + "@jest/types": "^29.4.1", + "jest-mock": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/reporters": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/@jest/reporters/-/reporters-29.4.1.tgz", + "integrity": "sha512-AISY5xpt2Xpxj9R6y0RF1+O6GRy9JsGa8+vK23Lmzdy1AYcpQn5ItX79wJSsTmfzPKSAcsY1LNt/8Y5Xe5LOSg==", + "dev": true, + "dependencies": { + "@bcoe/v8-coverage": "^0.2.3", + "@jest/console": "^29.4.1", + "@jest/test-result": "^29.4.1", + "@jest/transform": "^29.4.1", + "@jest/types": "^29.4.1", + "@jridgewell/trace-mapping": "^0.3.15", + "@types/node": "*", + "chalk": "^4.0.0", + "collect-v8-coverage": "^1.0.0", + "exit": "^0.1.2", + "glob": "^7.1.3", + "graceful-fs": "^4.2.9", + "istanbul-lib-coverage": "^3.0.0", + "istanbul-lib-instrument": "^5.1.0", + "istanbul-lib-report": "^3.0.0", + "istanbul-lib-source-maps": "^4.0.0", + "istanbul-reports": "^3.1.3", + "jest-message-util": "^29.4.1", + "jest-util": "^29.4.1", + "jest-worker": "^29.4.1", + "slash": "^3.0.0", + "string-length": "^4.0.1", + "strip-ansi": "^6.0.0", + "v8-to-istanbul": "^9.0.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + }, + "peerDependencies": { + "node-notifier": "^8.0.1 || ^9.0.0 || ^10.0.0" + }, + "peerDependenciesMeta": { + "node-notifier": { + "optional": true + } + } + }, + "node_modules/@jest/reporters/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/@jest/schemas": { + "version": "29.4.0", + "resolved": "https://registry.npmjs.org/@jest/schemas/-/schemas-29.4.0.tgz", + "integrity": "sha512-0E01f/gOZeNTG76i5eWWSupvSHaIINrTie7vCyjiYFKgzNdyEGd12BUv4oNBFHOqlHDbtoJi3HrQ38KCC90NsQ==", + "dev": true, + "dependencies": { + "@sinclair/typebox": "^0.25.16" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/source-map": { + "version": "29.2.0", + "resolved": "https://registry.npmjs.org/@jest/source-map/-/source-map-29.2.0.tgz", + "integrity": "sha512-1NX9/7zzI0nqa6+kgpSdKPK+WU1p+SJk3TloWZf5MzPbxri9UEeXX5bWZAPCzbQcyuAzubcdUHA7hcNznmRqWQ==", + "dev": true, + "dependencies": { + "@jridgewell/trace-mapping": "^0.3.15", + "callsites": "^3.0.0", + "graceful-fs": "^4.2.9" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/test-result": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/@jest/test-result/-/test-result-29.4.1.tgz", + "integrity": "sha512-WRt29Lwt+hEgfN8QDrXqXGgCTidq1rLyFqmZ4lmJOpVArC8daXrZWkWjiaijQvgd3aOUj2fM8INclKHsQW9YyQ==", + "dev": true, + "dependencies": { + "@jest/console": "^29.4.1", + "@jest/types": "^29.4.1", + "@types/istanbul-lib-coverage": "^2.0.0", + "collect-v8-coverage": "^1.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/test-sequencer": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/@jest/test-sequencer/-/test-sequencer-29.4.1.tgz", + "integrity": "sha512-v5qLBNSsM0eHzWLXsQ5fiB65xi49A3ILPSFQKPXzGL4Vyux0DPZAIN7NAFJa9b4BiTDP9MBF/Zqc/QA1vuiJ0w==", + "dev": true, + "dependencies": { + "@jest/test-result": "^29.4.1", + "graceful-fs": "^4.2.9", + "jest-haste-map": "^29.4.1", + "slash": "^3.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/transform": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/@jest/transform/-/transform-29.4.1.tgz", + "integrity": "sha512-5w6YJrVAtiAgr0phzKjYd83UPbCXsBRTeYI4BXokv9Er9CcrH9hfXL/crCvP2d2nGOcovPUnlYiLPFLZrkG5Hg==", + "dev": true, + "dependencies": { + "@babel/core": "^7.11.6", + "@jest/types": "^29.4.1", + "@jridgewell/trace-mapping": "^0.3.15", + "babel-plugin-istanbul": "^6.1.1", + "chalk": "^4.0.0", + "convert-source-map": "^2.0.0", + "fast-json-stable-stringify": "^2.1.0", + "graceful-fs": "^4.2.9", + "jest-haste-map": "^29.4.1", + "jest-regex-util": "^29.2.0", + "jest-util": "^29.4.1", + "micromatch": "^4.0.4", + "pirates": "^4.0.4", + "slash": "^3.0.0", + "write-file-atomic": "^5.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/transform/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/@jest/types": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-29.4.1.tgz", + "integrity": "sha512-zbrAXDUOnpJ+FMST2rV7QZOgec8rskg2zv8g2ajeqitp4tvZiyqTCYXANrKsM+ryj5o+LI+ZN2EgU9drrkiwSA==", + "dev": true, + "dependencies": { + "@jest/schemas": "^29.4.0", + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^17.0.8", + "chalk": "^4.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/@jest/types/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/@jridgewell/gen-mapping": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.1.1.tgz", + "integrity": "sha512-sQXCasFk+U8lWYEe66WxRDOE9PjVz4vSM51fTu3Hw+ClTpUSQb718772vH3pyS5pShp6lvQM7SxgIDXXXmOX7w==", + "dev": true, + "dependencies": { + "@jridgewell/set-array": "^1.0.0", + "@jridgewell/sourcemap-codec": "^1.4.10" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/resolve-uri": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.0.tgz", + "integrity": "sha512-F2msla3tad+Mfht5cJq7LSXcdudKTWCVYUgw6pLFOOHSTtZlj6SWNYAp+AhuqLmWdBO2X5hPrLcu8cVP8fy28w==", + "dev": true, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/set-array": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.1.2.tgz", + "integrity": "sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==", + "dev": true, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/source-map": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.2.tgz", + "integrity": "sha512-m7O9o2uR8k2ObDysZYzdfhb08VuEml5oWGiosa1VdaPZ/A6QyPkAJuwN0Q1lhULOf6B7MtQmHENS743hWtCrgw==", + "dev": true, + "dependencies": { + "@jridgewell/gen-mapping": "^0.3.0", + "@jridgewell/trace-mapping": "^0.3.9" + } + }, + "node_modules/@jridgewell/source-map/node_modules/@jridgewell/gen-mapping": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.2.tgz", + "integrity": "sha512-mh65xKQAzI6iBcFzwv28KVWSmCkdRBWoOh+bYQGW3+6OZvbbN3TqMGo5hqYxQniRcH9F2VZIoJCm4pa3BPDK/A==", + "dev": true, + "dependencies": { + "@jridgewell/set-array": "^1.0.1", + "@jridgewell/sourcemap-codec": "^1.4.10", + "@jridgewell/trace-mapping": "^0.3.9" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/sourcemap-codec": { + "version": "1.4.14", + "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.14.tgz", + "integrity": "sha512-XPSJHWmi394fuUuzDnGz1wiKqWfo1yXecHQMRf2l6hztTO+nPru658AyDngaBe7isIxEkRsPR3FZh+s7iVa4Uw==", + "dev": true + }, + "node_modules/@jridgewell/trace-mapping": { + "version": "0.3.17", + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.17.tgz", + "integrity": "sha512-MCNzAp77qzKca9+W/+I0+sEpaUnZoeasnghNeVc41VZCEKaCH73Vq3BZZ/SzWIgrqE4H4ceI+p+b6C0mHf9T4g==", + "dev": true, + "dependencies": { + "@jridgewell/resolve-uri": "3.1.0", + "@jridgewell/sourcemap-codec": "1.4.14" + } + }, + "node_modules/@lukeed/csprng": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@lukeed/csprng/-/csprng-1.0.1.tgz", + "integrity": "sha512-uSvJdwQU5nK+Vdf6zxcWAY2A8r7uqe+gePwLWzJ+fsQehq18pc0I2hJKwypZ2aLM90+Er9u1xn4iLJPZ+xlL4g==", + "engines": { + "node": ">=8" + } + }, + "node_modules/@nestjs/cli": { + "version": "9.2.0", + "resolved": "https://registry.npmjs.org/@nestjs/cli/-/cli-9.2.0.tgz", + "integrity": "sha512-6B1IjDcJbrOu55oMF67L1x5lDUOZ3Zs9l7bKCBH9D78965m8wq/2rlEWl/gJto5TABLQWy3hVvV/s8VzUlRMxw==", + "dev": true, + "dependencies": { + "@angular-devkit/core": "15.1.4", + "@angular-devkit/schematics": "15.1.4", + "@angular-devkit/schematics-cli": "15.1.4", + "@nestjs/schematics": "^9.0.0", + "chalk": "3.0.0", + "chokidar": "3.5.3", + "cli-table3": "0.6.3", + "commander": "4.1.1", + "fork-ts-checker-webpack-plugin": "7.3.0", + "inquirer": "7.3.3", + "node-emoji": "1.11.0", + "ora": "5.4.1", + "os-name": "4.0.1", + "rimraf": "4.1.2", + "shelljs": "0.8.5", + "source-map-support": "0.5.21", + "tree-kill": "1.2.2", + "tsconfig-paths": "4.1.2", + "tsconfig-paths-webpack-plugin": "4.0.0", + "typescript": "4.9.5", + "webpack": "5.75.0", + "webpack-node-externals": "3.0.0" + }, + "bin": { + "nest": "bin/nest.js" + }, + "engines": { + "node": ">= 12.9.0" + } + }, + "node_modules/@nestjs/cli/node_modules/strip-bom": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", + "integrity": "sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/@nestjs/cli/node_modules/tsconfig-paths": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-4.1.2.tgz", + "integrity": "sha512-uhxiMgnXQp1IR622dUXI+9Ehnws7i/y6xvpZB9IbUVOPy0muvdvgXeZOn88UcGPiT98Vp3rJPTa8bFoalZ3Qhw==", + "dev": true, + "dependencies": { + "json5": "^2.2.2", + "minimist": "^1.2.6", + "strip-bom": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/@nestjs/common": { + "version": "9.3.2", + "resolved": "https://registry.npmjs.org/@nestjs/common/-/common-9.3.2.tgz", + "integrity": "sha512-YUqY9qPMxiMqO/pRNXJehR18LFL6Y9BN5Qn0FylVbdpKd7/QKZHVWRKNaAYNu0mGfyJhRJI6oEr/1Tn5GEo6GQ==", + "dependencies": { + "iterare": "1.2.1", + "tslib": "2.5.0", + "uid": "2.0.1" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/nest" + }, + "peerDependencies": { + "cache-manager": "<=5", + "class-transformer": "*", + "class-validator": "*", + "reflect-metadata": "^0.1.12", + "rxjs": "^7.1.0" + }, + "peerDependenciesMeta": { + "cache-manager": { + "optional": true + }, + "class-transformer": { + "optional": true + }, + "class-validator": { + "optional": true + } + } + }, + "node_modules/@nestjs/core": { + "version": "9.3.2", + "resolved": "https://registry.npmjs.org/@nestjs/core/-/core-9.3.2.tgz", + "integrity": "sha512-79h4RvGAGFIIZJWIXqZ8xvhK/kIY6Fay7a1P0W4v7AUZsMIuNksct0uMzHaBqMT0lo+Ei+gU8PaWvzZt5lZvJw==", + "hasInstallScript": true, + "dependencies": { + "@nuxtjs/opencollective": "0.3.2", + "fast-safe-stringify": "2.1.1", + "iterare": "1.2.1", + "object-hash": "3.0.0", + "path-to-regexp": "3.2.0", + "tslib": "2.5.0", + "uuid": "9.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/nest" + }, + "peerDependencies": { + "@nestjs/common": "^9.0.0", + "@nestjs/microservices": "^9.0.0", + "@nestjs/platform-express": "^9.0.0", + "@nestjs/websockets": "^9.0.0", + "reflect-metadata": "^0.1.12", + "rxjs": "^7.1.0" + }, + "peerDependenciesMeta": { + "@nestjs/microservices": { + "optional": true + }, + "@nestjs/platform-express": { + "optional": true + }, + "@nestjs/websockets": { + "optional": true + } + } + }, + "node_modules/@nestjs/platform-express": { + "version": "9.3.2", + "resolved": "https://registry.npmjs.org/@nestjs/platform-express/-/platform-express-9.3.2.tgz", + "integrity": "sha512-hzLfUcJIFw8NIPlG88QJr+uSgJzkBkhxVsHGtRs+rNShzlMNfX63CPbkI4yfG4Eq0s8oYe598p6OE5O1z924Dg==", + "dependencies": { + "body-parser": "1.20.1", + "cors": "2.8.5", + "express": "4.18.2", + "multer": "1.4.4-lts.1", + "tslib": "2.5.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/nest" + }, + "peerDependencies": { + "@nestjs/common": "^9.0.0", + "@nestjs/core": "^9.0.0" + } + }, + "node_modules/@nestjs/schematics": { + "version": "9.0.4", + "resolved": "https://registry.npmjs.org/@nestjs/schematics/-/schematics-9.0.4.tgz", + "integrity": "sha512-egurCfAc4e5i1r2TmeAF0UrOKejFmT5oTdv4b7HcOVPupc3QGU7CbEfGleL3mkM5AjrixTQeMxU9bJ00ttAbGg==", + "dev": true, + "dependencies": { + "@angular-devkit/core": "15.0.4", + "@angular-devkit/schematics": "15.0.4", + "fs-extra": "11.1.0", + "jsonc-parser": "3.2.0", + "pluralize": "8.0.0" + }, + "peerDependencies": { + "typescript": "^4.3.5" + } + }, + "node_modules/@nestjs/schematics/node_modules/@angular-devkit/core": { + "version": "15.0.4", + "resolved": "https://registry.npmjs.org/@angular-devkit/core/-/core-15.0.4.tgz", + "integrity": "sha512-4ITpRAevd652SxB+qNesIQ9qfbm7wT5UBU5kJOPPwGL77I21g8CQpkmV1n5VSacPvC9Zbz90feOWexf7w7JzcA==", + "dev": true, + "dependencies": { + "ajv": "8.11.0", + "ajv-formats": "2.1.1", + "jsonc-parser": "3.2.0", + "rxjs": "6.6.7", + "source-map": "0.7.4" + }, + "engines": { + "node": "^14.20.0 || ^16.13.0 || >=18.10.0", + "npm": "^6.11.0 || ^7.5.6 || >=8.0.0", + "yarn": ">= 1.13.0" + }, + "peerDependencies": { + "chokidar": "^3.5.2" + }, + "peerDependenciesMeta": { + "chokidar": { + "optional": true + } + } + }, + "node_modules/@nestjs/schematics/node_modules/@angular-devkit/schematics": { + "version": "15.0.4", + "resolved": "https://registry.npmjs.org/@angular-devkit/schematics/-/schematics-15.0.4.tgz", + "integrity": "sha512-/gXiLFS0+xFdx6wPoBpe/c6/K9I5edMpaASqPf4XheKtrsSvL+qTlIi3nsbfItzOiDXbaBmlbxGfkMHz/yg0Ig==", + "dev": true, + "dependencies": { + "@angular-devkit/core": "15.0.4", + "jsonc-parser": "3.2.0", + "magic-string": "0.26.7", + "ora": "5.4.1", + "rxjs": "6.6.7" + }, + "engines": { + "node": "^14.20.0 || ^16.13.0 || >=18.10.0", + "npm": "^6.11.0 || ^7.5.6 || >=8.0.0", + "yarn": ">= 1.13.0" + } + }, + "node_modules/@nestjs/schematics/node_modules/ajv": { + "version": "8.11.0", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.11.0.tgz", + "integrity": "sha512-wGgprdCvMalC0BztXvitD2hC04YffAvtsUn93JbGXYLAtCUO4xd17mCCZQxUOItiBwZvJScWo8NIvQMQ71rdpg==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "json-schema-traverse": "^1.0.0", + "require-from-string": "^2.0.2", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/@nestjs/schematics/node_modules/magic-string": { + "version": "0.26.7", + "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.26.7.tgz", + "integrity": "sha512-hX9XH3ziStPoPhJxLq1syWuZMxbDvGNbVchfrdCtanC7D13888bMFow61x8axrx+GfHLtVeAx2kxL7tTGRl+Ow==", + "dev": true, + "dependencies": { + "sourcemap-codec": "^1.4.8" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/@nestjs/schematics/node_modules/rxjs": { + "version": "6.6.7", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.6.7.tgz", + "integrity": "sha512-hTdwr+7yYNIT5n4AMYp85KA6yw2Va0FLa3Rguvbpa4W3I5xynaBZo41cM3XM+4Q6fRMj3sBYIR1VAmZMXYJvRQ==", + "dev": true, + "dependencies": { + "tslib": "^1.9.0" + }, + "engines": { + "npm": ">=2.0.0" + } + }, + "node_modules/@nestjs/schematics/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "dev": true + }, + "node_modules/@nestjs/testing": { + "version": "9.3.2", + "resolved": "https://registry.npmjs.org/@nestjs/testing/-/testing-9.3.2.tgz", + "integrity": "sha512-A1DleYwUpA/MX4XLTOJYEkhEjdI0HyujTmOUoPzSplAPWXbR48DTtY3Pu3A/qM7A8JwPzfB37glFUAJvFFOYpg==", + "dev": true, + "dependencies": { + "tslib": "2.5.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/nest" + }, + "peerDependencies": { + "@nestjs/common": "^9.0.0", + "@nestjs/core": "^9.0.0", + "@nestjs/microservices": "^9.0.0", + "@nestjs/platform-express": "^9.0.0" + }, + "peerDependenciesMeta": { + "@nestjs/microservices": { + "optional": true + }, + "@nestjs/platform-express": { + "optional": true + } + } + }, + "node_modules/@nodelib/fs.scandir": { + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", + "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", + "dev": true, + "dependencies": { + "@nodelib/fs.stat": "2.0.5", + "run-parallel": "^1.1.9" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/@nodelib/fs.stat": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", + "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", + "dev": true, + "engines": { + "node": ">= 8" + } + }, + "node_modules/@nodelib/fs.walk": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", + "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", + "dev": true, + "dependencies": { + "@nodelib/fs.scandir": "2.1.5", + "fastq": "^1.6.0" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/@nuxtjs/opencollective": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@nuxtjs/opencollective/-/opencollective-0.3.2.tgz", + "integrity": "sha512-um0xL3fO7Mf4fDxcqx9KryrB7zgRM5JSlvGN5AGkP6JLM5XEKyjeAiPbNxdXVXQ16isuAhYpvP88NgL2BGd6aA==", + "dependencies": { + "chalk": "^4.1.0", + "consola": "^2.15.0", + "node-fetch": "^2.6.1" + }, + "bin": { + "opencollective": "bin/opencollective.js" + }, + "engines": { + "node": ">=8.0.0", + "npm": ">=5.0.0" + } + }, + "node_modules/@nuxtjs/opencollective/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/@sinclair/typebox": { + "version": "0.25.21", + "resolved": "https://registry.npmjs.org/@sinclair/typebox/-/typebox-0.25.21.tgz", + "integrity": "sha512-gFukHN4t8K4+wVC+ECqeqwzBDeFeTzBXroBTqE6vcWrQGbEUpHO7LYdG0f4xnvYq4VOEwITSlHlp0JBAIFMS/g==", + "dev": true + }, + "node_modules/@sinonjs/commons": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@sinonjs/commons/-/commons-2.0.0.tgz", + "integrity": "sha512-uLa0j859mMrg2slwQYdO/AkrOfmH+X6LTVmNTS9CqexuE2IvVORIkSpJLqePAbEnKJ77aMmCwr1NUZ57120Xcg==", + "dev": true, + "dependencies": { + "type-detect": "4.0.8" + } + }, + "node_modules/@sinonjs/fake-timers": { + "version": "10.0.2", + "resolved": "https://registry.npmjs.org/@sinonjs/fake-timers/-/fake-timers-10.0.2.tgz", + "integrity": "sha512-SwUDyjWnah1AaNl7kxsa7cfLhlTYoiyhDAIgyh+El30YvXs/o7OLXpYH88Zdhyx9JExKrmHDJ+10bwIcY80Jmw==", + "dev": true, + "dependencies": { + "@sinonjs/commons": "^2.0.0" + } + }, + "node_modules/@tsconfig/node10": { + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/@tsconfig/node10/-/node10-1.0.9.tgz", + "integrity": "sha512-jNsYVVxU8v5g43Erja32laIDHXeoNvFEpX33OK4d6hljo3jDhCBDhx5dhCCTMWUojscpAagGiRkBKxpdl9fxqA==", + "dev": true + }, + "node_modules/@tsconfig/node12": { + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/@tsconfig/node12/-/node12-1.0.11.tgz", + "integrity": "sha512-cqefuRsh12pWyGsIoBKJA9luFu3mRxCA+ORZvA4ktLSzIuCUtWVxGIuXigEwO5/ywWFMZ2QEGKWvkZG1zDMTag==", + "dev": true + }, + "node_modules/@tsconfig/node14": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/@tsconfig/node14/-/node14-1.0.3.tgz", + "integrity": "sha512-ysT8mhdixWK6Hw3i1V2AeRqZ5WfXg1G43mqoYlM2nc6388Fq5jcXyr5mRsqViLx/GJYdoL0bfXD8nmF+Zn/Iow==", + "dev": true + }, + "node_modules/@tsconfig/node16": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/@tsconfig/node16/-/node16-1.0.3.tgz", + "integrity": "sha512-yOlFc+7UtL/89t2ZhjPvvB/DeAr3r+Dq58IgzsFkOAvVC6NMJXmCGjbptdXdR9qsX7pKcTL+s87FtYREi2dEEQ==", + "dev": true + }, + "node_modules/@types/babel__core": { + "version": "7.20.0", + "resolved": "https://registry.npmjs.org/@types/babel__core/-/babel__core-7.20.0.tgz", + "integrity": "sha512-+n8dL/9GWblDO0iU6eZAwEIJVr5DWigtle+Q6HLOrh/pdbXOhOtqzq8VPPE2zvNJzSKY4vH/z3iT3tn0A3ypiQ==", + "dev": true, + "dependencies": { + "@babel/parser": "^7.20.7", + "@babel/types": "^7.20.7", + "@types/babel__generator": "*", + "@types/babel__template": "*", + "@types/babel__traverse": "*" + } + }, + "node_modules/@types/babel__generator": { + "version": "7.6.4", + "resolved": "https://registry.npmjs.org/@types/babel__generator/-/babel__generator-7.6.4.tgz", + "integrity": "sha512-tFkciB9j2K755yrTALxD44McOrk+gfpIpvC3sxHjRawj6PfnQxrse4Clq5y/Rq+G3mrBurMax/lG8Qn2t9mSsg==", + "dev": true, + "dependencies": { + "@babel/types": "^7.0.0" + } + }, + "node_modules/@types/babel__template": { + "version": "7.4.1", + "resolved": "https://registry.npmjs.org/@types/babel__template/-/babel__template-7.4.1.tgz", + "integrity": "sha512-azBFKemX6kMg5Io+/rdGT0dkGreboUVR0Cdm3fz9QJWpaQGJRQXl7C+6hOTCZcMll7KFyEQpgbYI2lHdsS4U7g==", + "dev": true, + "dependencies": { + "@babel/parser": "^7.1.0", + "@babel/types": "^7.0.0" + } + }, + "node_modules/@types/babel__traverse": { + "version": "7.18.3", + "resolved": "https://registry.npmjs.org/@types/babel__traverse/-/babel__traverse-7.18.3.tgz", + "integrity": "sha512-1kbcJ40lLB7MHsj39U4Sh1uTd2E7rLEa79kmDpI6cy+XiXsteB3POdQomoq4FxszMrO3ZYchkhYJw7A2862b3w==", + "dev": true, + "dependencies": { + "@babel/types": "^7.3.0" + } + }, + "node_modules/@types/body-parser": { + "version": "1.19.2", + "resolved": "https://registry.npmjs.org/@types/body-parser/-/body-parser-1.19.2.tgz", + "integrity": "sha512-ALYone6pm6QmwZoAgeyNksccT9Q4AWZQ6PvfwR37GT6r6FWUPguq6sUmNGSMV2Wr761oQoBxwGGa6DR5o1DC9g==", + "dev": true, + "dependencies": { + "@types/connect": "*", + "@types/node": "*" + } + }, + "node_modules/@types/connect": { + "version": "3.4.35", + "resolved": "https://registry.npmjs.org/@types/connect/-/connect-3.4.35.tgz", + "integrity": "sha512-cdeYyv4KWoEgpBISTxWvqYsVy444DOqehiF3fM3ne10AmJ62RSyNkUnxMJXHQWRQQX2eR94m5y1IZyDwBjV9FQ==", + "dev": true, + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@types/cookiejar": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/@types/cookiejar/-/cookiejar-2.1.2.tgz", + "integrity": "sha512-t73xJJrvdTjXrn4jLS9VSGRbz0nUY3cl2DMGDU48lKl+HR9dbbjW2A9r3g40VA++mQpy6uuHg33gy7du2BKpog==", + "dev": true + }, + "node_modules/@types/eslint": { + "version": "8.21.0", + "resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-8.21.0.tgz", + "integrity": "sha512-35EhHNOXgxnUgh4XCJsGhE7zdlDhYDN/aMG6UbkByCFFNgQ7b3U+uVoqBpicFydR8JEfgdjCF7SJ7MiJfzuiTA==", + "dev": true, + "dependencies": { + "@types/estree": "*", + "@types/json-schema": "*" + } + }, + "node_modules/@types/eslint-scope": { + "version": "3.7.4", + "resolved": "https://registry.npmjs.org/@types/eslint-scope/-/eslint-scope-3.7.4.tgz", + "integrity": "sha512-9K4zoImiZc3HlIp6AVUDE4CWYx22a+lhSZMYNpbjW04+YF0KWj4pJXnEMjdnFTiQibFFmElcsasJXDbdI/EPhA==", + "dev": true, + "dependencies": { + "@types/eslint": "*", + "@types/estree": "*" + } + }, + "node_modules/@types/estree": { + "version": "0.0.51", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-0.0.51.tgz", + "integrity": "sha512-CuPgU6f3eT/XgKKPqKd/gLZV1Xmvf1a2R5POBOGQa6uv82xpls89HU5zKeVoyR8XzHd1RGNOlQlvUe3CFkjWNQ==", + "dev": true + }, + "node_modules/@types/express": { + "version": "4.17.17", + "resolved": "https://registry.npmjs.org/@types/express/-/express-4.17.17.tgz", + "integrity": "sha512-Q4FmmuLGBG58btUnfS1c1r/NQdlp3DMfGDGig8WhfpA2YRUtEkxAjkZb0yvplJGYdF1fsQ81iMDcH24sSCNC/Q==", + "dev": true, + "dependencies": { + "@types/body-parser": "*", + "@types/express-serve-static-core": "^4.17.33", + "@types/qs": "*", + "@types/serve-static": "*" + } + }, + "node_modules/@types/express-serve-static-core": { + "version": "4.17.33", + "resolved": "https://registry.npmjs.org/@types/express-serve-static-core/-/express-serve-static-core-4.17.33.tgz", + "integrity": "sha512-TPBqmR/HRYI3eC2E5hmiivIzv+bidAfXofM+sbonAGvyDhySGw9/PQZFt2BLOrjUUR++4eJVpx6KnLQK1Fk9tA==", + "dev": true, + "dependencies": { + "@types/node": "*", + "@types/qs": "*", + "@types/range-parser": "*" + } + }, + "node_modules/@types/graceful-fs": { + "version": "4.1.6", + "resolved": "https://registry.npmjs.org/@types/graceful-fs/-/graceful-fs-4.1.6.tgz", + "integrity": "sha512-Sig0SNORX9fdW+bQuTEovKj3uHcUL6LQKbCrrqb1X7J6/ReAbhCXRAhc+SMejhLELFj2QcyuxmUooZ4bt5ReSw==", + "dev": true, + "dependencies": { + "@types/node": "*" + } + }, + "node_modules/@types/istanbul-lib-coverage": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/@types/istanbul-lib-coverage/-/istanbul-lib-coverage-2.0.4.tgz", + "integrity": "sha512-z/QT1XN4K4KYuslS23k62yDIDLwLFkzxOuMplDtObz0+y7VqJCaO2o+SPwHCvLFZh7xazvvoor2tA/hPz9ee7g==", + "dev": true + }, + "node_modules/@types/istanbul-lib-report": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/@types/istanbul-lib-report/-/istanbul-lib-report-3.0.0.tgz", + "integrity": "sha512-plGgXAPfVKFoYfa9NpYDAkseG+g6Jr294RqeqcqDixSbU34MZVJRi/P+7Y8GDpzkEwLaGZZOpKIEmeVZNtKsrg==", + "dev": true, + "dependencies": { + "@types/istanbul-lib-coverage": "*" + } + }, + "node_modules/@types/istanbul-reports": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/@types/istanbul-reports/-/istanbul-reports-3.0.1.tgz", + "integrity": "sha512-c3mAZEuK0lvBp8tmuL74XRKn1+y2dcwOUpH7x4WrF6gk1GIgiluDRgMYQtw2OFcBvAJWlt6ASU3tSqxp0Uu0Aw==", + "dev": true, + "dependencies": { + "@types/istanbul-lib-report": "*" + } + }, + "node_modules/@types/jest": { + "version": "29.2.4", + "resolved": "https://registry.npmjs.org/@types/jest/-/jest-29.2.4.tgz", + "integrity": "sha512-PipFB04k2qTRPePduVLTRiPzQfvMeLwUN3Z21hsAKaB/W9IIzgB2pizCL466ftJlcyZqnHoC9ZHpxLGl3fS86A==", + "dev": true, + "dependencies": { + "expect": "^29.0.0", + "pretty-format": "^29.0.0" + } + }, + "node_modules/@types/json-schema": { + "version": "7.0.11", + "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.11.tgz", + "integrity": "sha512-wOuvG1SN4Us4rez+tylwwwCV1psiNVOkJeM3AUWUNWg/jDQY2+HE/444y5gc+jBmRqASOm2Oeh5c1axHobwRKQ==", + "dev": true + }, + "node_modules/@types/json5": { + "version": "0.0.29", + "resolved": "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz", + "integrity": "sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==", + "dev": true, + "peer": true + }, + "node_modules/@types/mime": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/@types/mime/-/mime-3.0.1.tgz", + "integrity": "sha512-Y4XFY5VJAuw0FgAqPNd6NNoV44jbq9Bz2L7Rh/J6jLTiHBSBJa9fxqQIvkIld4GsoDOcCbvzOUAbLPsSKKg+uA==", + "dev": true + }, + "node_modules/@types/node": { + "version": "18.11.18", + "resolved": "https://registry.npmjs.org/@types/node/-/node-18.11.18.tgz", + "integrity": "sha512-DHQpWGjyQKSHj3ebjFI/wRKcqQcdR+MoFBygntYOZytCqNfkd2ZC4ARDJ2DQqhjH5p85Nnd3jhUJIXrszFX/JA==", + "dev": true + }, + "node_modules/@types/parse-json": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/@types/parse-json/-/parse-json-4.0.0.tgz", + "integrity": "sha512-//oorEZjL6sbPcKUaCdIGlIUeH26mgzimjBB77G6XRgnDl/L5wOnpyBGRe/Mmf5CVW3PwEBE1NjiMZ/ssFh4wA==", + "dev": true + }, + "node_modules/@types/prettier": { + "version": "2.7.2", + "resolved": "https://registry.npmjs.org/@types/prettier/-/prettier-2.7.2.tgz", + "integrity": "sha512-KufADq8uQqo1pYKVIYzfKbJfBAc0sOeXqGbFaSpv8MRmC/zXgowNZmFcbngndGk922QDmOASEXUZCaY48gs4cg==", + "dev": true + }, + "node_modules/@types/qs": { + "version": "6.9.7", + "resolved": "https://registry.npmjs.org/@types/qs/-/qs-6.9.7.tgz", + "integrity": "sha512-FGa1F62FT09qcrueBA6qYTrJPVDzah9a+493+o2PCXsesWHIn27G98TsSMs3WPNbZIEj4+VJf6saSFpvD+3Zsw==", + "dev": true + }, + "node_modules/@types/range-parser": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/@types/range-parser/-/range-parser-1.2.4.tgz", + "integrity": "sha512-EEhsLsD6UsDM1yFhAvy0Cjr6VwmpMWqFBCb9w07wVugF7w9nfajxLuVmngTIpgS6svCnm6Vaw+MZhoDCKnOfsw==", + "dev": true + }, + "node_modules/@types/semver": { + "version": "7.3.13", + "resolved": "https://registry.npmjs.org/@types/semver/-/semver-7.3.13.tgz", + "integrity": "sha512-21cFJr9z3g5dW8B0CVI9g2O9beqaThGQ6ZFBqHfwhzLDKUxaqTIy3vnfah/UPkfOiF2pLq+tGz+W8RyCskuslw==", + "dev": true + }, + "node_modules/@types/serve-static": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/@types/serve-static/-/serve-static-1.15.0.tgz", + "integrity": "sha512-z5xyF6uh8CbjAu9760KDKsH2FcDxZ2tFCsA4HIMWE6IkiYMXfVoa+4f9KX+FN0ZLsaMw1WNG2ETLA6N+/YA+cg==", + "dev": true, + "dependencies": { + "@types/mime": "*", + "@types/node": "*" + } + }, + "node_modules/@types/stack-utils": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/@types/stack-utils/-/stack-utils-2.0.1.tgz", + "integrity": "sha512-Hl219/BT5fLAaz6NDkSuhzasy49dwQS/DSdu4MdggFB8zcXv7vflBI3xp7FEmkmdDkBUI2bPUNeMttp2knYdxw==", + "dev": true + }, + "node_modules/@types/superagent": { + "version": "4.1.16", + "resolved": "https://registry.npmjs.org/@types/superagent/-/superagent-4.1.16.tgz", + "integrity": "sha512-tLfnlJf6A5mB6ddqF159GqcDizfzbMUB1/DeT59/wBNqzRTNNKsaw79A/1TZ84X+f/EwWH8FeuSkjlCLyqS/zQ==", + "dev": true, + "dependencies": { + "@types/cookiejar": "*", + "@types/node": "*" + } + }, + "node_modules/@types/supertest": { + "version": "2.0.12", + "resolved": "https://registry.npmjs.org/@types/supertest/-/supertest-2.0.12.tgz", + "integrity": "sha512-X3HPWTwXRerBZS7Mo1k6vMVR1Z6zmJcDVn5O/31whe0tnjE4te6ZJSJGq1RiqHPjzPdMTfjCFogDJmwng9xHaQ==", + "dev": true, + "dependencies": { + "@types/superagent": "*" + } + }, + "node_modules/@types/yargs": { + "version": "17.0.22", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-17.0.22.tgz", + "integrity": "sha512-pet5WJ9U8yPVRhkwuEIp5ktAeAqRZOq4UdAyWLWzxbtpyXnzbtLdKiXAjJzi/KLmPGS9wk86lUFWZFN6sISo4g==", + "dev": true, + "dependencies": { + "@types/yargs-parser": "*" + } + }, + "node_modules/@types/yargs-parser": { + "version": "21.0.0", + "resolved": "https://registry.npmjs.org/@types/yargs-parser/-/yargs-parser-21.0.0.tgz", + "integrity": "sha512-iO9ZQHkZxHn4mSakYV0vFHAVDyEOIJQrV2uZ06HxEPcx+mt8swXoZHIbaaJ2crJYFfErySgktuTZ3BeLz+XmFA==", + "dev": true + }, + "node_modules/@typescript-eslint/eslint-plugin": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.50.0.tgz", + "integrity": "sha512-vwksQWSFZiUhgq3Kv7o1Jcj0DUNylwnIlGvKvLLYsq8pAWha6/WCnXUeaSoNNha/K7QSf2+jvmkxggC1u3pIwQ==", + "dev": true, + "dependencies": { + "@typescript-eslint/scope-manager": "5.50.0", + "@typescript-eslint/type-utils": "5.50.0", + "@typescript-eslint/utils": "5.50.0", + "debug": "^4.3.4", + "grapheme-splitter": "^1.0.4", + "ignore": "^5.2.0", + "natural-compare-lite": "^1.4.0", + "regexpp": "^3.2.0", + "semver": "^7.3.7", + "tsutils": "^3.21.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "@typescript-eslint/parser": "^5.0.0", + "eslint": "^6.0.0 || ^7.0.0 || ^8.0.0" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/@typescript-eslint/parser": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.50.0.tgz", + "integrity": "sha512-KCcSyNaogUDftK2G9RXfQyOCt51uB5yqC6pkUYqhYh8Kgt+DwR5M0EwEAxGPy/+DH6hnmKeGsNhiZRQxjH71uQ==", + "dev": true, + "dependencies": { + "@typescript-eslint/scope-manager": "5.50.0", + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/typescript-estree": "5.50.0", + "debug": "^4.3.4" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^6.0.0 || ^7.0.0 || ^8.0.0" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/@typescript-eslint/scope-manager": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.50.0.tgz", + "integrity": "sha512-rt03kaX+iZrhssaT974BCmoUikYtZI24Vp/kwTSy841XhiYShlqoshRFDvN1FKKvU2S3gK+kcBW1EA7kNUrogg==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/visitor-keys": "5.50.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@typescript-eslint/type-utils": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.50.0.tgz", + "integrity": "sha512-dcnXfZ6OGrNCO7E5UY/i0ktHb7Yx1fV6fnQGGrlnfDhilcs6n19eIRcvLBqx6OQkrPaFlDPk3OJ0WlzQfrV0bQ==", + "dev": true, + "dependencies": { + "@typescript-eslint/typescript-estree": "5.50.0", + "@typescript-eslint/utils": "5.50.0", + "debug": "^4.3.4", + "tsutils": "^3.21.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "*" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/@typescript-eslint/types": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.50.0.tgz", + "integrity": "sha512-atruOuJpir4OtyNdKahiHZobPKFvZnBnfDiyEaBf6d9vy9visE7gDjlmhl+y29uxZ2ZDgvXijcungGFjGGex7w==", + "dev": true, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@typescript-eslint/typescript-estree": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.50.0.tgz", + "integrity": "sha512-Gq4zapso+OtIZlv8YNAStFtT6d05zyVCK7Fx3h5inlLBx2hWuc/0465C2mg/EQDDU2LKe52+/jN4f0g9bd+kow==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/visitor-keys": "5.50.0", + "debug": "^4.3.4", + "globby": "^11.1.0", + "is-glob": "^4.0.3", + "semver": "^7.3.7", + "tsutils": "^3.21.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, + "node_modules/@typescript-eslint/utils": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.50.0.tgz", + "integrity": "sha512-v/AnUFImmh8G4PH0NDkf6wA8hujNNcrwtecqW4vtQ1UOSNBaZl49zP1SHoZ/06e+UiwzHpgb5zP5+hwlYYWYAw==", + "dev": true, + "dependencies": { + "@types/json-schema": "^7.0.9", + "@types/semver": "^7.3.12", + "@typescript-eslint/scope-manager": "5.50.0", + "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/typescript-estree": "5.50.0", + "eslint-scope": "^5.1.1", + "eslint-utils": "^3.0.0", + "semver": "^7.3.7" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "eslint": "^6.0.0 || ^7.0.0 || ^8.0.0" + } + }, + "node_modules/@typescript-eslint/visitor-keys": { + "version": "5.50.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.50.0.tgz", + "integrity": "sha512-cdMeD9HGu6EXIeGOh2yVW6oGf9wq8asBgZx7nsR/D36gTfQ0odE5kcRYe5M81vjEFAcPeugXrHg78Imu55F6gg==", + "dev": true, + "dependencies": { + "@typescript-eslint/types": "5.50.0", + "eslint-visitor-keys": "^3.3.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/typescript-eslint" + } + }, + "node_modules/@webassemblyjs/ast": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.11.1.tgz", + "integrity": "sha512-ukBh14qFLjxTQNTXocdyksN5QdM28S1CxHt2rdskFyL+xFV7VremuBLVbmCePj+URalXBENx/9Lm7lnhihtCSw==", + "dev": true, + "dependencies": { + "@webassemblyjs/helper-numbers": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1" + } + }, + "node_modules/@webassemblyjs/floating-point-hex-parser": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.11.1.tgz", + "integrity": "sha512-iGRfyc5Bq+NnNuX8b5hwBrRjzf0ocrJPI6GWFodBFzmFnyvrQ83SHKhmilCU/8Jv67i4GJZBMhEzltxzcNagtQ==", + "dev": true + }, + "node_modules/@webassemblyjs/helper-api-error": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-api-error/-/helper-api-error-1.11.1.tgz", + "integrity": "sha512-RlhS8CBCXfRUR/cwo2ho9bkheSXG0+NwooXcc3PAILALf2QLdFyj7KGsKRbVc95hZnhnERon4kW/D3SZpp6Tcg==", + "dev": true + }, + "node_modules/@webassemblyjs/helper-buffer": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-buffer/-/helper-buffer-1.11.1.tgz", + "integrity": "sha512-gwikF65aDNeeXa8JxXa2BAk+REjSyhrNC9ZwdT0f8jc4dQQeDQ7G4m0f2QCLPJiMTTO6wfDmRmj/pW0PsUvIcA==", + "dev": true + }, + "node_modules/@webassemblyjs/helper-numbers": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-numbers/-/helper-numbers-1.11.1.tgz", + "integrity": "sha512-vDkbxiB8zfnPdNK9Rajcey5C0w+QJugEglN0of+kmO8l7lDb77AnlKYQF7aarZuCrv+l0UvqL+68gSDr3k9LPQ==", + "dev": true, + "dependencies": { + "@webassemblyjs/floating-point-hex-parser": "1.11.1", + "@webassemblyjs/helper-api-error": "1.11.1", + "@xtuc/long": "4.2.2" + } + }, + "node_modules/@webassemblyjs/helper-wasm-bytecode": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.11.1.tgz", + "integrity": "sha512-PvpoOGiJwXeTrSf/qfudJhwlvDQxFgelbMqtq52WWiXC6Xgg1IREdngmPN3bs4RoO83PnL/nFrxucXj1+BX62Q==", + "dev": true + }, + "node_modules/@webassemblyjs/helper-wasm-section": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.11.1.tgz", + "integrity": "sha512-10P9No29rYX1j7F3EVPX3JvGPQPae+AomuSTPiF9eBQeChHI6iqjMIwR9JmOJXwpnn/oVGDk7I5IlskuMwU/pg==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-buffer": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1", + "@webassemblyjs/wasm-gen": "1.11.1" + } + }, + "node_modules/@webassemblyjs/ieee754": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.11.1.tgz", + "integrity": "sha512-hJ87QIPtAMKbFq6CGTkZYJivEwZDbQUgYd3qKSadTNOhVY7p+gfP6Sr0lLRVTaG1JjFj+r3YchoqRYxNH3M0GQ==", + "dev": true, + "dependencies": { + "@xtuc/ieee754": "^1.2.0" + } + }, + "node_modules/@webassemblyjs/leb128": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.11.1.tgz", + "integrity": "sha512-BJ2P0hNZ0u+Th1YZXJpzW6miwqQUGcIHT1G/sf72gLVD9DZ5AdYTqPNbHZh6K1M5VmKvFXwGSWZADz+qBWxeRw==", + "dev": true, + "dependencies": { + "@xtuc/long": "4.2.2" + } + }, + "node_modules/@webassemblyjs/utf8": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.11.1.tgz", + "integrity": "sha512-9kqcxAEdMhiwQkHpkNiorZzqpGrodQQ2IGrHHxCy+Ozng0ofyMA0lTqiLkVs1uzTRejX+/O0EOT7KxqVPuXosQ==", + "dev": true + }, + "node_modules/@webassemblyjs/wasm-edit": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-edit/-/wasm-edit-1.11.1.tgz", + "integrity": "sha512-g+RsupUC1aTHfR8CDgnsVRVZFJqdkFHpsHMfJuWQzWU3tvnLC07UqHICfP+4XyL2tnr1amvl1Sdp06TnYCmVkA==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-buffer": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1", + "@webassemblyjs/helper-wasm-section": "1.11.1", + "@webassemblyjs/wasm-gen": "1.11.1", + "@webassemblyjs/wasm-opt": "1.11.1", + "@webassemblyjs/wasm-parser": "1.11.1", + "@webassemblyjs/wast-printer": "1.11.1" + } + }, + "node_modules/@webassemblyjs/wasm-gen": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-gen/-/wasm-gen-1.11.1.tgz", + "integrity": "sha512-F7QqKXwwNlMmsulj6+O7r4mmtAlCWfO/0HdgOxSklZfQcDu0TpLiD1mRt/zF25Bk59FIjEuGAIyn5ei4yMfLhA==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1", + "@webassemblyjs/ieee754": "1.11.1", + "@webassemblyjs/leb128": "1.11.1", + "@webassemblyjs/utf8": "1.11.1" + } + }, + "node_modules/@webassemblyjs/wasm-opt": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-opt/-/wasm-opt-1.11.1.tgz", + "integrity": "sha512-VqnkNqnZlU5EB64pp1l7hdm3hmQw7Vgqa0KF/KCNO9sIpI6Fk6brDEiX+iCOYrvMuBWDws0NkTOxYEb85XQHHw==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-buffer": "1.11.1", + "@webassemblyjs/wasm-gen": "1.11.1", + "@webassemblyjs/wasm-parser": "1.11.1" + } + }, + "node_modules/@webassemblyjs/wasm-parser": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.11.1.tgz", + "integrity": "sha512-rrBujw+dJu32gYB7/Lup6UhdkPx9S9SnobZzRVL7VcBH9Bt9bCBLEuX/YXOOtBsOZ4NQrRykKhffRWHvigQvOA==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/helper-api-error": "1.11.1", + "@webassemblyjs/helper-wasm-bytecode": "1.11.1", + "@webassemblyjs/ieee754": "1.11.1", + "@webassemblyjs/leb128": "1.11.1", + "@webassemblyjs/utf8": "1.11.1" + } + }, + "node_modules/@webassemblyjs/wast-printer": { + "version": "1.11.1", + "resolved": "https://registry.npmjs.org/@webassemblyjs/wast-printer/-/wast-printer-1.11.1.tgz", + "integrity": "sha512-IQboUWM4eKzWW+N/jij2sRatKMh99QEelo3Eb2q0qXkvPRISAj8Qxtmw5itwqK+TTkBuUIE45AxYPToqPtL5gg==", + "dev": true, + "dependencies": { + "@webassemblyjs/ast": "1.11.1", + "@xtuc/long": "4.2.2" + } + }, + "node_modules/@xtuc/ieee754": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/@xtuc/ieee754/-/ieee754-1.2.0.tgz", + "integrity": "sha512-DX8nKgqcGwsc0eJSqYt5lwP4DH5FlHnmuWWBRy7X0NcaGR0ZtuyeESgMwTYVEtxmsNGY+qit4QYT/MIYTOTPeA==", + "dev": true + }, + "node_modules/@xtuc/long": { + "version": "4.2.2", + "resolved": "https://registry.npmjs.org/@xtuc/long/-/long-4.2.2.tgz", + "integrity": "sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ==", + "dev": true + }, + "node_modules/accepts": { + "version": "1.3.8", + "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.8.tgz", + "integrity": "sha512-PYAthTa2m2VKxuvSD3DPC/Gy+U+sOA1LAuT8mkmRuvw+NACSaeXEQ+NHcVF7rONl6qcaxV3Uuemwawk+7+SJLw==", + "dependencies": { + "mime-types": "~2.1.34", + "negotiator": "0.6.3" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/acorn": { + "version": "8.8.2", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.8.2.tgz", + "integrity": "sha512-xjIYgE8HBrkpd/sJqOGNspf8uHG+NOHGOw6a/Urj8taM2EXfdNAH2oFcPeIFfsv3+kz/mJrS5VuMqbNLjCa2vw==", + "dev": true, + "bin": { + "acorn": "bin/acorn" + }, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/acorn-import-assertions": { + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/acorn-import-assertions/-/acorn-import-assertions-1.8.0.tgz", + "integrity": "sha512-m7VZ3jwz4eK6A4Vtt8Ew1/mNbP24u0FhdyfA7fSvnJR6LMdfOYnmuIrrJAgrYfYJ10F/otaHTtrtrtmHdMNzEw==", + "dev": true, + "peerDependencies": { + "acorn": "^8" + } + }, + "node_modules/acorn-jsx": { + "version": "5.3.2", + "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.3.2.tgz", + "integrity": "sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==", + "dev": true, + "peerDependencies": { + "acorn": "^6.0.0 || ^7.0.0 || ^8.0.0" + } + }, + "node_modules/acorn-walk": { + "version": "8.2.0", + "resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-8.2.0.tgz", + "integrity": "sha512-k+iyHEuPgSw6SbuDpGQM+06HQUa04DZ3o+F6CSzXMvvI5KMvnaEqXe+YVe555R9nn6GPt404fos4wcgpw12SDA==", + "dev": true, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/ajv": { + "version": "8.12.0", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.12.0.tgz", + "integrity": "sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "json-schema-traverse": "^1.0.0", + "require-from-string": "^2.0.2", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/ajv-formats": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ajv-formats/-/ajv-formats-2.1.1.tgz", + "integrity": "sha512-Wx0Kx52hxE7C18hkMEggYlEifqWZtYaRgouJor+WMdPnQyEK13vgEWyVNup7SoeeoLMsr4kf5h6dOW11I15MUA==", + "dev": true, + "dependencies": { + "ajv": "^8.0.0" + }, + "peerDependencies": { + "ajv": "^8.0.0" + }, + "peerDependenciesMeta": { + "ajv": { + "optional": true + } + } + }, + "node_modules/ansi-colors": { + "version": "4.1.3", + "resolved": "https://registry.npmjs.org/ansi-colors/-/ansi-colors-4.1.3.tgz", + "integrity": "sha512-/6w/C21Pm1A7aZitlI5Ni/2J6FFQN8i1Cvz3kHABAAbw93v/NlvKdVOqz7CCWz/3iv/JplRSEEZ83XION15ovw==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/ansi-escapes": { + "version": "4.3.2", + "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-4.3.2.tgz", + "integrity": "sha512-gKXj5ALrKWQLsYG9jlTRmR/xKluxHV+Z9QEwNIgCfM1/uwPMCuzVVnh5mwTd+OuBZcwSIMbqssNWRm1lE51QaQ==", + "dev": true, + "dependencies": { + "type-fest": "^0.21.3" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/ansi-escapes/node_modules/type-fest": { + "version": "0.21.3", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.21.3.tgz", + "integrity": "sha512-t0rzBq87m3fVcduHDUFhKmyyX+9eo6WQjZvf51Ea/M0Q7+T374Jp1aUiyUl0GKxp8M/OETVHSDvmkyPgvX+X2w==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/ansi-regex": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", + "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dependencies": { + "color-convert": "^2.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/anymatch": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.3.tgz", + "integrity": "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==", + "dev": true, + "dependencies": { + "normalize-path": "^3.0.0", + "picomatch": "^2.0.4" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/append-field": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/append-field/-/append-field-1.0.0.tgz", + "integrity": "sha512-klpgFSWLW1ZEs8svjfb7g4qWY0YS5imI82dTg+QahUvJ8YqAY0P10Uk8tTyh9ZGuYEZEMaeJYCF5BFuX552hsw==" + }, + "node_modules/arg": { + "version": "4.1.3", + "resolved": "https://registry.npmjs.org/arg/-/arg-4.1.3.tgz", + "integrity": "sha512-58S9QDqG0Xx27YwPSt9fJxivjYl432YCwfDMfZ+71RAqUrZef7LrKQZ3LHLOwCS4FLNBplP533Zx895SeOCHvA==", + "dev": true + }, + "node_modules/argparse": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-2.0.1.tgz", + "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==", + "dev": true + }, + "node_modules/array-flatten": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", + "integrity": "sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==" + }, + "node_modules/array-includes": { + "version": "3.1.6", + "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.6.tgz", + "integrity": "sha512-sgTbLvL6cNnw24FnbaDyjmvddQ2ML8arZsgaJhoABMoplz/4QRhtrYS+alr1BUM1Bwp6dhx8vVCBSLG+StwOFw==", + "dev": true, + "peer": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4", + "get-intrinsic": "^1.1.3", + "is-string": "^1.0.7" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/array-union": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/array-union/-/array-union-2.1.0.tgz", + "integrity": "sha512-HGyxoOTYUyCM6stUe6EJgnd4EoewAI7zMdfqO+kGjnlZmBDz/cR5pf8r/cR4Wq60sL/p0IkcjUEEPwS3GFrIyw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/array.prototype.flat": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/array.prototype.flat/-/array.prototype.flat-1.3.1.tgz", + "integrity": "sha512-roTU0KWIOmJ4DRLmwKd19Otg0/mT3qPNt0Qb3GWW8iObuZXxrjB/pzn0R3hqpRSWg4HCwqx+0vwOnWnvlOyeIA==", + "dev": true, + "peer": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4", + "es-shim-unscopables": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/array.prototype.flatmap": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/array.prototype.flatmap/-/array.prototype.flatmap-1.3.1.tgz", + "integrity": "sha512-8UGn9O1FDVvMNB0UlLv4voxRMze7+FpHyF5mSMRjWHUMlpoDViniy05870VlxhfgTnLbpuwTzvD76MTtWxB/mQ==", + "dev": true, + "peer": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4", + "es-shim-unscopables": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/asap": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", + "integrity": "sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==", + "dev": true + }, + "node_modules/asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==", + "dev": true + }, + "node_modules/available-typed-arrays": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.5.tgz", + "integrity": "sha512-DMD0KiN46eipeziST1LPP/STfDU0sufISXmjSgvVsoU2tqxctQeASejWcfNtxYKqETM1UxQ8sp2OrSBWpHY6sw==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/babel-jest": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/babel-jest/-/babel-jest-29.4.1.tgz", + "integrity": "sha512-xBZa/pLSsF/1sNpkgsiT3CmY7zV1kAsZ9OxxtrFqYucnOuRftXAfcJqcDVyOPeN4lttWTwhLdu0T9f8uvoPEUg==", + "dev": true, + "dependencies": { + "@jest/transform": "^29.4.1", + "@types/babel__core": "^7.1.14", + "babel-plugin-istanbul": "^6.1.1", + "babel-preset-jest": "^29.4.0", + "chalk": "^4.0.0", + "graceful-fs": "^4.2.9", + "slash": "^3.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + }, + "peerDependencies": { + "@babel/core": "^7.8.0" + } + }, + "node_modules/babel-jest/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/babel-plugin-istanbul": { + "version": "6.1.1", + "resolved": "https://registry.npmjs.org/babel-plugin-istanbul/-/babel-plugin-istanbul-6.1.1.tgz", + "integrity": "sha512-Y1IQok9821cC9onCx5otgFfRm7Lm+I+wwxOx738M/WLPZ9Q42m4IG5W0FNX8WLL2gYMZo3JkuXIH2DOpWM+qwA==", + "dev": true, + "dependencies": { + "@babel/helper-plugin-utils": "^7.0.0", + "@istanbuljs/load-nyc-config": "^1.0.0", + "@istanbuljs/schema": "^0.1.2", + "istanbul-lib-instrument": "^5.0.4", + "test-exclude": "^6.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/babel-plugin-jest-hoist": { + "version": "29.4.0", + "resolved": "https://registry.npmjs.org/babel-plugin-jest-hoist/-/babel-plugin-jest-hoist-29.4.0.tgz", + "integrity": "sha512-a/sZRLQJEmsmejQ2rPEUe35nO1+C9dc9O1gplH1SXmJxveQSRUYdBk8yGZG/VOUuZs1u2aHZJusEGoRMbhhwCg==", + "dev": true, + "dependencies": { + "@babel/template": "^7.3.3", + "@babel/types": "^7.3.3", + "@types/babel__core": "^7.1.14", + "@types/babel__traverse": "^7.0.6" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/babel-preset-current-node-syntax": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/babel-preset-current-node-syntax/-/babel-preset-current-node-syntax-1.0.1.tgz", + "integrity": "sha512-M7LQ0bxarkxQoN+vz5aJPsLBn77n8QgTFmo8WK0/44auK2xlCXrYcUxHFxgU7qW5Yzw/CjmLRK2uJzaCd7LvqQ==", + "dev": true, + "dependencies": { + "@babel/plugin-syntax-async-generators": "^7.8.4", + "@babel/plugin-syntax-bigint": "^7.8.3", + "@babel/plugin-syntax-class-properties": "^7.8.3", + "@babel/plugin-syntax-import-meta": "^7.8.3", + "@babel/plugin-syntax-json-strings": "^7.8.3", + "@babel/plugin-syntax-logical-assignment-operators": "^7.8.3", + "@babel/plugin-syntax-nullish-coalescing-operator": "^7.8.3", + "@babel/plugin-syntax-numeric-separator": "^7.8.3", + "@babel/plugin-syntax-object-rest-spread": "^7.8.3", + "@babel/plugin-syntax-optional-catch-binding": "^7.8.3", + "@babel/plugin-syntax-optional-chaining": "^7.8.3", + "@babel/plugin-syntax-top-level-await": "^7.8.3" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/babel-preset-jest": { + "version": "29.4.0", + "resolved": "https://registry.npmjs.org/babel-preset-jest/-/babel-preset-jest-29.4.0.tgz", + "integrity": "sha512-fUB9vZflUSM3dO/6M2TCAepTzvA4VkOvl67PjErcrQMGt9Eve7uazaeyCZ2th3UtI7ljpiBJES0F7A1vBRsLZA==", + "dev": true, + "dependencies": { + "babel-plugin-jest-hoist": "^29.4.0", + "babel-preset-current-node-syntax": "^1.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0" + } + }, + "node_modules/balanced-match": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", + "dev": true + }, + "node_modules/base64-js": { + "version": "1.5.1", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", + "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ] + }, + "node_modules/binary-extensions": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.2.0.tgz", + "integrity": "sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/bl": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/bl/-/bl-4.1.0.tgz", + "integrity": "sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==", + "dev": true, + "dependencies": { + "buffer": "^5.5.0", + "inherits": "^2.0.4", + "readable-stream": "^3.4.0" + } + }, + "node_modules/bl/node_modules/readable-stream": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", + "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", + "dev": true, + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/body-parser": { + "version": "1.20.1", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.20.1.tgz", + "integrity": "sha512-jWi7abTbYwajOytWCQc37VulmWiRae5RyTpaCyDcS5/lMdtwSz5lOpDE67srw/HYe35f1z3fDQw+3txg7gNtWw==", + "dependencies": { + "bytes": "3.1.2", + "content-type": "~1.0.4", + "debug": "2.6.9", + "depd": "2.0.0", + "destroy": "1.2.0", + "http-errors": "2.0.0", + "iconv-lite": "0.4.24", + "on-finished": "2.4.1", + "qs": "6.11.0", + "raw-body": "2.5.1", + "type-is": "~1.6.18", + "unpipe": "1.0.0" + }, + "engines": { + "node": ">= 0.8", + "npm": "1.2.8000 || >= 1.4.16" + } + }, + "node_modules/body-parser/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/body-parser/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" + }, + "node_modules/brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "dev": true, + "dependencies": { + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" + } + }, + "node_modules/braces": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", + "integrity": "sha512-b8um+L1RzM3WDSzvhm6gIz1yfTbBt6YTlcEKAvsmqCZZFw46z626lVj9j1yEPW33H5H+lBQpZMP1k8l+78Ha0A==", + "dev": true, + "dependencies": { + "fill-range": "^7.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/browserslist": { + "version": "4.21.5", + "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.21.5.tgz", + "integrity": "sha512-tUkiguQGW7S3IhB7N+c2MV/HZPSCPAAiYBZXLsBhFB/PCy6ZKKsZrmBayHV9fdGV/ARIfJ14NkxKzRDjvp7L6w==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/browserslist" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/browserslist" + } + ], + "dependencies": { + "caniuse-lite": "^1.0.30001449", + "electron-to-chromium": "^1.4.284", + "node-releases": "^2.0.8", + "update-browserslist-db": "^1.0.10" + }, + "bin": { + "browserslist": "cli.js" + }, + "engines": { + "node": "^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7" + } + }, + "node_modules/bs-logger": { + "version": "0.2.6", + "resolved": "https://registry.npmjs.org/bs-logger/-/bs-logger-0.2.6.tgz", + "integrity": "sha512-pd8DCoxmbgc7hyPKOvxtqNcjYoOsABPQdcCUjGp3d42VR2CX1ORhk2A87oqqu5R1kk+76nsxZupkmyd+MVtCog==", + "dev": true, + "dependencies": { + "fast-json-stable-stringify": "2.x" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/bser": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/bser/-/bser-2.1.1.tgz", + "integrity": "sha512-gQxTNE/GAfIIrmHLUE3oJyp5FO6HRBfhjnw4/wMmA63ZGDJnWBmgY/lyQBpnDUkGmAhbSe39tx2d/iTOAfglwQ==", + "dev": true, + "dependencies": { + "node-int64": "^0.4.0" + } + }, + "node_modules/buffer": { + "version": "5.7.1", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz", + "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "dependencies": { + "base64-js": "^1.3.1", + "ieee754": "^1.1.13" + } + }, + "node_modules/buffer-from": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", + "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==" + }, + "node_modules/busboy": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/busboy/-/busboy-1.6.0.tgz", + "integrity": "sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA==", + "dependencies": { + "streamsearch": "^1.1.0" + }, + "engines": { + "node": ">=10.16.0" + } + }, + "node_modules/bytes": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", + "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/call-bind": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.2.tgz", + "integrity": "sha512-7O+FbCihrB5WGbFYesctwmTKae6rOiIzmz1icreWJ+0aA7LJfuqhEso2T9ncpcFtzMQtzXf2QGGueWJGTYsqrA==", + "dependencies": { + "function-bind": "^1.1.1", + "get-intrinsic": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/callsites": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", + "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/camelcase": { + "version": "5.3.1", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-5.3.1.tgz", + "integrity": "sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/caniuse-lite": { + "version": "1.0.30001450", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001450.tgz", + "integrity": "sha512-qMBmvmQmFXaSxexkjjfMvD5rnDL0+m+dUMZKoDYsGG8iZN29RuYh9eRoMvKsT6uMAWlyUUGDEQGJJYjzCIO9ew==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/browserslist" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/caniuse-lite" + } + ] + }, + "node_modules/chalk": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-3.0.0.tgz", + "integrity": "sha512-4D3B6Wf41KOYRFdszmDqMCGq5VV/uMAB273JILmO+3jAlh8X4qDtdtgCR3fxtbLEMzSx22QdhnDcJvu2u1fVwg==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/char-regex": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/char-regex/-/char-regex-1.0.2.tgz", + "integrity": "sha512-kWWXztvZ5SBQV+eRgKFeh8q5sLuZY2+8WUIzlxWVTg+oGwY14qylx1KbKzHd8P6ZYkAg0xyIDU9JMHhyJMZ1jw==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/chardet": { + "version": "0.7.0", + "resolved": "https://registry.npmjs.org/chardet/-/chardet-0.7.0.tgz", + "integrity": "sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==", + "dev": true + }, + "node_modules/chokidar": { + "version": "3.5.3", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.5.3.tgz", + "integrity": "sha512-Dr3sfKRP6oTcjf2JmUmFJfeVMvXBdegxB0iVQ5eb2V10uFJUCAS8OByZdVAyVb8xXNz3GjjTgj9kLWsZTqE6kw==", + "dev": true, + "funding": [ + { + "type": "individual", + "url": "https://paulmillr.com/funding/" + } + ], + "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" + }, + "engines": { + "node": ">= 8.10.0" + }, + "optionalDependencies": { + "fsevents": "~2.3.2" + } + }, + "node_modules/chrome-trace-event": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/chrome-trace-event/-/chrome-trace-event-1.0.3.tgz", + "integrity": "sha512-p3KULyQg4S7NIHixdwbGX+nFHkoBiA4YQmyWtjb8XngSKV124nJmRysgAeujbUVb15vh+RvFUfCPqU7rXk+hZg==", + "dev": true, + "engines": { + "node": ">=6.0" + } + }, + "node_modules/ci-info": { + "version": "3.7.1", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-3.7.1.tgz", + "integrity": "sha512-4jYS4MOAaCIStSRwiuxc4B8MYhIe676yO1sYGzARnjXkWpmzZMMYxY6zu8WYWDhSuth5zhrQ1rhNSibyyvv4/w==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/sibiraj-s" + } + ], + "engines": { + "node": ">=8" + } + }, + "node_modules/cjs-module-lexer": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/cjs-module-lexer/-/cjs-module-lexer-1.2.2.tgz", + "integrity": "sha512-cOU9usZw8/dXIXKtwa8pM0OTJQuJkxMN6w30csNRUerHfeQ5R6U3kkU/FtJeIf3M202OHfY2U8ccInBG7/xogA==", + "dev": true + }, + "node_modules/cli-cursor": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-3.1.0.tgz", + "integrity": "sha512-I/zHAwsKf9FqGoXM4WWRACob9+SNukZTd94DWF57E4toouRulbCxcUh6RKUEOQlYTHJnzkPMySvPNaaSLNfLZw==", + "dev": true, + "dependencies": { + "restore-cursor": "^3.1.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/cli-spinners": { + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-2.7.0.tgz", + "integrity": "sha512-qu3pN8Y3qHNgE2AFweciB1IfMnmZ/fsNTEE+NOFjmGB2F/7rLhnhzppvpCnN4FovtP26k8lHyy9ptEbNwWFLzw==", + "dev": true, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/cli-table3": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/cli-table3/-/cli-table3-0.6.3.tgz", + "integrity": "sha512-w5Jac5SykAeZJKntOxJCrm63Eg5/4dhMWIcuTbo9rpE+brgaSZo0RuNJZeOyMgsUdhDeojvgyQLmjI+K50ZGyg==", + "dev": true, + "dependencies": { + "string-width": "^4.2.0" + }, + "engines": { + "node": "10.* || >= 12.*" + }, + "optionalDependencies": { + "@colors/colors": "1.5.0" + } + }, + "node_modules/cli-width": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/cli-width/-/cli-width-3.0.0.tgz", + "integrity": "sha512-FxqpkPPwu1HjuN93Omfm4h8uIanXofW0RxVEW3k5RKx+mJJYSthzNhp32Kzxxy3YAEZ/Dc/EWN1vZRY0+kOhbw==", + "dev": true, + "engines": { + "node": ">= 10" + } + }, + "node_modules/cliui": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", + "integrity": "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==", + "dev": true, + "dependencies": { + "string-width": "^4.2.0", + "strip-ansi": "^6.0.1", + "wrap-ansi": "^7.0.0" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/clone": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.4.tgz", + "integrity": "sha512-JQHZ2QMW6l3aH/j6xCqQThY/9OH4D/9ls34cgkUBiEeocRTU04tHfKPBsUK1PqZCUQM7GiA0IIXJSuXHI64Kbg==", + "dev": true, + "engines": { + "node": ">=0.8" + } + }, + "node_modules/co": { + "version": "4.6.0", + "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", + "integrity": "sha512-QVb0dM5HvG+uaxitm8wONl7jltx8dqhfU33DcqtOZcLSVIKSDDLDi7+0LbAKiyI8hD9u42m2YxXSkMGWThaecQ==", + "dev": true, + "engines": { + "iojs": ">= 1.0.0", + "node": ">= 0.12.0" + } + }, + "node_modules/collect-v8-coverage": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/collect-v8-coverage/-/collect-v8-coverage-1.0.1.tgz", + "integrity": "sha512-iBPtljfCNcTKNAto0KEtDfZ3qzjJvqE3aTGZsbhjSBlorqpXJlaWWtPO35D+ZImoC3KWejX64o+yPGxhWSTzfg==", + "dev": true + }, + "node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" + }, + "node_modules/combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "dev": true, + "dependencies": { + "delayed-stream": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/commander": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/commander/-/commander-4.1.1.tgz", + "integrity": "sha512-NOKm8xhkzAjzFx8B2v5OAHT+u5pRQc2UCa2Vq9jYL/31o2wi9mxBA7LIFs3sV5VSC49z6pEhfbMULvShKj26WA==", + "dev": true, + "engines": { + "node": ">= 6" + } + }, + "node_modules/component-emitter": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.3.0.tgz", + "integrity": "sha512-Rd3se6QB+sO1TwqZjscQrurpEPIfO0/yYnSin6Q/rD3mOutHvUrCAhJub3r90uNb+SESBuE0QYoB90YdfatsRg==", + "dev": true + }, + "node_modules/concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", + "dev": true + }, + "node_modules/concat-stream": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.6.2.tgz", + "integrity": "sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw==", + "engines": [ + "node >= 0.8" + ], + "dependencies": { + "buffer-from": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^2.2.2", + "typedarray": "^0.0.6" + } + }, + "node_modules/confusing-browser-globals": { + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/confusing-browser-globals/-/confusing-browser-globals-1.0.11.tgz", + "integrity": "sha512-JsPKdmh8ZkmnHxDk55FZ1TqVLvEQTvoByJZRN9jzI0UjxK/QgAmsphz7PGtqgPieQZ/CQcHWXCR7ATDNhGe+YA==", + "dev": true + }, + "node_modules/consola": { + "version": "2.15.3", + "resolved": "https://registry.npmjs.org/consola/-/consola-2.15.3.tgz", + "integrity": "sha512-9vAdYbHj6x2fLKC4+oPH0kFzY/orMZyG2Aj+kNylHxKGJ/Ed4dpNyAQYwJOdqO4zdM7XpVHmyejQDcQHrnuXbw==" + }, + "node_modules/content-disposition": { + "version": "0.5.4", + "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.4.tgz", + "integrity": "sha512-FveZTNuGw04cxlAiWbzi6zTAL/lhehaWbTtgluJh4/E95DqMwTmha3KZN1aAWA8cFIhHzMZUvLevkw5Rqk+tSQ==", + "dependencies": { + "safe-buffer": "5.2.1" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/content-type": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.5.tgz", + "integrity": "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/convert-source-map": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz", + "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==", + "dev": true + }, + "node_modules/cookie": { + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.5.0.tgz", + "integrity": "sha512-YZ3GUyn/o8gfKJlnlX7g7xq4gyO6OSuhGPKaaGssGB2qgDUS0gPgtTvoyZLTt9Ab6dC4hfc9dV5arkvc/OCmrw==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/cookie-signature": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", + "integrity": "sha512-QADzlaHc8icV8I7vbaJXJwod9HWYp8uCqf1xa4OfNu1T7JVxQIrUgOWtHdNDtPiywmFbiS12VjotIXLrKM3orQ==" + }, + "node_modules/cookiejar": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/cookiejar/-/cookiejar-2.1.4.tgz", + "integrity": "sha512-LDx6oHrK+PhzLKJU9j5S7/Y3jM/mUHvD/DeI1WQmJn652iPC5Y4TBzC9l+5OMOXlyTTA+SmVUPm0HQUwpD5Jqw==", + "dev": true + }, + "node_modules/core-util-is": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz", + "integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==" + }, + "node_modules/cors": { + "version": "2.8.5", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", + "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", + "dependencies": { + "object-assign": "^4", + "vary": "^1" + }, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/cosmiconfig": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-7.1.0.tgz", + "integrity": "sha512-AdmX6xUzdNASswsFtmwSt7Vj8po9IuqXm0UXz7QKPuEUmPB4XyjGfaAr2PSuELMwkRMVH1EpIkX5bTZGRB3eCA==", + "dev": true, + "dependencies": { + "@types/parse-json": "^4.0.0", + "import-fresh": "^3.2.1", + "parse-json": "^5.0.0", + "path-type": "^4.0.0", + "yaml": "^1.10.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/create-require": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/create-require/-/create-require-1.1.1.tgz", + "integrity": "sha512-dcKFX3jn0MpIaXjisoRvexIJVEKzaq7z2rZKxf+MSr9TkdmHmsU4m2lcLojrj/FHl8mk5VxMmYA+ftRkP/3oKQ==", + "dev": true + }, + "node_modules/cross-spawn": { + "version": "7.0.3", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-7.0.3.tgz", + "integrity": "sha512-iRDPJKUPVEND7dHPO8rkbOnPpyDygcDFtWjpeWNCgy8WP2rXcxXL8TskReQl6OrB2G7+UJrags1q15Fudc7G6w==", + "dev": true, + "dependencies": { + "path-key": "^3.1.0", + "shebang-command": "^2.0.0", + "which": "^2.0.1" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/debug": { + "version": "4.3.4", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.4.tgz", + "integrity": "sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ==", + "dev": true, + "dependencies": { + "ms": "2.1.2" + }, + "engines": { + "node": ">=6.0" + }, + "peerDependenciesMeta": { + "supports-color": { + "optional": true + } + } + }, + "node_modules/dedent": { + "version": "0.7.0", + "resolved": "https://registry.npmjs.org/dedent/-/dedent-0.7.0.tgz", + "integrity": "sha512-Q6fKUPqnAHAyhiUgFU7BUzLiv0kd8saH9al7tnu5Q/okj6dnupxyTgFIBjVzJATdfIAm9NAsvXNzjaKa+bxVyA==", + "dev": true + }, + "node_modules/deep-is": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.4.tgz", + "integrity": "sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==", + "dev": true + }, + "node_modules/deepmerge": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/deepmerge/-/deepmerge-4.3.0.tgz", + "integrity": "sha512-z2wJZXrmeHdvYJp/Ux55wIjqo81G5Bp4c+oELTW+7ar6SogWHajt5a9gO3s3IDaGSAXjDk0vlQKN3rms8ab3og==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/defaults": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/defaults/-/defaults-1.0.4.tgz", + "integrity": "sha512-eFuaLoy/Rxalv2kr+lqMlUnrDWV+3j4pljOIJgLIhI058IQfWJ7vXhyEIHu+HtC738klGALYxOKDO0bQP3tg8A==", + "dev": true, + "dependencies": { + "clone": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/define-properties": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.1.4.tgz", + "integrity": "sha512-uckOqKcfaVvtBdsVkdPv3XjveQJsNQqmhXgRi8uhvWWuPYZCNlzT8qAyblUgNoXdHdjMTzAqeGjAoli8f+bzPA==", + "dev": true, + "dependencies": { + "has-property-descriptors": "^1.0.0", + "object-keys": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "dev": true, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/depd": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", + "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/destroy": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.2.0.tgz", + "integrity": "sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==", + "engines": { + "node": ">= 0.8", + "npm": "1.2.8000 || >= 1.4.16" + } + }, + "node_modules/detect-newline": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/detect-newline/-/detect-newline-3.1.0.tgz", + "integrity": "sha512-TLz+x/vEXm/Y7P7wn1EJFNLxYpUD4TgMosxY6fAVJUnJMbupHBOncxyWUG9OpTaH9EBD7uFI5LfEgmMOc54DsA==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/dezalgo": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/dezalgo/-/dezalgo-1.0.4.tgz", + "integrity": "sha512-rXSP0bf+5n0Qonsb+SVVfNfIsimO4HEtmnIpPHY8Q1UCzKlQrDMfdobr8nJOOsRgWCyMRqeSBQzmWUMq7zvVig==", + "dev": true, + "dependencies": { + "asap": "^2.0.0", + "wrappy": "1" + } + }, + "node_modules/diff": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/diff/-/diff-4.0.2.tgz", + "integrity": "sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==", + "dev": true, + "engines": { + "node": ">=0.3.1" + } + }, + "node_modules/diff-sequences": { + "version": "29.3.1", + "resolved": "https://registry.npmjs.org/diff-sequences/-/diff-sequences-29.3.1.tgz", + "integrity": "sha512-hlM3QR272NXCi4pq+N4Kok4kOp6EsgOM3ZSpJI7Da3UAs+Ttsi8MRmB6trM/lhyzUxGfOgnpkHtgqm5Q/CTcfQ==", + "dev": true, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/dir-glob": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-3.0.1.tgz", + "integrity": "sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA==", + "dev": true, + "dependencies": { + "path-type": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/doctrine": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", + "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", + "dev": true, + "dependencies": { + "esutils": "^2.0.2" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/ee-first": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", + "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==" + }, + "node_modules/electron-to-chromium": { + "version": "1.4.286", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.286.tgz", + "integrity": "sha512-Vp3CVhmYpgf4iXNKAucoQUDcCrBQX3XLBtwgFqP9BUXuucgvAV9zWp1kYU7LL9j4++s9O+12cb3wMtN4SJy6UQ==", + "dev": true + }, + "node_modules/emittery": { + "version": "0.13.1", + "resolved": "https://registry.npmjs.org/emittery/-/emittery-0.13.1.tgz", + "integrity": "sha512-DeWwawk6r5yR9jFgnDKYt4sLS0LmHJJi3ZOnb5/JdbYwj3nW+FxQnHIjhBKz8YLC7oRNPVM9NQ47I3CVx34eqQ==", + "dev": true, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sindresorhus/emittery?sponsor=1" + } + }, + "node_modules/emoji-regex": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", + "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", + "dev": true + }, + "node_modules/encodeurl": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", + "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w==", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/end-of-stream": { + "version": "1.4.4", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", + "integrity": "sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==", + "dev": true, + "dependencies": { + "once": "^1.4.0" + } + }, + "node_modules/enhanced-resolve": { + "version": "5.12.0", + "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.12.0.tgz", + "integrity": "sha512-QHTXI/sZQmko1cbDoNAa3mJ5qhWUUNAq3vR0/YiD379fWQrcfuoX1+HW2S0MTt7XmoPLapdaDKUtelUSPic7hQ==", + "dev": true, + "dependencies": { + "graceful-fs": "^4.2.4", + "tapable": "^2.2.0" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/enquirer": { + "version": "2.3.6", + "resolved": "https://registry.npmjs.org/enquirer/-/enquirer-2.3.6.tgz", + "integrity": "sha512-yjNnPr315/FjS4zIsUxYguYUPP2e1NK4d7E7ZOLiyYCcbFBiTMyID+2wvm2w6+pZ/odMA7cRkjhsPbltwBOrLg==", + "dev": true, + "dependencies": { + "ansi-colors": "^4.1.1" + }, + "engines": { + "node": ">=8.6" + } + }, + "node_modules/error-ex": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", + "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", + "dev": true, + "dependencies": { + "is-arrayish": "^0.2.1" + } + }, + "node_modules/es-abstract": { + "version": "1.21.1", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.21.1.tgz", + "integrity": "sha512-QudMsPOz86xYz/1dG1OuGBKOELjCh99IIWHLzy5znUB6j8xG2yMA7bfTV86VSqKF+Y/H08vQPR+9jyXpuC6hfg==", + "dev": true, + "dependencies": { + "available-typed-arrays": "^1.0.5", + "call-bind": "^1.0.2", + "es-set-tostringtag": "^2.0.1", + "es-to-primitive": "^1.2.1", + "function-bind": "^1.1.1", + "function.prototype.name": "^1.1.5", + "get-intrinsic": "^1.1.3", + "get-symbol-description": "^1.0.0", + "globalthis": "^1.0.3", + "gopd": "^1.0.1", + "has": "^1.0.3", + "has-property-descriptors": "^1.0.0", + "has-proto": "^1.0.1", + "has-symbols": "^1.0.3", + "internal-slot": "^1.0.4", + "is-array-buffer": "^3.0.1", + "is-callable": "^1.2.7", + "is-negative-zero": "^2.0.2", + "is-regex": "^1.1.4", + "is-shared-array-buffer": "^1.0.2", + "is-string": "^1.0.7", + "is-typed-array": "^1.1.10", + "is-weakref": "^1.0.2", + "object-inspect": "^1.12.2", + "object-keys": "^1.1.1", + "object.assign": "^4.1.4", + "regexp.prototype.flags": "^1.4.3", + "safe-regex-test": "^1.0.0", + "string.prototype.trimend": "^1.0.6", + "string.prototype.trimstart": "^1.0.6", + "typed-array-length": "^1.0.4", + "unbox-primitive": "^1.0.2", + "which-typed-array": "^1.1.9" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/es-module-lexer": { + "version": "0.9.3", + "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-0.9.3.tgz", + "integrity": "sha512-1HQ2M2sPtxwnvOvT1ZClHyQDiggdNjURWpY2we6aMKCQiUVxTmVs2UYPLIrD84sS+kMdUwfBSylbJPwNnBrnHQ==", + "dev": true + }, + "node_modules/es-set-tostringtag": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.0.1.tgz", + "integrity": "sha512-g3OMbtlwY3QewlqAiMLI47KywjWZoEytKr8pf6iTC8uJq5bIAH52Z9pnQ8pVL6whrCto53JZDuUIsifGeLorTg==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.1.3", + "has": "^1.0.3", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-shim-unscopables": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/es-shim-unscopables/-/es-shim-unscopables-1.0.0.tgz", + "integrity": "sha512-Jm6GPcCdC30eMLbZ2x8z2WuRwAws3zTBBKuusffYVUrNj/GVSUAZ+xKMaUpfNDR5IbyNA5LJbaecoUVbmUcB1w==", + "dev": true, + "peer": true, + "dependencies": { + "has": "^1.0.3" + } + }, + "node_modules/es-to-primitive": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.1.tgz", + "integrity": "sha512-QCOllgZJtaUo9miYBcLChTUaHNjJF3PYs1VidD7AwiEj1kYxKeQTctLAezAOH5ZKRH0g2IgPn6KwB4IT8iRpvA==", + "dev": true, + "dependencies": { + "is-callable": "^1.1.4", + "is-date-object": "^1.0.1", + "is-symbol": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/escalade": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", + "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/escape-html": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", + "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==" + }, + "node_modules/escape-string-regexp": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", + "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/eslint": { + "version": "8.2.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.2.0.tgz", + "integrity": "sha512-erw7XmM+CLxTOickrimJ1SiF55jiNlVSp2qqm0NuBWPtHYQCegD5ZMaW0c3i5ytPqL+SSLaCxdvQXFPLJn+ABw==", + "dev": true, + "dependencies": { + "@eslint/eslintrc": "^1.0.4", + "@humanwhocodes/config-array": "^0.6.0", + "ajv": "^6.10.0", + "chalk": "^4.0.0", + "cross-spawn": "^7.0.2", + "debug": "^4.3.2", + "doctrine": "^3.0.0", + "enquirer": "^2.3.5", + "escape-string-regexp": "^4.0.0", + "eslint-scope": "^6.0.0", + "eslint-utils": "^3.0.0", + "eslint-visitor-keys": "^3.0.0", + "espree": "^9.0.0", + "esquery": "^1.4.0", + "esutils": "^2.0.2", + "fast-deep-equal": "^3.1.3", + "file-entry-cache": "^6.0.1", + "functional-red-black-tree": "^1.0.1", + "glob-parent": "^6.0.1", + "globals": "^13.6.0", + "ignore": "^4.0.6", + "import-fresh": "^3.0.0", + "imurmurhash": "^0.1.4", + "is-glob": "^4.0.0", + "js-yaml": "^4.1.0", + "json-stable-stringify-without-jsonify": "^1.0.1", + "levn": "^0.4.1", + "lodash.merge": "^4.6.2", + "minimatch": "^3.0.4", + "natural-compare": "^1.4.0", + "optionator": "^0.9.1", + "progress": "^2.0.0", + "regexpp": "^3.2.0", + "semver": "^7.2.1", + "strip-ansi": "^6.0.1", + "strip-json-comments": "^3.1.0", + "text-table": "^0.2.0", + "v8-compile-cache": "^2.0.3" + }, + "bin": { + "eslint": "bin/eslint.js" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/eslint-config-airbnb-base": { + "version": "15.0.0", + "resolved": "https://registry.npmjs.org/eslint-config-airbnb-base/-/eslint-config-airbnb-base-15.0.0.tgz", + "integrity": "sha512-xaX3z4ZZIcFLvh2oUNvcX5oEofXda7giYmuplVxoOg5A7EXJMrUyqRgR+mhDhPK8LZ4PttFOBvCYDbX3sUoUig==", + "dev": true, + "dependencies": { + "confusing-browser-globals": "^1.0.10", + "object.assign": "^4.1.2", + "object.entries": "^1.1.5", + "semver": "^6.3.0" + }, + "engines": { + "node": "^10.12.0 || >=12.0.0" + }, + "peerDependencies": { + "eslint": "^7.32.0 || ^8.2.0", + "eslint-plugin-import": "^2.25.2" + } + }, + "node_modules/eslint-config-airbnb-base/node_modules/semver": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "dev": true, + "bin": { + "semver": "bin/semver.js" + } + }, + "node_modules/eslint-config-airbnb-typescript": { + "version": "17.0.0", + "resolved": "https://registry.npmjs.org/eslint-config-airbnb-typescript/-/eslint-config-airbnb-typescript-17.0.0.tgz", + "integrity": "sha512-elNiuzD0kPAPTXjFWg+lE24nMdHMtuxgYoD30OyMD6yrW1AhFZPAg27VX7d3tzOErw+dgJTNWfRSDqEcXb4V0g==", + "dev": true, + "dependencies": { + "eslint-config-airbnb-base": "^15.0.0" + }, + "peerDependencies": { + "@typescript-eslint/eslint-plugin": "^5.13.0", + "@typescript-eslint/parser": "^5.0.0", + "eslint": "^7.32.0 || ^8.2.0", + "eslint-plugin-import": "^2.25.3" + } + }, + "node_modules/eslint-import-resolver-node": { + "version": "0.3.7", + "resolved": "https://registry.npmjs.org/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.7.tgz", + "integrity": "sha512-gozW2blMLJCeFpBwugLTGyvVjNoeo1knonXAcatC6bjPBZitotxdWf7Gimr25N4c0AAOo4eOUfaG82IJPDpqCA==", + "dev": true, + "peer": true, + "dependencies": { + "debug": "^3.2.7", + "is-core-module": "^2.11.0", + "resolve": "^1.22.1" + } + }, + "node_modules/eslint-import-resolver-node/node_modules/debug": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", + "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "dev": true, + "peer": true, + "dependencies": { + "ms": "^2.1.1" + } + }, + "node_modules/eslint-module-utils": { + "version": "2.7.4", + "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.7.4.tgz", + "integrity": "sha512-j4GT+rqzCoRKHwURX7pddtIPGySnX9Si/cgMI5ztrcqOPtk5dDEeZ34CQVPphnqkJytlc97Vuk05Um2mJ3gEQA==", + "dev": true, + "peer": true, + "dependencies": { + "debug": "^3.2.7" + }, + "engines": { + "node": ">=4" + }, + "peerDependenciesMeta": { + "eslint": { + "optional": true + } + } + }, + "node_modules/eslint-module-utils/node_modules/debug": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", + "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "dev": true, + "peer": true, + "dependencies": { + "ms": "^2.1.1" + } + }, + "node_modules/eslint-plugin-import": { + "version": "2.27.5", + "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.27.5.tgz", + "integrity": "sha512-LmEt3GVofgiGuiE+ORpnvP+kAm3h6MLZJ4Q5HCyHADofsb4VzXFsRiWj3c0OFiV+3DWFh0qg3v9gcPlfc3zRow==", + "dev": true, + "peer": true, + "dependencies": { + "array-includes": "^3.1.6", + "array.prototype.flat": "^1.3.1", + "array.prototype.flatmap": "^1.3.1", + "debug": "^3.2.7", + "doctrine": "^2.1.0", + "eslint-import-resolver-node": "^0.3.7", + "eslint-module-utils": "^2.7.4", + "has": "^1.0.3", + "is-core-module": "^2.11.0", + "is-glob": "^4.0.3", + "minimatch": "^3.1.2", + "object.values": "^1.1.6", + "resolve": "^1.22.1", + "semver": "^6.3.0", + "tsconfig-paths": "^3.14.1" + }, + "engines": { + "node": ">=4" + }, + "peerDependencies": { + "eslint": "^2 || ^3 || ^4 || ^5 || ^6 || ^7.2.0 || ^8" + } + }, + "node_modules/eslint-plugin-import/node_modules/debug": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", + "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", + "dev": true, + "peer": true, + "dependencies": { + "ms": "^2.1.1" + } + }, + "node_modules/eslint-plugin-import/node_modules/doctrine": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", + "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", + "dev": true, + "peer": true, + "dependencies": { + "esutils": "^2.0.2" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/eslint-plugin-import/node_modules/json5": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/json5/-/json5-1.0.2.tgz", + "integrity": "sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA==", + "dev": true, + "peer": true, + "dependencies": { + "minimist": "^1.2.0" + }, + "bin": { + "json5": "lib/cli.js" + } + }, + "node_modules/eslint-plugin-import/node_modules/semver": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "dev": true, + "peer": true, + "bin": { + "semver": "bin/semver.js" + } + }, + "node_modules/eslint-plugin-import/node_modules/strip-bom": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", + "integrity": "sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==", + "dev": true, + "peer": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/eslint-plugin-import/node_modules/tsconfig-paths": { + "version": "3.14.1", + "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.14.1.tgz", + "integrity": "sha512-fxDhWnFSLt3VuTwtvJt5fpwxBHg5AdKWMsgcPOOIilyjymcYVZoCQF8fvFRezCNfblEXmi+PcM1eYHeOAgXCOQ==", + "dev": true, + "peer": true, + "dependencies": { + "@types/json5": "^0.0.29", + "json5": "^1.0.1", + "minimist": "^1.2.6", + "strip-bom": "^3.0.0" + } + }, + "node_modules/eslint-scope": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", + "integrity": "sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==", + "dev": true, + "dependencies": { + "esrecurse": "^4.3.0", + "estraverse": "^4.1.1" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/eslint-utils": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/eslint-utils/-/eslint-utils-3.0.0.tgz", + "integrity": "sha512-uuQC43IGctw68pJA1RgbQS8/NP7rch6Cwd4j3ZBtgo4/8Flj4eGE7ZYSZRN3iq5pVUv6GPdW5Z1RFleo84uLDA==", + "dev": true, + "dependencies": { + "eslint-visitor-keys": "^2.0.0" + }, + "engines": { + "node": "^10.0.0 || ^12.0.0 || >= 14.0.0" + }, + "funding": { + "url": "https://github.com/sponsors/mysticatea" + }, + "peerDependencies": { + "eslint": ">=5" + } + }, + "node_modules/eslint-utils/node_modules/eslint-visitor-keys": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-2.1.0.tgz", + "integrity": "sha512-0rSmRBzXgDzIsD6mGdJgevzgezI534Cer5L/vyMX0kHzT/jiB43jRhd9YUlMGYLQy2zprNmoT8qasCGtY+QaKw==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/eslint-visitor-keys": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-3.3.0.tgz", + "integrity": "sha512-mQ+suqKJVyeuwGYHAdjMFqjCyfl8+Ldnxuyp3ldiMBFKkvytrXUZWaiPCEav8qDHKty44bD+qV1IP4T+w+xXRA==", + "dev": true, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + } + }, + "node_modules/eslint/node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/eslint/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/eslint/node_modules/eslint-scope": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-6.0.0.tgz", + "integrity": "sha512-uRDL9MWmQCkaFus8RF5K9/L/2fn+80yoW3jkD53l4shjCh26fCtvJGasxjUqP5OT87SYTxCVA3BwTUzuELx9kA==", + "dev": true, + "dependencies": { + "esrecurse": "^4.3.0", + "estraverse": "^5.2.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + } + }, + "node_modules/eslint/node_modules/estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/eslint/node_modules/glob-parent": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-6.0.2.tgz", + "integrity": "sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==", + "dev": true, + "dependencies": { + "is-glob": "^4.0.3" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/eslint/node_modules/ignore": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", + "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", + "dev": true, + "engines": { + "node": ">= 4" + } + }, + "node_modules/eslint/node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "node_modules/espree": { + "version": "9.4.1", + "resolved": "https://registry.npmjs.org/espree/-/espree-9.4.1.tgz", + "integrity": "sha512-XwctdmTO6SIvCzd9810yyNzIrOrqNYV9Koizx4C/mRhf9uq0o4yHoCEU/670pOxOL/MSraektvSAji79kX90Vg==", + "dev": true, + "dependencies": { + "acorn": "^8.8.0", + "acorn-jsx": "^5.3.2", + "eslint-visitor-keys": "^3.3.0" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/eslint" + } + }, + "node_modules/esprima": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", + "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", + "dev": true, + "bin": { + "esparse": "bin/esparse.js", + "esvalidate": "bin/esvalidate.js" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/esquery": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.4.0.tgz", + "integrity": "sha512-cCDispWt5vHHtwMY2YrAQ4ibFkAL8RbH5YGBnZBc90MolvvfkkQcJro/aZiAQUlQ3qgrYS6D6v8Gc5G5CQsc9w==", + "dev": true, + "dependencies": { + "estraverse": "^5.1.0" + }, + "engines": { + "node": ">=0.10" + } + }, + "node_modules/esquery/node_modules/estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/esrecurse": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", + "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", + "dev": true, + "dependencies": { + "estraverse": "^5.2.0" + }, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/esrecurse/node_modules/estraverse": { + "version": "5.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", + "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", + "dev": true, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/estraverse": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.3.0.tgz", + "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==", + "dev": true, + "engines": { + "node": ">=4.0" + } + }, + "node_modules/esutils": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.3.tgz", + "integrity": "sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/etag": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", + "integrity": "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/events": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/events/-/events-3.3.0.tgz", + "integrity": "sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==", + "dev": true, + "engines": { + "node": ">=0.8.x" + } + }, + "node_modules/execa": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/execa/-/execa-5.1.1.tgz", + "integrity": "sha512-8uSpZZocAZRBAPIEINJj3Lo9HyGitllczc27Eh5YYojjMFMn8yHMDMaUHE2Jqfq05D/wucwI4JGURyXt1vchyg==", + "dev": true, + "dependencies": { + "cross-spawn": "^7.0.3", + "get-stream": "^6.0.0", + "human-signals": "^2.1.0", + "is-stream": "^2.0.0", + "merge-stream": "^2.0.0", + "npm-run-path": "^4.0.1", + "onetime": "^5.1.2", + "signal-exit": "^3.0.3", + "strip-final-newline": "^2.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sindresorhus/execa?sponsor=1" + } + }, + "node_modules/exit": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/exit/-/exit-0.1.2.tgz", + "integrity": "sha512-Zk/eNKV2zbjpKzrsQ+n1G6poVbErQxJ0LBOJXaKZ1EViLzH+hrLu9cdXI4zw9dBQJslwBEpbQ2P1oS7nDxs6jQ==", + "dev": true, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/expect": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/expect/-/expect-29.4.1.tgz", + "integrity": "sha512-OKrGESHOaMxK3b6zxIq9SOW8kEXztKff/Dvg88j4xIJxur1hspEbedVkR3GpHe5LO+WB2Qw7OWN0RMTdp6as5A==", + "dev": true, + "dependencies": { + "@jest/expect-utils": "^29.4.1", + "jest-get-type": "^29.2.0", + "jest-matcher-utils": "^29.4.1", + "jest-message-util": "^29.4.1", + "jest-util": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/express": { + "version": "4.18.2", + "resolved": "https://registry.npmjs.org/express/-/express-4.18.2.tgz", + "integrity": "sha512-5/PsL6iGPdfQ/lKM1UuielYgv3BUoJfz1aUwU9vHZ+J7gyvwdQXFEBIEIaxeGf0GIcreATNyBExtalisDbuMqQ==", + "dependencies": { + "accepts": "~1.3.8", + "array-flatten": "1.1.1", + "body-parser": "1.20.1", + "content-disposition": "0.5.4", + "content-type": "~1.0.4", + "cookie": "0.5.0", + "cookie-signature": "1.0.6", + "debug": "2.6.9", + "depd": "2.0.0", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "finalhandler": "1.2.0", + "fresh": "0.5.2", + "http-errors": "2.0.0", + "merge-descriptors": "1.0.1", + "methods": "~1.1.2", + "on-finished": "2.4.1", + "parseurl": "~1.3.3", + "path-to-regexp": "0.1.7", + "proxy-addr": "~2.0.7", + "qs": "6.11.0", + "range-parser": "~1.2.1", + "safe-buffer": "5.2.1", + "send": "0.18.0", + "serve-static": "1.15.0", + "setprototypeof": "1.2.0", + "statuses": "2.0.1", + "type-is": "~1.6.18", + "utils-merge": "1.0.1", + "vary": "~1.1.2" + }, + "engines": { + "node": ">= 0.10.0" + } + }, + "node_modules/express/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/express/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" + }, + "node_modules/express/node_modules/path-to-regexp": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", + "integrity": "sha512-5DFkuoqlv1uYQKxy8omFBeJPQcdoE07Kv2sferDCrAq1ohOU+MSDswDIbnx3YAM60qIOnYa53wBhXW0EbMonrQ==" + }, + "node_modules/external-editor": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-3.1.0.tgz", + "integrity": "sha512-hMQ4CX1p1izmuLYyZqLMO/qGNw10wSv9QDCPfzXfyFrOaCSSoRfqE1Kf1s5an66J5JZC62NewG+mK49jOCtQew==", + "dev": true, + "dependencies": { + "chardet": "^0.7.0", + "iconv-lite": "^0.4.24", + "tmp": "^0.0.33" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/fast-deep-equal": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", + "dev": true + }, + "node_modules/fast-glob": { + "version": "3.2.12", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.12.tgz", + "integrity": "sha512-DVj4CQIYYow0BlaelwK1pHl5n5cRSJfM60UA0zK891sVInoPri2Ekj7+e1CT3/3qxXenpI+nBBmQAcJPJgaj4w==", + "dev": true, + "dependencies": { + "@nodelib/fs.stat": "^2.0.2", + "@nodelib/fs.walk": "^1.2.3", + "glob-parent": "^5.1.2", + "merge2": "^1.3.0", + "micromatch": "^4.0.4" + }, + "engines": { + "node": ">=8.6.0" + } + }, + "node_modules/fast-json-stable-stringify": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", + "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", + "dev": true + }, + "node_modules/fast-levenshtein": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", + "integrity": "sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==", + "dev": true + }, + "node_modules/fast-safe-stringify": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/fast-safe-stringify/-/fast-safe-stringify-2.1.1.tgz", + "integrity": "sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==" + }, + "node_modules/fastq": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.15.0.tgz", + "integrity": "sha512-wBrocU2LCXXa+lWBt8RoIRD89Fi8OdABODa/kEnyeyjS5aZO5/GNvI5sEINADqP/h8M29UHTHUb53sUu5Ihqdw==", + "dev": true, + "dependencies": { + "reusify": "^1.0.4" + } + }, + "node_modules/fb-watchman": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/fb-watchman/-/fb-watchman-2.0.2.tgz", + "integrity": "sha512-p5161BqbuCaSnB8jIbzQHOlpgsPmK5rJVDfDKO91Axs5NC1uu3HRQm6wt9cd9/+GtQQIO53JdGXXoyDpTAsgYA==", + "dev": true, + "dependencies": { + "bser": "2.1.1" + } + }, + "node_modules/figures": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/figures/-/figures-3.2.0.tgz", + "integrity": "sha512-yaduQFRKLXYOGgEn6AZau90j3ggSOyiqXU0F9JZfeXYhNa+Jk4X+s45A2zg5jns87GAFa34BBm2kXw4XpNcbdg==", + "dev": true, + "dependencies": { + "escape-string-regexp": "^1.0.5" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/figures/node_modules/escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha512-vbRorB5FUQWvla16U8R/qgaFIya2qGzwDrNmCZuYKrbdSUMG6I1ZCGQRefkRVhuOkIGVne7BQ35DSfo1qvJqFg==", + "dev": true, + "engines": { + "node": ">=0.8.0" + } + }, + "node_modules/file-entry-cache": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-6.0.1.tgz", + "integrity": "sha512-7Gps/XWymbLk2QLYK4NzpMOrYjMhdIxXuIvy2QBsLE6ljuodKvdkWs/cpyJJ3CVIVpH0Oi1Hvg1ovbMzLdFBBg==", + "dev": true, + "dependencies": { + "flat-cache": "^3.0.4" + }, + "engines": { + "node": "^10.12.0 || >=12.0.0" + } + }, + "node_modules/fill-range": { + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz", + "integrity": "sha512-qOo9F+dMUmC2Lcb4BbVvnKJxTPjCm+RRpe4gDuGrzkL7mEVl/djYSu2OdQ2Pa302N4oqkSg9ir6jaLWJ2USVpQ==", + "dev": true, + "dependencies": { + "to-regex-range": "^5.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/finalhandler": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.2.0.tgz", + "integrity": "sha512-5uXcUVftlQMFnWC9qu/svkWv3GTd2PfUhK/3PLkYNAe7FbqJMt3515HaxE6eRL74GdsriiwujiawdaB1BpEISg==", + "dependencies": { + "debug": "2.6.9", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "on-finished": "2.4.1", + "parseurl": "~1.3.3", + "statuses": "2.0.1", + "unpipe": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/finalhandler/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/finalhandler/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" + }, + "node_modules/flat-cache": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-3.0.4.tgz", + "integrity": "sha512-dm9s5Pw7Jc0GvMYbshN6zchCA9RgQlzzEZX3vylR9IqFfS8XciblUXOKfW6SiuJ0e13eDYZoZV5wdrev7P3Nwg==", + "dev": true, + "dependencies": { + "flatted": "^3.1.0", + "rimraf": "^3.0.2" + }, + "engines": { + "node": "^10.12.0 || >=12.0.0" + } + }, + "node_modules/flat-cache/node_modules/rimraf": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", + "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", + "dev": true, + "dependencies": { + "glob": "^7.1.3" + }, + "bin": { + "rimraf": "bin.js" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/flatted": { + "version": "3.2.7", + "resolved": "https://registry.npmjs.org/flatted/-/flatted-3.2.7.tgz", + "integrity": "sha512-5nqDSxl8nn5BSNxyR3n4I6eDmbolI6WT+QqR547RwxQapgjQBmtktdP+HTBb/a/zLsbzERTONyUB5pefh5TtjQ==", + "dev": true + }, + "node_modules/for-each": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", + "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", + "dev": true, + "dependencies": { + "is-callable": "^1.1.3" + } + }, + "node_modules/fork-ts-checker-webpack-plugin": { + "version": "7.3.0", + "resolved": "https://registry.npmjs.org/fork-ts-checker-webpack-plugin/-/fork-ts-checker-webpack-plugin-7.3.0.tgz", + "integrity": "sha512-IN+XTzusCjR5VgntYFgxbxVx3WraPRnKehBFrf00cMSrtUuW9MsG9dhL6MWpY6MkjC3wVwoujfCDgZZCQwbswA==", + "dev": true, + "dependencies": { + "@babel/code-frame": "^7.16.7", + "chalk": "^4.1.2", + "chokidar": "^3.5.3", + "cosmiconfig": "^7.0.1", + "deepmerge": "^4.2.2", + "fs-extra": "^10.0.0", + "memfs": "^3.4.1", + "minimatch": "^3.0.4", + "node-abort-controller": "^3.0.1", + "schema-utils": "^3.1.1", + "semver": "^7.3.5", + "tapable": "^2.2.1" + }, + "engines": { + "node": ">=12.13.0", + "yarn": ">=1.0.0" + }, + "peerDependencies": { + "typescript": ">3.6.0", + "vue-template-compiler": "*", + "webpack": "^5.11.0" + }, + "peerDependenciesMeta": { + "vue-template-compiler": { + "optional": true + } + } + }, + "node_modules/fork-ts-checker-webpack-plugin/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/fork-ts-checker-webpack-plugin/node_modules/fs-extra": { + "version": "10.1.0", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-10.1.0.tgz", + "integrity": "sha512-oRXApq54ETRj4eMiFzGnHWGy+zo5raudjuxN0b8H7s/RU2oW0Wvsx9O0ACRN/kRq9E8Vu/ReskGB5o3ji+FzHQ==", + "dev": true, + "dependencies": { + "graceful-fs": "^4.2.0", + "jsonfile": "^6.0.1", + "universalify": "^2.0.0" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/form-data": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.0.tgz", + "integrity": "sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==", + "dev": true, + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/formidable": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/formidable/-/formidable-2.1.2.tgz", + "integrity": "sha512-CM3GuJ57US06mlpQ47YcunuUZ9jpm8Vx+P2CGt2j7HpgkKZO/DJYQ0Bobim8G6PFQmK5lOqOOdUXboU+h73A4g==", + "dev": true, + "dependencies": { + "dezalgo": "^1.0.4", + "hexoid": "^1.0.0", + "once": "^1.4.0", + "qs": "^6.11.0" + }, + "funding": { + "url": "https://ko-fi.com/tunnckoCore/commissions" + } + }, + "node_modules/forwarded": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", + "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/fresh": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", + "integrity": "sha512-zJ2mQYM18rEFOudeV4GShTGIQ7RbzA7ozbU9I/XBpm7kqgMywgmylMwXHxZJmkVoYkna9d2pVXVXPdYTP9ej8Q==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/fs-extra": { + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-11.1.0.tgz", + "integrity": "sha512-0rcTq621PD5jM/e0a3EJoGC/1TC5ZBCERW82LQuwfGnCa1V8w7dpYH1yNu+SLb6E5dkeCBzKEyLGlFrnr+dUyw==", + "dev": true, + "dependencies": { + "graceful-fs": "^4.2.0", + "jsonfile": "^6.0.1", + "universalify": "^2.0.0" + }, + "engines": { + "node": ">=14.14" + } + }, + "node_modules/fs-monkey": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/fs-monkey/-/fs-monkey-1.0.3.tgz", + "integrity": "sha512-cybjIfiiE+pTWicSCLFHSrXZ6EilF30oh91FDP9S2B051prEa7QWfrVTQm10/dDpswBDXZugPa1Ogu8Yh+HV0Q==", + "dev": true + }, + "node_modules/fs.realpath": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", + "dev": true + }, + "node_modules/fsevents": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz", + "integrity": "sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==", + "dev": true, + "hasInstallScript": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, + "node_modules/function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==" + }, + "node_modules/function.prototype.name": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/function.prototype.name/-/function.prototype.name-1.1.5.tgz", + "integrity": "sha512-uN7m/BzVKQnCUF/iW8jYea67v++2u7m5UgENbHRtdDVclOUP+FMPlCNdmk0h/ysGyo2tavMJEDqJAkJdRa1vMA==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.3", + "es-abstract": "^1.19.0", + "functions-have-names": "^1.2.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/functional-red-black-tree": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz", + "integrity": "sha512-dsKNQNdj6xA3T+QlADDA7mOSlX0qiMINjn0cgr+eGHGsbSHzTabcIogz2+p/iqP1Xs6EP/sS2SbqH+brGTbq0g==", + "dev": true + }, + "node_modules/functions-have-names": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/functions-have-names/-/functions-have-names-1.2.3.tgz", + "integrity": "sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/gensync": { + "version": "1.0.0-beta.2", + "resolved": "https://registry.npmjs.org/gensync/-/gensync-1.0.0-beta.2.tgz", + "integrity": "sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==", + "dev": true, + "engines": { + "node": ">=6.9.0" + } + }, + "node_modules/get-caller-file": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz", + "integrity": "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==", + "dev": true, + "engines": { + "node": "6.* || 8.* || >= 10.*" + } + }, + "node_modules/get-intrinsic": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.0.tgz", + "integrity": "sha512-L049y6nFOuom5wGyRc3/gdTLO94dySVKRACj1RmJZBQXlbTMhtNIgkWkUHq+jYmZvKf14EW1EoJnnjbmoHij0Q==", + "dependencies": { + "function-bind": "^1.1.1", + "has": "^1.0.3", + "has-symbols": "^1.0.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/get-package-type": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/get-package-type/-/get-package-type-0.1.0.tgz", + "integrity": "sha512-pjzuKtY64GYfWizNAJ0fr9VqttZkNiK2iS430LtIHzjBEr6bX8Am2zm4sW4Ro5wjWW5cAlRL1qAMTcXbjNAO2Q==", + "dev": true, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/get-stream": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-6.0.1.tgz", + "integrity": "sha512-ts6Wi+2j3jQjqi70w5AlN8DFnkSwC+MqmxEzdEALB2qXZYV3X/b1CTfgPLGJNMeAWxdPfU8FO1ms3NUfaHCPYg==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/get-symbol-description": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/get-symbol-description/-/get-symbol-description-1.0.0.tgz", + "integrity": "sha512-2EmdH1YvIQiZpltCNgkuiUnyukzxM/R6NDJX31Ke3BG1Nq5b0S2PhX59UKi9vZpPDQVdqn+1IcaAwnzTT5vCjw==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/glob": { + "version": "7.2.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", + "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", + "dev": true, + "dependencies": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.1.1", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + }, + "engines": { + "node": "*" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/glob-parent": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-5.1.2.tgz", + "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", + "dev": true, + "dependencies": { + "is-glob": "^4.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/glob-to-regexp": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/glob-to-regexp/-/glob-to-regexp-0.4.1.tgz", + "integrity": "sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==", + "dev": true + }, + "node_modules/globals": { + "version": "13.20.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-13.20.0.tgz", + "integrity": "sha512-Qg5QtVkCy/kv3FUSlu4ukeZDVf9ee0iXLAUYX13gbR17bnejFTzr4iS9bY7kwCf1NztRNm1t91fjOiyx4CSwPQ==", + "dev": true, + "dependencies": { + "type-fest": "^0.20.2" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/globalthis": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/globalthis/-/globalthis-1.0.3.tgz", + "integrity": "sha512-sFdI5LyBiNTHjRd7cGPWapiHWMOXKyuBNX/cWJ3NfzrZQVa8GI/8cofCl74AOVqq9W5kNmguTIzJ/1s2gyI9wA==", + "dev": true, + "dependencies": { + "define-properties": "^1.1.3" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/globby": { + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/globby/-/globby-11.1.0.tgz", + "integrity": "sha512-jhIXaOzy1sb8IyocaruWSn1TjmnBVs8Ayhcy83rmxNJ8q2uWKCAj3CnJY+KpGSXCueAPc0i05kVvVKtP1t9S3g==", + "dev": true, + "dependencies": { + "array-union": "^2.1.0", + "dir-glob": "^3.0.1", + "fast-glob": "^3.2.9", + "ignore": "^5.2.0", + "merge2": "^1.4.1", + "slash": "^3.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/gopd": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.0.1.tgz", + "integrity": "sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.1.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/graceful-fs": { + "version": "4.2.10", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.10.tgz", + "integrity": "sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==", + "dev": true + }, + "node_modules/grapheme-splitter": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/grapheme-splitter/-/grapheme-splitter-1.0.4.tgz", + "integrity": "sha512-bzh50DW9kTPM00T8y4o8vQg89Di9oLJVLW/KaOGIXJWP/iqCN6WKYkbNOF04vFLJhwcpYUh9ydh/+5vpOqV4YQ==", + "dev": true + }, + "node_modules/has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "dependencies": { + "function-bind": "^1.1.1" + }, + "engines": { + "node": ">= 0.4.0" + } + }, + "node_modules/has-bigints": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.0.2.tgz", + "integrity": "sha512-tSvCKtBr9lkF0Ex0aQiP9N+OpV4zi2r/Nee5VkRDbaqv35RLYMzbwQfFSZZH0kR+Rd6302UJZ2p/bJCEoR3VoQ==", + "dev": true, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "engines": { + "node": ">=8" + } + }, + "node_modules/has-property-descriptors": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.0.tgz", + "integrity": "sha512-62DVLZGoiEBDHQyqG4w9xCuZ7eJEwNmJRWw2VY84Oedb7WFcA27fiEVe8oUQx9hAUJ4ekurquucTGwsyO1XGdQ==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.1.1" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-proto": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.0.1.tgz", + "integrity": "sha512-7qE+iP+O+bgF9clE5+UoBFzE65mlBiVj3tKCrlNQ0Ogwm0BjpT/gK4SlLYDMybDh5I3TCTKnPPa0oMG7JDYrhg==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-symbols": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", + "integrity": "sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==", + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/has-tostringtag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.0.tgz", + "integrity": "sha512-kFjcSNhnlGV1kyoGk7OXKSawH5JOb/LzUc5w9B02hOTO0dfFRjbHQKvg1d6cf3HbeUmtU9VbbV3qzZ2Teh97WQ==", + "dev": true, + "dependencies": { + "has-symbols": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/hexoid": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/hexoid/-/hexoid-1.0.0.tgz", + "integrity": "sha512-QFLV0taWQOZtvIRIAdBChesmogZrtuXvVWsFHZTk2SU+anspqZ2vMnoLg7IE1+Uk16N19APic1BuF8bC8c2m5g==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/html-escaper": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/html-escaper/-/html-escaper-2.0.2.tgz", + "integrity": "sha512-H2iMtd0I4Mt5eYiapRdIDjp+XzelXQ0tFE4JS7YFwFevXXMmOp9myNrUvCg0D6ws8iqkRPBfKHgbwig1SmlLfg==", + "dev": true + }, + "node_modules/http-errors": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.0.tgz", + "integrity": "sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==", + "dependencies": { + "depd": "2.0.0", + "inherits": "2.0.4", + "setprototypeof": "1.2.0", + "statuses": "2.0.1", + "toidentifier": "1.0.1" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/human-signals": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/human-signals/-/human-signals-2.1.0.tgz", + "integrity": "sha512-B4FFZ6q/T2jhhksgkbEW3HBvWIfDW85snkQgawt07S7J5QXTk6BkNV+0yAeZrM5QpMAdYlocGoljn0sJ/WQkFw==", + "dev": true, + "engines": { + "node": ">=10.17.0" + } + }, + "node_modules/iconv-lite": { + "version": "0.4.24", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", + "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", + "dependencies": { + "safer-buffer": ">= 2.1.2 < 3" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/ieee754": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", + "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ] + }, + "node_modules/ignore": { + "version": "5.2.4", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.2.4.tgz", + "integrity": "sha512-MAb38BcSbH0eHNBxn7ql2NH/kX33OkB3lZ1BNdh7ENeRChHTYsTvWrMubiIAMNS2llXEEgZ1MUOBtXChP3kaFQ==", + "dev": true, + "engines": { + "node": ">= 4" + } + }, + "node_modules/import-fresh": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.0.tgz", + "integrity": "sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw==", + "dev": true, + "dependencies": { + "parent-module": "^1.0.0", + "resolve-from": "^4.0.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/import-local": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/import-local/-/import-local-3.1.0.tgz", + "integrity": "sha512-ASB07uLtnDs1o6EHjKpX34BKYDSqnFerfTOJL2HvMqF70LnxpjkzDB8J44oT9pu4AMPkQwf8jl6szgvNd2tRIg==", + "dev": true, + "dependencies": { + "pkg-dir": "^4.2.0", + "resolve-cwd": "^3.0.0" + }, + "bin": { + "import-local-fixture": "fixtures/cli.js" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==", + "dev": true, + "engines": { + "node": ">=0.8.19" + } + }, + "node_modules/inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==", + "dev": true, + "dependencies": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "node_modules/inherits": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==" + }, + "node_modules/inquirer": { + "version": "7.3.3", + "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-7.3.3.tgz", + "integrity": "sha512-JG3eIAj5V9CwcGvuOmoo6LB9kbAYT8HXffUl6memuszlwDC/qvFAJw49XJ5NROSFNPxp3iQg1GqkFhaY/CR0IA==", + "dev": true, + "dependencies": { + "ansi-escapes": "^4.2.1", + "chalk": "^4.1.0", + "cli-cursor": "^3.1.0", + "cli-width": "^3.0.0", + "external-editor": "^3.0.3", + "figures": "^3.0.0", + "lodash": "^4.17.19", + "mute-stream": "0.0.8", + "run-async": "^2.4.0", + "rxjs": "^6.6.0", + "string-width": "^4.1.0", + "strip-ansi": "^6.0.0", + "through": "^2.3.6" + }, + "engines": { + "node": ">=8.0.0" + } + }, + "node_modules/inquirer/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/inquirer/node_modules/rxjs": { + "version": "6.6.7", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.6.7.tgz", + "integrity": "sha512-hTdwr+7yYNIT5n4AMYp85KA6yw2Va0FLa3Rguvbpa4W3I5xynaBZo41cM3XM+4Q6fRMj3sBYIR1VAmZMXYJvRQ==", + "dev": true, + "dependencies": { + "tslib": "^1.9.0" + }, + "engines": { + "npm": ">=2.0.0" + } + }, + "node_modules/inquirer/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "dev": true + }, + "node_modules/internal-slot": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.0.4.tgz", + "integrity": "sha512-tA8URYccNzMo94s5MQZgH8NB/XTa6HsOo0MLfXTKKEnHVVdegzaQoFZ7Jp44bdvLvY2waT5dc+j5ICEswhi7UQ==", + "dev": true, + "dependencies": { + "get-intrinsic": "^1.1.3", + "has": "^1.0.3", + "side-channel": "^1.0.4" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/interpret": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.4.0.tgz", + "integrity": "sha512-agE4QfB2Lkp9uICn7BAqoscw4SZP9kTE2hxiFI3jBPmXJfdqiahTbUuKGsMoN2GtqL9AxhYioAcVvgsb1HvRbA==", + "dev": true, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/ipaddr.js": { + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", + "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==", + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/is-array-buffer": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-3.0.1.tgz", + "integrity": "sha512-ASfLknmY8Xa2XtB4wmbz13Wu202baeA18cJBCeCy0wXUHZF0IPyVEXqKEcd+t2fNSLLL1vC6k7lxZEojNbISXQ==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.1.3", + "is-typed-array": "^1.1.10" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-arrayish": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", + "integrity": "sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg==", + "dev": true + }, + "node_modules/is-bigint": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-bigint/-/is-bigint-1.0.4.tgz", + "integrity": "sha512-zB9CruMamjym81i2JZ3UMn54PKGsQzsJeo6xvN3HJJ4CAsQNB6iRutp2To77OfCNuoxspsIhzaPoO1zyCEhFOg==", + "dev": true, + "dependencies": { + "has-bigints": "^1.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-binary-path": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz", + "integrity": "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==", + "dev": true, + "dependencies": { + "binary-extensions": "^2.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/is-boolean-object": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/is-boolean-object/-/is-boolean-object-1.1.2.tgz", + "integrity": "sha512-gDYaKHJmnj4aWxyj6YHyXVpdQawtVLHU5cb+eztPGczf6cjuTdwve5ZIEfgXqH4e57An1D1AKf8CZ3kYrQRqYA==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-callable": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz", + "integrity": "sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-core-module": { + "version": "2.11.0", + "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.11.0.tgz", + "integrity": "sha512-RRjxlvLDkD1YJwDbroBHMb+cukurkDWNyHx7D3oNB5x9rb5ogcksMC5wHCadcXoo67gVr/+3GFySh3134zi6rw==", + "dev": true, + "dependencies": { + "has": "^1.0.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-date-object": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.5.tgz", + "integrity": "sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ==", + "dev": true, + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-fullwidth-code-point": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz", + "integrity": "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/is-generator-fn": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-generator-fn/-/is-generator-fn-2.1.0.tgz", + "integrity": "sha512-cTIB4yPYL/Grw0EaSzASzg6bBy9gqCofvWN8okThAYIxKJZC+udlRAmGbM0XLeniEJSs8uEgHPGuHSe1XsOLSQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/is-glob": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.3.tgz", + "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", + "dev": true, + "dependencies": { + "is-extglob": "^2.1.1" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-interactive": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-interactive/-/is-interactive-1.0.0.tgz", + "integrity": "sha512-2HvIEKRoqS62guEC+qBjpvRubdX910WCMuJTZ+I9yvqKU2/12eSL549HMwtabb4oupdj2sMP50k+XJfB/8JE6w==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/is-negative-zero": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.2.tgz", + "integrity": "sha512-dqJvarLawXsFbNDeJW7zAz8ItJ9cd28YufuuFzh0G8pNHjJMnY08Dv7sYX2uF5UpQOwieAeOExEYAWWfu7ZZUA==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-number": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", + "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", + "dev": true, + "engines": { + "node": ">=0.12.0" + } + }, + "node_modules/is-number-object": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.0.7.tgz", + "integrity": "sha512-k1U0IRzLMo7ZlYIfzRu23Oh6MiIFasgpb9X76eqfFZAqwH44UI4KTBvBYIZ1dSL9ZzChTB9ShHfLkR4pdW5krQ==", + "dev": true, + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-regex": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.1.4.tgz", + "integrity": "sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-shared-array-buffer": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-shared-array-buffer/-/is-shared-array-buffer-1.0.2.tgz", + "integrity": "sha512-sqN2UDu1/0y6uvXyStCOzyhAjCSlHceFoMKJW8W9EU9cvic/QdsZ0kEU93HEy3IUEFZIiH/3w+AH/UQbPHNdhA==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-stream": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", + "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/is-string": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/is-string/-/is-string-1.0.7.tgz", + "integrity": "sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg==", + "dev": true, + "dependencies": { + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-symbol": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.4.tgz", + "integrity": "sha512-C/CPBqKWnvdcxqIARxyOh4v1UUEOCHpgDa0WYgpKDFMszcrPcffg5uhwSgPCLD2WWxmq6isisz87tzT01tuGhg==", + "dev": true, + "dependencies": { + "has-symbols": "^1.0.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-typed-array": { + "version": "1.1.10", + "resolved": "https://registry.npmjs.org/is-typed-array/-/is-typed-array-1.1.10.tgz", + "integrity": "sha512-PJqgEHiWZvMpaFZ3uTc8kHPM4+4ADTlDniuQL7cU/UDA0Ql7F70yGfHph3cLNe+c9toaigv+DFzTJKhc2CtO6A==", + "dev": true, + "dependencies": { + "available-typed-arrays": "^1.0.5", + "call-bind": "^1.0.2", + "for-each": "^0.3.3", + "gopd": "^1.0.1", + "has-tostringtag": "^1.0.0" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/is-unicode-supported": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/is-unicode-supported/-/is-unicode-supported-0.1.0.tgz", + "integrity": "sha512-knxG2q4UC3u8stRGyAVJCOdxFmv5DZiRcdlIaAQXAbSfJya+OhopNotLQrstBhququ4ZpuKbDc/8S6mgXgPFPw==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/is-weakref": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-weakref/-/is-weakref-1.0.2.tgz", + "integrity": "sha512-qctsuLZmIQ0+vSSMfoVvyFe2+GSEvnmZ2ezTup1SBse9+twCCeial6EEi3Nc2KFcf6+qz2FBPnjXsk8xhKSaPQ==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==" + }, + "node_modules/isexe": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", + "dev": true + }, + "node_modules/istanbul-lib-coverage": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/istanbul-lib-coverage/-/istanbul-lib-coverage-3.2.0.tgz", + "integrity": "sha512-eOeJ5BHCmHYvQK7xt9GkdHuzuCGS1Y6g9Gvnx3Ym33fz/HpLRYxiS0wHNr+m/MBC8B647Xt608vCDEvhl9c6Mw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/istanbul-lib-instrument": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-5.2.1.tgz", + "integrity": "sha512-pzqtp31nLv/XFOzXGuvhCb8qhjmTVo5vjVk19XE4CRlSWz0KoeJ3bw9XsA7nOp9YBf4qHjwBxkDzKcME/J29Yg==", + "dev": true, + "dependencies": { + "@babel/core": "^7.12.3", + "@babel/parser": "^7.14.7", + "@istanbuljs/schema": "^0.1.2", + "istanbul-lib-coverage": "^3.2.0", + "semver": "^6.3.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/istanbul-lib-instrument/node_modules/semver": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "dev": true, + "bin": { + "semver": "bin/semver.js" + } + }, + "node_modules/istanbul-lib-report": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/istanbul-lib-report/-/istanbul-lib-report-3.0.0.tgz", + "integrity": "sha512-wcdi+uAKzfiGT2abPpKZ0hSU1rGQjUQnLvtY5MpQ7QCTahD3VODhcu4wcfY1YtkGaDD5yuydOLINXsfbus9ROw==", + "dev": true, + "dependencies": { + "istanbul-lib-coverage": "^3.0.0", + "make-dir": "^3.0.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/istanbul-lib-source-maps": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/istanbul-lib-source-maps/-/istanbul-lib-source-maps-4.0.1.tgz", + "integrity": "sha512-n3s8EwkdFIJCG3BPKBYvskgXGoy88ARzvegkitk60NxRdwltLOTaH7CUiMRXvwYorl0Q712iEjcWB+fK/MrWVw==", + "dev": true, + "dependencies": { + "debug": "^4.1.1", + "istanbul-lib-coverage": "^3.0.0", + "source-map": "^0.6.1" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/istanbul-lib-source-maps/node_modules/source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/istanbul-reports": { + "version": "3.1.5", + "resolved": "https://registry.npmjs.org/istanbul-reports/-/istanbul-reports-3.1.5.tgz", + "integrity": "sha512-nUsEMa9pBt/NOHqbcbeJEgqIlY/K7rVWUX6Lql2orY5e9roQOthbR3vtY4zzf2orPELg80fnxxk9zUyPlgwD1w==", + "dev": true, + "dependencies": { + "html-escaper": "^2.0.0", + "istanbul-lib-report": "^3.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/iterare": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/iterare/-/iterare-1.2.1.tgz", + "integrity": "sha512-RKYVTCjAnRthyJes037NX/IiqeidgN1xc3j1RjFfECFp28A1GVwK9nA+i0rJPaHqSZwygLzRnFlzUuHFoWWy+Q==", + "engines": { + "node": ">=6" + } + }, + "node_modules/jest": { + "version": "29.3.1", + "resolved": "https://registry.npmjs.org/jest/-/jest-29.3.1.tgz", + "integrity": "sha512-6iWfL5DTT0Np6UYs/y5Niu7WIfNv/wRTtN5RSXt2DIEft3dx3zPuw/3WJQBCJfmEzvDiEKwoqMbGD9n49+qLSA==", + "dev": true, + "dependencies": { + "@jest/core": "^29.3.1", + "@jest/types": "^29.3.1", + "import-local": "^3.0.2", + "jest-cli": "^29.3.1" + }, + "bin": { + "jest": "bin/jest.js" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + }, + "peerDependencies": { + "node-notifier": "^8.0.1 || ^9.0.0 || ^10.0.0" + }, + "peerDependenciesMeta": { + "node-notifier": { + "optional": true + } + } + }, + "node_modules/jest-changed-files": { + "version": "29.4.0", + "resolved": "https://registry.npmjs.org/jest-changed-files/-/jest-changed-files-29.4.0.tgz", + "integrity": "sha512-rnI1oPxgFghoz32Y8eZsGJMjW54UlqT17ycQeCEktcxxwqqKdlj9afl8LNeO0Pbu+h2JQHThQP0BzS67eTRx4w==", + "dev": true, + "dependencies": { + "execa": "^5.0.0", + "p-limit": "^3.1.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-circus": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-circus/-/jest-circus-29.4.1.tgz", + "integrity": "sha512-v02NuL5crMNY4CGPHBEflLzl4v91NFb85a+dH9a1pUNx6Xjggrd8l9pPy4LZ1VYNRXlb+f65+7O/MSIbLir6pA==", + "dev": true, + "dependencies": { + "@jest/environment": "^29.4.1", + "@jest/expect": "^29.4.1", + "@jest/test-result": "^29.4.1", + "@jest/types": "^29.4.1", + "@types/node": "*", + "chalk": "^4.0.0", + "co": "^4.6.0", + "dedent": "^0.7.0", + "is-generator-fn": "^2.0.0", + "jest-each": "^29.4.1", + "jest-matcher-utils": "^29.4.1", + "jest-message-util": "^29.4.1", + "jest-runtime": "^29.4.1", + "jest-snapshot": "^29.4.1", + "jest-util": "^29.4.1", + "p-limit": "^3.1.0", + "pretty-format": "^29.4.1", + "slash": "^3.0.0", + "stack-utils": "^2.0.3" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-circus/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-cli": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-cli/-/jest-cli-29.4.1.tgz", + "integrity": "sha512-jz7GDIhtxQ37M+9dlbv5K+/FVcIo1O/b1sX3cJgzlQUf/3VG25nvuWzlDC4F1FLLzUThJeWLu8I7JF9eWpuURQ==", + "dev": true, + "dependencies": { + "@jest/core": "^29.4.1", + "@jest/test-result": "^29.4.1", + "@jest/types": "^29.4.1", + "chalk": "^4.0.0", + "exit": "^0.1.2", + "graceful-fs": "^4.2.9", + "import-local": "^3.0.2", + "jest-config": "^29.4.1", + "jest-util": "^29.4.1", + "jest-validate": "^29.4.1", + "prompts": "^2.0.1", + "yargs": "^17.3.1" + }, + "bin": { + "jest": "bin/jest.js" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + }, + "peerDependencies": { + "node-notifier": "^8.0.1 || ^9.0.0 || ^10.0.0" + }, + "peerDependenciesMeta": { + "node-notifier": { + "optional": true + } + } + }, + "node_modules/jest-cli/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-config": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-config/-/jest-config-29.4.1.tgz", + "integrity": "sha512-g7p3q4NuXiM4hrS4XFATTkd+2z0Ml2RhFmFPM8c3WyKwVDNszbl4E7cV7WIx1YZeqqCtqbtTtZhGZWJlJqngzg==", + "dev": true, + "dependencies": { + "@babel/core": "^7.11.6", + "@jest/test-sequencer": "^29.4.1", + "@jest/types": "^29.4.1", + "babel-jest": "^29.4.1", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "deepmerge": "^4.2.2", + "glob": "^7.1.3", + "graceful-fs": "^4.2.9", + "jest-circus": "^29.4.1", + "jest-environment-node": "^29.4.1", + "jest-get-type": "^29.2.0", + "jest-regex-util": "^29.2.0", + "jest-resolve": "^29.4.1", + "jest-runner": "^29.4.1", + "jest-util": "^29.4.1", + "jest-validate": "^29.4.1", + "micromatch": "^4.0.4", + "parse-json": "^5.2.0", + "pretty-format": "^29.4.1", + "slash": "^3.0.0", + "strip-json-comments": "^3.1.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + }, + "peerDependencies": { + "@types/node": "*", + "ts-node": ">=9.0.0" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + }, + "ts-node": { + "optional": true + } + } + }, + "node_modules/jest-config/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-diff": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-diff/-/jest-diff-29.4.1.tgz", + "integrity": "sha512-uazdl2g331iY56CEyfbNA0Ut7Mn2ulAG5vUaEHXycf1L6IPyuImIxSz4F0VYBKi7LYIuxOwTZzK3wh5jHzASMw==", + "dev": true, + "dependencies": { + "chalk": "^4.0.0", + "diff-sequences": "^29.3.1", + "jest-get-type": "^29.2.0", + "pretty-format": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-diff/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-docblock": { + "version": "29.2.0", + "resolved": "https://registry.npmjs.org/jest-docblock/-/jest-docblock-29.2.0.tgz", + "integrity": "sha512-bkxUsxTgWQGbXV5IENmfiIuqZhJcyvF7tU4zJ/7ioTutdz4ToB5Yx6JOFBpgI+TphRY4lhOyCWGNH/QFQh5T6A==", + "dev": true, + "dependencies": { + "detect-newline": "^3.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-each": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-each/-/jest-each-29.4.1.tgz", + "integrity": "sha512-QlYFiX3llJMWUV0BtWht/esGEz9w+0i7BHwODKCze7YzZzizgExB9MOfiivF/vVT0GSQ8wXLhvHXh3x2fVD4QQ==", + "dev": true, + "dependencies": { + "@jest/types": "^29.4.1", + "chalk": "^4.0.0", + "jest-get-type": "^29.2.0", + "jest-util": "^29.4.1", + "pretty-format": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-each/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-environment-node": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-environment-node/-/jest-environment-node-29.4.1.tgz", + "integrity": "sha512-x/H2kdVgxSkxWAIlIh9MfMuBa0hZySmfsC5lCsWmWr6tZySP44ediRKDUiNggX/eHLH7Cd5ZN10Rw+XF5tXsqg==", + "dev": true, + "dependencies": { + "@jest/environment": "^29.4.1", + "@jest/fake-timers": "^29.4.1", + "@jest/types": "^29.4.1", + "@types/node": "*", + "jest-mock": "^29.4.1", + "jest-util": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-get-type": { + "version": "29.2.0", + "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-29.2.0.tgz", + "integrity": "sha512-uXNJlg8hKFEnDgFsrCjznB+sTxdkuqiCL6zMgA75qEbAJjJYTs9XPrvDctrEig2GDow22T/LvHgO57iJhXB/UA==", + "dev": true, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-haste-map": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-haste-map/-/jest-haste-map-29.4.1.tgz", + "integrity": "sha512-imTjcgfVVTvg02khXL11NNLTx9ZaofbAWhilrMg/G8dIkp+HYCswhxf0xxJwBkfhWb3e8dwbjuWburvxmcr58w==", + "dev": true, + "dependencies": { + "@jest/types": "^29.4.1", + "@types/graceful-fs": "^4.1.3", + "@types/node": "*", + "anymatch": "^3.0.3", + "fb-watchman": "^2.0.0", + "graceful-fs": "^4.2.9", + "jest-regex-util": "^29.2.0", + "jest-util": "^29.4.1", + "jest-worker": "^29.4.1", + "micromatch": "^4.0.4", + "walker": "^1.0.8" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + }, + "optionalDependencies": { + "fsevents": "^2.3.2" + } + }, + "node_modules/jest-leak-detector": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-leak-detector/-/jest-leak-detector-29.4.1.tgz", + "integrity": "sha512-akpZv7TPyGMnH2RimOCgy+hPmWZf55EyFUvymQ4LMsQP8xSPlZumCPtXGoDhFNhUE2039RApZkTQDKU79p/FiQ==", + "dev": true, + "dependencies": { + "jest-get-type": "^29.2.0", + "pretty-format": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-matcher-utils": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-matcher-utils/-/jest-matcher-utils-29.4.1.tgz", + "integrity": "sha512-k5h0u8V4nAEy6lSACepxL/rw78FLDkBnXhZVgFneVpnJONhb2DhZj/Gv4eNe+1XqQ5IhgUcqj745UwH0HJmMnA==", + "dev": true, + "dependencies": { + "chalk": "^4.0.0", + "jest-diff": "^29.4.1", + "jest-get-type": "^29.2.0", + "pretty-format": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-matcher-utils/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-message-util": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-29.4.1.tgz", + "integrity": "sha512-H4/I0cXUaLeCw6FM+i4AwCnOwHRgitdaUFOdm49022YD5nfyr8C/DrbXOBEyJaj+w/y0gGJ57klssOaUiLLQGQ==", + "dev": true, + "dependencies": { + "@babel/code-frame": "^7.12.13", + "@jest/types": "^29.4.1", + "@types/stack-utils": "^2.0.0", + "chalk": "^4.0.0", + "graceful-fs": "^4.2.9", + "micromatch": "^4.0.4", + "pretty-format": "^29.4.1", + "slash": "^3.0.0", + "stack-utils": "^2.0.3" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-message-util/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-mock": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-mock/-/jest-mock-29.4.1.tgz", + "integrity": "sha512-MwA4hQ7zBOcgVCVnsM8TzaFLVUD/pFWTfbkY953Y81L5ret3GFRZtmPmRFAjKQSdCKoJvvqOu6Bvfpqlwwb0dQ==", + "dev": true, + "dependencies": { + "@jest/types": "^29.4.1", + "@types/node": "*", + "jest-util": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-pnp-resolver": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/jest-pnp-resolver/-/jest-pnp-resolver-1.2.3.tgz", + "integrity": "sha512-+3NpwQEnRoIBtx4fyhblQDPgJI0H1IEIkX7ShLUjPGA7TtUTvI1oiKi3SR4oBR0hQhQR80l4WAe5RrXBwWMA8w==", + "dev": true, + "engines": { + "node": ">=6" + }, + "peerDependencies": { + "jest-resolve": "*" + }, + "peerDependenciesMeta": { + "jest-resolve": { + "optional": true + } + } + }, + "node_modules/jest-regex-util": { + "version": "29.2.0", + "resolved": "https://registry.npmjs.org/jest-regex-util/-/jest-regex-util-29.2.0.tgz", + "integrity": "sha512-6yXn0kg2JXzH30cr2NlThF+70iuO/3irbaB4mh5WyqNIvLLP+B6sFdluO1/1RJmslyh/f9osnefECflHvTbwVA==", + "dev": true, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-resolve": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-resolve/-/jest-resolve-29.4.1.tgz", + "integrity": "sha512-j/ZFNV2lm9IJ2wmlq1uYK0Y/1PiyDq9g4HEGsNTNr3viRbJdV+8Lf1SXIiLZXFvyiisu0qUyIXGBnw+OKWkJwQ==", + "dev": true, + "dependencies": { + "chalk": "^4.0.0", + "graceful-fs": "^4.2.9", + "jest-haste-map": "^29.4.1", + "jest-pnp-resolver": "^1.2.2", + "jest-util": "^29.4.1", + "jest-validate": "^29.4.1", + "resolve": "^1.20.0", + "resolve.exports": "^2.0.0", + "slash": "^3.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-resolve-dependencies": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-resolve-dependencies/-/jest-resolve-dependencies-29.4.1.tgz", + "integrity": "sha512-Y3QG3M1ncAMxfjbYgtqNXC5B595zmB6e//p/qpA/58JkQXu/IpLDoLeOa8YoYfsSglBKQQzNUqtfGJJT/qLmJg==", + "dev": true, + "dependencies": { + "jest-regex-util": "^29.2.0", + "jest-snapshot": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-resolve/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-runner": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-runner/-/jest-runner-29.4.1.tgz", + "integrity": "sha512-8d6XXXi7GtHmsHrnaqBKWxjKb166Eyj/ksSaUYdcBK09VbjPwIgWov1VwSmtupCIz8q1Xv4Qkzt/BTo3ZqiCeg==", + "dev": true, + "dependencies": { + "@jest/console": "^29.4.1", + "@jest/environment": "^29.4.1", + "@jest/test-result": "^29.4.1", + "@jest/transform": "^29.4.1", + "@jest/types": "^29.4.1", + "@types/node": "*", + "chalk": "^4.0.0", + "emittery": "^0.13.1", + "graceful-fs": "^4.2.9", + "jest-docblock": "^29.2.0", + "jest-environment-node": "^29.4.1", + "jest-haste-map": "^29.4.1", + "jest-leak-detector": "^29.4.1", + "jest-message-util": "^29.4.1", + "jest-resolve": "^29.4.1", + "jest-runtime": "^29.4.1", + "jest-util": "^29.4.1", + "jest-watcher": "^29.4.1", + "jest-worker": "^29.4.1", + "p-limit": "^3.1.0", + "source-map-support": "0.5.13" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-runner/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-runner/node_modules/source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/jest-runner/node_modules/source-map-support": { + "version": "0.5.13", + "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.13.tgz", + "integrity": "sha512-SHSKFHadjVA5oR4PPqhtAVdcBWwRYVd6g6cAXnIbRiIwc2EhPrTuKUBdSLvlEKyIP3GCf89fltvcZiP9MMFA1w==", + "dev": true, + "dependencies": { + "buffer-from": "^1.0.0", + "source-map": "^0.6.0" + } + }, + "node_modules/jest-runtime": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-runtime/-/jest-runtime-29.4.1.tgz", + "integrity": "sha512-UXTMU9uKu2GjYwTtoAw5rn4STxWw/nadOfW7v1sx6LaJYa3V/iymdCLQM6xy3+7C6mY8GfX22vKpgxY171UIoA==", + "dev": true, + "dependencies": { + "@jest/environment": "^29.4.1", + "@jest/fake-timers": "^29.4.1", + "@jest/globals": "^29.4.1", + "@jest/source-map": "^29.2.0", + "@jest/test-result": "^29.4.1", + "@jest/transform": "^29.4.1", + "@jest/types": "^29.4.1", + "@types/node": "*", + "chalk": "^4.0.0", + "cjs-module-lexer": "^1.0.0", + "collect-v8-coverage": "^1.0.0", + "glob": "^7.1.3", + "graceful-fs": "^4.2.9", + "jest-haste-map": "^29.4.1", + "jest-message-util": "^29.4.1", + "jest-mock": "^29.4.1", + "jest-regex-util": "^29.2.0", + "jest-resolve": "^29.4.1", + "jest-snapshot": "^29.4.1", + "jest-util": "^29.4.1", + "semver": "^7.3.5", + "slash": "^3.0.0", + "strip-bom": "^4.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-runtime/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-snapshot": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-snapshot/-/jest-snapshot-29.4.1.tgz", + "integrity": "sha512-l4iV8EjGgQWVz3ee/LR9sULDk2pCkqb71bjvlqn+qp90lFwpnulHj4ZBT8nm1hA1C5wowXLc7MGnw321u0tsYA==", + "dev": true, + "dependencies": { + "@babel/core": "^7.11.6", + "@babel/generator": "^7.7.2", + "@babel/plugin-syntax-jsx": "^7.7.2", + "@babel/plugin-syntax-typescript": "^7.7.2", + "@babel/traverse": "^7.7.2", + "@babel/types": "^7.3.3", + "@jest/expect-utils": "^29.4.1", + "@jest/transform": "^29.4.1", + "@jest/types": "^29.4.1", + "@types/babel__traverse": "^7.0.6", + "@types/prettier": "^2.1.5", + "babel-preset-current-node-syntax": "^1.0.0", + "chalk": "^4.0.0", + "expect": "^29.4.1", + "graceful-fs": "^4.2.9", + "jest-diff": "^29.4.1", + "jest-get-type": "^29.2.0", + "jest-haste-map": "^29.4.1", + "jest-matcher-utils": "^29.4.1", + "jest-message-util": "^29.4.1", + "jest-util": "^29.4.1", + "natural-compare": "^1.4.0", + "pretty-format": "^29.4.1", + "semver": "^7.3.5" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-snapshot/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-util": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-29.4.1.tgz", + "integrity": "sha512-bQy9FPGxVutgpN4VRc0hk6w7Hx/m6L53QxpDreTZgJd9gfx/AV2MjyPde9tGyZRINAUrSv57p2inGBu2dRLmkQ==", + "dev": true, + "dependencies": { + "@jest/types": "^29.4.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-util/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-validate": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-validate/-/jest-validate-29.4.1.tgz", + "integrity": "sha512-qNZXcZQdIQx4SfUB/atWnI4/I2HUvhz8ajOSYUu40CSmf9U5emil8EDHgE7M+3j9/pavtk3knlZBDsgFvv/SWw==", + "dev": true, + "dependencies": { + "@jest/types": "^29.4.1", + "camelcase": "^6.2.0", + "chalk": "^4.0.0", + "jest-get-type": "^29.2.0", + "leven": "^3.1.0", + "pretty-format": "^29.4.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-validate/node_modules/camelcase": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz", + "integrity": "sha512-Gmy6FhYlCY7uOElZUSbxo2UCDH8owEk996gkbrpsgGtrJLM3J7jGxl9Ic7Qwwj4ivOE5AWZWRMecDdF7hqGjFA==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/jest-validate/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-watcher": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-watcher/-/jest-watcher-29.4.1.tgz", + "integrity": "sha512-vFOzflGFs27nU6h8dpnVRER3O2rFtL+VMEwnG0H3KLHcllLsU8y9DchSh0AL/Rg5nN1/wSiQ+P4ByMGpuybaVw==", + "dev": true, + "dependencies": { + "@jest/test-result": "^29.4.1", + "@jest/types": "^29.4.1", + "@types/node": "*", + "ansi-escapes": "^4.2.1", + "chalk": "^4.0.0", + "emittery": "^0.13.1", + "jest-util": "^29.4.1", + "string-length": "^4.0.1" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-watcher/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/jest-worker": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-29.4.1.tgz", + "integrity": "sha512-O9doU/S1EBe+yp/mstQ0VpPwpv0Clgn68TkNwGxL6/usX/KUW9Arnn4ag8C3jc6qHcXznhsT5Na1liYzAsuAbQ==", + "dev": true, + "dependencies": { + "@types/node": "*", + "jest-util": "^29.4.1", + "merge-stream": "^2.0.0", + "supports-color": "^8.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/jest-worker/node_modules/supports-color": { + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", + "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "dev": true, + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/supports-color?sponsor=1" + } + }, + "node_modules/js-tokens": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", + "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", + "dev": true + }, + "node_modules/js-yaml": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz", + "integrity": "sha512-wpxZs9NoxZaJESJGIZTyDEaYpl0FKSA+FB9aJiyemKhMwkxQg63h4T1KJgUGHpTqPDNRcmmYLugrRjJlBtWvRA==", + "dev": true, + "dependencies": { + "argparse": "^2.0.1" + }, + "bin": { + "js-yaml": "bin/js-yaml.js" + } + }, + "node_modules/jsesc": { + "version": "2.5.2", + "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-2.5.2.tgz", + "integrity": "sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==", + "dev": true, + "bin": { + "jsesc": "bin/jsesc" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/json-parse-even-better-errors": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz", + "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==", + "dev": true + }, + "node_modules/json-schema-traverse": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", + "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==", + "dev": true + }, + "node_modules/json-stable-stringify-without-jsonify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz", + "integrity": "sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==", + "dev": true + }, + "node_modules/json5": { + "version": "2.2.3", + "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", + "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==", + "dev": true, + "bin": { + "json5": "lib/cli.js" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/jsonc-parser": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/jsonc-parser/-/jsonc-parser-3.2.0.tgz", + "integrity": "sha512-gfFQZrcTc8CnKXp6Y4/CBT3fTc0OVuDofpre4aEeEpSBPV5X5v4+Vmx+8snU7RLPrNHPKSgLxGo9YuQzz20o+w==", + "dev": true + }, + "node_modules/jsonfile": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-6.1.0.tgz", + "integrity": "sha512-5dgndWOriYSm5cnYaJNhalLNDKOqFwyDB/rr1E9ZsGciGvKPs8R2xYGCacuf3z6K1YKDz182fd+fY3cn3pMqXQ==", + "dev": true, + "dependencies": { + "universalify": "^2.0.0" + }, + "optionalDependencies": { + "graceful-fs": "^4.1.6" + } + }, + "node_modules/kleur": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/kleur/-/kleur-3.0.3.tgz", + "integrity": "sha512-eTIzlVOSUR+JxdDFepEYcBMtZ9Qqdef+rnzWdRZuMbOywu5tO2w2N7rqjoANZ5k9vywhL6Br1VRjUIgTQx4E8w==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/leven": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/leven/-/leven-3.1.0.tgz", + "integrity": "sha512-qsda+H8jTaUaN/x5vzW2rzc+8Rw4TAQ/4KjB46IwK5VH+IlVeeeje/EoZRpiXvIqjFgK84QffqPztGI3VBLG1A==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/levn": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/levn/-/levn-0.4.1.tgz", + "integrity": "sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==", + "dev": true, + "dependencies": { + "prelude-ls": "^1.2.1", + "type-check": "~0.4.0" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/lines-and-columns": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/lines-and-columns/-/lines-and-columns-1.2.4.tgz", + "integrity": "sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==", + "dev": true + }, + "node_modules/loader-runner": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.3.0.tgz", + "integrity": "sha512-3R/1M+yS3j5ou80Me59j7F9IMs4PXs3VqRrm0TU3AbKPxlmpoY1TNscJV/oGJXo8qCatFGTfDbY6W6ipGOYXfg==", + "dev": true, + "engines": { + "node": ">=6.11.5" + } + }, + "node_modules/lodash": { + "version": "4.17.21", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", + "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==", + "dev": true + }, + "node_modules/lodash.memoize": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/lodash.memoize/-/lodash.memoize-4.1.2.tgz", + "integrity": "sha512-t7j+NzmgnQzTAYXcsHYLgimltOV1MXHtlOWf6GjL9Kj8GK5FInw5JotxvbOs+IvV1/Dzo04/fCGfLVs7aXb4Ag==", + "dev": true + }, + "node_modules/lodash.merge": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/lodash.merge/-/lodash.merge-4.6.2.tgz", + "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", + "dev": true + }, + "node_modules/log-symbols": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-4.1.0.tgz", + "integrity": "sha512-8XPvpAA8uyhfteu8pIvQxpJZ7SYYdpUivZpGy6sFsBuKRY/7rQGavedeB8aK+Zkyq6upMFVL/9AW6vOYzfRyLg==", + "dev": true, + "dependencies": { + "chalk": "^4.1.0", + "is-unicode-supported": "^0.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/log-symbols/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/lru-cache": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", + "integrity": "sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==", + "dev": true, + "dependencies": { + "yallist": "^3.0.2" + } + }, + "node_modules/macos-release": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/macos-release/-/macos-release-2.5.0.tgz", + "integrity": "sha512-EIgv+QZ9r+814gjJj0Bt5vSLJLzswGmSUbUpbi9AIr/fsN2IWFBl2NucV9PAiek+U1STK468tEkxmVYUtuAN3g==", + "dev": true, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/magic-string": { + "version": "0.27.0", + "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.27.0.tgz", + "integrity": "sha512-8UnnX2PeRAPZuN12svgR9j7M1uWMovg/CEnIwIG0LFkXSJJe4PdfUGiTGl8V9bsBHFUtfVINcSyYxd7q+kx9fA==", + "dev": true, + "dependencies": { + "@jridgewell/sourcemap-codec": "^1.4.13" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/make-dir": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-3.1.0.tgz", + "integrity": "sha512-g3FeP20LNwhALb/6Cz6Dd4F2ngze0jz7tbzrD2wAV+o9FeNHe4rL+yK2md0J/fiSf1sa1ADhXqi5+oVwOM/eGw==", + "dev": true, + "dependencies": { + "semver": "^6.0.0" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/make-dir/node_modules/semver": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", + "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "dev": true, + "bin": { + "semver": "bin/semver.js" + } + }, + "node_modules/make-error": { + "version": "1.3.6", + "resolved": "https://registry.npmjs.org/make-error/-/make-error-1.3.6.tgz", + "integrity": "sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==", + "dev": true + }, + "node_modules/makeerror": { + "version": "1.0.12", + "resolved": "https://registry.npmjs.org/makeerror/-/makeerror-1.0.12.tgz", + "integrity": "sha512-JmqCvUhmt43madlpFzG4BQzG2Z3m6tvQDNKdClZnO3VbIudJYmxsT0FNJMeiB2+JTSlTQTSbU8QdesVmwJcmLg==", + "dev": true, + "dependencies": { + "tmpl": "1.0.5" + } + }, + "node_modules/media-typer": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", + "integrity": "sha512-dq+qelQ9akHpcOl/gUVRTxVIOkAJ1wR3QAvb4RsVjS8oVoFjDGTc679wJYmUmknUF5HwMLOgb5O+a3KxfWapPQ==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/memfs": { + "version": "3.4.13", + "resolved": "https://registry.npmjs.org/memfs/-/memfs-3.4.13.tgz", + "integrity": "sha512-omTM41g3Skpvx5dSYeZIbXKcXoAVc/AoMNwn9TKx++L/gaen/+4TTttmu8ZSch5vfVJ8uJvGbroTsIlslRg6lg==", + "dev": true, + "dependencies": { + "fs-monkey": "^1.0.3" + }, + "engines": { + "node": ">= 4.0.0" + } + }, + "node_modules/merge-descriptors": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", + "integrity": "sha512-cCi6g3/Zr1iqQi6ySbseM1Xvooa98N0w31jzUYrXPX2xqObmFGHJ0tQ5u74H3mVh7wLouTseZyYIq39g8cNp1w==" + }, + "node_modules/merge-stream": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", + "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==", + "dev": true + }, + "node_modules/merge2": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.4.1.tgz", + "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", + "dev": true, + "engines": { + "node": ">= 8" + } + }, + "node_modules/methods": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", + "integrity": "sha512-iclAHeNqNm68zFtnZ0e+1L2yUIdvzNoauKU4WBA3VvH/vPFieF7qfRlwUZU+DA9P9bPXIS90ulxoUoCH23sV2w==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/micromatch": { + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.5.tgz", + "integrity": "sha512-DMy+ERcEW2q8Z2Po+WNXuw3c5YaUSFjAO5GsJqfEl7UjvtIuFKO6ZrKvcItdy98dwFI2N1tg3zNIdKaQT+aNdA==", + "dev": true, + "dependencies": { + "braces": "^3.0.2", + "picomatch": "^2.3.1" + }, + "engines": { + "node": ">=8.6" + } + }, + "node_modules/mime": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", + "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", + "bin": { + "mime": "cli.js" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mimic-fn": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-2.1.0.tgz", + "integrity": "sha512-OqbOk5oEQeAZ8WXWydlu9HJjz9WVdEIvamMCcXmuqUYjTknH/sqsWvhQ3vgwKFRR1HpjvNBKQ37nbJgYzGqGcg==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/minimatch": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", + "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", + "dev": true, + "dependencies": { + "brace-expansion": "^1.1.7" + }, + "engines": { + "node": "*" + } + }, + "node_modules/minimist": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.7.tgz", + "integrity": "sha512-bzfL1YUZsP41gmu/qjrEk0Q6i2ix/cVeAhbCbqH9u3zYutS1cLg00qhrD0M2MVdCcx4Sc0UpP2eBWo9rotpq6g==", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/mkdirp": { + "version": "0.5.6", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.6.tgz", + "integrity": "sha512-FP+p8RB8OWpF3YZBCrP5gtADmtXApB5AMLn+vdyA+PyxCjrCs00mjyUozssO33cwDeT3wNGdLxJ5M//YqtHAJw==", + "dependencies": { + "minimist": "^1.2.6" + }, + "bin": { + "mkdirp": "bin/cmd.js" + } + }, + "node_modules/ms": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", + "dev": true + }, + "node_modules/multer": { + "version": "1.4.4-lts.1", + "resolved": "https://registry.npmjs.org/multer/-/multer-1.4.4-lts.1.tgz", + "integrity": "sha512-WeSGziVj6+Z2/MwQo3GvqzgR+9Uc+qt8SwHKh3gvNPiISKfsMfG4SvCOFYlxxgkXt7yIV2i1yczehm0EOKIxIg==", + "dependencies": { + "append-field": "^1.0.0", + "busboy": "^1.0.0", + "concat-stream": "^1.5.2", + "mkdirp": "^0.5.4", + "object-assign": "^4.1.1", + "type-is": "^1.6.4", + "xtend": "^4.0.0" + }, + "engines": { + "node": ">= 6.0.0" + } + }, + "node_modules/mute-stream": { + "version": "0.0.8", + "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.8.tgz", + "integrity": "sha512-nnbWWOkoWyUsTjKrhgD0dcz22mdkSnpYqbEjIm2nhwhuxlSkpywJmBo8h0ZqJdkp73mb90SssHkN4rsRaBAfAA==", + "dev": true + }, + "node_modules/natural-compare": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", + "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", + "dev": true + }, + "node_modules/natural-compare-lite": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare-lite/-/natural-compare-lite-1.4.0.tgz", + "integrity": "sha512-Tj+HTDSJJKaZnfiuw+iaF9skdPpTo2GtEly5JHnWV/hfv2Qj/9RKsGISQtLh2ox3l5EAGw487hnBee0sIJ6v2g==", + "dev": true + }, + "node_modules/negotiator": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz", + "integrity": "sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/neo-async": { + "version": "2.6.2", + "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.2.tgz", + "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==", + "dev": true + }, + "node_modules/node-abort-controller": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/node-abort-controller/-/node-abort-controller-3.1.1.tgz", + "integrity": "sha512-AGK2yQKIjRuqnc6VkX2Xj5d+QW8xZ87pa1UK6yA6ouUyuxfHuMP6umE5QK7UmTeOAymo+Zx1Fxiuw9rVx8taHQ==", + "dev": true + }, + "node_modules/node-emoji": { + "version": "1.11.0", + "resolved": "https://registry.npmjs.org/node-emoji/-/node-emoji-1.11.0.tgz", + "integrity": "sha512-wo2DpQkQp7Sjm2A0cq+sN7EHKO6Sl0ctXeBdFZrL9T9+UywORbufTcTZxom8YqpLQt/FqNMUkOpkZrJVYSKD3A==", + "dev": true, + "dependencies": { + "lodash": "^4.17.21" + } + }, + "node_modules/node-fetch": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.9.tgz", + "integrity": "sha512-DJm/CJkZkRjKKj4Zi4BsKVZh3ValV5IR5s7LVZnW+6YMh0W1BfNA8XSs6DLMGYlId5F3KnA70uu2qepcR08Qqg==", + "dependencies": { + "whatwg-url": "^5.0.0" + }, + "engines": { + "node": "4.x || >=6.0.0" + }, + "peerDependencies": { + "encoding": "^0.1.0" + }, + "peerDependenciesMeta": { + "encoding": { + "optional": true + } + } + }, + "node_modules/node-int64": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/node-int64/-/node-int64-0.4.0.tgz", + "integrity": "sha512-O5lz91xSOeoXP6DulyHfllpq+Eg00MWitZIbtPfoSEvqIHdl5gfcY6hYzDWnj0qD5tz52PI08u9qUvSVeUBeHw==", + "dev": true + }, + "node_modules/node-releases": { + "version": "2.0.9", + "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.9.tgz", + "integrity": "sha512-2xfmOrRkGogbTK9R6Leda0DGiXeY3p2NJpy4+gNCffdUvV6mdEJnaDEic1i3Ec2djAo8jWYoJMR5PB0MSMpxUA==", + "dev": true + }, + "node_modules/normalize-path": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", + "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/npm-run-path": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-4.0.1.tgz", + "integrity": "sha512-S48WzZW777zhNIrn7gxOlISNAqi9ZC/uQFnRdbeIHhZhCA6UqpkOT8T1G7BvfdgP4Er8gF4sUbaS0i7QvIfCWw==", + "dev": true, + "dependencies": { + "path-key": "^3.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/object-hash": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/object-hash/-/object-hash-3.0.0.tgz", + "integrity": "sha512-RSn9F68PjH9HqtltsSnqYC1XXoWe9Bju5+213R98cNGttag9q9yAOTzdbsqvIa7aNm5WffBZFpWYr2aWrklWAw==", + "engines": { + "node": ">= 6" + } + }, + "node_modules/object-inspect": { + "version": "1.12.3", + "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.3.tgz", + "integrity": "sha512-geUvdk7c+eizMNUDkRpW1wJwgfOiOeHbxBR/hLXK1aT6zmVSO0jsQcs7fj6MGw89jC/cjGfLcNOrtMYtGqm81g==", + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/object-keys": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", + "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==", + "dev": true, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/object.assign": { + "version": "4.1.4", + "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.4.tgz", + "integrity": "sha512-1mxKf0e58bvyjSCtKYY4sRe9itRk3PJpquJOjeIkz885CczcI4IvJJDLPS72oowuSh+pBxUFROpX+TU++hxhZQ==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "has-symbols": "^1.0.3", + "object-keys": "^1.1.1" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/object.entries": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/object.entries/-/object.entries-1.1.6.tgz", + "integrity": "sha512-leTPzo4Zvg3pmbQ3rDK69Rl8GQvIqMWubrkxONG9/ojtFE2rD9fjMKfSI5BxW3osRH1m6VdzmqK8oAY9aT4x5w==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/object.values": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/object.values/-/object.values-1.1.6.tgz", + "integrity": "sha512-FVVTkD1vENCsAcwNs9k6jea2uHC/X0+JcjG8YA60FN5CMaJmG95wT9jek/xX9nornqGRrBkKtzuAu2wuHpKqvw==", + "dev": true, + "peer": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/on-finished": { + "version": "2.4.1", + "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.4.1.tgz", + "integrity": "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==", + "dependencies": { + "ee-first": "1.1.1" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==", + "dev": true, + "dependencies": { + "wrappy": "1" + } + }, + "node_modules/onetime": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/onetime/-/onetime-5.1.2.tgz", + "integrity": "sha512-kbpaSSGJTWdAY5KPVeMOKXSrPtr8C8C7wodJbcsd51jRnmD+GZu8Y0VoU6Dm5Z4vWr0Ig/1NKuWRKf7j5aaYSg==", + "dev": true, + "dependencies": { + "mimic-fn": "^2.1.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/optionator": { + "version": "0.9.1", + "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.1.tgz", + "integrity": "sha512-74RlY5FCnhq4jRxVUPKDaRwrVNXMqsGsiW6AJw4XK8hmtm10wC0ypZBLw5IIp85NZMr91+qd1RvvENwg7jjRFw==", + "dev": true, + "dependencies": { + "deep-is": "^0.1.3", + "fast-levenshtein": "^2.0.6", + "levn": "^0.4.1", + "prelude-ls": "^1.2.1", + "type-check": "^0.4.0", + "word-wrap": "^1.2.3" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/ora": { + "version": "5.4.1", + "resolved": "https://registry.npmjs.org/ora/-/ora-5.4.1.tgz", + "integrity": "sha512-5b6Y85tPxZZ7QytO+BQzysW31HJku27cRIlkbAXaNx+BdcVi+LlRFmVXzeF6a7JCwJpyw5c4b+YSVImQIrBpuQ==", + "dev": true, + "dependencies": { + "bl": "^4.1.0", + "chalk": "^4.1.0", + "cli-cursor": "^3.1.0", + "cli-spinners": "^2.5.0", + "is-interactive": "^1.0.0", + "is-unicode-supported": "^0.1.0", + "log-symbols": "^4.1.0", + "strip-ansi": "^6.0.0", + "wcwidth": "^1.0.1" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/ora/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/os-name": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/os-name/-/os-name-4.0.1.tgz", + "integrity": "sha512-xl9MAoU97MH1Xt5K9ERft2YfCAoaO6msy1OBA0ozxEC0x0TmIoE6K3QvgJMMZA9yKGLmHXNY/YZoDbiGDj4zYw==", + "dev": true, + "dependencies": { + "macos-release": "^2.5.0", + "windows-release": "^4.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/os-tmpdir": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", + "integrity": "sha512-D2FR03Vir7FIu45XBY20mTb+/ZSWB00sjU9jdQXt83gDrI4Ztz5Fs7/yy74g2N5SVQY4xY1qDr4rNddwYRVX0g==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/p-limit": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-3.1.0.tgz", + "integrity": "sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==", + "dev": true, + "dependencies": { + "yocto-queue": "^0.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/p-try": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz", + "integrity": "sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/parent-module": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", + "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==", + "dev": true, + "dependencies": { + "callsites": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/parse-json": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-5.2.0.tgz", + "integrity": "sha512-ayCKvm/phCGxOkYRSCM82iDwct8/EonSEgCSxWxD7ve6jHggsFl4fZVQBPRNgQoKiuV/odhFrGzQXZwbifC8Rg==", + "dev": true, + "dependencies": { + "@babel/code-frame": "^7.0.0", + "error-ex": "^1.3.1", + "json-parse-even-better-errors": "^2.3.0", + "lines-and-columns": "^1.1.6" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/parseurl": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", + "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/path-exists": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", + "integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/path-key": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz", + "integrity": "sha512-ojmeN0qd+y0jszEtoY48r0Peq5dwMEkIlCOu6Q5f41lfkswXuKtYrhgoTpLnyIcHm24Uhqx+5Tqm2InSwLhE6Q==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/path-parse": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.7.tgz", + "integrity": "sha512-LDJzPVEEEPR+y48z93A0Ed0yXb8pAByGWo/k5YYdYgpY2/2EsOsksJrq7lOHxryrVOn1ejG6oAp8ahvOIQD8sw==", + "dev": true + }, + "node_modules/path-to-regexp": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-3.2.0.tgz", + "integrity": "sha512-jczvQbCUS7XmS7o+y1aEO9OBVFeZBQ1MDSEqmO7xSoPgOPoowY/SxLpZ6Vh97/8qHZOteiCKb7gkG9gA2ZUxJA==" + }, + "node_modules/path-type": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz", + "integrity": "sha512-gDKb8aZMDeD/tZWs9P6+q0J9Mwkdl6xMV8TjnGP3qJVJ06bdMgkbBlLU8IdfOsIsFz2BW1rNVT3XuNEl8zPAvw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/picocolors": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.0.0.tgz", + "integrity": "sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==", + "dev": true + }, + "node_modules/picomatch": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-2.3.1.tgz", + "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", + "dev": true, + "engines": { + "node": ">=8.6" + }, + "funding": { + "url": "https://github.com/sponsors/jonschlinkert" + } + }, + "node_modules/pirates": { + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/pirates/-/pirates-4.0.5.tgz", + "integrity": "sha512-8V9+HQPupnaXMA23c5hvl69zXvTwTzyAYasnkb0Tts4XvO4CliqONMOnvlq26rkhLC3nWDFBJf73LU1e1VZLaQ==", + "dev": true, + "engines": { + "node": ">= 6" + } + }, + "node_modules/pkg-dir": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-4.2.0.tgz", + "integrity": "sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ==", + "dev": true, + "dependencies": { + "find-up": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/pkg-dir/node_modules/find-up": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", + "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", + "dev": true, + "dependencies": { + "locate-path": "^5.0.0", + "path-exists": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/pkg-dir/node_modules/locate-path": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", + "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", + "dev": true, + "dependencies": { + "p-locate": "^4.1.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/pkg-dir/node_modules/p-limit": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", + "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", + "dev": true, + "dependencies": { + "p-try": "^2.0.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/pkg-dir/node_modules/p-locate": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", + "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", + "dev": true, + "dependencies": { + "p-limit": "^2.2.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/pluralize": { + "version": "8.0.0", + "resolved": "https://registry.npmjs.org/pluralize/-/pluralize-8.0.0.tgz", + "integrity": "sha512-Nc3IT5yHzflTfbjgqWcCPpo7DaKy4FnpB0l/zCAW0Tc7jxAiuqSxHasntB3D7887LSrA93kDJ9IXovxJYxyLCA==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/prelude-ls": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.2.1.tgz", + "integrity": "sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==", + "dev": true, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/pretty-format": { + "version": "29.4.1", + "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-29.4.1.tgz", + "integrity": "sha512-dt/Z761JUVsrIKaY215o1xQJBGlSmTx/h4cSqXqjHLnU1+Kt+mavVE7UgqJJO5ukx5HjSswHfmXz4LjS2oIJfg==", + "dev": true, + "dependencies": { + "@jest/schemas": "^29.4.0", + "ansi-styles": "^5.0.0", + "react-is": "^18.0.0" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + } + }, + "node_modules/pretty-format/node_modules/ansi-styles": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", + "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/process-nextick-args": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", + "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==" + }, + "node_modules/progress": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz", + "integrity": "sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==", + "dev": true, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/prompts": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/prompts/-/prompts-2.4.2.tgz", + "integrity": "sha512-NxNv/kLguCA7p3jE8oL2aEBsrJWgAakBpgmgK6lpPWV+WuOmY6r2/zbAVnP+T8bQlA0nzHXSJSJW0Hq7ylaD2Q==", + "dev": true, + "dependencies": { + "kleur": "^3.0.3", + "sisteransi": "^1.0.5" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/proxy-addr": { + "version": "2.0.7", + "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", + "integrity": "sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==", + "dependencies": { + "forwarded": "0.2.0", + "ipaddr.js": "1.9.1" + }, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/pump": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz", + "integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==", + "dev": true, + "dependencies": { + "end-of-stream": "^1.1.0", + "once": "^1.3.1" + } + }, + "node_modules/punycode": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.0.tgz", + "integrity": "sha512-rRV+zQD8tVFys26lAGR9WUuS4iUAngJScM+ZRSKtvl5tKeZ2t5bvdNFdNHBW9FWR4guGHlgmsZ1G7BSm2wTbuA==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/qs": { + "version": "6.11.0", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.11.0.tgz", + "integrity": "sha512-MvjoMCJwEarSbUYk5O+nmoSzSutSsTwF85zcHPQ9OrlFoZOYIjaqBAJIqIXjptyD5vThxGq52Xu/MaJzRkIk4Q==", + "dependencies": { + "side-channel": "^1.0.4" + }, + "engines": { + "node": ">=0.6" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/queue-microtask": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", + "integrity": "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ] + }, + "node_modules/randombytes": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", + "integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==", + "dev": true, + "dependencies": { + "safe-buffer": "^5.1.0" + } + }, + "node_modules/range-parser": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", + "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/raw-body": { + "version": "2.5.1", + "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.5.1.tgz", + "integrity": "sha512-qqJBtEyVgS0ZmPGdCFPWJ3FreoqvG4MVQln/kCgF7Olq95IbOp0/BWyMwbdtn4VTvkM8Y7khCQ2Xgk/tcrCXig==", + "dependencies": { + "bytes": "3.1.2", + "http-errors": "2.0.0", + "iconv-lite": "0.4.24", + "unpipe": "1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/react-is": { + "version": "18.2.0", + "resolved": "https://registry.npmjs.org/react-is/-/react-is-18.2.0.tgz", + "integrity": "sha512-xWGDIW6x921xtzPkhiULtthJHoJvBbF3q26fzloPCK0hsvxtPVelvftw3zjbHWSkR2km9Z+4uxbDDK/6Zw9B8w==", + "dev": true + }, + "node_modules/readable-stream": { + "version": "2.3.7", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.7.tgz", + "integrity": "sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==", + "dependencies": { + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" + } + }, + "node_modules/readable-stream/node_modules/safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==" + }, + "node_modules/readdirp": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-3.6.0.tgz", + "integrity": "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==", + "dev": true, + "dependencies": { + "picomatch": "^2.2.1" + }, + "engines": { + "node": ">=8.10.0" + } + }, + "node_modules/rechoir": { + "version": "0.6.2", + "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.6.2.tgz", + "integrity": "sha512-HFM8rkZ+i3zrV+4LQjwQ0W+ez98pApMGM3HUrN04j3CqzPOzl9nmP15Y8YXNm8QHGv/eacOVEjqhmWpkRV0NAw==", + "dev": true, + "dependencies": { + "resolve": "^1.1.6" + }, + "engines": { + "node": ">= 0.10" + } + }, + "node_modules/reflect-metadata": { + "version": "0.1.13", + "resolved": "https://registry.npmjs.org/reflect-metadata/-/reflect-metadata-0.1.13.tgz", + "integrity": "sha512-Ts1Y/anZELhSsjMcU605fU9RE4Oi3p5ORujwbIKXfWa+0Zxs510Qrmrce5/Jowq3cHSZSJqBjypxmHarc+vEWg==" + }, + "node_modules/regexp.prototype.flags": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.4.3.tgz", + "integrity": "sha512-fjggEOO3slI6Wvgjwflkc4NFRCTZAu5CnNfBd5qOMYhWdn67nJBBu34/TkD++eeFmd8C9r9jfXJ27+nSiRkSUA==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.3", + "functions-have-names": "^1.2.2" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/regexpp": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-3.2.0.tgz", + "integrity": "sha512-pq2bWo9mVD43nbts2wGv17XLiNLya+GklZ8kaDLV2Z08gDCsGpnKn9BFMepvWuHCbyVvY7J5o5+BVvoQbmlJLg==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/mysticatea" + } + }, + "node_modules/require-directory": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", + "integrity": "sha512-fGxEI7+wsG9xrvdjsrlmL22OMTTiHRwAMroiEeMgq8gzoLC/PQr7RsRDSTLUg/bZAZtF+TVIkHc6/4RIKrui+Q==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/require-from-string": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", + "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/resolve": { + "version": "1.22.1", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.22.1.tgz", + "integrity": "sha512-nBpuuYuY5jFsli/JIs1oldw6fOQCBioohqWZg/2hiaOybXOft4lonv85uDOKXdf8rhyK159cxU5cDcK/NKk8zw==", + "dev": true, + "dependencies": { + "is-core-module": "^2.9.0", + "path-parse": "^1.0.7", + "supports-preserve-symlinks-flag": "^1.0.0" + }, + "bin": { + "resolve": "bin/resolve" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/resolve-cwd": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/resolve-cwd/-/resolve-cwd-3.0.0.tgz", + "integrity": "sha512-OrZaX2Mb+rJCpH/6CpSqt9xFVpN++x01XnN2ie9g6P5/3xelLAkXWVADpdz1IHD/KFfEXyE6V0U01OQ3UO2rEg==", + "dev": true, + "dependencies": { + "resolve-from": "^5.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/resolve-cwd/node_modules/resolve-from": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz", + "integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/resolve-from": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", + "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/resolve.exports": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/resolve.exports/-/resolve.exports-2.0.0.tgz", + "integrity": "sha512-6K/gDlqgQscOlg9fSRpWstA8sYe8rbELsSTNpx+3kTrsVCzvSl0zIvRErM7fdl9ERWDsKnrLnwB+Ne89918XOg==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/restore-cursor": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-3.1.0.tgz", + "integrity": "sha512-l+sSefzHpj5qimhFSE5a8nufZYAM3sBSVMAPtYkmC+4EH2anSGaEMXSD0izRQbu9nfyQ9y5JrVmp7E8oZrUjvA==", + "dev": true, + "dependencies": { + "onetime": "^5.1.0", + "signal-exit": "^3.0.2" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/reusify": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/reusify/-/reusify-1.0.4.tgz", + "integrity": "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==", + "dev": true, + "engines": { + "iojs": ">=1.0.0", + "node": ">=0.10.0" + } + }, + "node_modules/rimraf": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-4.1.2.tgz", + "integrity": "sha512-BlIbgFryTbw3Dz6hyoWFhKk+unCcHMSkZGrTFVAx2WmttdBSonsdtRlwiuTbDqTKr+UlXIUqJVS4QT5tUzGENQ==", + "dev": true, + "bin": { + "rimraf": "dist/cjs/src/bin.js" + }, + "engines": { + "node": ">=14" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, + "node_modules/run-async": { + "version": "2.4.1", + "resolved": "https://registry.npmjs.org/run-async/-/run-async-2.4.1.tgz", + "integrity": "sha512-tvVnVv01b8c1RrA6Ep7JkStj85Guv/YrMcwqYQnwjsAS2cTmmPGBBjAjpCW7RrSodNSoE2/qg9O4bceNvUuDgQ==", + "dev": true, + "engines": { + "node": ">=0.12.0" + } + }, + "node_modules/run-parallel": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", + "integrity": "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "dependencies": { + "queue-microtask": "^1.2.2" + } + }, + "node_modules/rxjs": { + "version": "7.8.0", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.0.tgz", + "integrity": "sha512-F2+gxDshqmIub1KdvZkaEfGDwLNpPvk9Fs6LD/MyQxNgMds/WH9OdDDXOmxUZpME+iSK3rQCctkL0DYyytUqMg==", + "dependencies": { + "tslib": "^2.1.0" + } + }, + "node_modules/safe-buffer": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", + "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ] + }, + "node_modules/safe-regex-test": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.0.0.tgz", + "integrity": "sha512-JBUUzyOgEwXQY1NuPtvcj/qcBDbDmEvWufhlnXZIm75DEHp+afM1r1ujJpJsV/gSM4t59tpDyPi1sd6ZaPFfsA==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "get-intrinsic": "^1.1.3", + "is-regex": "^1.1.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" + }, + "node_modules/schema-utils": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.1.1.tgz", + "integrity": "sha512-Y5PQxS4ITlC+EahLuXaY86TXfR7Dc5lw294alXOq86JAHCihAIZfqv8nNCWvaEJvaC51uN9hbLGeV0cFBdH+Fw==", + "dev": true, + "dependencies": { + "@types/json-schema": "^7.0.8", + "ajv": "^6.12.5", + "ajv-keywords": "^3.5.2" + }, + "engines": { + "node": ">= 10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + } + }, + "node_modules/schema-utils/node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/schema-utils/node_modules/ajv-keywords": { + "version": "3.5.2", + "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", + "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", + "dev": true, + "peerDependencies": { + "ajv": "^6.9.1" + } + }, + "node_modules/schema-utils/node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "node_modules/semver": { + "version": "7.3.8", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.8.tgz", + "integrity": "sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/semver/node_modules/lru-cache": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", + "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", + "dev": true, + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/semver/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", + "dev": true + }, + "node_modules/send": { + "version": "0.18.0", + "resolved": "https://registry.npmjs.org/send/-/send-0.18.0.tgz", + "integrity": "sha512-qqWzuOjSFOuqPjFe4NOsMLafToQQwBSOEpS+FwEt3A2V3vKubTquT3vmLTQpFgMXp8AlFWFuP1qKaJZOtPpVXg==", + "dependencies": { + "debug": "2.6.9", + "depd": "2.0.0", + "destroy": "1.2.0", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "fresh": "0.5.2", + "http-errors": "2.0.0", + "mime": "1.6.0", + "ms": "2.1.3", + "on-finished": "2.4.1", + "range-parser": "~1.2.1", + "statuses": "2.0.1" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/send/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dependencies": { + "ms": "2.0.0" + } + }, + "node_modules/send/node_modules/debug/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" + }, + "node_modules/send/node_modules/ms": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", + "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==" + }, + "node_modules/serialize-javascript": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-6.0.1.tgz", + "integrity": "sha512-owoXEFjWRllis8/M1Q+Cw5k8ZH40e3zhp/ovX+Xr/vi1qj6QesbyXXViFbpNvWvPNAD62SutwEXavefrLJWj7w==", + "dev": true, + "dependencies": { + "randombytes": "^2.1.0" + } + }, + "node_modules/serve-static": { + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.15.0.tgz", + "integrity": "sha512-XGuRDNjXUijsUL0vl6nSD7cwURuzEgglbOaFuZM9g3kwDXOWVTck0jLzjPzGD+TazWbboZYu52/9/XPdUgne9g==", + "dependencies": { + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "parseurl": "~1.3.3", + "send": "0.18.0" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/setprototypeof": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", + "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==" + }, + "node_modules/shebang-command": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", + "integrity": "sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==", + "dev": true, + "dependencies": { + "shebang-regex": "^3.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/shebang-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-3.0.0.tgz", + "integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/shelljs": { + "version": "0.8.5", + "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.8.5.tgz", + "integrity": "sha512-TiwcRcrkhHvbrZbnRcFYMLl30Dfov3HKqzp5tO5b4pt6G/SezKcYhmDg15zXVBswHmctSAQKznqNW2LO5tTDow==", + "dev": true, + "dependencies": { + "glob": "^7.0.0", + "interpret": "^1.0.0", + "rechoir": "^0.6.2" + }, + "bin": { + "shjs": "bin/shjs" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/side-channel": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.4.tgz", + "integrity": "sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==", + "dependencies": { + "call-bind": "^1.0.0", + "get-intrinsic": "^1.0.2", + "object-inspect": "^1.9.0" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/signal-exit": { + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", + "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==", + "dev": true + }, + "node_modules/sisteransi": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/sisteransi/-/sisteransi-1.0.5.tgz", + "integrity": "sha512-bLGGlR1QxBcynn2d5YmDX4MGjlZvy2MRBDRNHLJ8VI6l6+9FUiyTFNJ0IveOSP0bcXgVDPRcfGqA0pjaqUpfVg==", + "dev": true + }, + "node_modules/slash": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/slash/-/slash-3.0.0.tgz", + "integrity": "sha512-g9Q1haeby36OSStwb4ntCGGGaKsaVSjQ68fBxoQcutl5fS1vuY18H3wSt3jFyFtrkx+Kz0V1G85A4MyAdDMi2Q==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/source-map": { + "version": "0.7.4", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.4.tgz", + "integrity": "sha512-l3BikUxvPOcn5E74dZiq5BGsTb5yEwhaTSzccU6t4sDOH8NWJCstKO5QT2CvtFoK6F0saL7p9xHAqHOlCPJygA==", + "dev": true, + "engines": { + "node": ">= 8" + } + }, + "node_modules/source-map-support": { + "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==", + "dev": true, + "dependencies": { + "buffer-from": "^1.0.0", + "source-map": "^0.6.0" + } + }, + "node_modules/source-map-support/node_modules/source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/sourcemap-codec": { + "version": "1.4.8", + "resolved": "https://registry.npmjs.org/sourcemap-codec/-/sourcemap-codec-1.4.8.tgz", + "integrity": "sha512-9NykojV5Uih4lgo5So5dtw+f0JgJX30KCNI8gwhz2J9A15wD0Ml6tjHKwf6fTSa6fAdVBdZeNOs9eJ71qCk8vA==", + "deprecated": "Please use @jridgewell/sourcemap-codec instead", + "dev": true + }, + "node_modules/sprintf-js": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", + "integrity": "sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==", + "dev": true + }, + "node_modules/stack-utils": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/stack-utils/-/stack-utils-2.0.6.tgz", + "integrity": "sha512-XlkWvfIm6RmsWtNJx+uqtKLS8eqFbxUg0ZzLXqY0caEy9l7hruX8IpiDnjsLavoBgqCCR71TqWO8MaXYheJ3RQ==", + "dev": true, + "dependencies": { + "escape-string-regexp": "^2.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/stack-utils/node_modules/escape-string-regexp": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-2.0.0.tgz", + "integrity": "sha512-UpzcLCXolUWcNu5HtVMHYdXJjArjsF9C0aNnquZYY4uW/Vu0miy5YoWvbV345HauVvcAUnpRuhMMcqTcGOY2+w==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/statuses": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", + "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/streamsearch": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/streamsearch/-/streamsearch-1.1.0.tgz", + "integrity": "sha512-Mcc5wHehp9aXz1ax6bZUyY5afg9u2rv5cqQI3mRrYkGC8rW2hM02jWuwjtL++LS5qinSyhj2QfLyNsuc+VsExg==", + "engines": { + "node": ">=10.0.0" + } + }, + "node_modules/string_decoder": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "dependencies": { + "safe-buffer": "~5.1.0" + } + }, + "node_modules/string_decoder/node_modules/safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==" + }, + "node_modules/string-length": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/string-length/-/string-length-4.0.2.tgz", + "integrity": "sha512-+l6rNN5fYHNhZZy41RXsYptCjA2Igmq4EG7kZAYFQI1E1VTXarr6ZPXBg6eq7Y6eK4FEhY6AJlyuFIb/v/S0VQ==", + "dev": true, + "dependencies": { + "char-regex": "^1.0.2", + "strip-ansi": "^6.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/string-width": { + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", + "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", + "dev": true, + "dependencies": { + "emoji-regex": "^8.0.0", + "is-fullwidth-code-point": "^3.0.0", + "strip-ansi": "^6.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/string.prototype.trimend": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.6.tgz", + "integrity": "sha512-JySq+4mrPf9EsDBEDYMOb/lM7XQLulwg5R/m1r0PXEFqrV0qHvl58sdTilSXtKOflCsK2E8jxf+GKC0T07RWwQ==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/string.prototype.trimstart": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.6.tgz", + "integrity": "sha512-omqjMDaY92pbn5HOX7f9IccLA+U1tA9GvtU4JrodiXFfYB7jPzzHpRzpglLAjtUV6bB557zwClJezTqnAiYnQA==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "define-properties": "^1.1.4", + "es-abstract": "^1.20.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/strip-ansi": { + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", + "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", + "dev": true, + "dependencies": { + "ansi-regex": "^5.0.1" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/strip-bom": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-4.0.0.tgz", + "integrity": "sha512-3xurFv5tEgii33Zi8Jtp55wEIILR9eh34FAW00PZf+JnSsTmV/ioewSgQl97JHvgjoRGwPShsWm+IdrxB35d0w==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/strip-final-newline": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/strip-final-newline/-/strip-final-newline-2.0.0.tgz", + "integrity": "sha512-BrpvfNAE3dcvq7ll3xVumzjKjZQ5tI1sEUIKr3Uoks0XUl45St3FlatVqef9prk4jRDzhW6WZg+3bk93y6pLjA==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/strip-json-comments": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-3.1.1.tgz", + "integrity": "sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==", + "dev": true, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/superagent": { + "version": "8.0.9", + "resolved": "https://registry.npmjs.org/superagent/-/superagent-8.0.9.tgz", + "integrity": "sha512-4C7Bh5pyHTvU33KpZgwrNKh/VQnvgtCSqPRfJAUdmrtSYePVzVg4E4OzsrbkhJj9O7SO6Bnv75K/F8XVZT8YHA==", + "dev": true, + "dependencies": { + "component-emitter": "^1.3.0", + "cookiejar": "^2.1.4", + "debug": "^4.3.4", + "fast-safe-stringify": "^2.1.1", + "form-data": "^4.0.0", + "formidable": "^2.1.2", + "methods": "^1.1.2", + "mime": "2.6.0", + "qs": "^6.11.0", + "semver": "^7.3.8" + }, + "engines": { + "node": ">=6.4.0 <13 || >=14" + } + }, + "node_modules/superagent/node_modules/mime": { + "version": "2.6.0", + "resolved": "https://registry.npmjs.org/mime/-/mime-2.6.0.tgz", + "integrity": "sha512-USPkMeET31rOMiarsBNIHZKLGgvKc/LrjofAnBlOttf5ajRvqiRA8QsenbcooctK6d6Ts6aqZXBA+XbkKthiQg==", + "dev": true, + "bin": { + "mime": "cli.js" + }, + "engines": { + "node": ">=4.0.0" + } + }, + "node_modules/supertest": { + "version": "6.3.3", + "resolved": "https://registry.npmjs.org/supertest/-/supertest-6.3.3.tgz", + "integrity": "sha512-EMCG6G8gDu5qEqRQ3JjjPs6+FYT1a7Hv5ApHvtSghmOFJYtsU5S+pSb6Y2EUeCEY3CmEL3mmQ8YWlPOzQomabA==", + "dev": true, + "dependencies": { + "methods": "^1.1.2", + "superagent": "^8.0.5" + }, + "engines": { + "node": ">=6.4.0" + } + }, + "node_modules/supports-color": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", + "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/supports-preserve-symlinks-flag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", + "integrity": "sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==", + "dev": true, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/symbol-observable": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-4.0.0.tgz", + "integrity": "sha512-b19dMThMV4HVFynSAM1++gBHAbk2Tc/osgLIBZMKsyqh34jb2e8Os7T6ZW/Bt3pJFdBTd2JwAnAAEQV7rSNvcQ==", + "dev": true, + "engines": { + "node": ">=0.10" + } + }, + "node_modules/tapable": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz", + "integrity": "sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/terser": { + "version": "5.16.3", + "resolved": "https://registry.npmjs.org/terser/-/terser-5.16.3.tgz", + "integrity": "sha512-v8wWLaS/xt3nE9dgKEWhNUFP6q4kngO5B8eYFUuebsu7Dw/UNAnpUod6UHo04jSSkv8TzKHjZDSd7EXdDQAl8Q==", + "dev": true, + "dependencies": { + "@jridgewell/source-map": "^0.3.2", + "acorn": "^8.5.0", + "commander": "^2.20.0", + "source-map-support": "~0.5.20" + }, + "bin": { + "terser": "bin/terser" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/terser-webpack-plugin": { + "version": "5.3.6", + "resolved": "https://registry.npmjs.org/terser-webpack-plugin/-/terser-webpack-plugin-5.3.6.tgz", + "integrity": "sha512-kfLFk+PoLUQIbLmB1+PZDMRSZS99Mp+/MHqDNmMA6tOItzRt+Npe3E+fsMs5mfcM0wCtrrdU387UnV+vnSffXQ==", + "dev": true, + "dependencies": { + "@jridgewell/trace-mapping": "^0.3.14", + "jest-worker": "^27.4.5", + "schema-utils": "^3.1.1", + "serialize-javascript": "^6.0.0", + "terser": "^5.14.1" + }, + "engines": { + "node": ">= 10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependencies": { + "webpack": "^5.1.0" + }, + "peerDependenciesMeta": { + "@swc/core": { + "optional": true + }, + "esbuild": { + "optional": true + }, + "uglify-js": { + "optional": true + } + } + }, + "node_modules/terser-webpack-plugin/node_modules/jest-worker": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", + "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", + "dev": true, + "dependencies": { + "@types/node": "*", + "merge-stream": "^2.0.0", + "supports-color": "^8.0.0" + }, + "engines": { + "node": ">= 10.13.0" + } + }, + "node_modules/terser-webpack-plugin/node_modules/supports-color": { + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", + "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "dev": true, + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/supports-color?sponsor=1" + } + }, + "node_modules/terser/node_modules/commander": { + "version": "2.20.3", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", + "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==", + "dev": true + }, + "node_modules/test-exclude": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/test-exclude/-/test-exclude-6.0.0.tgz", + "integrity": "sha512-cAGWPIyOHU6zlmg88jwm7VRyXnMN7iV68OGAbYDk/Mh/xC/pzVPlQtY6ngoIH/5/tciuhGfvESU8GrHrcxD56w==", + "dev": true, + "dependencies": { + "@istanbuljs/schema": "^0.1.2", + "glob": "^7.1.4", + "minimatch": "^3.0.4" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/text-table": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", + "integrity": "sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw==", + "dev": true + }, + "node_modules/through": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", + "integrity": "sha512-w89qg7PI8wAdvX60bMDP+bFoD5Dvhm9oLheFp5O4a2QF0cSBGsBX4qZmadPMvVqlLJBBci+WqGGOAPvcDeNSVg==", + "dev": true + }, + "node_modules/tmp": { + "version": "0.0.33", + "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", + "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==", + "dev": true, + "dependencies": { + "os-tmpdir": "~1.0.2" + }, + "engines": { + "node": ">=0.6.0" + } + }, + "node_modules/tmpl": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/tmpl/-/tmpl-1.0.5.tgz", + "integrity": "sha512-3f0uOEAQwIqGuWW2MVzYg8fV/QNnc/IpuJNG837rLuczAaLVHslWHZQj4IGiEl5Hs3kkbhwL9Ab7Hrsmuj+Smw==", + "dev": true + }, + "node_modules/to-fast-properties": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-2.0.0.tgz", + "integrity": "sha512-/OaKK0xYrs3DmxRYqL/yDc+FxFUVYhDlXMhRmv3z915w2HF1tnN1omB354j8VUGO/hbRzyD6Y3sA7v7GS/ceog==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/to-regex-range": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", + "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", + "dev": true, + "dependencies": { + "is-number": "^7.0.0" + }, + "engines": { + "node": ">=8.0" + } + }, + "node_modules/toidentifier": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", + "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==", + "engines": { + "node": ">=0.6" + } + }, + "node_modules/tr46": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", + "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==" + }, + "node_modules/tree-kill": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/tree-kill/-/tree-kill-1.2.2.tgz", + "integrity": "sha512-L0Orpi8qGpRG//Nd+H90vFB+3iHnue1zSSGmNOOCh1GLJ7rUKVwV2HvijphGQS2UmhUZewS9VgvxYIdgr+fG1A==", + "dev": true, + "bin": { + "tree-kill": "cli.js" + } + }, + "node_modules/ts-jest": { + "version": "29.0.3", + "resolved": "https://registry.npmjs.org/ts-jest/-/ts-jest-29.0.3.tgz", + "integrity": "sha512-Ibygvmuyq1qp/z3yTh9QTwVVAbFdDy/+4BtIQR2sp6baF2SJU/8CKK/hhnGIDY2L90Az2jIqTwZPnN2p+BweiQ==", + "dev": true, + "dependencies": { + "bs-logger": "0.x", + "fast-json-stable-stringify": "2.x", + "jest-util": "^29.0.0", + "json5": "^2.2.1", + "lodash.memoize": "4.x", + "make-error": "1.x", + "semver": "7.x", + "yargs-parser": "^21.0.1" + }, + "bin": { + "ts-jest": "cli.js" + }, + "engines": { + "node": "^14.15.0 || ^16.10.0 || >=18.0.0" + }, + "peerDependencies": { + "@babel/core": ">=7.0.0-beta.0 <8", + "@jest/types": "^29.0.0", + "babel-jest": "^29.0.0", + "jest": "^29.0.0", + "typescript": ">=4.3" + }, + "peerDependenciesMeta": { + "@babel/core": { + "optional": true + }, + "@jest/types": { + "optional": true + }, + "babel-jest": { + "optional": true + }, + "esbuild": { + "optional": true + } + } + }, + "node_modules/ts-loader": { + "version": "9.4.2", + "resolved": "https://registry.npmjs.org/ts-loader/-/ts-loader-9.4.2.tgz", + "integrity": "sha512-OmlC4WVmFv5I0PpaxYb+qGeGOdm5giHU7HwDDUjw59emP2UYMHy9fFSDcYgSNoH8sXcj4hGCSEhlDZ9ULeDraA==", + "dev": true, + "dependencies": { + "chalk": "^4.1.0", + "enhanced-resolve": "^5.0.0", + "micromatch": "^4.0.0", + "semver": "^7.3.4" + }, + "engines": { + "node": ">=12.0.0" + }, + "peerDependencies": { + "typescript": "*", + "webpack": "^5.0.0" + } + }, + "node_modules/ts-loader/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/ts-node": { + "version": "10.9.1", + "resolved": "https://registry.npmjs.org/ts-node/-/ts-node-10.9.1.tgz", + "integrity": "sha512-NtVysVPkxxrwFGUUxGYhfux8k78pQB3JqYBXlLRZgdGUqTO5wU/UyHop5p70iEbGhB7q5KmiZiU0Y3KlJrScEw==", + "dev": true, + "dependencies": { + "@cspotcode/source-map-support": "^0.8.0", + "@tsconfig/node10": "^1.0.7", + "@tsconfig/node12": "^1.0.7", + "@tsconfig/node14": "^1.0.0", + "@tsconfig/node16": "^1.0.2", + "acorn": "^8.4.1", + "acorn-walk": "^8.1.1", + "arg": "^4.1.0", + "create-require": "^1.1.0", + "diff": "^4.0.1", + "make-error": "^1.1.1", + "v8-compile-cache-lib": "^3.0.1", + "yn": "3.1.1" + }, + "bin": { + "ts-node": "dist/bin.js", + "ts-node-cwd": "dist/bin-cwd.js", + "ts-node-esm": "dist/bin-esm.js", + "ts-node-script": "dist/bin-script.js", + "ts-node-transpile-only": "dist/bin-transpile.js", + "ts-script": "dist/bin-script-deprecated.js" + }, + "peerDependencies": { + "@swc/core": ">=1.2.50", + "@swc/wasm": ">=1.2.50", + "@types/node": "*", + "typescript": ">=2.7" + }, + "peerDependenciesMeta": { + "@swc/core": { + "optional": true + }, + "@swc/wasm": { + "optional": true + } + } + }, + "node_modules/tsconfig-paths": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-4.1.1.tgz", + "integrity": "sha512-VgPrtLKpRgEAJsMj5Q/I/mXouC6A/7eJ/X4Nuk6o0cRPwBtznYxTCU4FodbexbzH9somBPEXYi0ZkUViUpJ21Q==", + "dev": true, + "dependencies": { + "json5": "^2.2.1", + "minimist": "^1.2.6", + "strip-bom": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/tsconfig-paths-webpack-plugin": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/tsconfig-paths-webpack-plugin/-/tsconfig-paths-webpack-plugin-4.0.0.tgz", + "integrity": "sha512-fw/7265mIWukrSHd0i+wSwx64kYUSAKPfxRDksjKIYTxSAp9W9/xcZVBF4Kl0eqQd5eBpAQ/oQrc5RyM/0c1GQ==", + "dev": true, + "dependencies": { + "chalk": "^4.1.0", + "enhanced-resolve": "^5.7.0", + "tsconfig-paths": "^4.0.0" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/tsconfig-paths-webpack-plugin/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/tsconfig-paths/node_modules/strip-bom": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", + "integrity": "sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/tslib": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.5.0.tgz", + "integrity": "sha512-336iVw3rtn2BUK7ORdIAHTyxHGRIHVReokCR3XjbckJMK7ms8FysBfhLR8IXnAgy7T0PTPNBWKiH514FOW/WSg==" + }, + "node_modules/tsutils": { + "version": "3.21.0", + "resolved": "https://registry.npmjs.org/tsutils/-/tsutils-3.21.0.tgz", + "integrity": "sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA==", + "dev": true, + "dependencies": { + "tslib": "^1.8.1" + }, + "engines": { + "node": ">= 6" + }, + "peerDependencies": { + "typescript": ">=2.8.0 || >= 3.2.0-dev || >= 3.3.0-dev || >= 3.4.0-dev || >= 3.5.0-dev || >= 3.6.0-dev || >= 3.6.0-beta || >= 3.7.0-dev || >= 3.7.0-beta" + } + }, + "node_modules/tsutils/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "dev": true + }, + "node_modules/type-check": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.4.0.tgz", + "integrity": "sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==", + "dev": true, + "dependencies": { + "prelude-ls": "^1.2.1" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/type-detect": { + "version": "4.0.8", + "resolved": "https://registry.npmjs.org/type-detect/-/type-detect-4.0.8.tgz", + "integrity": "sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/type-fest": { + "version": "0.20.2", + "resolved": "https://registry.npmjs.org/type-fest/-/type-fest-0.20.2.tgz", + "integrity": "sha512-Ne+eE4r0/iWnpAxD852z3A+N0Bt5RN//NjJwRd2VFHEmrywxf5vsZlh4R6lixl6B+wz/8d+maTSAkN1FIkI3LQ==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/type-is": { + "version": "1.6.18", + "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", + "integrity": "sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==", + "dependencies": { + "media-typer": "0.3.0", + "mime-types": "~2.1.24" + }, + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/typed-array-length": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/typed-array-length/-/typed-array-length-1.0.4.tgz", + "integrity": "sha512-KjZypGq+I/H7HI5HlOoGHkWUUGq+Q0TPhQurLbyrVrvnKTBgzLhIJ7j6J/XTQOi0d1RjyZ0wdas8bKs2p0x3Ng==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "for-each": "^0.3.3", + "is-typed-array": "^1.1.9" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/typedarray": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", + "integrity": "sha512-/aCDEGatGvZ2BIk+HmLf4ifCJFwvKFNb9/JeZPMulfgFracn9QFcAf5GO8B/mweUjSoblS5In0cWhqpfs/5PQA==" + }, + "node_modules/typescript": { + "version": "4.9.5", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.9.5.tgz", + "integrity": "sha512-1FXk9E2Hm+QzZQ7z+McJiHL4NW1F2EzMu9Nq9i3zAaGqibafqYwCVU6WyWAuyQRRzOlxou8xZSyXLEN8oKj24g==", + "dev": true, + "bin": { + "tsc": "bin/tsc", + "tsserver": "bin/tsserver" + }, + "engines": { + "node": ">=4.2.0" + } + }, + "node_modules/uid": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/uid/-/uid-2.0.1.tgz", + "integrity": "sha512-PF+1AnZgycpAIEmNtjxGBVmKbZAQguaa4pBUq6KNaGEcpzZ2klCNZLM34tsjp76maN00TttiiUf6zkIBpJQm2A==", + "dependencies": { + "@lukeed/csprng": "^1.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/unbox-primitive": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.0.2.tgz", + "integrity": "sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw==", + "dev": true, + "dependencies": { + "call-bind": "^1.0.2", + "has-bigints": "^1.0.2", + "has-symbols": "^1.0.3", + "which-boxed-primitive": "^1.0.2" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/universalify": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.0.tgz", + "integrity": "sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ==", + "dev": true, + "engines": { + "node": ">= 10.0.0" + } + }, + "node_modules/unpipe": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", + "integrity": "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/update-browserslist-db": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.0.10.tgz", + "integrity": "sha512-OztqDenkfFkbSG+tRxBeAnCVPckDBcvibKd35yDONx6OU8N7sqgwc7rCbkJ/WcYtVRZ4ba68d6byhC21GFh7sQ==", + "dev": true, + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/browserslist" + }, + { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/browserslist" + } + ], + "dependencies": { + "escalade": "^3.1.1", + "picocolors": "^1.0.0" + }, + "bin": { + "browserslist-lint": "cli.js" + }, + "peerDependencies": { + "browserslist": ">= 4.21.0" + } + }, + "node_modules/uri-js": { + "version": "4.4.1", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", + "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", + "dev": true, + "dependencies": { + "punycode": "^2.1.0" + } + }, + "node_modules/util-deprecate": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", + "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==" + }, + "node_modules/utils-merge": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", + "integrity": "sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA==", + "engines": { + "node": ">= 0.4.0" + } + }, + "node_modules/uuid": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.0.tgz", + "integrity": "sha512-MXcSTerfPa4uqyzStbRoTgt5XIe3x5+42+q1sDuy3R5MDk66URdLMOZe5aPX/SQd+kuYAh0FdP/pO28IkQyTeg==", + "bin": { + "uuid": "dist/bin/uuid" + } + }, + "node_modules/v8-compile-cache": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz", + "integrity": "sha512-l8lCEmLcLYZh4nbunNZvQCJc5pv7+RCwa8q/LdUx8u7lsWvPDKmpodJAJNwkAhJC//dFY48KuIEmjtd4RViDrA==", + "dev": true + }, + "node_modules/v8-compile-cache-lib": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz", + "integrity": "sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg==", + "dev": true + }, + "node_modules/v8-to-istanbul": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/v8-to-istanbul/-/v8-to-istanbul-9.0.1.tgz", + "integrity": "sha512-74Y4LqY74kLE6IFyIjPtkSTWzUZmj8tdHT9Ii/26dvQ6K9Dl2NbEfj0XgU2sHCtKgt5VupqhlO/5aWuqS+IY1w==", + "dev": true, + "dependencies": { + "@jridgewell/trace-mapping": "^0.3.12", + "@types/istanbul-lib-coverage": "^2.0.1", + "convert-source-map": "^1.6.0" + }, + "engines": { + "node": ">=10.12.0" + } + }, + "node_modules/v8-to-istanbul/node_modules/convert-source-map": { + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.9.0.tgz", + "integrity": "sha512-ASFBup0Mz1uyiIjANan1jzLQami9z1PoYSZCiiYW2FczPbenXc45FZdBZLzOT+r6+iciuEModtmCti+hjaAk0A==", + "dev": true + }, + "node_modules/vary": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", + "integrity": "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==", + "engines": { + "node": ">= 0.8" + } + }, + "node_modules/walker": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/walker/-/walker-1.0.8.tgz", + "integrity": "sha512-ts/8E8l5b7kY0vlWLewOkDXMmPdLcVV4GmOQLyxuSswIJsweeFZtAsMF7k1Nszz+TYBQrlYRmzOnr398y1JemQ==", + "dev": true, + "dependencies": { + "makeerror": "1.0.12" + } + }, + "node_modules/watchpack": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.4.0.tgz", + "integrity": "sha512-Lcvm7MGST/4fup+ifyKi2hjyIAwcdI4HRgtvTpIUxBRhB+RFtUh8XtDOxUfctVCnhVi+QQj49i91OyvzkJl6cg==", + "dev": true, + "dependencies": { + "glob-to-regexp": "^0.4.1", + "graceful-fs": "^4.1.2" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/wcwidth": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/wcwidth/-/wcwidth-1.0.1.tgz", + "integrity": "sha512-XHPEwS0q6TaxcvG85+8EYkbiCux2XtWG2mkc47Ng2A77BQu9+DqIOJldST4HgPkuea7dvKSj5VgX3P1d4rW8Tg==", + "dev": true, + "dependencies": { + "defaults": "^1.0.3" + } + }, + "node_modules/webidl-conversions": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", + "integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==" + }, + "node_modules/webpack": { + "version": "5.75.0", + "resolved": "https://registry.npmjs.org/webpack/-/webpack-5.75.0.tgz", + "integrity": "sha512-piaIaoVJlqMsPtX/+3KTTO6jfvrSYgauFVdt8cr9LTHKmcq/AMd4mhzsiP7ZF/PGRNPGA8336jldh9l2Kt2ogQ==", + "dev": true, + "dependencies": { + "@types/eslint-scope": "^3.7.3", + "@types/estree": "^0.0.51", + "@webassemblyjs/ast": "1.11.1", + "@webassemblyjs/wasm-edit": "1.11.1", + "@webassemblyjs/wasm-parser": "1.11.1", + "acorn": "^8.7.1", + "acorn-import-assertions": "^1.7.6", + "browserslist": "^4.14.5", + "chrome-trace-event": "^1.0.2", + "enhanced-resolve": "^5.10.0", + "es-module-lexer": "^0.9.0", + "eslint-scope": "5.1.1", + "events": "^3.2.0", + "glob-to-regexp": "^0.4.1", + "graceful-fs": "^4.2.9", + "json-parse-even-better-errors": "^2.3.1", + "loader-runner": "^4.2.0", + "mime-types": "^2.1.27", + "neo-async": "^2.6.2", + "schema-utils": "^3.1.0", + "tapable": "^2.1.1", + "terser-webpack-plugin": "^5.1.3", + "watchpack": "^2.4.0", + "webpack-sources": "^3.2.3" + }, + "bin": { + "webpack": "bin/webpack.js" + }, + "engines": { + "node": ">=10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependenciesMeta": { + "webpack-cli": { + "optional": true + } + } + }, + "node_modules/webpack-node-externals": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/webpack-node-externals/-/webpack-node-externals-3.0.0.tgz", + "integrity": "sha512-LnL6Z3GGDPht/AigwRh2dvL9PQPFQ8skEpVrWZXLWBYmqcaojHNN0onvHzie6rq7EWKrrBfPYqNEzTJgiwEQDQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/webpack-sources": { + "version": "3.2.3", + "resolved": "https://registry.npmjs.org/webpack-sources/-/webpack-sources-3.2.3.tgz", + "integrity": "sha512-/DyMEOrDgLKKIG0fmvtz+4dUX/3Ghozwgm6iPp8KRhvn+eQf9+Q7GWxVNMk3+uCPWfdXYC4ExGBckIXdFEfH1w==", + "dev": true, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/whatwg-url": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", + "integrity": "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==", + "dependencies": { + "tr46": "~0.0.3", + "webidl-conversions": "^3.0.0" + } + }, + "node_modules/which": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", + "integrity": "sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==", + "dev": true, + "dependencies": { + "isexe": "^2.0.0" + }, + "bin": { + "node-which": "bin/node-which" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/which-boxed-primitive": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/which-boxed-primitive/-/which-boxed-primitive-1.0.2.tgz", + "integrity": "sha512-bwZdv0AKLpplFY2KZRX6TvyuN7ojjr7lwkg6ml0roIy9YeuSr7JS372qlNW18UQYzgYK9ziGcerWqZOmEn9VNg==", + "dev": true, + "dependencies": { + "is-bigint": "^1.0.1", + "is-boolean-object": "^1.1.0", + "is-number-object": "^1.0.4", + "is-string": "^1.0.5", + "is-symbol": "^1.0.3" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/which-typed-array": { + "version": "1.1.9", + "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.9.tgz", + "integrity": "sha512-w9c4xkx6mPidwp7180ckYWfMmvxpjlZuIudNtDf4N/tTAUB8VJbX25qZoAsrtGuYNnGw3pa0AXgbGKRB8/EceA==", + "dev": true, + "dependencies": { + "available-typed-arrays": "^1.0.5", + "call-bind": "^1.0.2", + "for-each": "^0.3.3", + "gopd": "^1.0.1", + "has-tostringtag": "^1.0.0", + "is-typed-array": "^1.1.10" + }, + "engines": { + "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" + } + }, + "node_modules/windows-release": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/windows-release/-/windows-release-4.0.0.tgz", + "integrity": "sha512-OxmV4wzDKB1x7AZaZgXMVsdJ1qER1ed83ZrTYd5Bwq2HfJVg3DJS8nqlAG4sMoJ7mu8cuRmLEYyU13BKwctRAg==", + "dev": true, + "dependencies": { + "execa": "^4.0.2" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/windows-release/node_modules/execa": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/execa/-/execa-4.1.0.tgz", + "integrity": "sha512-j5W0//W7f8UxAn8hXVnwG8tLwdiUy4FJLcSupCg6maBYZDpyBvTApK7KyuI4bKj8KOh1r2YH+6ucuYtJv1bTZA==", + "dev": true, + "dependencies": { + "cross-spawn": "^7.0.0", + "get-stream": "^5.0.0", + "human-signals": "^1.1.1", + "is-stream": "^2.0.0", + "merge-stream": "^2.0.0", + "npm-run-path": "^4.0.0", + "onetime": "^5.1.0", + "signal-exit": "^3.0.2", + "strip-final-newline": "^2.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sindresorhus/execa?sponsor=1" + } + }, + "node_modules/windows-release/node_modules/get-stream": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-5.2.0.tgz", + "integrity": "sha512-nBF+F1rAZVCu/p7rjzgA+Yb4lfYXrpl7a6VmJrU8wF9I1CKvP/QwPNZHnOlwbTkY6dvtFIzFMSyQXbLoTQPRpA==", + "dev": true, + "dependencies": { + "pump": "^3.0.0" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/windows-release/node_modules/human-signals": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/human-signals/-/human-signals-1.1.1.tgz", + "integrity": "sha512-SEQu7vl8KjNL2eoGBLF3+wAjpsNfA9XMlXAYj/3EdaNfAlxKthD1xjEQfGOUhllCGGJVNY34bRr6lPINhNjyZw==", + "dev": true, + "engines": { + "node": ">=8.12.0" + } + }, + "node_modules/word-wrap": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/word-wrap/-/word-wrap-1.2.3.tgz", + "integrity": "sha512-Hz/mrNwitNRh/HUAtM/VT/5VH+ygD6DV7mYKZAtHOrbs8U7lvPS6xf7EJKMF0uW1KJCl0H701g3ZGus+muE5vQ==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/wrap-ansi": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", + "integrity": "sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.0.0", + "string-width": "^4.1.0", + "strip-ansi": "^6.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/wrap-ansi?sponsor=1" + } + }, + "node_modules/wrappy": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", + "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", + "dev": true + }, + "node_modules/write-file-atomic": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-5.0.0.tgz", + "integrity": "sha512-R7NYMnHSlV42K54lwY9lvW6MnSm1HSJqZL3xiSgi9E7//FYaI74r2G0rd+/X6VAMkHEdzxQaU5HUOXWUz5kA/w==", + "dev": true, + "dependencies": { + "imurmurhash": "^0.1.4", + "signal-exit": "^3.0.7" + }, + "engines": { + "node": "^14.17.0 || ^16.13.0 || >=18.0.0" + } + }, + "node_modules/xtend": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.2.tgz", + "integrity": "sha512-LKYU1iAXJXUgAXn9URjiu+MWhyUXHsvfp7mcuYm9dSUKK0/CjtrUwFAxD82/mCWbtLsGjFIad0wIsod4zrTAEQ==", + "engines": { + "node": ">=0.4" + } + }, + "node_modules/y18n": { + "version": "5.0.8", + "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", + "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==", + "dev": true, + "engines": { + "node": ">=10" + } + }, + "node_modules/yallist": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.1.1.tgz", + "integrity": "sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==", + "dev": true + }, + "node_modules/yaml": { + "version": "1.10.2", + "resolved": "https://registry.npmjs.org/yaml/-/yaml-1.10.2.tgz", + "integrity": "sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==", + "dev": true, + "engines": { + "node": ">= 6" + } + }, + "node_modules/yargs": { + "version": "17.6.2", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.6.2.tgz", + "integrity": "sha512-1/9UrdHjDZc0eOU0HxOHoS78C69UD3JRMvzlJ7S79S2nTaWRA/whGCTV8o9e/N/1Va9YIV7Q4sOxD8VV4pCWOw==", + "dev": true, + "dependencies": { + "cliui": "^8.0.1", + "escalade": "^3.1.1", + "get-caller-file": "^2.0.5", + "require-directory": "^2.1.1", + "string-width": "^4.2.3", + "y18n": "^5.0.5", + "yargs-parser": "^21.1.1" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/yargs-parser": { + "version": "21.1.1", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz", + "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==", + "dev": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/yn": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/yn/-/yn-3.1.1.tgz", + "integrity": "sha512-Ux4ygGWsu2c7isFWe8Yu1YluJmqVhxqK2cLXNQA5AcC3QfbGNpM7fu0Y8b/z16pXLnFxZYvWhd3fhBY9DLmC6Q==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/yocto-queue": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/yocto-queue/-/yocto-queue-0.1.0.tgz", + "integrity": "sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + } + } +} diff --git a/server/package.json b/server/package.json new file mode 100644 index 0000000..cda54ae --- /dev/null +++ b/server/package.json @@ -0,0 +1,67 @@ +{ + "name": "rs-clone-server", + "version": "0.0.1", + "private": true, + "author": "HardManDev ", + "license": "MIT", + "scripts": { + "build": "nest build", + "start": "nest start", + "start:dev": "nest start --watch", + "start:debug": "nest start --debug --watch", + "start:prod": "node dist/main", + "lint": "eslint \"{src,apps,libs,test}/**/*.ts\"", + "lint:fix": "eslint \"{src,apps,libs,test}/**/*.ts\" --fix", + "test": "jest", + "test:watch": "jest --watch", + "test:cov": "jest --coverage", + "test:debug": "node --inspect-brk -r tsconfig-paths/register -r ts-node/register node_modules/.bin/jest --runInBand", + "test:e2e": "jest --config ./test/jest-e2e.json" + }, + "dependencies": { + "@nestjs/common": "^9.0.0", + "@nestjs/core": "^9.0.0", + "@nestjs/platform-express": "^9.0.0", + "reflect-metadata": "^0.1.13", + "rxjs": "^7.2.0" + }, + "devDependencies": { + "@nestjs/cli": "^9.0.0", + "@nestjs/schematics": "^9.0.0", + "@nestjs/testing": "^9.0.0", + "@types/express": "^4.17.13", + "@types/jest": "29.2.4", + "@types/node": "18.11.18", + "@types/supertest": "^2.0.11", + "@typescript-eslint/eslint-plugin": "^5.50.0", + "@typescript-eslint/parser": "^5.50.0", + "eslint": "^8.2.0", + "eslint-config-airbnb-base": "^15.0.0", + "eslint-config-airbnb-typescript": "^17.0.0", + "jest": "29.3.1", + "source-map-support": "^0.5.20", + "supertest": "^6.1.3", + "ts-jest": "29.0.3", + "ts-loader": "^9.2.3", + "ts-node": "^10.0.0", + "tsconfig-paths": "4.1.1", + "typescript": "^4.7.4" + }, + "jest": { + "moduleFileExtensions": [ + "js", + "json", + "ts" + ], + "rootDir": "src", + "testRegex": ".*\\.spec\\.ts$", + "transform": { + "^.+\\.(t|j)s$": "ts-jest" + }, + "collectCoverageFrom": [ + "**/*.(t|j)s" + ], + "coverageDirectory": "../coverage", + "testEnvironment": "node" + } +} diff --git a/server/src/app.controller.ts b/server/src/app.controller.ts new file mode 100644 index 0000000..81e3721 --- /dev/null +++ b/server/src/app.controller.ts @@ -0,0 +1,14 @@ +import { Controller, Get } from '@nestjs/common'; +import AppService from './app.service'; + +@Controller() +class AppController { + constructor(private readonly appService: AppService) {} + + @Get() + getHello(): string { + return this.appService.getHello(); + } +} + +export default AppController; diff --git a/server/src/app.module.ts b/server/src/app.module.ts new file mode 100644 index 0000000..7c7ce14 --- /dev/null +++ b/server/src/app.module.ts @@ -0,0 +1,12 @@ +import { Module } from '@nestjs/common'; +import AppController from './app.controller'; +import AppService from './app.service'; + +@Module({ + imports: [], + controllers: [AppController], + providers: [AppService], +}) +class AppModule {} + +export default AppModule; diff --git a/server/src/app.service.ts b/server/src/app.service.ts new file mode 100644 index 0000000..17c14bc --- /dev/null +++ b/server/src/app.service.ts @@ -0,0 +1,10 @@ +import { Injectable } from '@nestjs/common'; + +@Injectable() +class AppService { + getHello(): string { + return 'Hello World!'; + } +} + +export default AppService; diff --git a/server/src/main.ts b/server/src/main.ts new file mode 100644 index 0000000..693e845 --- /dev/null +++ b/server/src/main.ts @@ -0,0 +1,11 @@ +import { NestFactory } from '@nestjs/core'; +import AppModule from './app.module'; + +async function bootstrap() { + const app = await NestFactory.create(AppModule); + await app.listen(3000); +} + +(async () => { + await bootstrap(); +})(); diff --git a/server/tsconfig.build.json b/server/tsconfig.build.json new file mode 100644 index 0000000..64f86c6 --- /dev/null +++ b/server/tsconfig.build.json @@ -0,0 +1,4 @@ +{ + "extends": "./tsconfig.json", + "exclude": ["node_modules", "test", "dist", "**/*spec.ts"] +} diff --git a/server/tsconfig.json b/server/tsconfig.json new file mode 100644 index 0000000..e08b719 --- /dev/null +++ b/server/tsconfig.json @@ -0,0 +1,21 @@ +{ + "compilerOptions": { + "module": "commonjs", + "declaration": true, + "removeComments": true, + "emitDecoratorMetadata": true, + "experimentalDecorators": true, + "allowSyntheticDefaultImports": true, + "target": "es2017", + "sourceMap": true, + "outDir": "./dist", + "baseUrl": "./", + "incremental": true, + "skipLibCheck": true, + "strictNullChecks": true, + "noImplicitAny": true, + "strictBindCallApply": false, + "forceConsistentCasingInFileNames": false, + "noFallthroughCasesInSwitch": false + } +} From e1118b9fb274a1134286b1ecbddc9992285c55ef Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 02:41:07 +0300 Subject: [PATCH 008/196] feat: create linters checks workflow --- .github/workflows/linterChecks.yml | 41 ++++++++++++++++++++++++++++++ .idea/.gitignore | 6 +++++ .idea/modules.xml | 8 ++++++ .idea/rs-clone.iml | 12 +++++++++ .idea/vcs.xml | 6 +++++ 5 files changed, 73 insertions(+) create mode 100644 .github/workflows/linterChecks.yml create mode 100644 .idea/.gitignore create mode 100644 .idea/modules.xml create mode 100644 .idea/rs-clone.iml create mode 100644 .idea/vcs.xml diff --git a/.github/workflows/linterChecks.yml b/.github/workflows/linterChecks.yml new file mode 100644 index 0000000..530ee3c --- /dev/null +++ b/.github/workflows/linterChecks.yml @@ -0,0 +1,41 @@ +name: Lint on Pull Request + +on: + pull_request: + branches: + - master + - develop + +jobs: + lint: + runs-on: ubuntu-latest + + steps: + - name: Checkout code + uses: actions/checkout@v2 + + - name: Set up Node JS + uses: actions/setup-node@v2 + with: + node-version: 18.14.0 + + - name: Checkout to server + uses: cd ./server + + - name: Install dependencies for server + run: npm ci + + - name: Run ESLint for server + run: npm run lint + + - name: Checkout to client + uses: cd ./client + + - name: Install dependencies for client + run: npm ci + + - name: Run ESLint for client + run: npm run eslint + + - name: Run Stylelint for client + run: npm run stylelint diff --git a/.idea/.gitignore b/.idea/.gitignore new file mode 100644 index 0000000..df8562c --- /dev/null +++ b/.idea/.gitignore @@ -0,0 +1,6 @@ +# Default ignored files +/shelf/ +/workspace.xml +misc.xml +# Editor-based HTTP Client requests +/httpRequests/ diff --git a/.idea/modules.xml b/.idea/modules.xml new file mode 100644 index 0000000..08dc69f --- /dev/null +++ b/.idea/modules.xml @@ -0,0 +1,8 @@ + + + + + + + + \ No newline at end of file diff --git a/.idea/rs-clone.iml b/.idea/rs-clone.iml new file mode 100644 index 0000000..0c8867d --- /dev/null +++ b/.idea/rs-clone.iml @@ -0,0 +1,12 @@ + + + + + + + + + + + + \ No newline at end of file diff --git a/.idea/vcs.xml b/.idea/vcs.xml new file mode 100644 index 0000000..35eb1dd --- /dev/null +++ b/.idea/vcs.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file From cbb02787ebb5e8705a48194d8bbc4eff0ee48320 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 02:42:38 +0300 Subject: [PATCH 009/196] fix: linters checks workflow --- .github/workflows/linterChecks.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/linterChecks.yml b/.github/workflows/linterChecks.yml index 530ee3c..7d952cc 100644 --- a/.github/workflows/linterChecks.yml +++ b/.github/workflows/linterChecks.yml @@ -20,7 +20,7 @@ jobs: node-version: 18.14.0 - name: Checkout to server - uses: cd ./server + run: cd ./server - name: Install dependencies for server run: npm ci @@ -29,7 +29,7 @@ jobs: run: npm run lint - name: Checkout to client - uses: cd ./client + run: cd ./client - name: Install dependencies for client run: npm ci From 6eea3c399765389cf5aba63d97501d6b90445aae Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 02:42:38 +0300 Subject: [PATCH 010/196] fix: linters checks workflow --- .github/workflows/linterChecks.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/linterChecks.yml b/.github/workflows/linterChecks.yml index 530ee3c..d870f5b 100644 --- a/.github/workflows/linterChecks.yml +++ b/.github/workflows/linterChecks.yml @@ -20,16 +20,16 @@ jobs: node-version: 18.14.0 - name: Checkout to server - uses: cd ./server + run: cd ./server - name: Install dependencies for server - run: npm ci + run: npm i - name: Run ESLint for server run: npm run lint - name: Checkout to client - uses: cd ./client + run: cd ./client - name: Install dependencies for client run: npm ci From bb1162ea2c1517da04afd9809058b1ff6af2ceac Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 02:57:37 +0300 Subject: [PATCH 011/196] fix: linters checks workflow --- .github/workflows/linterChecks.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/linterChecks.yml b/.github/workflows/linterChecks.yml index d870f5b..7d952cc 100644 --- a/.github/workflows/linterChecks.yml +++ b/.github/workflows/linterChecks.yml @@ -23,7 +23,7 @@ jobs: run: cd ./server - name: Install dependencies for server - run: npm i + run: npm ci - name: Run ESLint for server run: npm run lint From 8b638cb11176ca940accbef0c6f899ff5cc90588 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 02:59:07 +0300 Subject: [PATCH 012/196] fix: linters checks workflow --- .github/workflows/linterChecks.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.github/workflows/linterChecks.yml b/.github/workflows/linterChecks.yml index 7d952cc..8d37721 100644 --- a/.github/workflows/linterChecks.yml +++ b/.github/workflows/linterChecks.yml @@ -19,6 +19,9 @@ jobs: with: node-version: 18.14.0 + - name: Debug + run: pwd + - name: Checkout to server run: cd ./server From 246a142866b05e254a7a40b7d672239a9e13c6e7 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 03:00:06 +0300 Subject: [PATCH 013/196] fix: linters checks workflow --- .github/workflows/linterChecks.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/linterChecks.yml b/.github/workflows/linterChecks.yml index 8d37721..629e9d3 100644 --- a/.github/workflows/linterChecks.yml +++ b/.github/workflows/linterChecks.yml @@ -20,7 +20,7 @@ jobs: node-version: 18.14.0 - name: Debug - run: pwd + run: ls -al - name: Checkout to server run: cd ./server From 7fa50ca29944e048608c728b66dd69de3c1d93a3 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 03:01:20 +0300 Subject: [PATCH 014/196] fix: linters checks workflow --- .github/workflows/linterChecks.yml | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/.github/workflows/linterChecks.yml b/.github/workflows/linterChecks.yml index 629e9d3..7584b28 100644 --- a/.github/workflows/linterChecks.yml +++ b/.github/workflows/linterChecks.yml @@ -19,11 +19,8 @@ jobs: with: node-version: 18.14.0 - - name: Debug - run: ls -al - - name: Checkout to server - run: cd ./server + run: cd ./server && ls -al - name: Install dependencies for server run: npm ci From fe21935c0947dcbf3ae15c7087870cdbb3fee9e9 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 03:03:04 +0300 Subject: [PATCH 015/196] fix: linters checks workflow --- .github/workflows/linterChecks.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/linterChecks.yml b/.github/workflows/linterChecks.yml index 7584b28..3f613a2 100644 --- a/.github/workflows/linterChecks.yml +++ b/.github/workflows/linterChecks.yml @@ -20,10 +20,10 @@ jobs: node-version: 18.14.0 - name: Checkout to server - run: cd ./server && ls -al + run: cd ./server - name: Install dependencies for server - run: npm ci + run: ls -al && npm ci - name: Run ESLint for server run: npm run lint From ad487766aab0e33b0edee8ac55c0172d37a2b879 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 03:04:53 +0300 Subject: [PATCH 016/196] fix: linters checks workflow --- .github/workflows/linterChecks.yml | 10 ++-------- 1 file changed, 2 insertions(+), 8 deletions(-) diff --git a/.github/workflows/linterChecks.yml b/.github/workflows/linterChecks.yml index 3f613a2..3c985bd 100644 --- a/.github/workflows/linterChecks.yml +++ b/.github/workflows/linterChecks.yml @@ -19,20 +19,14 @@ jobs: with: node-version: 18.14.0 - - name: Checkout to server - run: cd ./server - - name: Install dependencies for server - run: ls -al && npm ci + run: cd ./server && npm ci - name: Run ESLint for server run: npm run lint - - name: Checkout to client - run: cd ./client - - name: Install dependencies for client - run: npm ci + run: cd ./client && npm ci - name: Run ESLint for client run: npm run eslint From 1d1be42cd2e4f0e14ecb7e10307722872ece323a Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 03:06:41 +0300 Subject: [PATCH 017/196] fix: linters checks workflow --- .github/workflows/linterChecks.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/linterChecks.yml b/.github/workflows/linterChecks.yml index 3c985bd..53643e1 100644 --- a/.github/workflows/linterChecks.yml +++ b/.github/workflows/linterChecks.yml @@ -23,13 +23,13 @@ jobs: run: cd ./server && npm ci - name: Run ESLint for server - run: npm run lint + run: cd ./server && npm run lint - name: Install dependencies for client run: cd ./client && npm ci - name: Run ESLint for client - run: npm run eslint + run: cd ./client && npm run eslint - name: Run Stylelint for client - run: npm run stylelint + run: cd ./client && npm run stylelint From 1a19ed8af502934e43b403f8043e112b2f463e50 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 03:43:35 +0300 Subject: [PATCH 018/196] fix: fix app listen port --- server/src/main.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/src/main.ts b/server/src/main.ts index 693e845..10ff064 100644 --- a/server/src/main.ts +++ b/server/src/main.ts @@ -3,7 +3,7 @@ import AppModule from './app.module'; async function bootstrap() { const app = await NestFactory.create(AppModule); - await app.listen(3000); + await app.listen(process.env.PORT || 3000); } (async () => { From 38343f6ca8e107602dfb76e1d8d9a1456f55af70 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 12:05:02 +0300 Subject: [PATCH 019/196] feat: create webpack environment variables definition --- client/.idea/workspace.xml | 142 ------------------------------------- client/webpack.config.js | 18 +++-- 2 files changed, 13 insertions(+), 147 deletions(-) delete mode 100644 client/.idea/workspace.xml diff --git a/client/.idea/workspace.xml b/client/.idea/workspace.xml deleted file mode 100644 index 88b81cb..0000000 --- a/client/.idea/workspace.xml +++ /dev/null @@ -1,142 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - 1675540728000 - - - 1675540954239 - - - 1675541118737 - - - 1675541696041 - - - 1675545875673 - - - 1675547769856 - - - 1675550093677 - - - 1675550371091 - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/client/webpack.config.js b/client/webpack.config.js index dc2258f..47e24f7 100644 --- a/client/webpack.config.js +++ b/client/webpack.config.js @@ -1,4 +1,5 @@ const path = require('path'); +const webpack = require('webpack'); const HtmlWebpackPlugin = require('html-webpack-plugin'); const MiniCssExtractPlugin = require('mini-css-extract-plugin'); const { CleanWebpackPlugin } = require('clean-webpack-plugin'); @@ -88,7 +89,14 @@ module.exports = async (env, argv) => { new MiniCssExtractPlugin({ filename: resolveFilename(isDevelopment, true, 'css'), }), - new CleanWebpackPlugin() + new CleanWebpackPlugin(), + new webpack.DefinePlugin({ + 'process.env': { + 'API_URL': JSON.stringify( + process.env.API_URL || 'http://localhost:3000' + ), + } + }), ], module: { rules: [ @@ -100,12 +108,12 @@ module.exports = async (env, argv) => { options: { presets: [ "@babel/preset-env", - "@babel/preset-typescript" + "@babel/preset-typescript", ] } } ], - exclude: /node_modules/ + exclude: /node_modules/, }, { test: /\.(css)$/i, @@ -118,14 +126,14 @@ module.exports = async (env, argv) => { { test: /\.(png|jpe?g|gif|svg|ttf|woff|woff2)$/i, dependency: { - not: ['url'] + not: ['url'], }, use: [ { loader: 'url-loader', options: { limit: 8192, - name: '[path][name].[ext]' + name: '[path][name].[ext]', }, }, ], From 014b34cb96f178c0bb37f95aacda22baf14c8b0d Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 12:05:35 +0300 Subject: [PATCH 020/196] feat: create mock API test --- client/src/index.ts | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/client/src/index.ts b/client/src/index.ts index 6625124..722f9e4 100644 --- a/client/src/index.ts +++ b/client/src/index.ts @@ -1 +1,15 @@ import '@styles/main'; + +( + async (): Promise => { + const text = await fetch( + `${process.env.API_URL}`, + { + method: 'GET', + }, + ) + .then((res) => res.text()); + + console.log(text); + } +)(); From 034b15498841ec5e05509323ee91aca2d360ce79 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 12:13:45 +0300 Subject: [PATCH 021/196] feat: update ESLint rules --- server/.eslintrc.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/server/.eslintrc.json b/server/.eslintrc.json index fa62d77..ea321cc 100644 --- a/server/.eslintrc.json +++ b/server/.eslintrc.json @@ -22,9 +22,9 @@ "no-param-reassign": "off", "class-methods-use-this": "warn", "@typescript-eslint/interface-name-prefix": "off", - "@typescript-eslint/explicit-function-return-type": "off", + "@typescript-eslint/explicit-function-return-type": "error", "@typescript-eslint/explicit-module-boundary-types": "off", - "@typescript-eslint/no-explicit-any": "off", + "@typescript-eslint/no-explicit-any": "error", "max-len": [ "error", { From 69c1dedb84b4a685a894fe048d03b0c17095e9d8 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 12:14:47 +0300 Subject: [PATCH 022/196] refactor: apply ESLint rules --- server/src/main.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/server/src/main.ts b/server/src/main.ts index 10ff064..fda7e58 100644 --- a/server/src/main.ts +++ b/server/src/main.ts @@ -1,11 +1,11 @@ import { NestFactory } from '@nestjs/core'; import AppModule from './app.module'; -async function bootstrap() { +async function bootstrap(): Promise { const app = await NestFactory.create(AppModule); await app.listen(process.env.PORT || 3000); } -(async () => { +(async (): Promise => { await bootstrap(); })(); From f441375d99cb11be5055d69b23f88796696e4104 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 12:15:10 +0300 Subject: [PATCH 023/196] feat: enable CORS --- server/src/main.ts | 1 + 1 file changed, 1 insertion(+) diff --git a/server/src/main.ts b/server/src/main.ts index fda7e58..2705ff8 100644 --- a/server/src/main.ts +++ b/server/src/main.ts @@ -3,6 +3,7 @@ import AppModule from './app.module'; async function bootstrap(): Promise { const app = await NestFactory.create(AppModule); + app.enableCors(); await app.listen(process.env.PORT || 3000); } From d54d8d213900e6d0c9df7fad9855e3841706401a Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 12:43:24 +0300 Subject: [PATCH 024/196] docs: add action badges --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 9f5f96d..08e24bc 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,7 @@ # RS Clone [![LICENSE](https://img.shields.io/badge/License-MIT-yellow.svg?style=flat-square)](https://opensource.org/licenses/MIT) +[![Linters checks](https://github.com/HardManDev/rs-clone/actions/workflows/linterChecks.yml/badge.svg?branch=develop&event=workflow_run&style=flat-square)](https://github.com/HardManDev/rs-clone/actions/workflows/linterChecks.yml) +[![Netlify Status](https://api.netlify.com/api/v1/badges/94ea65cd-5857-4022-a8f4-923b64062608/deploy-status?style=flat-square)](https://app.netlify.com/sites/hardmandev-rs-clone/deploys) [RSSchool](https://rs.school/) final [task](https://github.com/rolling-scopes-school/tasks/blob/master/tasks/rsclone/rsclone.md). From 49a5f83421a3c2097ee7297361c6715c04f98cfe Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 12:58:01 +0300 Subject: [PATCH 025/196] docs: create build and start information --- README.md | 36 +++++++++++++++++++++++++++++++++++- 1 file changed, 35 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 08e24bc..55ddd95 100644 --- a/README.md +++ b/README.md @@ -6,7 +6,41 @@ [RSSchool](https://rs.school/) final [task](https://github.com/rolling-scopes-school/tasks/blob/master/tasks/rsclone/rsclone.md). -> *Read more at here after release...* +## Documentation +[![Run in Postman](https://run.pstmn.io/button.svg)](https://god.gw.postman.com/run-collection/19172739-501a8909-9425-4213-b8ea-ccc0d8cd0817?action=collection%2Ffork&collection-url=entityId%3D19172739-501a8909-9425-4213-b8ea-ccc0d8cd0817%26entityType%3Dcollection%26workspaceId%3D82b9cb23-0a2f-430a-b89d-751ccaa7f4bc) +> API Documentation in postman \ +> NOTE: For test fork this postman collection + +## Build +#### Build a server: +```bash +cd ./server +npm install +npm run build +``` +> NOTE: Build result folder: ./server/dist +#### Build a client: +```bash +cd ./client +npm install +npm run build +``` +> NOTE: Build result folder: ./client/dist + +## Start +#### Start a server: +```bash +cd ./server +npm run start:dev +``` +> NOTE: Default URL: http://localhost:3000 +#### Start a client: +```bash +cd ./client +npm run start:dev +``` +> NOTE: Default URL: http://localhost:8080 + ## License This software is licensed under the From f3a73323032bd109d99c3c81a7b32aca1d5b5f37 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Feb 2023 13:09:30 +0300 Subject: [PATCH 026/196] fix: lint on PR badges --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 55ddd95..f6a1026 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # RS Clone [![LICENSE](https://img.shields.io/badge/License-MIT-yellow.svg?style=flat-square)](https://opensource.org/licenses/MIT) -[![Linters checks](https://github.com/HardManDev/rs-clone/actions/workflows/linterChecks.yml/badge.svg?branch=develop&event=workflow_run&style=flat-square)](https://github.com/HardManDev/rs-clone/actions/workflows/linterChecks.yml) +[![Linters checks](https://github.com/HardManDev/rs-clone/actions/workflows/linterChecks.yml/badge.svg)](https://github.com/HardManDev/rs-clone/actions/workflows/linterChecks.yml) [![Netlify Status](https://api.netlify.com/api/v1/badges/94ea65cd-5857-4022-a8f4-923b64062608/deploy-status?style=flat-square)](https://app.netlify.com/sites/hardmandev-rs-clone/deploys) [RSSchool](https://rs.school/) final From 3b8b5ba1d5fa25f59ce3b6cb52b1f96e91e7e910 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sun, 5 Feb 2023 16:25:58 +0300 Subject: [PATCH 027/196] feat: create level area, player move --- client/src/index.html | 28 +- client/src/index.ts | 33 +- client/src/scripts/components/dave.ts | 85 +++++ client/src/scripts/components/game.ts | 159 ++++++++ client/src/scripts/components/zombie.ts | 52 +++ client/src/scripts/controllers/controller.ts | 373 +++++++++++++++++++ client/src/types/types.ts | 6 + 7 files changed, 710 insertions(+), 26 deletions(-) create mode 100644 client/src/scripts/components/dave.ts create mode 100644 client/src/scripts/components/game.ts create mode 100644 client/src/scripts/components/zombie.ts create mode 100644 client/src/scripts/controllers/controller.ts create mode 100644 client/src/types/types.ts diff --git a/client/src/index.html b/client/src/index.html index 53c4655..d65fe9b 100644 --- a/client/src/index.html +++ b/client/src/index.html @@ -1,11 +1,17 @@ - - - - - - - RS Clone - - - - + + + + + + + RS Clone + + +
+
+
+
+
+
+ + diff --git a/client/src/index.ts b/client/src/index.ts index 722f9e4..bac7271 100644 --- a/client/src/index.ts +++ b/client/src/index.ts @@ -1,15 +1,18 @@ -import '@styles/main'; - -( - async (): Promise => { - const text = await fetch( - `${process.env.API_URL}`, - { - method: 'GET', - }, - ) - .then((res) => res.text()); - - console.log(text); - } -)(); +import '@styles/main'; +import Controller from './scripts/controllers/controller'; + +new Controller(); + +( + async (): Promise => { + const text = await fetch( + `${process.env.API_URL}`, + { + method: 'GET', + }, + ) + .then((res) => res.text()); + + console.log(text); + } +)(); diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts new file mode 100644 index 0000000..4a942b1 --- /dev/null +++ b/client/src/scripts/components/dave.ts @@ -0,0 +1,85 @@ +class Player { + x = 0; + + y = 0; + + w = 60; + + h = 96; + + lookingLeft = false; + + lookingRight = false; + + movingLeft = false; + + movingRight = false; + + falling = false; + + movingUp = false; + + movingDown = false; + + stopped = false; + + jumping = false; + + lookingDown = false; + + lookingUp = false; + + startJumpingDown = false; + + sprite: HTMLElement = document.createElement('div'); + + velicity = 0; + + jumpStartVelocity = 10; + + constructor() { + this.sprite.classList.add('player'); + this.sprite.style.width = `${this.w}px`; + this.sprite.style.height = `${this.h}px`; + } + + setView(): void { + if (this.falling) { + if (this.lookingLeft) { + this.sprite.innerHTML = ''; + } else if (this.lookingRight) { + this.sprite.innerHTML = ''; + } + } else if (this.jumping) { + if (this.lookingLeft) { + this.sprite.innerHTML = ''; + } else if (this.lookingRight) { + this.sprite.innerHTML = ''; + } + } else if (this.movingLeft || this.lookingLeft) { + this.sprite.innerHTML = ''; + } else if (this.movingRight || this.lookingRight) { + this.sprite.innerHTML = ''; + } + } + + correctPosByDiff(dX: number, dY: number, playgroundW: number, playgroundH: number): void { + this.x += dX; + this.y += dY; + if (this.x < 0) { + this.x = 0; + } + if (this.y < 0) { + this.y = 0; + } + if (this.x > playgroundW - this.w) { + this.x = playgroundW - this.w; + } + if (this.y > playgroundH - this.h) { + this.y = playgroundH - this.h; + } + this.sprite.style.transform = `translate(${this.x}px, ${this.y}px)`; + } +} + +export default Player; diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts new file mode 100644 index 0000000..8452901 --- /dev/null +++ b/client/src/scripts/components/game.ts @@ -0,0 +1,159 @@ +import { Rect } from '../../types/types'; +import Player from './dave'; +import Zombie from './zombie'; + +class GameView { + levelArea: HTMLElement = document.createElement('div'); + + levelAreaX: number = 0; + + levelAreaY: number = 0; + + levelAreaW: number = 2880; + + levelAreaH: number = 1776; + + viewArea: HTMLElement = document.createElement('div'); + + viewAreaW: number = 960; + + viewAreaH: number = 630; + + playerArea: HTMLElement = document.createElement('div'); + + playerAreaW: number = 260; + + playerAreaH: number = 300; + + walls: Rect[] = []; + + platforms: Rect[] = []; + + zombies: Zombie[] = []; + + constructor() { + this.levelArea.classList.add('playground-area'); + this.levelArea.style.width = `${this.levelAreaW}px`; + this.levelArea.style.height = `${this.levelAreaH}px`; + this.viewArea.classList.add('view-area'); + this.viewArea.style.width = `${this.viewAreaW}px`; + this.viewArea.style.height = `${this.viewAreaH}px`; + this.playerArea.classList.add('player-area'); + this.playerArea.style.width = `${this.playerAreaW}px`; + this.playerArea.style.height = `${this.playerAreaH}px`; + this.playerArea.style.left = `${this.viewAreaW / 2 - this.playerAreaW / 2}px`; + this.playerArea.style.top = `${this.viewAreaH / 2 - this.playerAreaH / 2}px`; + + this.viewArea.append(this.levelArea, this.playerArea); + document.querySelectorAll('.opacity_side')[0]?.after(this.viewArea); + } + + loadWalls(): void { + this.walls.push({ + x: 0, y: 600, w: 400, h: 10, + }); + this.walls.push({ + x: 500, y: 200, w: 10, h: 500, + }); + this.walls.push({ + x: 1900, y: 300, w: 10, h: 500, + }); + this.walls.push({ + x: 200, y: 300, w: 1000, h: 10, + }); + this.walls.push({ + x: 400, y: 800, w: 1000, h: 10, + }); + this.walls.push({ + x: 1500, y: 1500, w: 1000, h: 10, + }); + this.walls.push({ + x: 1000, y: 200, w: 10, h: 100, + }); + + this.walls.forEach((item) => { + const elem: HTMLElement = document.createElement('div'); + elem.classList.add('wall'); + elem.style.width = `${item.w}px`; + elem.style.height = `${item.h}px`; + elem.style.left = `${item.x}px`; + elem.style.top = `${item.y}px`; + this.levelArea.append(elem); + }); + } + + loadPlatforms(): void { + this.platforms.push({ + x: 1000, y: 600, w: 200, h: 1, + }); + this.platforms.push({ + x: 1200, y: 550, w: 200, h: 1, + }); + this.platforms.push({ + x: 1400, y: 500, w: 200, h: 1, + }); + this.platforms.push({ + x: 1600, y: 450, w: 200, h: 1, + }); + this.platforms.push({ + x: 1800, y: 400, w: 200, h: 1, + }); + this.platforms.forEach((item) => { + const elem: HTMLElement = document.createElement('div'); + elem.classList.add('wall'); + elem.style.width = `${item.w}px`; + elem.style.height = `${item.h}px`; + elem.style.left = `${item.x}px`; + elem.style.top = `${item.y}px`; + this.levelArea.append(elem); + }); + } + + insertPlayer(player: Player): void { + this.levelArea.append(player.sprite); + } + + loadZombies(): void { + this.zombies.push(new Zombie(800, 100)); + this.zombies.forEach((item) => { + this.levelArea.append(item.sprite); + }); + } + + correctPlaygroundPosition(dave: Rect): void { + const daveViewX = dave.x + this.levelAreaX; + const rAreaX = this.viewAreaW / 2 + this.playerAreaW / 2 - dave.w; + const lAreaX = this.viewAreaW / 2 - this.playerAreaW / 2; + if (daveViewX > rAreaX) { + this.levelAreaX = rAreaX - dave.x; + } + if (daveViewX < lAreaX) { + this.levelAreaX = this.viewAreaW / 2 + - this.playerAreaW / 2 - dave.x; + } + if (this.levelAreaX > 0) this.levelAreaX = 0; + if ( + this.levelAreaX < this.viewAreaW - this.levelAreaW) { + this.levelAreaX = this.viewAreaW - this.levelAreaW; + } + + const daveViewY = dave.y + this.levelAreaY; + const tAreaY = this.viewAreaH / 2 - this.playerAreaH / 2; + const bAreaY = this.viewAreaH / 2 + this.playerAreaH / 2 - dave.h; + if (daveViewY > bAreaY) { + this.levelAreaY = bAreaY - dave.y; + } + if (daveViewY < tAreaY) { + this.levelAreaY = this.viewAreaH / 2 + - this.playerAreaH / 2 - dave.y; + } + if (this.levelAreaY > 0) this.levelAreaY = 0; + if ( + this.levelAreaY < this.viewAreaH - this.levelAreaH) { + this.levelAreaY = this.viewAreaH - this.levelAreaH; + } + this.levelArea.style.transform = `translate(${this.levelAreaX}px, ${this.levelAreaY}px)`; + } +} + +export default GameView; diff --git a/client/src/scripts/components/zombie.ts b/client/src/scripts/components/zombie.ts new file mode 100644 index 0000000..e968b9a --- /dev/null +++ b/client/src/scripts/components/zombie.ts @@ -0,0 +1,52 @@ +class Zombie { + X = 0; + + Y = 0; + + W = 100; + + H = 200; + + movingLeft = false; + + movingRight = true; + + movingUp = false; + + movingDown = false; + + sprite: HTMLElement = document.createElement('div'); + + constructor(x: number, y: number) { + this.sprite.classList.add('zombie'); + this.X = x; + this.Y = y; + this.sprite.style.width = `${this.W}px`; + this.sprite.style.height = `${this.H}px`; + this.setPosition(); + } + + setView(): void { + if (this.movingLeft) { + this.sprite.innerHTML = ''; + } else if (this.movingRight) { + this.sprite.innerHTML = ''; + } + } + + setPosition(): void { + this.sprite.style.transform = `translate(${this.X}px, ${this.Y}px)`; + } + + swapMoving(): void { + if (this.movingRight) { + this.movingRight = false; + this.movingLeft = true; + } else if (this.movingLeft) { + this.movingRight = true; + this.movingLeft = false; + } + } +} + +export default Zombie; diff --git a/client/src/scripts/controllers/controller.ts b/client/src/scripts/controllers/controller.ts new file mode 100644 index 0000000..1618903 --- /dev/null +++ b/client/src/scripts/controllers/controller.ts @@ -0,0 +1,373 @@ +import { Rect } from '../../types/types'; +import Player from '../components/dave'; +import GameView from '../components/game'; + +class Controller { + gameView: GameView; + + dave: Player; + + constructor() { + this.gameView = new GameView(); + this.gameView.loadWalls(); + this.gameView.loadPlatforms(); + this.gameView.loadZombies(); + this.dave = new Player(); + this.gameView.insertPlayer(this.dave); + this.animate(); + this.setListener(); + this.animateZombies(); + } + + getHorizDiffMovingLeftRight(): number { + let dX = 0; + if (this.dave.movingRight) { + dX = 10; + } else if (this.dave.movingLeft) { + dX = -10; + } + if (this.isCrossWithWalls({ + x: this.dave.x + ((dX < 0) ? dX : 0), + y: this.dave.y, + w: this.dave.w + ((dX > 0) ? dX : 0), + h: this.dave.h, + }).length === 0) { + return dX; + } + return 0; + } + + getDiffFalling(): [number, number] { + let dX = 0; + let dY = 0; + dY = this.dave.velicity * 2 + 2; + if (this.dave.movingRight) { + dX = 10; + } else if (this.dave.movingLeft) { + dX = -10; + } + this.dave.velicity += 0.5; + const walls: Rect[] = this.isCrossWithWalls({ + x: this.dave.x + ((dX < 0) ? dX : 0), + y: this.dave.y + ((dY < 0) ? dY : 0), + w: this.dave.w + ((dX > 0) ? dX : 0), + h: this.dave.h + ((dY > 0) ? dY : 0), + }); + const platform: Rect | null = this.isCrossWithPlatforms( + { + x: this.dave.x + ((dX < 0) ? dX : 0), + y: this.dave.y + ((dY < 0) ? dY : 0), + w: this.dave.w + ((dX > 0) ? dX : 0), + h: this.dave.h + ((dY > 0) ? dY : 0), + }, + { + x: this.dave.x, + y: this.dave.w, + w: this.dave.y, + h: this.dave.h, + }, + ); + if (platform) { + walls.push(platform); + } + + if (walls.length !== 0) { + let wallUnder: Rect | null = null; + let wallLeft: Rect | null = null; + let wallRight: Rect | null = null; + for (let i = 0; i < walls.length; i += 1) { + if (this.dave.x < walls[i].x + walls[i].w + && this.dave.x + this.dave.w > walls[i].x + && this.dave.y + this.dave.h <= walls[i].y) { + wallUnder = walls[i]; + } + if (dX > 0 && this.dave.x + dX + this.dave.w >= walls[i].x) { + wallRight = walls[i]; + } + if (dX < 0 && this.dave.x + dX <= walls[i].x + walls[i].w) { + wallLeft = walls[i]; + } + } + if (wallUnder) { + dY = wallUnder.y - this.dave.h - this.dave.y; + this.dave.falling = false; + this.dave.velicity = 0; + if ((wallRight && dX > 0) || (wallLeft && dX < 0)) { + dX = 0; + } + } else { + dX = 0; + } + } + return [dX, dY]; + } + + getDiffJumping(): [number, number] { + let dX = 0; + let dY = 0; + dY = -this.dave.velicity * 2 - 2; + if (this.dave.movingRight) { + dX = 10; + } else if (this.dave.movingLeft) { + dX = -10; + } + + this.dave.velicity -= 0.5; + const walls: Rect[] = this.isCrossWithWalls({ + x: this.dave.x + ((dX < 0) ? dX : 0), + y: this.dave.y + ((dY < 0) ? dY : 0), + w: this.dave.w + ((dX > 0) ? dX : 0), + h: this.dave.h + ((dY > 0) ? dY : 0), + }); + if (walls.length !== 0) { + let wallAbove: Rect | null = null; + let wallLeft: Rect | null = null; + let wallRight: Rect | null = null; + for (let i = 0; i < walls.length; i += 1) { + if (this.dave.x < walls[i].x + walls[i].w + && this.dave.x + this.dave.w > walls[i].x + && this.dave.y >= walls[i].y + walls[i].h) { + wallAbove = walls[i]; + } + if (dX > 0 && this.dave.x + dX + this.dave.w >= walls[i].x) { + wallRight = walls[i]; + } + if (dX < 0 && this.dave.x + dX <= walls[i].x + walls[i].w) { + wallLeft = walls[i]; + } + } + if (wallAbove) { + dY = wallAbove.y + wallAbove.h - this.dave.y; + this.dave.falling = false; + this.dave.velicity = 0; + if ((wallRight && dX > 0) || (wallLeft && dX < 0)) { + dX = 0; + } + } else { + dX = 0; + } + } + if (this.dave.velicity === 0) { + this.dave.falling = true; + this.dave.jumping = false; + } + return [dX, dY]; + } + + getDiffStartJumpingDown(): [number, number] { + let dX = 0; + let dY = 0; + dY = this.dave.velicity * 2 + 2; + if (this.dave.movingRight) { + dX = 10; + } else if (this.dave.movingLeft) { + dX = -10; + } + this.dave.startJumpingDown = false; + this.dave.velicity += 0.5; + const walls: Rect[] = this.isCrossWithWalls({ + x: this.dave.x + ((dX < 0) ? dX : 0), + y: this.dave.y + ((dY < 0) ? dY : 0), + w: this.dave.w + ((dX > 0) ? dX : 0), + h: this.dave.h + ((dY > 0) ? dY : 0), + }); + if (walls.length === 0) { + this.dave.falling = true; + } + return [dX, dY]; + } + + animate(): void { + const tick = () => { + if (!this.dave.stopped) { + let dX = 0; + let dY = 0; + if (!this.dave.falling && !this.dave.jumping && !this.dave.startJumpingDown) { + if (this.isDaveHasToFall()) { + this.dave.falling = true; + } else { + dX = this.getHorizDiffMovingLeftRight(); + } + } else if (this.dave.falling) { + [dX, dY] = this.getDiffFalling(); + } else if (this.dave.jumping) { + [dX, dY] = this.getDiffJumping(); + } else if (this.dave.startJumpingDown) { + [dX, dY] = this.getDiffStartJumpingDown(); + } + + this.dave.correctPosByDiff(dX, dY, this.gameView.levelAreaW, this.gameView.levelAreaH); + this.gameView.correctPlaygroundPosition({ + x: this.dave.x, + y: this.dave.y, + w: this.dave.w, + h: this.dave.h, + }); + } else if (this.isDaveHasToFall()) { + this.dave.stopped = false; + this.dave.falling = true; + } + this.dave.setView(); + requestAnimationFrame(tick); + }; + tick(); + } + + isCrossWithWalls(rectCommon: Rect): Rect[] { + const crossWalls: Rect[] = []; + for (let i = 0; i < this.gameView.walls.length; i += 1) { + if ( + rectCommon.x < this.gameView.walls[i].x + this.gameView.walls[i].w + && rectCommon.x + rectCommon.w > this.gameView.walls[i].x + && rectCommon.y < this.gameView.walls[i].y + this.gameView.walls[i].h + && rectCommon.h + rectCommon.y > this.gameView.walls[i].y + ) { + crossWalls.push(this.gameView.walls[i]); + } + } + return crossWalls; + } + + isCrossWithPlatforms(rectCommon: Rect, rectStart: Rect): Rect | null { + for (let i = 0; i < this.gameView.platforms.length; i += 1) { + if ( + rectCommon.x < this.gameView.platforms[i].x + this.gameView.platforms[i].w + && rectCommon.x + rectCommon.w > this.gameView.platforms[i].x + && rectCommon.y < this.gameView.platforms[i].y + this.gameView.platforms[i].h + && rectCommon.h + rectCommon.y > this.gameView.platforms[i].y + && rectStart.x < this.gameView.platforms[i].x + this.gameView.platforms[i].w + && rectStart.x + rectStart.w > this.gameView.platforms[i].x + && rectStart.y + rectStart.h <= this.gameView.platforms[i].y + ) { + return this.gameView.platforms[i]; + } + } + return null; + } + + isDaveHasToFall(): boolean { + const underWalls: Rect[] = this.isCrossWithWalls( + { + x: this.dave.x, + y: this.dave.y + this.dave.h, + w: this.dave.w, + h: 1, + }, + ); + const underPlatforms: Rect | null = this.isCrossWithPlatforms( + { + x: this.dave.x, + y: this.dave.y + this.dave.h, + w: this.dave.w, + h: 1, + }, + { + x: this.dave.x, + y: this.dave.y, + w: this.dave.w, + h: this.dave.h, + }, + ); + if (underWalls.length === 0 && underPlatforms === null) { + return true; + } + return false; + } + + setListener(): void { + window.addEventListener('keydown', (e: KeyboardEvent) => { + this.dave.stopped = false; + switch (e.code) { + case 'ArrowLeft': + this.dave.movingRight = false; + this.dave.movingLeft = true; + this.dave.lookingRight = false; + this.dave.lookingLeft = true; + break; + case 'ArrowRight': + this.dave.movingRight = true; + this.dave.movingLeft = false; + this.dave.lookingRight = true; + this.dave.lookingLeft = false; + break; + case 'ArrowUp': + if (!this.dave.falling && !this.dave.jumping) { + this.dave.lookingDown = false; + this.dave.lookingUp = true; + } + break; + case 'ArrowDown': + if (!this.dave.falling && !this.dave.jumping) { + this.dave.lookingDown = true; + this.dave.lookingUp = false; + } + break; + case 'Space': + if (!this.dave.falling && !this.dave.jumping) { + if (this.dave.lookingDown) { + this.dave.startJumpingDown = true; + } else { + this.dave.jumping = true; + } + this.dave.velicity = this.dave.jumpStartVelocity; + } + break; + default: + this.dave.setView(); + break; + } + }); + window.addEventListener('keyup', (e: KeyboardEvent) => { + if (!this.dave.falling && !this.dave.jumping) { + // this.dave.stopped = true; + } + if (e.code === 'ArrowRight') { + this.dave.movingRight = false; + } + if (e.code === 'ArrowLeft') { + this.dave.movingLeft = false; + } + if (e.code === 'ArrowUp') { + this.dave.movingUp = false; + if (!this.dave.falling && !this.dave.jumping) { + this.dave.lookingUp = false; + } + } + if (e.code === 'ArrowDown') { + this.dave.movingDown = false; + if (!this.dave.falling && !this.dave.jumping) { + this.dave.lookingDown = false; + } + } + this.dave.setView(); + }); + } + + animateZombies(): void { + for (let i = 0; i < this.gameView.zombies.length; i += 1) { + const item = this.gameView.zombies[i]; + setInterval(() => { + console.log(1); + let dX = 0; + if (item.movingRight) { + dX = 10; + } else if (item.movingLeft) { + dX = -10; + } + if (this.isCrossWithWalls({ + x: item.X + ((dX < 0) ? dX : 0), + y: item.Y, + w: item.W + ((dX > 0) ? dX : 0), + h: item.H, + }).length === 0) { + item.X += dX; + } else { + item.swapMoving(); + } + item.setPosition(); + }, 500); + } + } +} + +export default Controller; diff --git a/client/src/types/types.ts b/client/src/types/types.ts new file mode 100644 index 0000000..d074d9f --- /dev/null +++ b/client/src/types/types.ts @@ -0,0 +1,6 @@ +export type Rect = { + x: number; + y: number; + w: number; + h: number; +}; From 257ad928fd42a87f391f6f8093a6741351568997 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sun, 5 Feb 2023 16:33:15 +0300 Subject: [PATCH 028/196] fix: add lost styles --- client/src/styles/main.scss | 74 ++++++++++++++++++++++++++++++++++--- 1 file changed, 69 insertions(+), 5 deletions(-) diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index cca57b3..cefde1d 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -1,5 +1,69 @@ -* { - margin: 0; - padding: 0; - box-sizing: border-box; -} +* { + margin: 0; + padding: 0; + box-sizing: border-box; +} + +body { + overflow: hidden; + height: 100vw; +} + +#container { + display: flex; + justify-content: center; +} + +.view-area { + position: relative; + background-color: white; + opacity: 1; +} + +.player-area { + position: absolute; + border: 1px dashed green; +} + +.playground-area { + position: absolute; +} + +.player { + position: absolute; + top: 0px; + left: 0px; + background-color: brown; +} + +.wall { + position: absolute; + background-color: black; +} + +.opacity { + background: rgba(200, 200, 150, 0.95); + z-index: 10; + position: relative; +} + +.opacity_side { + flex-grow: 1; +} + +.opacity_top { + width: 100%; + height: 100px; +} + +.opacity_bottom { + width: 100%; + height: 100%; +} + +.zombie { + position: absolute; + top: 0px; + left: 0px; + background-color:burlywood; +} \ No newline at end of file From 792214a59cbf18d1eb9bdc8c279d779763fc80ab Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sun, 5 Feb 2023 17:22:34 +0300 Subject: [PATCH 029/196] fix: CRLF in index.ts --- client/src/index.ts | 36 ++++++++++++++++++------------------ 1 file changed, 18 insertions(+), 18 deletions(-) diff --git a/client/src/index.ts b/client/src/index.ts index bac7271..5d9943f 100644 --- a/client/src/index.ts +++ b/client/src/index.ts @@ -1,18 +1,18 @@ -import '@styles/main'; -import Controller from './scripts/controllers/controller'; - -new Controller(); - -( - async (): Promise => { - const text = await fetch( - `${process.env.API_URL}`, - { - method: 'GET', - }, - ) - .then((res) => res.text()); - - console.log(text); - } -)(); +import '@styles/main'; +import Controller from './scripts/controllers/controller'; + +new Controller(); + +( + async (): Promise => { + const text = await fetch( + `${process.env.API_URL}`, + { + method: 'GET', + }, + ) + .then((res) => res.text()); + + console.log(text); + } +)(); From ae5caa5c2ec3f7be389b6f96e58662674a719069 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sun, 5 Feb 2023 17:46:21 +0300 Subject: [PATCH 030/196] fix: eslint errors --- client/src/index.ts | 2 +- client/src/scripts/components/dave.ts | 17 ++++--- client/src/scripts/components/game.ts | 16 +++---- client/src/scripts/controllers/controller.ts | 48 ++++++++++++-------- 4 files changed, 49 insertions(+), 34 deletions(-) diff --git a/client/src/index.ts b/client/src/index.ts index 5d9943f..4f8c0dd 100644 --- a/client/src/index.ts +++ b/client/src/index.ts @@ -1,7 +1,7 @@ import '@styles/main'; import Controller from './scripts/controllers/controller'; -new Controller(); +const controller = new Controller(); ( async (): Promise => { diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index 4a942b1..97f6482 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -33,7 +33,7 @@ class Player { sprite: HTMLElement = document.createElement('div'); - velicity = 0; + velocity = 0; jumpStartVelocity = 10; @@ -63,7 +63,12 @@ class Player { } } - correctPosByDiff(dX: number, dY: number, playgroundW: number, playgroundH: number): void { + correctPosByDiff( + dX: number, + dY: number, + levelW: number, + levelH: number, + ): void { this.x += dX; this.y += dY; if (this.x < 0) { @@ -72,11 +77,11 @@ class Player { if (this.y < 0) { this.y = 0; } - if (this.x > playgroundW - this.w) { - this.x = playgroundW - this.w; + if (this.x > levelW - this.w) { + this.x = levelW - this.w; } - if (this.y > playgroundH - this.h) { - this.y = playgroundH - this.h; + if (this.y > levelH - this.h) { + this.y = levelH - this.h; } this.sprite.style.transform = `translate(${this.x}px, ${this.y}px)`; } diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 8452901..f05f5ad 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -5,25 +5,25 @@ import Zombie from './zombie'; class GameView { levelArea: HTMLElement = document.createElement('div'); - levelAreaX: number = 0; + levelAreaX = 0; - levelAreaY: number = 0; + levelAreaY = 0; - levelAreaW: number = 2880; + levelAreaW = 2880; - levelAreaH: number = 1776; + levelAreaH = 1776; viewArea: HTMLElement = document.createElement('div'); - viewAreaW: number = 960; + viewAreaW = 960; - viewAreaH: number = 630; + viewAreaH = 630; playerArea: HTMLElement = document.createElement('div'); - playerAreaW: number = 260; + playerAreaW = 260; - playerAreaH: number = 300; + playerAreaH = 300; walls: Rect[] = []; diff --git a/client/src/scripts/controllers/controller.ts b/client/src/scripts/controllers/controller.ts index 1618903..490a126 100644 --- a/client/src/scripts/controllers/controller.ts +++ b/client/src/scripts/controllers/controller.ts @@ -19,7 +19,7 @@ class Controller { this.animateZombies(); } - getHorizDiffMovingLeftRight(): number { + getHorizontalDiffMovingLeftRight(): number { let dX = 0; if (this.dave.movingRight) { dX = 10; @@ -40,13 +40,13 @@ class Controller { getDiffFalling(): [number, number] { let dX = 0; let dY = 0; - dY = this.dave.velicity * 2 + 2; + dY = this.dave.velocity * 2 + 2; if (this.dave.movingRight) { dX = 10; } else if (this.dave.movingLeft) { dX = -10; } - this.dave.velicity += 0.5; + this.dave.velocity += 0.5; const walls: Rect[] = this.isCrossWithWalls({ x: this.dave.x + ((dX < 0) ? dX : 0), y: this.dave.y + ((dY < 0) ? dY : 0), @@ -91,7 +91,7 @@ class Controller { if (wallUnder) { dY = wallUnder.y - this.dave.h - this.dave.y; this.dave.falling = false; - this.dave.velicity = 0; + this.dave.velocity = 0; if ((wallRight && dX > 0) || (wallLeft && dX < 0)) { dX = 0; } @@ -105,14 +105,14 @@ class Controller { getDiffJumping(): [number, number] { let dX = 0; let dY = 0; - dY = -this.dave.velicity * 2 - 2; + dY = -this.dave.velocity * 2 - 2; if (this.dave.movingRight) { dX = 10; } else if (this.dave.movingLeft) { dX = -10; } - this.dave.velicity -= 0.5; + this.dave.velocity -= 0.5; const walls: Rect[] = this.isCrossWithWalls({ x: this.dave.x + ((dX < 0) ? dX : 0), y: this.dave.y + ((dY < 0) ? dY : 0), @@ -139,7 +139,7 @@ class Controller { if (wallAbove) { dY = wallAbove.y + wallAbove.h - this.dave.y; this.dave.falling = false; - this.dave.velicity = 0; + this.dave.velocity = 0; if ((wallRight && dX > 0) || (wallLeft && dX < 0)) { dX = 0; } @@ -147,7 +147,7 @@ class Controller { dX = 0; } } - if (this.dave.velicity === 0) { + if (this.dave.velocity === 0) { this.dave.falling = true; this.dave.jumping = false; } @@ -157,14 +157,14 @@ class Controller { getDiffStartJumpingDown(): [number, number] { let dX = 0; let dY = 0; - dY = this.dave.velicity * 2 + 2; + dY = this.dave.velocity * 2 + 2; if (this.dave.movingRight) { dX = 10; } else if (this.dave.movingLeft) { dX = -10; } this.dave.startJumpingDown = false; - this.dave.velicity += 0.5; + this.dave.velocity += 0.5; const walls: Rect[] = this.isCrossWithWalls({ x: this.dave.x + ((dX < 0) ? dX : 0), y: this.dave.y + ((dY < 0) ? dY : 0), @@ -178,15 +178,18 @@ class Controller { } animate(): void { - const tick = () => { + const tick = (): void => { if (!this.dave.stopped) { let dX = 0; let dY = 0; - if (!this.dave.falling && !this.dave.jumping && !this.dave.startJumpingDown) { + if ( + !this.dave.falling + && !this.dave.jumping + && !this.dave.startJumpingDown) { if (this.isDaveHasToFall()) { this.dave.falling = true; } else { - dX = this.getHorizDiffMovingLeftRight(); + dX = this.getHorizontalDiffMovingLeftRight(); } } else if (this.dave.falling) { [dX, dY] = this.getDiffFalling(); @@ -196,7 +199,12 @@ class Controller { [dX, dY] = this.getDiffStartJumpingDown(); } - this.dave.correctPosByDiff(dX, dY, this.gameView.levelAreaW, this.gameView.levelAreaH); + this.dave.correctPosByDiff( + dX, + dY, + this.gameView.levelAreaW, + this.gameView.levelAreaH, + ); this.gameView.correctPlaygroundPosition({ x: this.dave.x, y: this.dave.y, @@ -231,11 +239,14 @@ class Controller { isCrossWithPlatforms(rectCommon: Rect, rectStart: Rect): Rect | null { for (let i = 0; i < this.gameView.platforms.length; i += 1) { if ( - rectCommon.x < this.gameView.platforms[i].x + this.gameView.platforms[i].w + rectCommon.x < this.gameView.platforms[i].x + + this.gameView.platforms[i].w && rectCommon.x + rectCommon.w > this.gameView.platforms[i].x - && rectCommon.y < this.gameView.platforms[i].y + this.gameView.platforms[i].h + && rectCommon.y < this.gameView.platforms[i].y + + this.gameView.platforms[i].h && rectCommon.h + rectCommon.y > this.gameView.platforms[i].y - && rectStart.x < this.gameView.platforms[i].x + this.gameView.platforms[i].w + && rectStart.x < this.gameView.platforms[i].x + + this.gameView.platforms[i].w && rectStart.x + rectStart.w > this.gameView.platforms[i].x && rectStart.y + rectStart.h <= this.gameView.platforms[i].y ) { @@ -309,7 +320,7 @@ class Controller { } else { this.dave.jumping = true; } - this.dave.velicity = this.dave.jumpStartVelocity; + this.dave.velocity = this.dave.jumpStartVelocity; } break; default: @@ -347,7 +358,6 @@ class Controller { for (let i = 0; i < this.gameView.zombies.length; i += 1) { const item = this.gameView.zombies[i]; setInterval(() => { - console.log(1); let dX = 0; if (item.movingRight) { dX = 10; From 6c8e971caac16c5cd45dc147232c3cb2471f6a02 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sun, 5 Feb 2023 18:00:10 +0300 Subject: [PATCH 031/196] fix: stylelint main.css errors --- client/src/styles/main.scss | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index cefde1d..5976884 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -31,8 +31,8 @@ body { .player { position: absolute; - top: 0px; - left: 0px; + top: 0; + left: 0; background-color: brown; } @@ -42,7 +42,7 @@ body { } .opacity { - background: rgba(200, 200, 150, 0.95); + background: rgb(200 200 150 / 95%); z-index: 10; position: relative; } @@ -63,7 +63,7 @@ body { .zombie { position: absolute; - top: 0px; - left: 0px; - background-color:burlywood; -} \ No newline at end of file + top: 0; + left: 0; + background-color: burlywood; +} From 275fa9b21ed6678ec9c307d53e74484c44caeebd Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Mon, 6 Feb 2023 00:24:24 +0300 Subject: [PATCH 032/196] feat: add level1 structure --- client/src/assets/levels/LEVEL01_high_res.png | Bin 0 -> 44597 bytes client/src/assets/levels/level1.ts | 36 ++++++ client/src/scripts/components/dave.ts | 6 +- client/src/scripts/components/game.ts | 114 +++++++++++------- client/src/scripts/components/zombie.ts | 14 ++- client/src/scripts/controllers/controller.ts | 51 ++++---- client/src/styles/main.scss | 12 +- client/src/types/types.ts | 11 ++ 8 files changed, 167 insertions(+), 77 deletions(-) create mode 100644 client/src/assets/levels/LEVEL01_high_res.png create mode 100644 client/src/assets/levels/level1.ts diff --git a/client/src/assets/levels/LEVEL01_high_res.png b/client/src/assets/levels/LEVEL01_high_res.png new file mode 100644 index 0000000000000000000000000000000000000000..ab728cf0049bdd4e174d24028ebf913d12e5140e GIT binary patch literal 44597 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 { + this.zombies.push(new Zombie(zombie)); }); - this.walls.push({ - x: 400, y: 800, w: 1000, h: 10, - }); - this.walls.push({ - x: 1500, y: 1500, w: 1000, h: 10, + this.showZombies(); + this.levelArea.classList.add('level1'); + } + + loadBorders(entityType: LevelEntity): Rect[] { + const entities: Rect[] = []; + LEVEL1.split('\n').forEach((line, indx) => { + const arrLine: string[] = line.split(' '); + let bricksCount = 0; + let brickPos = -1; + for (let i = 0; i < arrLine.length; i += 1) { + if (arrLine[i] === entityType) { + if (bricksCount === 0) { + brickPos = i; + } + bricksCount += 1; + if (i === arrLine.length - 1) { + entities.push({ + x: brickPos * this.tileSize, + y: indx * this.tileSize, + w: bricksCount * this.tileSize, + h: entityType === LevelEntity.WALL ? this.tileSize : 1, + }); + bricksCount = 0; + brickPos = -1; + } + } else if (brickPos !== -1) { + entities.push({ + x: brickPos * this.tileSize, + y: indx * this.tileSize, + w: bricksCount * this.tileSize, + h: entityType === LevelEntity.WALL ? this.tileSize : 1, + }); + bricksCount = 0; + brickPos = -1; + } + } }); - this.walls.push({ - x: 1000, y: 200, w: 10, h: 100, + return entities; + } + + loadMonsters(entityType: LevelEntity): LeftFeet[] { + const monsters: LeftFeet[] = []; + LEVEL1.split('\n').forEach((line, indx) => { + const arrLine = line.split(' '); + for (let i = 0; i < arrLine.length; i += 1) { + if (arrLine[i] === entityType) { + monsters.push({ + x: i * this.tileSize, + y: (indx + 1) * this.tileSize, + }); + } + } }); + return monsters; + } + showWalls(): void { this.walls.forEach((item) => { const elem: HTMLElement = document.createElement('div'); elem.classList.add('wall'); @@ -82,22 +128,7 @@ class GameView { }); } - loadPlatforms(): void { - this.platforms.push({ - x: 1000, y: 600, w: 200, h: 1, - }); - this.platforms.push({ - x: 1200, y: 550, w: 200, h: 1, - }); - this.platforms.push({ - x: 1400, y: 500, w: 200, h: 1, - }); - this.platforms.push({ - x: 1600, y: 450, w: 200, h: 1, - }); - this.platforms.push({ - x: 1800, y: 400, w: 200, h: 1, - }); + showPlatforms(): void { this.platforms.forEach((item) => { const elem: HTMLElement = document.createElement('div'); elem.classList.add('wall'); @@ -113,14 +144,13 @@ class GameView { this.levelArea.append(player.sprite); } - loadZombies(): void { - this.zombies.push(new Zombie(800, 100)); + showZombies(): void { this.zombies.forEach((item) => { this.levelArea.append(item.sprite); }); } - correctPlaygroundPosition(dave: Rect): void { + correctLevelPosition(dave: Rect): void { const daveViewX = dave.x + this.levelAreaX; const rAreaX = this.viewAreaW / 2 + this.playerAreaW / 2 - dave.w; const lAreaX = this.viewAreaW / 2 - this.playerAreaW / 2; diff --git a/client/src/scripts/components/zombie.ts b/client/src/scripts/components/zombie.ts index e968b9a..74a8065 100644 --- a/client/src/scripts/components/zombie.ts +++ b/client/src/scripts/components/zombie.ts @@ -1,11 +1,13 @@ +import { LeftFeet } from '../../types/types'; + class Zombie { X = 0; Y = 0; - W = 100; + W = 64; - H = 200; + H = 120; movingLeft = false; @@ -15,12 +17,14 @@ class Zombie { movingDown = false; + stepSize = 16; + sprite: HTMLElement = document.createElement('div'); - constructor(x: number, y: number) { + constructor(leftFeet: LeftFeet) { this.sprite.classList.add('zombie'); - this.X = x; - this.Y = y; + this.X = leftFeet.x; + this.Y = leftFeet.y - this.H; this.sprite.style.width = `${this.W}px`; this.sprite.style.height = `${this.H}px`; this.setPosition(); diff --git a/client/src/scripts/controllers/controller.ts b/client/src/scripts/controllers/controller.ts index 490a126..ddf4a72 100644 --- a/client/src/scripts/controllers/controller.ts +++ b/client/src/scripts/controllers/controller.ts @@ -9,9 +9,8 @@ class Controller { constructor() { this.gameView = new GameView(); - this.gameView.loadWalls(); - this.gameView.loadPlatforms(); - this.gameView.loadZombies(); + this.gameView.loadLevelEntities(); + // this.gameView.loadZombies(); this.dave = new Player(); this.gameView.insertPlayer(this.dave); this.animate(); @@ -22,9 +21,9 @@ class Controller { getHorizontalDiffMovingLeftRight(): number { let dX = 0; if (this.dave.movingRight) { - dX = 10; + dX = this.dave.stepSize; } else if (this.dave.movingLeft) { - dX = -10; + dX = -this.dave.stepSize; } if (this.isCrossWithWalls({ x: this.dave.x + ((dX < 0) ? dX : 0), @@ -42,9 +41,9 @@ class Controller { let dY = 0; dY = this.dave.velocity * 2 + 2; if (this.dave.movingRight) { - dX = 10; + dX = this.dave.stepSize; } else if (this.dave.movingLeft) { - dX = -10; + dX = -this.dave.stepSize; } this.dave.velocity += 0.5; const walls: Rect[] = this.isCrossWithWalls({ @@ -53,7 +52,7 @@ class Controller { w: this.dave.w + ((dX > 0) ? dX : 0), h: this.dave.h + ((dY > 0) ? dY : 0), }); - const platform: Rect | null = this.isCrossWithPlatforms( + const platforms: Rect[] = this.isCrossWithPlatforms( { x: this.dave.x + ((dX < 0) ? dX : 0), y: this.dave.y + ((dY < 0) ? dY : 0), @@ -67,8 +66,8 @@ class Controller { h: this.dave.h, }, ); - if (platform) { - walls.push(platform); + if (platforms.length) { + walls.push(...platforms); } if (walls.length !== 0) { @@ -107,9 +106,9 @@ class Controller { let dY = 0; dY = -this.dave.velocity * 2 - 2; if (this.dave.movingRight) { - dX = 10; + dX = this.dave.stepSize; } else if (this.dave.movingLeft) { - dX = -10; + dX = -this.dave.stepSize; } this.dave.velocity -= 0.5; @@ -156,12 +155,11 @@ class Controller { getDiffStartJumpingDown(): [number, number] { let dX = 0; - let dY = 0; - dY = this.dave.velocity * 2 + 2; + let dY = this.dave.velocity * 2 + 2; if (this.dave.movingRight) { - dX = 10; + dX = this.dave.stepSize; } else if (this.dave.movingLeft) { - dX = -10; + dX = -this.dave.stepSize; } this.dave.startJumpingDown = false; this.dave.velocity += 0.5; @@ -173,6 +171,8 @@ class Controller { }); if (walls.length === 0) { this.dave.falling = true; + } else { + dY = 0; } return [dX, dY]; } @@ -205,7 +205,7 @@ class Controller { this.gameView.levelAreaW, this.gameView.levelAreaH, ); - this.gameView.correctPlaygroundPosition({ + this.gameView.correctLevelPosition({ x: this.dave.x, y: this.dave.y, w: this.dave.w, @@ -236,7 +236,8 @@ class Controller { return crossWalls; } - isCrossWithPlatforms(rectCommon: Rect, rectStart: Rect): Rect | null { + isCrossWithPlatforms(rectCommon: Rect, rectStart: Rect): Rect[] { + const crossPlatforms: Rect[] = []; for (let i = 0; i < this.gameView.platforms.length; i += 1) { if ( rectCommon.x < this.gameView.platforms[i].x @@ -250,10 +251,10 @@ class Controller { && rectStart.x + rectStart.w > this.gameView.platforms[i].x && rectStart.y + rectStart.h <= this.gameView.platforms[i].y ) { - return this.gameView.platforms[i]; + crossPlatforms.push(this.gameView.platforms[i]); } } - return null; + return crossPlatforms; } isDaveHasToFall(): boolean { @@ -265,7 +266,7 @@ class Controller { h: 1, }, ); - const underPlatforms: Rect | null = this.isCrossWithPlatforms( + const underPlatforms: Rect[] = this.isCrossWithPlatforms( { x: this.dave.x, y: this.dave.y + this.dave.h, @@ -279,7 +280,7 @@ class Controller { h: this.dave.h, }, ); - if (underWalls.length === 0 && underPlatforms === null) { + if (underWalls.length === 0 && underPlatforms.length === 0) { return true; } return false; @@ -360,9 +361,9 @@ class Controller { setInterval(() => { let dX = 0; if (item.movingRight) { - dX = 10; + dX = item.stepSize; } else if (item.movingLeft) { - dX = -10; + dX = -item.stepSize; } if (this.isCrossWithWalls({ x: item.X + ((dX < 0) ? dX : 0), @@ -375,7 +376,7 @@ class Controller { item.swapMoving(); } item.setPosition(); - }, 500); + }, 300); } } } diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index 5976884..0252e78 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -22,13 +22,18 @@ body { .player-area { position: absolute; - border: 1px dashed green; + + /* border: 1px dashed green; */ } -.playground-area { +.level-area { position: absolute; } +.level1 { + background: url("./../assets/levels/LEVEL01_high_res.png") no-repeat no-repeat; +} + .player { position: absolute; top: 0; @@ -38,7 +43,8 @@ body { .wall { position: absolute; - background-color: black; + + /* background-color: black; */ } .opacity { diff --git a/client/src/types/types.ts b/client/src/types/types.ts index d074d9f..83a1425 100644 --- a/client/src/types/types.ts +++ b/client/src/types/types.ts @@ -4,3 +4,14 @@ export type Rect = { w: number; h: number; }; + +export type LeftFeet = { + x: number; + y: number; +}; + +export enum LevelEntity { + WALL = '1', + PLATFORM = '2', + ZOMBIE = 'Z', +} From 3f7398361f6bbba2dcaad6b8868c6a2a28dbdecf Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Mon, 6 Feb 2023 14:36:54 +0300 Subject: [PATCH 033/196] refactor: changes after code review --- client/src/index.ts | 5 +- client/src/scripts/components/dave.ts | 2 + client/src/scripts/components/game.ts | 1 + client/src/scripts/components/zombie.ts | 2 + .../{controller.ts => playLevel.ts} | 25 ++++---- client/src/styles/dave.css | 6 ++ client/src/styles/level.css | 50 +++++++++++++++ client/src/styles/main.scss | 64 ------------------- client/src/styles/zombie.css | 6 ++ client/src/types/types.ts | 2 + 10 files changed, 86 insertions(+), 77 deletions(-) rename client/src/scripts/controllers/{controller.ts => playLevel.ts} (96%) create mode 100644 client/src/styles/dave.css create mode 100644 client/src/styles/level.css create mode 100644 client/src/styles/zombie.css diff --git a/client/src/index.ts b/client/src/index.ts index 4f8c0dd..fd7c0a9 100644 --- a/client/src/index.ts +++ b/client/src/index.ts @@ -1,7 +1,8 @@ import '@styles/main'; -import Controller from './scripts/controllers/controller'; +import PlayLevel from './scripts/controllers/playLevel'; -const controller = new Controller(); +const playLevel = new PlayLevel(); +playLevel.startGame(); ( async (): Promise => { diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index 97f6482..102f0a2 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -1,3 +1,5 @@ +import '@styles/dave'; + class Player { x = 0; diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index f05f5ad..22a543a 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -1,3 +1,4 @@ +import '@styles/level'; import { Rect } from '../../types/types'; import Player from './dave'; import Zombie from './zombie'; diff --git a/client/src/scripts/components/zombie.ts b/client/src/scripts/components/zombie.ts index e968b9a..399735b 100644 --- a/client/src/scripts/components/zombie.ts +++ b/client/src/scripts/components/zombie.ts @@ -1,3 +1,5 @@ +import '@styles/zombie'; + class Zombie { X = 0; diff --git a/client/src/scripts/controllers/controller.ts b/client/src/scripts/controllers/playLevel.ts similarity index 96% rename from client/src/scripts/controllers/controller.ts rename to client/src/scripts/controllers/playLevel.ts index 490a126..d297b6e 100644 --- a/client/src/scripts/controllers/controller.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -1,25 +1,28 @@ -import { Rect } from '../../types/types'; +import { Offset, Rect } from '../../types/types'; import Player from '../components/dave'; import GameView from '../components/game'; -class Controller { +class PlayLevel { gameView: GameView; dave: Player; constructor() { this.gameView = new GameView(); + this.dave = new Player(); + } + + startGame(): void { this.gameView.loadWalls(); this.gameView.loadPlatforms(); this.gameView.loadZombies(); - this.dave = new Player(); this.gameView.insertPlayer(this.dave); this.animate(); this.setListener(); this.animateZombies(); } - getHorizontalDiffMovingLeftRight(): number { + getHorizontalDiffMovingLeftRight(): Offset { let dX = 0; if (this.dave.movingRight) { dX = 10; @@ -32,12 +35,12 @@ class Controller { w: this.dave.w + ((dX > 0) ? dX : 0), h: this.dave.h, }).length === 0) { - return dX; + return [dX, 0]; } - return 0; + return [0, 0]; } - getDiffFalling(): [number, number] { + getDiffFalling(): Offset { let dX = 0; let dY = 0; dY = this.dave.velocity * 2 + 2; @@ -102,7 +105,7 @@ class Controller { return [dX, dY]; } - getDiffJumping(): [number, number] { + getDiffJumping(): Offset { let dX = 0; let dY = 0; dY = -this.dave.velocity * 2 - 2; @@ -154,7 +157,7 @@ class Controller { return [dX, dY]; } - getDiffStartJumpingDown(): [number, number] { + getDiffStartJumpingDown(): Offset { let dX = 0; let dY = 0; dY = this.dave.velocity * 2 + 2; @@ -189,7 +192,7 @@ class Controller { if (this.isDaveHasToFall()) { this.dave.falling = true; } else { - dX = this.getHorizontalDiffMovingLeftRight(); + [dX, dY] = this.getHorizontalDiffMovingLeftRight(); } } else if (this.dave.falling) { [dX, dY] = this.getDiffFalling(); @@ -380,4 +383,4 @@ class Controller { } } -export default Controller; +export default PlayLevel; diff --git a/client/src/styles/dave.css b/client/src/styles/dave.css new file mode 100644 index 0000000..21b52f9 --- /dev/null +++ b/client/src/styles/dave.css @@ -0,0 +1,6 @@ +.player { + position: absolute; + top: 0; + left: 0; + background-color: brown; +} \ No newline at end of file diff --git a/client/src/styles/level.css b/client/src/styles/level.css new file mode 100644 index 0000000..7116fd0 --- /dev/null +++ b/client/src/styles/level.css @@ -0,0 +1,50 @@ +body { + overflow: hidden; + height: 100vw; +} + +#container { + display: flex; + justify-content: center; +} + +.view-area { + position: relative; + background-color: white; + opacity: 1; +} + +.player-area { + position: absolute; + border: 1px dashed green; +} + +.playground-area { + position: absolute; +} + +.wall { + position: absolute; + background-color: black; +} + +.opacity { + background: rgb(200 200 150 / 95%); + z-index: 10; + position: relative; +} + +.opacity_side { + flex-grow: 1; +} + +.opacity_top { + width: 100%; + height: 100px; +} + +.opacity_bottom { + width: 100%; + height: 100%; +} + diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index 5976884..5bb33ba 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -3,67 +3,3 @@ padding: 0; box-sizing: border-box; } - -body { - overflow: hidden; - height: 100vw; -} - -#container { - display: flex; - justify-content: center; -} - -.view-area { - position: relative; - background-color: white; - opacity: 1; -} - -.player-area { - position: absolute; - border: 1px dashed green; -} - -.playground-area { - position: absolute; -} - -.player { - position: absolute; - top: 0; - left: 0; - background-color: brown; -} - -.wall { - position: absolute; - background-color: black; -} - -.opacity { - background: rgb(200 200 150 / 95%); - z-index: 10; - position: relative; -} - -.opacity_side { - flex-grow: 1; -} - -.opacity_top { - width: 100%; - height: 100px; -} - -.opacity_bottom { - width: 100%; - height: 100%; -} - -.zombie { - position: absolute; - top: 0; - left: 0; - background-color: burlywood; -} diff --git a/client/src/styles/zombie.css b/client/src/styles/zombie.css new file mode 100644 index 0000000..aa37cc2 --- /dev/null +++ b/client/src/styles/zombie.css @@ -0,0 +1,6 @@ +.zombie { + position: absolute; + top: 0; + left: 0; + background-color: burlywood; +} diff --git a/client/src/types/types.ts b/client/src/types/types.ts index d074d9f..5d363f4 100644 --- a/client/src/types/types.ts +++ b/client/src/types/types.ts @@ -4,3 +4,5 @@ export type Rect = { w: number; h: number; }; + +export type Offset = [number, number]; From c41ff12567376793ce7e619282c5172841f0fbe6 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Mon, 6 Feb 2023 21:41:27 +0300 Subject: [PATCH 034/196] refactor: player state, move, look, shoot enums --- client/src/assets/levels/level1.ts | 2 +- client/src/scripts/components/dave.ts | 57 ++++---- client/src/scripts/components/game.ts | 37 +++--- client/src/scripts/components/zombie.ts | 18 +-- client/src/scripts/controllers/playLevel.ts | 136 +++++++++----------- client/src/types/types.ts | 28 ++++ 6 files changed, 149 insertions(+), 129 deletions(-) diff --git a/client/src/assets/levels/level1.ts b/client/src/assets/levels/level1.ts index 493f09c..ff98442 100644 --- a/client/src/assets/levels/level1.ts +++ b/client/src/assets/levels/level1.ts @@ -30,7 +30,7 @@ export const LEVEL1 = `0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 0 0 0 0 0 0 2 0 1 1 0 0 0 0 0 0 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 0 0 0 0 2 2 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 0 0 0 0 0 0 0 0 2 2 2 2 2 0 0 0 0 1 0 0 0 0 0 0 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 Z 0 0 0 0 0 0 Z 0 0 0 0 0 0 0 0 Z 0 0 0 0 0 0 2 2 2 2 2 2 2 0 0 0 1 -0 0 0 0 0 0 0 0 1 1 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 +0 D 0 0 0 0 0 0 1 1 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0`; export const LEVEL2 = ''; diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index d41a4ba..ce35762 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -1,4 +1,7 @@ import '@styles/dave'; +import { + DaveLook, DaveMove, DaveShoot, DaveState, LeftFeet, +} from '../../types/types'; class Player { x = 0; @@ -9,29 +12,13 @@ class Player { h = 96; - lookingLeft = false; + state: DaveState = DaveState.STANDING; - lookingRight = false; + look: DaveLook = DaveLook.RIGHT; - movingLeft = false; + shoot: DaveShoot = DaveShoot.CENTER; - movingRight = false; - - falling = false; - - movingUp = false; - - movingDown = false; - - stopped = false; - - jumping = false; - - lookingDown = false; - - lookingUp = false; - - startJumpingDown = false; + move: DaveMove = DaveMove.NONE; sprite: HTMLElement = document.createElement('div'); @@ -41,28 +28,36 @@ class Player { jumpStartVelocity = 8; - constructor() { + constructor(leftFeet: LeftFeet) { this.sprite.classList.add('player'); + this.x = leftFeet.x; + this.y = leftFeet.y - this.h; this.sprite.style.width = `${this.w}px`; this.sprite.style.height = `${this.h}px`; + this.setPosition(); } setView(): void { - if (this.falling) { - if (this.lookingLeft) { + console.log(this.state); + if (this.state === DaveState.FALLING) { + if (this.look === DaveLook.LEFT) { this.sprite.innerHTML = ''; - } else if (this.lookingRight) { + } else if (this.look === DaveLook.RIGHT) { this.sprite.innerHTML = ''; } - } else if (this.jumping) { - if (this.lookingLeft) { + } else if (this.state === DaveState.JUMPING_UP) { + if (this.look === DaveLook.LEFT) { this.sprite.innerHTML = ''; - } else if (this.lookingRight) { + } else if (this.look === DaveLook.RIGHT) { this.sprite.innerHTML = ''; } - } else if (this.movingLeft || this.lookingLeft) { + } else if (this.shoot === DaveShoot.UP) { + this.sprite.innerHTML = 'Shooting UP'; + } else if (this.shoot === DaveShoot.DOWN) { + this.sprite.innerHTML = 'Shooting DOWN'; + } else if (this.look === DaveLook.LEFT) { this.sprite.innerHTML = ''; - } else if (this.movingRight || this.lookingRight) { + } else if (this.look === DaveLook.RIGHT) { this.sprite.innerHTML = ''; } } @@ -89,6 +84,10 @@ class Player { } this.sprite.style.transform = `translate(${this.x}px, ${this.y}px)`; } + + setPosition(): void { + this.sprite.style.transform = `translate(${this.x}px, ${this.y}px)`; + } } export default Player; diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 6974109..98a8e36 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -36,6 +36,8 @@ class GameView { zombies: Zombie[] = []; + dave: Player; + constructor() { this.levelArea.classList.add('level-area'); this.levelArea.style.width = `${this.levelAreaW}px`; @@ -58,10 +60,13 @@ class GameView { this.showWalls(); this.platforms = this.loadBorders(LevelEntity.PLATFORM); this.showPlatforms(); - this.loadMonsters(LevelEntity.ZOMBIE).forEach((zombie) => { + this.loadCharacters(LevelEntity.ZOMBIE).forEach((zombie) => { this.zombies.push(new Zombie(zombie)); }); this.showZombies(); + this.dave = new Player(this.loadCharacters(LevelEntity.DAVE)[0]); + this.insertPlayer(); + this.correctLevelPosition(); this.levelArea.classList.add('level1'); } @@ -102,20 +107,20 @@ class GameView { return entities; } - loadMonsters(entityType: LevelEntity): LeftFeet[] { - const monsters: LeftFeet[] = []; + loadCharacters(entityType: LevelEntity): LeftFeet[] { + const characters: LeftFeet[] = []; LEVEL1.split('\n').forEach((line, indx) => { const arrLine = line.split(' '); for (let i = 0; i < arrLine.length; i += 1) { if (arrLine[i] === entityType) { - monsters.push({ + characters.push({ x: i * this.tileSize, y: (indx + 1) * this.tileSize, }); } } }); - return monsters; + return characters; } showWalls(): void { @@ -142,8 +147,8 @@ class GameView { }); } - insertPlayer(player: Player): void { - this.levelArea.append(player.sprite); + insertPlayer(): void { + this.levelArea.append(this.dave.sprite); } showZombies(): void { @@ -152,16 +157,16 @@ class GameView { }); } - correctLevelPosition(dave: Rect): void { - const daveViewX = dave.x + this.levelAreaX; - const rAreaX = this.viewAreaW / 2 + this.playerAreaW / 2 - dave.w; + correctLevelPosition(): void { + const daveViewX = this.dave.x + this.levelAreaX; + const rAreaX = this.viewAreaW / 2 + this.playerAreaW / 2 - this.dave.w; const lAreaX = this.viewAreaW / 2 - this.playerAreaW / 2; if (daveViewX > rAreaX) { - this.levelAreaX = rAreaX - dave.x; + this.levelAreaX = rAreaX - this.dave.x; } if (daveViewX < lAreaX) { this.levelAreaX = this.viewAreaW / 2 - - this.playerAreaW / 2 - dave.x; + - this.playerAreaW / 2 - this.dave.x; } if (this.levelAreaX > 0) this.levelAreaX = 0; if ( @@ -169,15 +174,15 @@ class GameView { this.levelAreaX = this.viewAreaW - this.levelAreaW; } - const daveViewY = dave.y + this.levelAreaY; + const daveViewY = this.dave.y + this.levelAreaY; const tAreaY = this.viewAreaH / 2 - this.playerAreaH / 2; - const bAreaY = this.viewAreaH / 2 + this.playerAreaH / 2 - dave.h; + const bAreaY = this.viewAreaH / 2 + this.playerAreaH / 2 - this.dave.h; if (daveViewY > bAreaY) { - this.levelAreaY = bAreaY - dave.y; + this.levelAreaY = bAreaY - this.dave.y; } if (daveViewY < tAreaY) { this.levelAreaY = this.viewAreaH / 2 - - this.playerAreaH / 2 - dave.y; + - this.playerAreaH / 2 - this.dave.y; } if (this.levelAreaY > 0) this.levelAreaY = 0; if ( diff --git a/client/src/scripts/components/zombie.ts b/client/src/scripts/components/zombie.ts index c6debe9..02431f4 100644 --- a/client/src/scripts/components/zombie.ts +++ b/client/src/scripts/components/zombie.ts @@ -2,13 +2,13 @@ import '@styles/zombie'; import { LeftFeet } from '../../types/types'; class Zombie { - X = 0; + x = 0; - Y = 0; + y = 0; - W = 64; + w = 64; - H = 120; + h = 120; movingLeft = false; @@ -24,10 +24,10 @@ class Zombie { constructor(leftFeet: LeftFeet) { this.sprite.classList.add('zombie'); - this.X = leftFeet.x; - this.Y = leftFeet.y - this.H; - this.sprite.style.width = `${this.W}px`; - this.sprite.style.height = `${this.H}px`; + this.x = leftFeet.x; + this.y = leftFeet.y - this.h; + this.sprite.style.width = `${this.w}px`; + this.sprite.style.height = `${this.h}px`; this.setPosition(); } @@ -40,7 +40,7 @@ class Zombie { } setPosition(): void { - this.sprite.style.transform = `translate(${this.X}px, ${this.Y}px)`; + this.sprite.style.transform = `translate(${this.x}px, ${this.y}px)`; } swapMoving(): void { diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index c44fe69..f1e3cee 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -1,4 +1,6 @@ -import { Offset, Rect } from '../../types/types'; +import { + DaveLook, DaveMove, DaveShoot, DaveState, Offset, Rect, +} from '../../types/types'; import Player from '../components/dave'; import GameView from '../components/game'; @@ -9,12 +11,11 @@ class PlayLevel { constructor() { this.gameView = new GameView(); - this.dave = new Player(); } startGame(): void { this.gameView.loadLevelEntities(); - this.gameView.insertPlayer(this.dave); + this.dave = this.gameView.dave; this.animate(); this.setListener(); this.animateZombies(); @@ -22,9 +23,9 @@ class PlayLevel { getHorizontalDiffMovingLeftRight(): Offset { let dX = 0; - if (this.dave.movingRight) { + if (this.dave.move === DaveMove.RIGHT) { dX = this.dave.stepSize; - } else if (this.dave.movingLeft) { + } else if (this.dave.move === DaveMove.LEFT) { dX = -this.dave.stepSize; } if (this.isCrossWithWalls({ @@ -42,9 +43,9 @@ class PlayLevel { let dX = 0; let dY = 0; dY = this.dave.velocity * 2 + 2; - if (this.dave.movingRight) { + if (this.dave.move === DaveMove.RIGHT) { dX = this.dave.stepSize; - } else if (this.dave.movingLeft) { + } else if (this.dave.move === DaveMove.LEFT) { dX = -this.dave.stepSize; } this.dave.velocity += 0.5; @@ -91,7 +92,9 @@ class PlayLevel { } if (wallUnder) { dY = wallUnder.y - this.dave.h - this.dave.y; - this.dave.falling = false; + this.dave.state = this.dave.move === DaveMove.NONE + ? DaveState.STANDING + : DaveState.RUNNING; this.dave.velocity = 0; if ((wallRight && dX > 0) || (wallLeft && dX < 0)) { dX = 0; @@ -107,9 +110,9 @@ class PlayLevel { let dX = 0; let dY = 0; dY = -this.dave.velocity * 2 - 2; - if (this.dave.movingRight) { + if (this.dave.move === DaveMove.RIGHT) { dX = this.dave.stepSize; - } else if (this.dave.movingLeft) { + } else if (this.dave.move === DaveMove.LEFT) { dX = -this.dave.stepSize; } @@ -139,7 +142,7 @@ class PlayLevel { } if (wallAbove) { dY = wallAbove.y + wallAbove.h - this.dave.y; - this.dave.falling = false; + this.dave.state = DaveState.FALLING; this.dave.velocity = 0; if ((wallRight && dX > 0) || (wallLeft && dX < 0)) { dX = 0; @@ -149,8 +152,7 @@ class PlayLevel { } } if (this.dave.velocity === 0) { - this.dave.falling = true; - this.dave.jumping = false; + this.dave.state = DaveState.FALLING; } return [dX, dY]; } @@ -158,12 +160,12 @@ class PlayLevel { getDiffStartJumpingDown(): Offset { let dX = 0; let dY = this.dave.velocity * 2 + 2; - if (this.dave.movingRight) { + if (this.dave.move === DaveMove.RIGHT) { dX = this.dave.stepSize; - } else if (this.dave.movingLeft) { + } else if (this.dave.move === DaveMove.LEFT) { dX = -this.dave.stepSize; } - this.dave.startJumpingDown = false; + this.dave.state = DaveState.STANDING; this.dave.velocity += 0.5; const walls: Rect[] = this.isCrossWithWalls({ x: this.dave.x + ((dX < 0) ? dX : 0), @@ -172,7 +174,7 @@ class PlayLevel { h: this.dave.h + ((dY > 0) ? dY : 0), }); if (walls.length === 0) { - this.dave.falling = true; + this.dave.state = DaveState.FALLING; } else { dY = 0; } @@ -181,23 +183,20 @@ class PlayLevel { animate(): void { const tick = (): void => { - if (!this.dave.stopped) { + if (this.dave.state !== DaveState.STANDING) { let dX = 0; let dY = 0; - if ( - !this.dave.falling - && !this.dave.jumping - && !this.dave.startJumpingDown) { + if (this.dave.state === DaveState.RUNNING) { if (this.isDaveHasToFall()) { - this.dave.falling = true; + this.dave.state = DaveState.FALLING; } else { [dX, dY] = this.getHorizontalDiffMovingLeftRight(); } - } else if (this.dave.falling) { + } else if (this.dave.state === DaveState.FALLING) { [dX, dY] = this.getDiffFalling(); - } else if (this.dave.jumping) { + } else if (this.dave.state === DaveState.JUMPING_UP) { [dX, dY] = this.getDiffJumping(); - } else if (this.dave.startJumpingDown) { + } else if (this.dave.state === DaveState.JUMPING_DOWN) { [dX, dY] = this.getDiffStartJumpingDown(); } @@ -207,15 +206,9 @@ class PlayLevel { this.gameView.levelAreaW, this.gameView.levelAreaH, ); - this.gameView.correctLevelPosition({ - x: this.dave.x, - y: this.dave.y, - w: this.dave.w, - h: this.dave.h, - }); + this.gameView.correctLevelPosition(); } else if (this.isDaveHasToFall()) { - this.dave.stopped = false; - this.dave.falling = true; + this.dave.state = DaveState.FALLING; } this.dave.setView(); requestAnimationFrame(tick); @@ -290,38 +283,42 @@ class PlayLevel { setListener(): void { window.addEventListener('keydown', (e: KeyboardEvent) => { - this.dave.stopped = false; switch (e.code) { case 'ArrowLeft': - this.dave.movingRight = false; - this.dave.movingLeft = true; - this.dave.lookingRight = false; - this.dave.lookingLeft = true; + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.SHOOTING) { + this.dave.state = DaveState.RUNNING; + } + this.dave.move = DaveMove.LEFT; + this.dave.look = DaveLook.LEFT; break; case 'ArrowRight': - this.dave.movingRight = true; - this.dave.movingLeft = false; - this.dave.lookingRight = true; - this.dave.lookingLeft = false; + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.SHOOTING) { + this.dave.state = DaveState.RUNNING; + } + this.dave.move = DaveMove.RIGHT; + this.dave.look = DaveLook.RIGHT; break; case 'ArrowUp': - if (!this.dave.falling && !this.dave.jumping) { - this.dave.lookingDown = false; - this.dave.lookingUp = true; + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.SHOOTING) { + this.dave.shoot = DaveShoot.UP; } break; case 'ArrowDown': - if (!this.dave.falling && !this.dave.jumping) { - this.dave.lookingDown = true; - this.dave.lookingUp = false; + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.SHOOTING) { + this.dave.shoot = DaveShoot.DOWN; } break; case 'Space': - if (!this.dave.falling && !this.dave.jumping) { - if (this.dave.lookingDown) { - this.dave.startJumpingDown = true; + if (this.dave.state === DaveState.RUNNING + || this.dave.state === DaveState.STANDING) { + if (this.dave.shoot === DaveShoot.DOWN) { + this.dave.state = DaveState.JUMPING_DOWN; } else { - this.dave.jumping = true; + this.dave.state = DaveState.JUMPING_UP; } this.dave.velocity = this.dave.jumpStartVelocity; } @@ -332,26 +329,17 @@ class PlayLevel { } }); window.addEventListener('keyup', (e: KeyboardEvent) => { - if (!this.dave.falling && !this.dave.jumping) { - // this.dave.stopped = true; - } - if (e.code === 'ArrowRight') { - this.dave.movingRight = false; - } - if (e.code === 'ArrowLeft') { - this.dave.movingLeft = false; + if (e.code === 'ArrowRight' || e.code === 'ArrowLeft') { + if (this.dave.state === DaveState.RUNNING) { + this.dave.state = DaveState.STANDING; + } + this.dave.move = DaveMove.NONE; } if (e.code === 'ArrowUp') { - this.dave.movingUp = false; - if (!this.dave.falling && !this.dave.jumping) { - this.dave.lookingUp = false; - } + this.dave.shoot = DaveShoot.CENTER; } if (e.code === 'ArrowDown') { - this.dave.movingDown = false; - if (!this.dave.falling && !this.dave.jumping) { - this.dave.lookingDown = false; - } + this.dave.shoot = DaveShoot.CENTER; } this.dave.setView(); }); @@ -368,12 +356,12 @@ class PlayLevel { dX = -item.stepSize; } if (this.isCrossWithWalls({ - x: item.X + ((dX < 0) ? dX : 0), - y: item.Y, - w: item.W + ((dX > 0) ? dX : 0), - h: item.H, + x: item.x + ((dX < 0) ? dX : 0), + y: item.y, + w: item.w + ((dX > 0) ? dX : 0), + h: item.h, }).length === 0) { - item.X += dX; + item.x += dX; } else { item.swapMoving(); } diff --git a/client/src/types/types.ts b/client/src/types/types.ts index 3217958..5dcca5c 100644 --- a/client/src/types/types.ts +++ b/client/src/types/types.ts @@ -14,5 +14,33 @@ export enum LevelEntity { WALL = '1', PLATFORM = '2', ZOMBIE = 'Z', + DAVE = 'D', } export type Offset = [number, number]; + +export enum DaveState { + STANDING, + RUNNING, + JUMPING_DOWN, + JUMPING_UP, + FALLING, + SHOOTING, + RECHARGING, +} + +export enum DaveMove { + LEFT, + RIGHT, + NONE, +} + +export enum DaveLook { + LEFT, + RIGHT, +} + +export enum DaveShoot { + UP, + CENTER, + DOWN, +} From 2d6515cb05dae049fc2205939dd7cc4455de05ea Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Thu, 9 Feb 2023 00:34:00 +0300 Subject: [PATCH 035/196] feat: add shooting 6 angles, monster health loose and die --- client/src/index.html | 1 + client/src/scripts/components/dave.ts | 23 +- client/src/scripts/components/game.ts | 26 +- client/src/scripts/components/zombie.ts | 16 ++ client/src/scripts/controllers/playLevel.ts | 267 ++++++++++++++++++-- client/src/styles/level.css | 2 +- client/src/styles/zombie.css | 4 + client/src/types/types.ts | 1 + 8 files changed, 319 insertions(+), 21 deletions(-) diff --git a/client/src/index.html b/client/src/index.html index d65fe9b..f809063 100644 --- a/client/src/index.html +++ b/client/src/index.html @@ -10,6 +10,7 @@
+
diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index ce35762..87091d7 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -1,6 +1,6 @@ import '@styles/dave'; import { - DaveLook, DaveMove, DaveShoot, DaveState, LeftFeet, + DaveLook, DaveMove, DaveShoot, DaveState, LeftFeet, Offset, } from '../../types/types'; class Player { @@ -38,7 +38,6 @@ class Player { } setView(): void { - console.log(this.state); if (this.state === DaveState.FALLING) { if (this.look === DaveLook.LEFT) { this.sprite.innerHTML = ''; @@ -62,6 +61,26 @@ class Player { } } + showShootLine( + canvas: HTMLCanvasElement, + canvasData: ImageData, + offset: Offset, + ): void { + const fromX: number = this.x + this.w / 2; + const fromY: number = this.y + this.h / 2; + const ctx: CanvasRenderingContext2D | null = canvas.getContext('2d'); + + if (ctx) { + ctx.putImageData(canvasData, 0, 0); + ctx.strokeStyle = 'black'; + ctx.lineWidth = 3; + ctx.beginPath(); + ctx.moveTo(fromX, fromY); + ctx.lineTo(fromX + offset[0], fromY + offset[1]); + ctx.stroke(); + } + } + correctPosByDiff( dX: number, dY: number, diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 98a8e36..28b8aa1 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -38,6 +38,10 @@ class GameView { dave: Player; + canvas: HTMLCanvasElement = document.createElement('canvas'); + + canvasData: ImageData; + constructor() { this.levelArea.classList.add('level-area'); this.levelArea.style.width = `${this.levelAreaW}px`; @@ -51,6 +55,20 @@ class GameView { this.playerArea.style.left = `${this.viewAreaW / 2 - this.playerAreaW / 2}px`; this.playerArea.style.top = `${this.viewAreaH / 2 - this.playerAreaH / 2}px`; + this.canvas.width = this.levelAreaW; + this.canvas.height = this.levelAreaH; + this.canvas.style.position = 'absolute'; + this.canvas.style.top = '0'; + this.canvas.style.left = '0'; + this.levelArea.append(this.canvas); + const ctx: CanvasRenderingContext2D = this.canvas.getContext('2d')!; + this.canvasData = ctx.getImageData( + 0, + 0, + this.canvas.width, + this.canvas.height, + ); + this.viewArea.append(this.levelArea, this.playerArea); document.querySelectorAll('.opacity_side')[0]?.after(this.viewArea); } @@ -185,12 +203,16 @@ class GameView { - this.playerAreaH / 2 - this.dave.y; } if (this.levelAreaY > 0) this.levelAreaY = 0; - if ( - this.levelAreaY < this.viewAreaH - this.levelAreaH) { + if (this.levelAreaY < this.viewAreaH - this.levelAreaH) { this.levelAreaY = this.viewAreaH - this.levelAreaH; } this.levelArea.style.transform = `translate(${this.levelAreaX}px, ${this.levelAreaY}px)`; } + + removeZombie(monster: Zombie): void { + monster.removeSprite(); + this.zombies.splice(this.zombies.indexOf(monster), 1); + } } export default GameView; diff --git a/client/src/scripts/components/zombie.ts b/client/src/scripts/components/zombie.ts index 02431f4..3334a59 100644 --- a/client/src/scripts/components/zombie.ts +++ b/client/src/scripts/components/zombie.ts @@ -20,6 +20,8 @@ class Zombie { stepSize = 16; + health = 2; + sprite: HTMLElement = document.createElement('div'); constructor(leftFeet: LeftFeet) { @@ -52,6 +54,20 @@ class Zombie { this.movingLeft = false; } } + + getAttacked(): void { + this.health -= 1; + if (this.health > 0) { + this.sprite.classList.add('attacked'); + setTimeout(() => { + this.sprite.classList.remove('attacked'); + }, 200); + } + } + + removeSprite(): void { + this.sprite.remove(); + } } export default Zombie; diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index f1e3cee..705a8f3 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -1,7 +1,9 @@ +/* eslint-disable class-methods-use-this */ import { DaveLook, DaveMove, DaveShoot, DaveState, Offset, Rect, } from '../../types/types'; import Player from '../components/dave'; +import Zombie from '../components/zombie'; import GameView from '../components/game'; class PlayLevel { @@ -181,6 +183,24 @@ class PlayLevel { return [dX, dY]; } + getDiffShooting(): Offset { + let dX = 0; + if (this.dave.look === DaveLook.LEFT) { + dX = this.dave.stepSize; + } else if (this.dave.look === DaveLook.RIGHT) { + dX = -this.dave.stepSize; + } + if (this.isCrossWithWalls({ + x: this.dave.x + ((dX < 0) ? dX : 0), + y: this.dave.y, + w: this.dave.w + ((dX > 0) ? dX : 0), + h: this.dave.h, + }).length === 0) { + return [dX, 0]; + } + return [0, 0]; + } + animate(): void { const tick = (): void => { if (this.dave.state !== DaveState.STANDING) { @@ -198,6 +218,8 @@ class PlayLevel { [dX, dY] = this.getDiffJumping(); } else if (this.dave.state === DaveState.JUMPING_DOWN) { [dX, dY] = this.getDiffStartJumpingDown(); + } else if (this.dave.state === DaveState.SHOOTING) { + [dX, dY] = this.getDiffShooting(); } this.dave.correctPosByDiff( @@ -211,6 +233,11 @@ class PlayLevel { this.dave.state = DaveState.FALLING; } this.dave.setView(); + this.dave.showShootLine( + this.gameView.canvas, + this.gameView.canvasData, + this.calcEndOfLineShoot(), + ); requestAnimationFrame(tick); }; tick(); @@ -285,30 +312,38 @@ class PlayLevel { window.addEventListener('keydown', (e: KeyboardEvent) => { switch (e.code) { case 'ArrowLeft': - if (this.dave.state === DaveState.STANDING - || this.dave.state === DaveState.SHOOTING) { + if (e.altKey) { + e.preventDefault(); + } + if (this.dave.state === DaveState.STANDING) { this.dave.state = DaveState.RUNNING; } - this.dave.move = DaveMove.LEFT; - this.dave.look = DaveLook.LEFT; + if (this.dave.state !== DaveState.SHOOTING + && this.dave.state !== DaveState.STUCK) { + this.dave.move = DaveMove.LEFT; + this.dave.look = DaveLook.LEFT; + } break; case 'ArrowRight': - if (this.dave.state === DaveState.STANDING - || this.dave.state === DaveState.SHOOTING) { + if (e.altKey) { + e.preventDefault(); + } + if (this.dave.state === DaveState.STANDING) { this.dave.state = DaveState.RUNNING; } - this.dave.move = DaveMove.RIGHT; - this.dave.look = DaveLook.RIGHT; + if (this.dave.state !== DaveState.SHOOTING + && this.dave.state !== DaveState.STUCK) { + this.dave.move = DaveMove.RIGHT; + this.dave.look = DaveLook.RIGHT; + } break; case 'ArrowUp': - if (this.dave.state === DaveState.STANDING - || this.dave.state === DaveState.SHOOTING) { + if (this.dave.state === DaveState.STANDING) { this.dave.shoot = DaveShoot.UP; } break; case 'ArrowDown': - if (this.dave.state === DaveState.STANDING - || this.dave.state === DaveState.SHOOTING) { + if (this.dave.state === DaveState.STANDING) { this.dave.shoot = DaveShoot.DOWN; } break; @@ -323,6 +358,23 @@ class PlayLevel { this.dave.velocity = this.dave.jumpStartVelocity; } break; + case 'AltLeft': + if (e.altKey) { + e.preventDefault(); + } + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.RUNNING + || this.dave.state === DaveState.RECHARGING) { + this.dave.state = DaveState.SHOOTING; + this.daveShoot(); + setTimeout(() => { + this.dave.state = DaveState.STUCK; + setTimeout(() => { + this.dave.state = DaveState.STANDING; + }, 200); + }, 50); + } + break; default: this.dave.setView(); break; @@ -346,9 +398,9 @@ class PlayLevel { } animateZombies(): void { - for (let i = 0; i < this.gameView.zombies.length; i += 1) { - const item = this.gameView.zombies[i]; - setInterval(() => { + setInterval(() => { + for (let i = 0; i < this.gameView.zombies.length; i += 1) { + const item = this.gameView.zombies[i]; let dX = 0; if (item.movingRight) { dX = item.stepSize; @@ -366,8 +418,191 @@ class PlayLevel { item.swapMoving(); } item.setPosition(); - }, 300); + } + }, 300); + } + + calcEndOfLineShoot(): Offset { + let dX = 0; + let dY = 0; + const toLeft: number = this.dave.x + + this.gameView.levelAreaX + this.dave.w / 2; + const toRight: number = this.gameView.viewAreaW - toLeft; + const toTop: number = this.dave.y + + this.gameView.levelAreaY + this.dave.h / 2; + const toBottom: number = this.gameView.viewAreaH - toTop; + if (this.dave.look === DaveLook.LEFT) { + dX = -toLeft; + if (this.dave.shoot === DaveShoot.UP) { + if (-toLeft < -toTop) { + dX = -toTop; + dY = -toTop; + } else { + dY = -toLeft; + } + } else if (this.dave.shoot === DaveShoot.DOWN) { + if (toLeft > toBottom) { + dX = -toBottom; + dY = toBottom; + } else { + dY = toLeft; + } + } else { + dY = 0; + } + } else if (this.dave.look === DaveLook.RIGHT) { + dX = toRight; + if (this.dave.shoot === DaveShoot.UP) { + if (-toRight < -toTop) { + dX = toTop; + dY = -toTop; + } else { + dY = -toRight; + } + } else if (this.dave.shoot === DaveShoot.DOWN) { + if (toRight > toBottom) { + dX = toBottom; + dY = toBottom; + } else { + dY = toRight; + } + } else { + dY = 0; + } + } + + return [dX, dY]; + } + + daveShoot(): void { + const fromX: number = this.dave.x + this.dave.w / 2; + const fromY: number = this.dave.y + this.dave.h / 2; + const [dX, dY] = this.calcEndOfLineShoot(); + let closestWall: Rect | undefined; + this.gameView.walls.forEach((wall) => { + if (this.isLineCrossRect(fromX, fromY, fromX + dX, fromY + dY, wall)) { + if (!closestWall || this.isOneRectCloserAnother(wall, closestWall)) { + closestWall = wall; + } + } + }); + let closestMonster: Zombie | undefined; + this.gameView.zombies.forEach((monster) => { + if (this.isLineCrossRect(fromX, fromY, fromX + dX, fromY + dY, monster)) { + if (!closestMonster + || this.isOneRectCloserAnother(monster, closestMonster)) { + closestMonster = monster; + } + } + }); + if ((closestMonster && !closestWall) + || (closestMonster + && closestWall + && this.isOneRectCloserAnother(closestMonster, closestWall)) + ) { + closestMonster.getAttacked(); + if (closestMonster.health === 0) { + this.gameView.removeZombie(closestMonster); + } + } + } + + isOneRectCloserAnother(wall: Rect, monster: Rect): boolean { + if (this.dave.look === DaveLook.RIGHT) { + if (this.dave.shoot === DaveShoot.CENTER) { + return (wall.x + wall.w < monster.x); + } if (this.dave.shoot === DaveShoot.UP) { + return !!((wall.x + wall.w <= monster.x + || wall.y >= monster.y + monster.h)); + } if (this.dave.shoot === DaveShoot.DOWN) { + return !!((wall.x + wall.w <= monster.x + || wall.y + wall.h <= monster.y)); + } + } else if (this.dave.look === DaveLook.LEFT) { + if (this.dave.shoot === DaveShoot.CENTER) { + return (wall.x >= monster.x + monster.w); + } if (this.dave.shoot === DaveShoot.UP) { + return !!((wall.x >= monster.x + monster.w + || wall.y >= monster.y + monster.h)); + } if (this.dave.shoot === DaveShoot.DOWN) { + return !!((wall.x >= monster.x + monster.w + || wall.y + wall.h <= monster.y)); + } + } + return false; + } + + isLineCrossLine( + x1: number, + y1: number, + x2: number, + y2: number, + x3: number, + y3: number, + x4: number, + y4: number, + ): boolean { + const uA: number = ((x4 - x3) * (y1 - y3) - (y4 - y3) * (x1 - x3)) + / ((y4 - y3) * (x2 - x1) - (x4 - x3) * (y2 - y1)); + const uB: number = ((x2 - x1) * (y1 - y3) - (y2 - y1) * (x1 - x3)) + / ((y4 - y3) * (x2 - x1) - (x4 - x3) * (y2 - y1)); + if (uA >= 0 && uA <= 1 && uB >= 0 && uB <= 1) { + return true; } + return false; + } + + isLineCrossRect( + x1: number, + y1: number, + x2: number, + y2: number, + rect: Rect, + ): boolean { + const left: boolean = this.isLineCrossLine( + x1, + y1, + x2, + y2, + rect.x, + rect.y, + rect.x, + rect.y + rect.h, + ); + const right: boolean = this.isLineCrossLine( + x1, + y1, + x2, + y2, + rect.x + rect.w, + rect.y, + rect.x + rect.w, + rect.y + rect.h, + ); + const top: boolean = this.isLineCrossLine( + x1, + y1, + x2, + y2, + rect.x, + rect.y, + rect.x + rect.w, + rect.y, + ); + const bottom: boolean = this.isLineCrossLine( + x1, + y1, + x2, + y2, + rect.x, + rect.y + rect.h, + rect.x + rect.w, + rect.y + rect.h, + ); + if (left || right || top || bottom) { + return true; + } + return false; } } diff --git a/client/src/styles/level.css b/client/src/styles/level.css index 6ff4654..f3f017b 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -52,4 +52,4 @@ body { .opacity_bottom { width: 100%; height: 100%; -} \ No newline at end of file +} diff --git a/client/src/styles/zombie.css b/client/src/styles/zombie.css index aa37cc2..0f75814 100644 --- a/client/src/styles/zombie.css +++ b/client/src/styles/zombie.css @@ -4,3 +4,7 @@ left: 0; background-color: burlywood; } + +.zombie.attacked { + background-color: crimson; +} diff --git a/client/src/types/types.ts b/client/src/types/types.ts index 5dcca5c..33956ee 100644 --- a/client/src/types/types.ts +++ b/client/src/types/types.ts @@ -26,6 +26,7 @@ export enum DaveState { FALLING, SHOOTING, RECHARGING, + STUCK, } export enum DaveMove { From 86bef101114b213ce5ab700817cd75467d42a162 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Thu, 9 Feb 2023 17:24:53 +0300 Subject: [PATCH 036/196] refactor: add type for Line --- client/src/scripts/components/dave.ts | 7 +- client/src/scripts/components/game.ts | 2 +- client/src/scripts/components/zombie.ts | 2 +- client/src/scripts/controllers/playLevel.ts | 123 +++++++++----------- client/src/types/{types.ts => dave.ts} | 20 ---- client/src/types/game.ts | 26 +++++ 6 files changed, 91 insertions(+), 89 deletions(-) rename client/src/types/{types.ts => dave.ts} (50%) create mode 100644 client/src/types/game.ts diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index 87091d7..7b35dd6 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -1,7 +1,10 @@ import '@styles/dave'; import { - DaveLook, DaveMove, DaveShoot, DaveState, LeftFeet, Offset, -} from '../../types/types'; + LeftFeet, Offset, +} from '../../types/game'; +import { + DaveLook, DaveMove, DaveShoot, DaveState, +} from '../../types/dave'; class Player { x = 0; diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 28b8aa1..c817866 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -1,6 +1,6 @@ import '@styles/level'; -import { Rect, LevelEntity, LeftFeet } from '../../types/types'; +import { Rect, LevelEntity, LeftFeet } from '../../types/game'; import Player from './dave'; import Zombie from './zombie'; import { LEVEL1 } from '../../assets/levels/level1'; diff --git a/client/src/scripts/components/zombie.ts b/client/src/scripts/components/zombie.ts index 3334a59..71c359b 100644 --- a/client/src/scripts/components/zombie.ts +++ b/client/src/scripts/components/zombie.ts @@ -1,5 +1,5 @@ import '@styles/zombie'; -import { LeftFeet } from '../../types/types'; +import { LeftFeet } from '../../types/game'; class Zombie { x = 0; diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index 705a8f3..d3604f7 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -1,7 +1,10 @@ /* eslint-disable class-methods-use-this */ import { - DaveLook, DaveMove, DaveShoot, DaveState, Offset, Rect, -} from '../../types/types'; + Line, Offset, Rect, +} from '../../types/game'; +import { + DaveLook, DaveMove, DaveShoot, DaveState, +} from '../../types/dave'; import Player from '../components/dave'; import Zombie from '../components/zombie'; import GameView from '../components/game'; @@ -480,7 +483,13 @@ class PlayLevel { const [dX, dY] = this.calcEndOfLineShoot(); let closestWall: Rect | undefined; this.gameView.walls.forEach((wall) => { - if (this.isLineCrossRect(fromX, fromY, fromX + dX, fromY + dY, wall)) { + if (this.isLineCrossRect( + { + x1: fromX, + y1: fromY, + x2: fromX + dX, + y2: fromY + dY + }, wall)) { if (!closestWall || this.isOneRectCloserAnother(wall, closestWall)) { closestWall = wall; } @@ -488,7 +497,13 @@ class PlayLevel { }); let closestMonster: Zombie | undefined; this.gameView.zombies.forEach((monster) => { - if (this.isLineCrossRect(fromX, fromY, fromX + dX, fromY + dY, monster)) { + if (this.isLineCrossRect( + { + x1: fromX, + y1: fromY, + x2: fromX + dX, + y2: fromY + dY + }, monster)) { if (!closestMonster || this.isOneRectCloserAnother(monster, closestMonster)) { closestMonster = monster; @@ -532,73 +547,51 @@ class PlayLevel { return false; } - isLineCrossLine( - x1: number, - y1: number, - x2: number, - y2: number, - x3: number, - y3: number, - x4: number, - y4: number, - ): boolean { - const uA: number = ((x4 - x3) * (y1 - y3) - (y4 - y3) * (x1 - x3)) - / ((y4 - y3) * (x2 - x1) - (x4 - x3) * (y2 - y1)); - const uB: number = ((x2 - x1) * (y1 - y3) - (y2 - y1) * (x1 - x3)) - / ((y4 - y3) * (x2 - x1) - (x4 - x3) * (y2 - y1)); + isLineCrossLine(line1: Line, line2: Line): boolean { + const x2x1: number = line1.x2 - line1.x1; + const x4x3: number = line2.x2 - line2.x1; + const y2y1: number = line1.y2 - line1.y1; + const y4y3: number = line2.y2 - line2.y1; + const x1x3: number = line1.x1 - line2.x1; + const y1y3: number = line1.y1 - line2.y1; + const d: number = (y4y3 * x2x1 - x4x3 * y2y1); + const uA: number = (x4x3 * y1y3 - y4y3 * x1x3) / d; + const uB: number = (x2x1 * y1y3 - y2y1 * x1x3) / d; if (uA >= 0 && uA <= 1 && uB >= 0 && uB <= 1) { return true; } return false; } - isLineCrossRect( - x1: number, - y1: number, - x2: number, - y2: number, - rect: Rect, - ): boolean { - const left: boolean = this.isLineCrossLine( - x1, - y1, - x2, - y2, - rect.x, - rect.y, - rect.x, - rect.y + rect.h, - ); - const right: boolean = this.isLineCrossLine( - x1, - y1, - x2, - y2, - rect.x + rect.w, - rect.y, - rect.x + rect.w, - rect.y + rect.h, - ); - const top: boolean = this.isLineCrossLine( - x1, - y1, - x2, - y2, - rect.x, - rect.y, - rect.x + rect.w, - rect.y, - ); - const bottom: boolean = this.isLineCrossLine( - x1, - y1, - x2, - y2, - rect.x, - rect.y + rect.h, - rect.x + rect.w, - rect.y + rect.h, - ); + isLineCrossRect(line: Line, rect: Rect): boolean { + const left: boolean = this.isLineCrossLine(line, + { + x1: rect.x, + y1: rect.y, + x2: rect.x, + y2: rect.y + rect.h + }); + const right: boolean = this.isLineCrossLine(line, + { + x1: rect.x + rect.w, + y1: rect.y, + x2: rect.x + rect.w, + y2: rect.y + rect.h, + }); + const top: boolean = this.isLineCrossLine(line, + { + x1: rect.x, + y1: rect.y, + x2: rect.x + rect.w, + y2: rect.y, + }); + const bottom: boolean = this.isLineCrossLine(line, + { + x1: rect.x, + y1: rect.y + rect.h, + x2: rect.x + rect.w, + y2: rect.y + rect.h, + }); if (left || right || top || bottom) { return true; } diff --git a/client/src/types/types.ts b/client/src/types/dave.ts similarity index 50% rename from client/src/types/types.ts rename to client/src/types/dave.ts index 33956ee..4f4955c 100644 --- a/client/src/types/types.ts +++ b/client/src/types/dave.ts @@ -1,23 +1,3 @@ -export type Rect = { - x: number; - y: number; - w: number; - h: number; -}; - -export type LeftFeet = { - x: number; - y: number; -}; - -export enum LevelEntity { - WALL = '1', - PLATFORM = '2', - ZOMBIE = 'Z', - DAVE = 'D', -} -export type Offset = [number, number]; - export enum DaveState { STANDING, RUNNING, diff --git a/client/src/types/game.ts b/client/src/types/game.ts new file mode 100644 index 0000000..32b67cd --- /dev/null +++ b/client/src/types/game.ts @@ -0,0 +1,26 @@ +export type Rect = { + x: number; + y: number; + w: number; + h: number; +}; + +export type LeftFeet = { + x: number; + y: number; +}; + +export enum LevelEntity { + WALL = '1', + PLATFORM = '2', + ZOMBIE = 'Z', + DAVE = 'D', +} +export type Offset = [number, number]; + +export type Line = { + x1: number; + y1: number; + x2: number; + y2: number; +} From 7c3fc2b6ae47cbc7ffbf1d59df39115929b79d4f Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Thu, 9 Feb 2023 17:27:31 +0300 Subject: [PATCH 037/196] refactor: split types --- client/src/scripts/components/dave.ts | 8 ++-- client/src/scripts/components/game.ts | 2 +- client/src/scripts/components/zombie.ts | 2 +- client/src/scripts/controllers/playLevel.ts | 7 +++- client/src/types/dave.ts | 26 ++++++++++++ client/src/types/game.ts | 19 +++++++++ client/src/types/types.ts | 46 --------------------- 7 files changed, 57 insertions(+), 53 deletions(-) create mode 100644 client/src/types/dave.ts create mode 100644 client/src/types/game.ts delete mode 100644 client/src/types/types.ts diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index ce35762..fe1f594 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -1,8 +1,10 @@ import '@styles/dave'; import { - DaveLook, DaveMove, DaveShoot, DaveState, LeftFeet, -} from '../../types/types'; - + LeftFeet, +} from '../../types/game'; +import { + DaveLook, DaveMove, DaveShoot, DaveState, +} from '../../types/dave'; class Player { x = 0; diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 98a8e36..498ae80 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -1,6 +1,6 @@ import '@styles/level'; -import { Rect, LevelEntity, LeftFeet } from '../../types/types'; +import { Rect, LevelEntity, LeftFeet } from '../../types/game'; import Player from './dave'; import Zombie from './zombie'; import { LEVEL1 } from '../../assets/levels/level1'; diff --git a/client/src/scripts/components/zombie.ts b/client/src/scripts/components/zombie.ts index 02431f4..cfdafa1 100644 --- a/client/src/scripts/components/zombie.ts +++ b/client/src/scripts/components/zombie.ts @@ -1,5 +1,5 @@ import '@styles/zombie'; -import { LeftFeet } from '../../types/types'; +import { LeftFeet } from '../../types/game'; class Zombie { x = 0; diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index f1e3cee..70be162 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -1,6 +1,9 @@ import { - DaveLook, DaveMove, DaveShoot, DaveState, Offset, Rect, -} from '../../types/types'; + Offset, Rect, +} from '../../types/game'; +import { + DaveLook, DaveMove, DaveShoot, DaveState, +} from '../../types/dave'; import Player from '../components/dave'; import GameView from '../components/game'; diff --git a/client/src/types/dave.ts b/client/src/types/dave.ts new file mode 100644 index 0000000..d511c6f --- /dev/null +++ b/client/src/types/dave.ts @@ -0,0 +1,26 @@ +export enum DaveState { + STANDING, + RUNNING, + JUMPING_DOWN, + JUMPING_UP, + FALLING, + SHOOTING, + RECHARGING, +} + +export enum DaveMove { + LEFT, + RIGHT, + NONE, +} + +export enum DaveLook { + LEFT, + RIGHT, +} + +export enum DaveShoot { + UP, + CENTER, + DOWN, +} diff --git a/client/src/types/game.ts b/client/src/types/game.ts new file mode 100644 index 0000000..3bda956 --- /dev/null +++ b/client/src/types/game.ts @@ -0,0 +1,19 @@ +export type Rect = { + x: number; + y: number; + w: number; + h: number; +}; + +export type LeftFeet = { + x: number; + y: number; +}; + +export enum LevelEntity { + WALL = '1', + PLATFORM = '2', + ZOMBIE = 'Z', + DAVE = 'D', +} +export type Offset = [number, number]; diff --git a/client/src/types/types.ts b/client/src/types/types.ts deleted file mode 100644 index 5dcca5c..0000000 --- a/client/src/types/types.ts +++ /dev/null @@ -1,46 +0,0 @@ -export type Rect = { - x: number; - y: number; - w: number; - h: number; -}; - -export type LeftFeet = { - x: number; - y: number; -}; - -export enum LevelEntity { - WALL = '1', - PLATFORM = '2', - ZOMBIE = 'Z', - DAVE = 'D', -} -export type Offset = [number, number]; - -export enum DaveState { - STANDING, - RUNNING, - JUMPING_DOWN, - JUMPING_UP, - FALLING, - SHOOTING, - RECHARGING, -} - -export enum DaveMove { - LEFT, - RIGHT, - NONE, -} - -export enum DaveLook { - LEFT, - RIGHT, -} - -export enum DaveShoot { - UP, - CENTER, - DOWN, -} From 7bb2ebaa79465d106902c8b9310d9cdace7edbea Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Thu, 9 Feb 2023 17:28:59 +0300 Subject: [PATCH 038/196] refactor: eslint format --- client/src/scripts/components/dave.ts | 1 + 1 file changed, 1 insertion(+) diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index fe1f594..511c253 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -5,6 +5,7 @@ import { import { DaveLook, DaveMove, DaveShoot, DaveState, } from '../../types/dave'; + class Player { x = 0; From 1f8b2346f0c476a213da9519cb10c08238ebdb84 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Thu, 9 Feb 2023 22:49:48 +0300 Subject: [PATCH 039/196] feat: add shooting monsters 6 angles, 2 types of monsters --- client/src/assets/levels/level1.ts | 10 +-- client/src/scripts/components/crone.ts | 41 +++++++++++ client/src/scripts/components/game.ts | 22 +++--- client/src/scripts/components/monster.ts | 69 ++++++++++++++++++ client/src/scripts/components/zombie.ts | 46 +++--------- client/src/scripts/controllers/playLevel.ts | 79 +++++++++++++++------ client/src/styles/crone.css | 10 +++ client/src/types/game.ts | 7 ++ 8 files changed, 211 insertions(+), 73 deletions(-) create mode 100644 client/src/scripts/components/crone.ts create mode 100644 client/src/scripts/components/monster.ts create mode 100644 client/src/styles/crone.css diff --git a/client/src/assets/levels/level1.ts b/client/src/assets/levels/level1.ts index ff98442..4a6e6ba 100644 --- a/client/src/assets/levels/level1.ts +++ b/client/src/assets/levels/level1.ts @@ -1,9 +1,9 @@ export const LEVEL1 = `0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 1 0 0 1 +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 Z 0 0 1 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 2 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 1 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 2 0 0 0 1 +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 C 0 0 0 0 1 0 1 0 0 0 0 0 0 0 Z 0 0 0 0 0 Z 0 0 0 0 0 2 2 2 2 0 C 0 1 0 0 0 0 0 0 2 2 2 2 0 0 0 0 0 0 0 0 2 1 2 2 2 1 1 1 1 1 1 1 1 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 0 0 0 0 2 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 @@ -11,13 +11,13 @@ export const LEVEL1 = `0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 1 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 +0 0 0 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 C 0 1 0 0 0 0 0 0 0 1 0 0 0 0 Z 0 0 Z 0 0 0 0 0 0 0 0 0 Z 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 1 1 1 1 1 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 2 2 2 1 1 1 1 1 1 1 1 1 1 1 1 0 0 0 0 0 2 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 1 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 0 0 0 0 0 0 1 +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 C 0 0 0 1 0 0 0 0 0 1 0 0 0 0 0 C 0 0 0 0 2 2 2 0 Z 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 1 1 1 1 1 1 1 1 1 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 2 2 1 1 1 1 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 @@ -29,7 +29,7 @@ export const LEVEL1 = `0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 0 0 0 0 0 0 2 0 1 1 0 0 0 0 0 0 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 0 0 0 0 2 2 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 0 0 0 0 0 0 0 0 2 2 2 2 2 0 0 0 0 1 -0 0 0 0 0 0 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 Z 0 0 0 0 0 0 Z 0 0 0 0 0 0 0 0 Z 0 0 0 0 0 0 2 2 2 2 2 2 2 0 0 0 1 +0 0 0 0 0 0 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 Z 0 0 0 0 0 0 Z 0 0 Z 0 0 0 0 0 0 0 0 0 0 0 Z 2 2 2 2 2 2 2 0 Z 0 1 0 D 0 0 0 0 0 0 1 1 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0`; diff --git a/client/src/scripts/components/crone.ts b/client/src/scripts/components/crone.ts new file mode 100644 index 0000000..5452147 --- /dev/null +++ b/client/src/scripts/components/crone.ts @@ -0,0 +1,41 @@ +import '@styles/crone'; +import { LeftFeet } from '../../types/game'; +import Monster from './monster'; + +class Crone extends Monster { + x = 0; + + y = 0; + + w = 64; + + h = 72; + + movingLeft = false; + + movingRight = true; + + stepSize = 24; + + health = 2; + + randomSteps = 0; + + moveTicks = 2; + + moveTicksMax = 2; + + sprite: HTMLElement = document.createElement('div'); + + constructor(leftFeet: LeftFeet) { + super(); + this.sprite.classList.add('crone'); + this.x = leftFeet.x; + this.y = leftFeet.y - this.h; + this.sprite.style.width = `${this.w}px`; + this.sprite.style.height = `${this.h}px`; + this.setPosition(); + } +} + +export default Crone; diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index c817866..d582adf 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -4,6 +4,9 @@ import { Rect, LevelEntity, LeftFeet } from '../../types/game'; import Player from './dave'; import Zombie from './zombie'; import { LEVEL1 } from '../../assets/levels/level1'; +import Crone from './crone'; + +export type Monster = Zombie | Crone; class GameView { levelArea: HTMLElement = document.createElement('div'); @@ -34,7 +37,7 @@ class GameView { platforms: Rect[] = []; - zombies: Zombie[] = []; + monsters: Monster[] = []; dave: Player; @@ -78,10 +81,13 @@ class GameView { this.showWalls(); this.platforms = this.loadBorders(LevelEntity.PLATFORM); this.showPlatforms(); - this.loadCharacters(LevelEntity.ZOMBIE).forEach((zombie) => { - this.zombies.push(new Zombie(zombie)); + this.loadCharacters(LevelEntity.ZOMBIE).forEach((leftFeet) => { + this.monsters.push(new Zombie(leftFeet)); + }); + this.loadCharacters(LevelEntity.CRONE).forEach((leftFeet) => { + this.monsters.push(new Crone(leftFeet)); }); - this.showZombies(); + this.showMonsters(); this.dave = new Player(this.loadCharacters(LevelEntity.DAVE)[0]); this.insertPlayer(); this.correctLevelPosition(); @@ -169,8 +175,8 @@ class GameView { this.levelArea.append(this.dave.sprite); } - showZombies(): void { - this.zombies.forEach((item) => { + showMonsters(): void { + this.monsters.forEach((item) => { this.levelArea.append(item.sprite); }); } @@ -209,9 +215,9 @@ class GameView { this.levelArea.style.transform = `translate(${this.levelAreaX}px, ${this.levelAreaY}px)`; } - removeZombie(monster: Zombie): void { + removeZombie(monster: Monster): void { monster.removeSprite(); - this.zombies.splice(this.zombies.indexOf(monster), 1); + this.monsters.splice(this.monsters.indexOf(monster), 1); } } diff --git a/client/src/scripts/components/monster.ts b/client/src/scripts/components/monster.ts new file mode 100644 index 0000000..9e35739 --- /dev/null +++ b/client/src/scripts/components/monster.ts @@ -0,0 +1,69 @@ +import { LeftFeet } from '../../types/game'; + +class Monster { + x: number; + + y: number; + + w: number; + + h: number; + + movingLeft: boolean; + + movingRight: boolean; + + movingUp: boolean; + + movingDown: boolean; + + stepSize: number; + + health: number; + + randomSteps: number; + + moveTicks: number; + + moveTicksMax: number; + + sprite: HTMLElement; + + constructor() { + this.sprite = document.createElement('div'); + } + + setPosition(): void { + this.sprite.style.transform = `translate(${this.x}px, ${this.y}px)`; + } + + swapMoving(): void { + if (this.movingRight) { + this.movingRight = false; + this.movingLeft = true; + } else if (this.movingLeft) { + this.movingRight = true; + this.movingLeft = false; + } + } + + getAttacked(): void { + this.health -= 1; + if (this.health > 0) { + this.sprite.classList.add('attacked'); + setTimeout(() => { + this.sprite.classList.remove('attacked'); + }, 200); + } + } + + removeSprite(): void { + this.sprite.remove(); + } + + setRandomSteps(): void { + this.randomSteps = Math.ceil(Math.random() * 7); + } +} + +export default Monster; diff --git a/client/src/scripts/components/zombie.ts b/client/src/scripts/components/zombie.ts index 71c359b..d59e14d 100644 --- a/client/src/scripts/components/zombie.ts +++ b/client/src/scripts/components/zombie.ts @@ -1,7 +1,8 @@ import '@styles/zombie'; import { LeftFeet } from '../../types/game'; +import Monster from './monster'; -class Zombie { +class Zombie extends Monster { x = 0; y = 0; @@ -22,9 +23,16 @@ class Zombie { health = 2; + randomSteps = 0; + + moveTicks = 4; + + moveTicksMax = 4; + sprite: HTMLElement = document.createElement('div'); constructor(leftFeet: LeftFeet) { + super(); this.sprite.classList.add('zombie'); this.x = leftFeet.x; this.y = leftFeet.y - this.h; @@ -32,42 +40,6 @@ class Zombie { this.sprite.style.height = `${this.h}px`; this.setPosition(); } - - setView(): void { - if (this.movingLeft) { - this.sprite.innerHTML = ''; - } else if (this.movingRight) { - this.sprite.innerHTML = ''; - } - } - - setPosition(): void { - this.sprite.style.transform = `translate(${this.x}px, ${this.y}px)`; - } - - swapMoving(): void { - if (this.movingRight) { - this.movingRight = false; - this.movingLeft = true; - } else if (this.movingLeft) { - this.movingRight = true; - this.movingLeft = false; - } - } - - getAttacked(): void { - this.health -= 1; - if (this.health > 0) { - this.sprite.classList.add('attacked'); - setTimeout(() => { - this.sprite.classList.remove('attacked'); - }, 200); - } - } - - removeSprite(): void { - this.sprite.remove(); - } } export default Zombie; diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index 2e50dc5..76b103e 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -1,13 +1,13 @@ /* eslint-disable class-methods-use-this */ import { - Line, Offset, Rect, + Line, Offset, Position, Rect, } from '../../types/game'; import { DaveLook, DaveMove, DaveShoot, DaveState, } from '../../types/dave'; import Player from '../components/dave'; import Zombie from '../components/zombie'; -import GameView from '../components/game'; +import GameView, { Monster } from '../components/game'; class PlayLevel { gameView: GameView; @@ -402,27 +402,60 @@ class PlayLevel { animateZombies(): void { setInterval(() => { - for (let i = 0; i < this.gameView.zombies.length; i += 1) { - const item = this.gameView.zombies[i]; - let dX = 0; - if (item.movingRight) { - dX = item.stepSize; - } else if (item.movingLeft) { - dX = -item.stepSize; - } - if (this.isCrossWithWalls({ - x: item.x + ((dX < 0) ? dX : 0), - y: item.y, - w: item.w + ((dX > 0) ? dX : 0), - h: item.h, - }).length === 0) { - item.x += dX; - } else { - item.swapMoving(); + for (let i = 0; i < this.gameView.monsters.length; i += 1) { + const monster = this.gameView.monsters[i]; + if (monster.moveTicks === monster.moveTicksMax) { + monster.moveTicks -= 1; + let dX = 0; + if (monster.movingRight) { + dX = monster.stepSize; + } else if (monster.movingLeft) { + dX = -monster.stepSize; + } + if (this.isCrossWithWalls({ + x: monster.x + ((dX < 0) ? dX : 0), + y: monster.y, + w: monster.w + ((dX > 0) ? dX : 0), + h: monster.h, + }).length === 0) { + const whereIsDave: Position = this.isDaveNearMonster(monster); + if ( + (whereIsDave === Position.LEFT && monster.movingRight) + || (whereIsDave === Position.RIGHT && monster.movingLeft) + ) { + if (monster.randomSteps > 0) { + monster.x += dX; + monster.randomSteps -= 1; + } else { + monster.swapMoving(); + monster.setRandomSteps(); + } + } else { + monster.x += dX; + } + } else { + monster.swapMoving(); + } + monster.setPosition(); + } else if (monster.moveTicks === 0) { + monster.moveTicks = monster.moveTicksMax; + } else if (monster.moveTicks < monster.moveTicksMax) { + monster.moveTicks -= 1; } - item.setPosition(); } - }, 300); + }, 50); + } + + isDaveNearMonster(monster: Monster): Position { + const diffX: number = this.dave.x - monster.x; + const diffY: number = this.dave.y - monster.y; + if (Math.abs(diffX) > this.gameView.viewAreaW / 2 + || Math.abs(diffY) > this.gameView.viewAreaH / 4) { + return Position.NONE; + } if (diffX > 0) { + return Position.RIGHT; + } + return Position.LEFT; } calcEndOfLineShoot(): Offset { @@ -494,8 +527,8 @@ class PlayLevel { } } }); - let closestMonster: Zombie | undefined; - this.gameView.zombies.forEach((monster) => { + let closestMonster: Monster | undefined; + this.gameView.monsters.forEach((monster) => { if (this.isLineCrossRect({ x1: fromX, y1: fromY, diff --git a/client/src/styles/crone.css b/client/src/styles/crone.css new file mode 100644 index 0000000..a3df570 --- /dev/null +++ b/client/src/styles/crone.css @@ -0,0 +1,10 @@ +.crone { + position: absolute; + top: 0; + left: 0; + background-color:cadetblue; +} + +.crone.attacked { + background-color: green; +} diff --git a/client/src/types/game.ts b/client/src/types/game.ts index 88c9a20..08c05d4 100644 --- a/client/src/types/game.ts +++ b/client/src/types/game.ts @@ -15,6 +15,7 @@ export enum LevelEntity { PLATFORM = '2', ZOMBIE = 'Z', DAVE = 'D', + CRONE = 'C', } export type Offset = [number, number]; @@ -24,3 +25,9 @@ export type Line = { x2: number; y2: number; }; + +export enum Position { + NONE, + LEFT, + RIGHT, +} From 53fe7920ab5c4f22891db8ec22e7a3612167ee1b Mon Sep 17 00:00:00 2001 From: HardManDev Date: Fri, 10 Feb 2023 20:40:56 +0300 Subject: [PATCH 040/196] refactor: reinitialize nest js project --- server/.eslintrc.js | 25 + server/.eslintrc.json | 51 - server/.idea/.gitignore | 2 +- server/.idea/codeStyles/Project.xml | 52 + server/.idea/codeStyles/codeStyleConfig.xml | 5 + server/.idea/jsLinters/eslint.xml | 6 - server/.idea/prettier.xml | 6 + server/.prettierrc | 4 + server/package-lock.json | 1869 ++++++------------- server/package.json | 12 +- server/src/app.controller.spec.ts | 22 + server/src/app.controller.ts | 6 +- server/src/app.module.ts | 8 +- server/src/app.service.ts | 4 +- server/src/main.ts | 4 +- server/test/app.e2e-spec.ts | 24 + server/test/jest-e2e.json | 9 + 17 files changed, 697 insertions(+), 1412 deletions(-) create mode 100644 server/.eslintrc.js delete mode 100644 server/.eslintrc.json create mode 100644 server/.idea/codeStyles/Project.xml create mode 100644 server/.idea/codeStyles/codeStyleConfig.xml delete mode 100644 server/.idea/jsLinters/eslint.xml create mode 100644 server/.idea/prettier.xml create mode 100644 server/.prettierrc create mode 100644 server/src/app.controller.spec.ts create mode 100644 server/test/app.e2e-spec.ts create mode 100644 server/test/jest-e2e.json diff --git a/server/.eslintrc.js b/server/.eslintrc.js new file mode 100644 index 0000000..95f16da --- /dev/null +++ b/server/.eslintrc.js @@ -0,0 +1,25 @@ +module.exports = { + parser: '@typescript-eslint/parser', + parserOptions: { + project: 'tsconfig.json', + tsconfigRootDir: __dirname, + sourceType: 'module', + }, + plugins: ['@typescript-eslint/eslint-plugin'], + extends: [ + 'plugin:@typescript-eslint/recommended', + 'plugin:prettier/recommended', + ], + root: true, + env: { + node: true, + jest: true, + }, + ignorePatterns: ['.eslintrc.js'], + rules: { + '@typescript-eslint/interface-name-prefix': 'off', + '@typescript-eslint/explicit-module-boundary-types': 'off', + '@typescript-eslint/no-explicit-any': 'error', + '@typescript-eslint/explicit-function-return-type': 'error', + }, +}; diff --git a/server/.eslintrc.json b/server/.eslintrc.json deleted file mode 100644 index ea321cc..0000000 --- a/server/.eslintrc.json +++ /dev/null @@ -1,51 +0,0 @@ -{ - "root": true, - "env": { - "node": true, - "jest": true - }, - "plugins": [ - "@typescript-eslint/eslint-plugin" - ], - "extends": [ - "airbnb-base", - "airbnb-typescript/base", - "eslint:recommended", - "plugin:@typescript-eslint/recommended" - ], - "parser": "@typescript-eslint/parser", - "parserOptions": { - "project": "tsconfig.json", - "sourceType": "module" - }, - "rules": { - "no-param-reassign": "off", - "class-methods-use-this": "warn", - "@typescript-eslint/interface-name-prefix": "off", - "@typescript-eslint/explicit-function-return-type": "error", - "@typescript-eslint/explicit-module-boundary-types": "off", - "@typescript-eslint/no-explicit-any": "error", - "max-len": [ - "error", - { - "code": 80, - "tabWidth": 2, - "ignoreComments": true, - "ignoreTrailingComments": true, - "ignoreUrls": true, - "ignoreStrings": true, - "ignoreTemplateLiterals": true, - "ignoreRegExpLiterals": true - } - ], - "max-lines-per-function": [ - "warn", - { - "max": 40, - "skipBlankLines": true, - "skipComments": true, - "IIFEs": true - } - ] - } -} diff --git a/server/.idea/.gitignore b/server/.idea/.gitignore index df8562c..8d7d3ef 100644 --- a/server/.idea/.gitignore +++ b/server/.idea/.gitignore @@ -1,6 +1,6 @@ # Default ignored files /shelf/ /workspace.xml -misc.xml +/misc.xml # Editor-based HTTP Client requests /httpRequests/ diff --git a/server/.idea/codeStyles/Project.xml b/server/.idea/codeStyles/Project.xml new file mode 100644 index 0000000..20798be --- /dev/null +++ b/server/.idea/codeStyles/Project.xml @@ -0,0 +1,52 @@ + + + + \ No newline at end of file diff --git a/server/.idea/codeStyles/codeStyleConfig.xml b/server/.idea/codeStyles/codeStyleConfig.xml new file mode 100644 index 0000000..79ee123 --- /dev/null +++ b/server/.idea/codeStyles/codeStyleConfig.xml @@ -0,0 +1,5 @@ + + + + \ No newline at end of file diff --git a/server/.idea/jsLinters/eslint.xml b/server/.idea/jsLinters/eslint.xml deleted file mode 100644 index 541945b..0000000 --- a/server/.idea/jsLinters/eslint.xml +++ /dev/null @@ -1,6 +0,0 @@ - - - - - \ No newline at end of file diff --git a/server/.idea/prettier.xml b/server/.idea/prettier.xml new file mode 100644 index 0000000..b0ab31a --- /dev/null +++ b/server/.idea/prettier.xml @@ -0,0 +1,6 @@ + + + + + \ No newline at end of file diff --git a/server/.prettierrc b/server/.prettierrc new file mode 100644 index 0000000..dcb7279 --- /dev/null +++ b/server/.prettierrc @@ -0,0 +1,4 @@ +{ + "singleQuote": true, + "trailingComma": "all" +} \ No newline at end of file diff --git a/server/package-lock.json b/server/package-lock.json index 8db2af1..d28f1f7 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -23,12 +23,13 @@ "@types/jest": "29.2.4", "@types/node": "18.11.18", "@types/supertest": "^2.0.11", - "@typescript-eslint/eslint-plugin": "^5.50.0", - "@typescript-eslint/parser": "^5.50.0", - "eslint": "^8.2.0", - "eslint-config-airbnb-base": "^15.0.0", - "eslint-config-airbnb-typescript": "^17.0.0", + "@typescript-eslint/eslint-plugin": "^5.0.0", + "@typescript-eslint/parser": "^5.0.0", + "eslint": "^8.0.1", + "eslint-config-prettier": "^8.3.0", + "eslint-plugin-prettier": "^4.0.0", "jest": "29.3.1", + "prettier": "^2.3.2", "source-map-support": "^0.5.20", "supertest": "^6.1.3", "ts-jest": "29.0.3", @@ -872,19 +873,32 @@ "dev": true }, "node_modules/@humanwhocodes/config-array": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.6.0.tgz", - "integrity": "sha512-JQlEKbcgEUjBFhLIF4iqM7u/9lwgHRBcpHrmUNCALK0Q3amXN6lxdoXLnF0sm11E9VqTmBALR87IlUg1bZ8A9A==", + "version": "0.11.8", + "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.11.8.tgz", + "integrity": "sha512-UybHIJzJnR5Qc/MsD9Kr+RpO2h+/P1GhOwdiLPXK5TWk5sgTdu88bTD9UP+CKbPPh5Rni1u0GjAdYQLemG8g+g==", "dev": true, "dependencies": { - "@humanwhocodes/object-schema": "^1.2.0", + "@humanwhocodes/object-schema": "^1.2.1", "debug": "^4.1.1", - "minimatch": "^3.0.4" + "minimatch": "^3.0.5" }, "engines": { "node": ">=10.10.0" } }, + "node_modules/@humanwhocodes/module-importer": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz", + "integrity": "sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==", + "dev": true, + "engines": { + "node": ">=12.22" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/nzakas" + } + }, "node_modules/@humanwhocodes/object-schema": { "version": "1.2.1", "resolved": "https://registry.npmjs.org/@humanwhocodes/object-schema/-/object-schema-1.2.1.tgz", @@ -1000,16 +1014,16 @@ } }, "node_modules/@jest/console": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/@jest/console/-/console-29.4.1.tgz", - "integrity": "sha512-m+XpwKSi3PPM9znm5NGS8bBReeAJJpSkL1OuFCqaMaJL2YX9YXLkkI+MBchMPwu+ZuM2rynL51sgfkQteQ1CKQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/console/-/console-29.4.2.tgz", + "integrity": "sha512-0I/rEJwMpV9iwi9cDEnT71a5nNGK9lj8Z4+1pRAU2x/thVXCDnaTGrvxyK+cAqZTFVFCiR+hfVrP4l2m+dCmQg==", "dev": true, "dependencies": { - "@jest/types": "^29.4.1", + "@jest/types": "^29.4.2", "@types/node": "*", "chalk": "^4.0.0", - "jest-message-util": "^29.4.1", - "jest-util": "^29.4.1", + "jest-message-util": "^29.4.2", + "jest-util": "^29.4.2", "slash": "^3.0.0" }, "engines": { @@ -1033,37 +1047,37 @@ } }, "node_modules/@jest/core": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/@jest/core/-/core-29.4.1.tgz", - "integrity": "sha512-RXFTohpBqpaTebNdg5l3I5yadnKo9zLBajMT0I38D0tDhreVBYv3fA8kywthI00sWxPztWLD3yjiUkewwu/wKA==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/core/-/core-29.4.2.tgz", + "integrity": "sha512-KGuoQah0P3vGNlaS/l9/wQENZGNKGoWb+OPxh3gz+YzG7/XExvYu34MzikRndQCdM2S0tzExN4+FL37i6gZmCQ==", "dev": true, "dependencies": { - "@jest/console": "^29.4.1", - "@jest/reporters": "^29.4.1", - "@jest/test-result": "^29.4.1", - "@jest/transform": "^29.4.1", - "@jest/types": "^29.4.1", + "@jest/console": "^29.4.2", + "@jest/reporters": "^29.4.2", + "@jest/test-result": "^29.4.2", + "@jest/transform": "^29.4.2", + "@jest/types": "^29.4.2", "@types/node": "*", "ansi-escapes": "^4.2.1", "chalk": "^4.0.0", "ci-info": "^3.2.0", "exit": "^0.1.2", "graceful-fs": "^4.2.9", - "jest-changed-files": "^29.4.0", - "jest-config": "^29.4.1", - "jest-haste-map": "^29.4.1", - "jest-message-util": "^29.4.1", - "jest-regex-util": "^29.2.0", - "jest-resolve": "^29.4.1", - "jest-resolve-dependencies": "^29.4.1", - "jest-runner": "^29.4.1", - "jest-runtime": "^29.4.1", - "jest-snapshot": "^29.4.1", - "jest-util": "^29.4.1", - "jest-validate": "^29.4.1", - "jest-watcher": "^29.4.1", + "jest-changed-files": "^29.4.2", + "jest-config": "^29.4.2", + "jest-haste-map": "^29.4.2", + "jest-message-util": "^29.4.2", + "jest-regex-util": "^29.4.2", + "jest-resolve": "^29.4.2", + "jest-resolve-dependencies": "^29.4.2", + "jest-runner": "^29.4.2", + "jest-runtime": "^29.4.2", + "jest-snapshot": "^29.4.2", + "jest-util": "^29.4.2", + "jest-validate": "^29.4.2", + "jest-watcher": "^29.4.2", "micromatch": "^4.0.4", - "pretty-format": "^29.4.1", + "pretty-format": "^29.4.2", "slash": "^3.0.0", "strip-ansi": "^6.0.0" }, @@ -1096,88 +1110,88 @@ } }, "node_modules/@jest/environment": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/@jest/environment/-/environment-29.4.1.tgz", - "integrity": "sha512-pJ14dHGSQke7Q3mkL/UZR9ZtTOxqskZaC91NzamEH4dlKRt42W+maRBXiw/LWkdJe+P0f/zDR37+SPMplMRlPg==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/environment/-/environment-29.4.2.tgz", + "integrity": "sha512-JKs3VUtse0vQfCaFGJRX1bir9yBdtasxziSyu+pIiEllAQOe4oQhdCYIf3+Lx+nGglFktSKToBnRJfD5QKp+NQ==", "dev": true, "dependencies": { - "@jest/fake-timers": "^29.4.1", - "@jest/types": "^29.4.1", + "@jest/fake-timers": "^29.4.2", + "@jest/types": "^29.4.2", "@types/node": "*", - "jest-mock": "^29.4.1" + "jest-mock": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/@jest/expect": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/@jest/expect/-/expect-29.4.1.tgz", - "integrity": "sha512-ZxKJP5DTUNF2XkpJeZIzvnzF1KkfrhEF6Rz0HGG69fHl6Bgx5/GoU3XyaeFYEjuuKSOOsbqD/k72wFvFxc3iTw==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/expect/-/expect-29.4.2.tgz", + "integrity": "sha512-NUAeZVApzyaeLjfWIV/64zXjA2SS+NuUPHpAlO7IwVMGd5Vf9szTl9KEDlxY3B4liwLO31os88tYNHl6cpjtKQ==", "dev": true, "dependencies": { - "expect": "^29.4.1", - "jest-snapshot": "^29.4.1" + "expect": "^29.4.2", + "jest-snapshot": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/@jest/expect-utils": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/@jest/expect-utils/-/expect-utils-29.4.1.tgz", - "integrity": "sha512-w6YJMn5DlzmxjO00i9wu2YSozUYRBhIoJ6nQwpMYcBMtiqMGJm1QBzOf6DDgRao8dbtpDoaqLg6iiQTvv0UHhQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/expect-utils/-/expect-utils-29.4.2.tgz", + "integrity": "sha512-Dd3ilDJpBnqa0GiPN7QrudVs0cczMMHtehSo2CSTjm3zdHx0RcpmhFNVEltuEFeqfLIyWKFI224FsMSQ/nsJQA==", "dev": true, "dependencies": { - "jest-get-type": "^29.2.0" + "jest-get-type": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/@jest/fake-timers": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/@jest/fake-timers/-/fake-timers-29.4.1.tgz", - "integrity": "sha512-/1joI6rfHFmmm39JxNfmNAO3Nwm6Y0VoL5fJDy7H1AtWrD1CgRtqJbN9Ld6rhAkGO76qqp4cwhhxJ9o9kYjQMw==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/fake-timers/-/fake-timers-29.4.2.tgz", + "integrity": "sha512-Ny1u0Wg6kCsHFWq7A/rW/tMhIedq2siiyHyLpHCmIhP7WmcAmd2cx95P+0xtTZlj5ZbJxIRQi4OPydZZUoiSQQ==", "dev": true, "dependencies": { - "@jest/types": "^29.4.1", + "@jest/types": "^29.4.2", "@sinonjs/fake-timers": "^10.0.2", "@types/node": "*", - "jest-message-util": "^29.4.1", - "jest-mock": "^29.4.1", - "jest-util": "^29.4.1" + "jest-message-util": "^29.4.2", + "jest-mock": "^29.4.2", + "jest-util": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/@jest/globals": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/@jest/globals/-/globals-29.4.1.tgz", - "integrity": "sha512-znoK2EuFytbHH0ZSf2mQK2K1xtIgmaw4Da21R2C/NE/+NnItm5mPEFQmn8gmF3f0rfOlmZ3Y3bIf7bFj7DHxAA==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/globals/-/globals-29.4.2.tgz", + "integrity": "sha512-zCk70YGPzKnz/I9BNFDPlK+EuJLk21ur/NozVh6JVM86/YYZtZHqxFFQ62O9MWq7uf3vIZnvNA0BzzrtxD9iyg==", "dev": true, "dependencies": { - "@jest/environment": "^29.4.1", - "@jest/expect": "^29.4.1", - "@jest/types": "^29.4.1", - "jest-mock": "^29.4.1" + "@jest/environment": "^29.4.2", + "@jest/expect": "^29.4.2", + "@jest/types": "^29.4.2", + "jest-mock": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/@jest/reporters": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/@jest/reporters/-/reporters-29.4.1.tgz", - "integrity": "sha512-AISY5xpt2Xpxj9R6y0RF1+O6GRy9JsGa8+vK23Lmzdy1AYcpQn5ItX79wJSsTmfzPKSAcsY1LNt/8Y5Xe5LOSg==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/reporters/-/reporters-29.4.2.tgz", + "integrity": "sha512-10yw6YQe75zCgYcXgEND9kw3UZZH5tJeLzWv4vTk/2mrS1aY50A37F+XT2hPO5OqQFFnUWizXD8k1BMiATNfUw==", "dev": true, "dependencies": { "@bcoe/v8-coverage": "^0.2.3", - "@jest/console": "^29.4.1", - "@jest/test-result": "^29.4.1", - "@jest/transform": "^29.4.1", - "@jest/types": "^29.4.1", + "@jest/console": "^29.4.2", + "@jest/test-result": "^29.4.2", + "@jest/transform": "^29.4.2", + "@jest/types": "^29.4.2", "@jridgewell/trace-mapping": "^0.3.15", "@types/node": "*", "chalk": "^4.0.0", @@ -1190,9 +1204,9 @@ "istanbul-lib-report": "^3.0.0", "istanbul-lib-source-maps": "^4.0.0", "istanbul-reports": "^3.1.3", - "jest-message-util": "^29.4.1", - "jest-util": "^29.4.1", - "jest-worker": "^29.4.1", + "jest-message-util": "^29.4.2", + "jest-util": "^29.4.2", + "jest-worker": "^29.4.2", "slash": "^3.0.0", "string-length": "^4.0.1", "strip-ansi": "^6.0.0", @@ -1227,9 +1241,9 @@ } }, "node_modules/@jest/schemas": { - "version": "29.4.0", - "resolved": "https://registry.npmjs.org/@jest/schemas/-/schemas-29.4.0.tgz", - "integrity": "sha512-0E01f/gOZeNTG76i5eWWSupvSHaIINrTie7vCyjiYFKgzNdyEGd12BUv4oNBFHOqlHDbtoJi3HrQ38KCC90NsQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/schemas/-/schemas-29.4.2.tgz", + "integrity": "sha512-ZrGzGfh31NtdVH8tn0mgJw4khQuNHiKqdzJAFbCaERbyCP9tHlxWuL/mnMu8P7e/+k4puWjI1NOzi/sFsjce/g==", "dev": true, "dependencies": { "@sinclair/typebox": "^0.25.16" @@ -1239,9 +1253,9 @@ } }, "node_modules/@jest/source-map": { - "version": "29.2.0", - "resolved": "https://registry.npmjs.org/@jest/source-map/-/source-map-29.2.0.tgz", - "integrity": "sha512-1NX9/7zzI0nqa6+kgpSdKPK+WU1p+SJk3TloWZf5MzPbxri9UEeXX5bWZAPCzbQcyuAzubcdUHA7hcNznmRqWQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/source-map/-/source-map-29.4.2.tgz", + "integrity": "sha512-tIoqV5ZNgYI9XCKXMqbYe5JbumcvyTgNN+V5QW4My033lanijvCD0D4PI9tBw4pRTqWOc00/7X3KVvUh+qnF4Q==", "dev": true, "dependencies": { "@jridgewell/trace-mapping": "^0.3.15", @@ -1253,13 +1267,13 @@ } }, "node_modules/@jest/test-result": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/@jest/test-result/-/test-result-29.4.1.tgz", - "integrity": "sha512-WRt29Lwt+hEgfN8QDrXqXGgCTidq1rLyFqmZ4lmJOpVArC8daXrZWkWjiaijQvgd3aOUj2fM8INclKHsQW9YyQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/test-result/-/test-result-29.4.2.tgz", + "integrity": "sha512-HZsC3shhiHVvMtP+i55MGR5bPcc3obCFbA5bzIOb8pCjwBZf11cZliJncCgaVUbC5yoQNuGqCkC0Q3t6EItxZA==", "dev": true, "dependencies": { - "@jest/console": "^29.4.1", - "@jest/types": "^29.4.1", + "@jest/console": "^29.4.2", + "@jest/types": "^29.4.2", "@types/istanbul-lib-coverage": "^2.0.0", "collect-v8-coverage": "^1.0.0" }, @@ -1268,14 +1282,14 @@ } }, "node_modules/@jest/test-sequencer": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/@jest/test-sequencer/-/test-sequencer-29.4.1.tgz", - "integrity": "sha512-v5qLBNSsM0eHzWLXsQ5fiB65xi49A3ILPSFQKPXzGL4Vyux0DPZAIN7NAFJa9b4BiTDP9MBF/Zqc/QA1vuiJ0w==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/test-sequencer/-/test-sequencer-29.4.2.tgz", + "integrity": "sha512-9Z2cVsD6CcObIVrWigHp2McRJhvCxL27xHtrZFgNC1RwnoSpDx6fZo8QYjJmziFlW9/hr78/3sxF54S8B6v8rg==", "dev": true, "dependencies": { - "@jest/test-result": "^29.4.1", + "@jest/test-result": "^29.4.2", "graceful-fs": "^4.2.9", - "jest-haste-map": "^29.4.1", + "jest-haste-map": "^29.4.2", "slash": "^3.0.0" }, "engines": { @@ -1283,26 +1297,26 @@ } }, "node_modules/@jest/transform": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/@jest/transform/-/transform-29.4.1.tgz", - "integrity": "sha512-5w6YJrVAtiAgr0phzKjYd83UPbCXsBRTeYI4BXokv9Er9CcrH9hfXL/crCvP2d2nGOcovPUnlYiLPFLZrkG5Hg==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/transform/-/transform-29.4.2.tgz", + "integrity": "sha512-kf1v5iTJHn7p9RbOsBuc/lcwyPtJaZJt5885C98omWz79NIeD3PfoiiaPSu7JyCyFzNOIzKhmMhQLUhlTL9BvQ==", "dev": true, "dependencies": { "@babel/core": "^7.11.6", - "@jest/types": "^29.4.1", + "@jest/types": "^29.4.2", "@jridgewell/trace-mapping": "^0.3.15", "babel-plugin-istanbul": "^6.1.1", "chalk": "^4.0.0", "convert-source-map": "^2.0.0", "fast-json-stable-stringify": "^2.1.0", "graceful-fs": "^4.2.9", - "jest-haste-map": "^29.4.1", - "jest-regex-util": "^29.2.0", - "jest-util": "^29.4.1", + "jest-haste-map": "^29.4.2", + "jest-regex-util": "^29.4.2", + "jest-util": "^29.4.2", "micromatch": "^4.0.4", "pirates": "^4.0.4", "slash": "^3.0.0", - "write-file-atomic": "^5.0.0" + "write-file-atomic": "^4.0.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" @@ -1325,12 +1339,12 @@ } }, "node_modules/@jest/types": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/@jest/types/-/types-29.4.1.tgz", - "integrity": "sha512-zbrAXDUOnpJ+FMST2rV7QZOgec8rskg2zv8g2ajeqitp4tvZiyqTCYXANrKsM+ryj5o+LI+ZN2EgU9drrkiwSA==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-29.4.2.tgz", + "integrity": "sha512-CKlngyGP0fwlgC1BRUtPZSiWLBhyS9dKwKmyGxk8Z6M82LBEGB2aLQSg+U1MyLsU+M7UjnlLllBM2BLWKVm/Uw==", "dev": true, "dependencies": { - "@jest/schemas": "^29.4.0", + "@jest/schemas": "^29.4.2", "@types/istanbul-lib-coverage": "^2.0.0", "@types/istanbul-reports": "^3.0.0", "@types/node": "*", @@ -1496,9 +1510,9 @@ } }, "node_modules/@nestjs/common": { - "version": "9.3.2", - "resolved": "https://registry.npmjs.org/@nestjs/common/-/common-9.3.2.tgz", - "integrity": "sha512-YUqY9qPMxiMqO/pRNXJehR18LFL6Y9BN5Qn0FylVbdpKd7/QKZHVWRKNaAYNu0mGfyJhRJI6oEr/1Tn5GEo6GQ==", + "version": "9.3.8", + "resolved": "https://registry.npmjs.org/@nestjs/common/-/common-9.3.8.tgz", + "integrity": "sha512-CM2+pSDvOrEXETCYciXQPYP9iCral3zu6GHbQkP1PKyyZDtvVsRNoVJ/zVFdmEUwsqvsV75X1VvyXt5w4OA1mg==", "dependencies": { "iterare": "1.2.1", "tslib": "2.5.0", @@ -1528,18 +1542,17 @@ } }, "node_modules/@nestjs/core": { - "version": "9.3.2", - "resolved": "https://registry.npmjs.org/@nestjs/core/-/core-9.3.2.tgz", - "integrity": "sha512-79h4RvGAGFIIZJWIXqZ8xvhK/kIY6Fay7a1P0W4v7AUZsMIuNksct0uMzHaBqMT0lo+Ei+gU8PaWvzZt5lZvJw==", + "version": "9.3.8", + "resolved": "https://registry.npmjs.org/@nestjs/core/-/core-9.3.8.tgz", + "integrity": "sha512-LtKMF7qzlSN+B4lItxHc/r9IJTSgURZAT5LqMtZynmYDpIkkiG7UrKKx/jAolUF41SGkKXzC6Lh+yralZ97i5A==", "hasInstallScript": true, "dependencies": { "@nuxtjs/opencollective": "0.3.2", "fast-safe-stringify": "2.1.1", "iterare": "1.2.1", - "object-hash": "3.0.0", "path-to-regexp": "3.2.0", "tslib": "2.5.0", - "uuid": "9.0.0" + "uid": "2.0.1" }, "funding": { "type": "opencollective", @@ -1566,9 +1579,9 @@ } }, "node_modules/@nestjs/platform-express": { - "version": "9.3.2", - "resolved": "https://registry.npmjs.org/@nestjs/platform-express/-/platform-express-9.3.2.tgz", - "integrity": "sha512-hzLfUcJIFw8NIPlG88QJr+uSgJzkBkhxVsHGtRs+rNShzlMNfX63CPbkI4yfG4Eq0s8oYe598p6OE5O1z924Dg==", + "version": "9.3.8", + "resolved": "https://registry.npmjs.org/@nestjs/platform-express/-/platform-express-9.3.8.tgz", + "integrity": "sha512-VY0tZbMPXyLypIm1FwpFC+xv0DR0RWx+M4baD9JiLmh+jdojm/blfzoFqVMRoZ33F9Q3iUjrQfSJOfgbbTiv5g==", "dependencies": { "body-parser": "1.20.1", "cors": "2.8.5", @@ -1692,9 +1705,9 @@ "dev": true }, "node_modules/@nestjs/testing": { - "version": "9.3.2", - "resolved": "https://registry.npmjs.org/@nestjs/testing/-/testing-9.3.2.tgz", - "integrity": "sha512-A1DleYwUpA/MX4XLTOJYEkhEjdI0HyujTmOUoPzSplAPWXbR48DTtY3Pu3A/qM7A8JwPzfB37glFUAJvFFOYpg==", + "version": "9.3.8", + "resolved": "https://registry.npmjs.org/@nestjs/testing/-/testing-9.3.8.tgz", + "integrity": "sha512-QyGOfrEOWbT8mi7ruYnh/taKuHDv4caAyf4WZ1YKkGn4tCeTKKNXSvV/y+NoO5o9Li/sLiq9B8EmleB1fxGajw==", "dev": true, "dependencies": { "tslib": "2.5.0" @@ -1997,13 +2010,6 @@ "integrity": "sha512-wOuvG1SN4Us4rez+tylwwwCV1psiNVOkJeM3AUWUNWg/jDQY2+HE/444y5gc+jBmRqASOm2Oeh5c1axHobwRKQ==", "dev": true }, - "node_modules/@types/json5": { - "version": "0.0.29", - "resolved": "https://registry.npmjs.org/@types/json5/-/json5-0.0.29.tgz", - "integrity": "sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==", - "dev": true, - "peer": true - }, "node_modules/@types/mime": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/@types/mime/-/mime-3.0.1.tgz", @@ -2097,14 +2103,14 @@ "dev": true }, "node_modules/@typescript-eslint/eslint-plugin": { - "version": "5.50.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.50.0.tgz", - "integrity": "sha512-vwksQWSFZiUhgq3Kv7o1Jcj0DUNylwnIlGvKvLLYsq8pAWha6/WCnXUeaSoNNha/K7QSf2+jvmkxggC1u3pIwQ==", + "version": "5.51.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.51.0.tgz", + "integrity": "sha512-wcAwhEWm1RgNd7dxD/o+nnLW8oH+6RK1OGnmbmkj/GGoDPV1WWMVP0FXYQBivKHdwM1pwii3bt//RC62EriIUQ==", "dev": true, "dependencies": { - "@typescript-eslint/scope-manager": "5.50.0", - "@typescript-eslint/type-utils": "5.50.0", - "@typescript-eslint/utils": "5.50.0", + "@typescript-eslint/scope-manager": "5.51.0", + "@typescript-eslint/type-utils": "5.51.0", + "@typescript-eslint/utils": "5.51.0", "debug": "^4.3.4", "grapheme-splitter": "^1.0.4", "ignore": "^5.2.0", @@ -2131,14 +2137,14 @@ } }, "node_modules/@typescript-eslint/parser": { - "version": "5.50.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.50.0.tgz", - "integrity": "sha512-KCcSyNaogUDftK2G9RXfQyOCt51uB5yqC6pkUYqhYh8Kgt+DwR5M0EwEAxGPy/+DH6hnmKeGsNhiZRQxjH71uQ==", + "version": "5.51.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.51.0.tgz", + "integrity": "sha512-fEV0R9gGmfpDeRzJXn+fGQKcl0inIeYobmmUWijZh9zA7bxJ8clPhV9up2ZQzATxAiFAECqPQyMDB4o4B81AaA==", "dev": true, "dependencies": { - "@typescript-eslint/scope-manager": "5.50.0", - "@typescript-eslint/types": "5.50.0", - "@typescript-eslint/typescript-estree": "5.50.0", + "@typescript-eslint/scope-manager": "5.51.0", + "@typescript-eslint/types": "5.51.0", + "@typescript-eslint/typescript-estree": "5.51.0", "debug": "^4.3.4" }, "engines": { @@ -2158,13 +2164,13 @@ } }, "node_modules/@typescript-eslint/scope-manager": { - "version": "5.50.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.50.0.tgz", - "integrity": "sha512-rt03kaX+iZrhssaT974BCmoUikYtZI24Vp/kwTSy841XhiYShlqoshRFDvN1FKKvU2S3gK+kcBW1EA7kNUrogg==", + "version": "5.51.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.51.0.tgz", + "integrity": "sha512-gNpxRdlx5qw3yaHA0SFuTjW4rxeYhpHxt491PEcKF8Z6zpq0kMhe0Tolxt0qjlojS+/wArSDlj/LtE69xUJphQ==", "dev": true, "dependencies": { - "@typescript-eslint/types": "5.50.0", - "@typescript-eslint/visitor-keys": "5.50.0" + "@typescript-eslint/types": "5.51.0", + "@typescript-eslint/visitor-keys": "5.51.0" }, "engines": { "node": "^12.22.0 || ^14.17.0 || >=16.0.0" @@ -2175,13 +2181,13 @@ } }, "node_modules/@typescript-eslint/type-utils": { - "version": "5.50.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.50.0.tgz", - "integrity": "sha512-dcnXfZ6OGrNCO7E5UY/i0ktHb7Yx1fV6fnQGGrlnfDhilcs6n19eIRcvLBqx6OQkrPaFlDPk3OJ0WlzQfrV0bQ==", + "version": "5.51.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.51.0.tgz", + "integrity": "sha512-QHC5KKyfV8sNSyHqfNa0UbTbJ6caB8uhcx2hYcWVvJAZYJRBo5HyyZfzMdRx8nvS+GyMg56fugMzzWnojREuQQ==", "dev": true, "dependencies": { - "@typescript-eslint/typescript-estree": "5.50.0", - "@typescript-eslint/utils": "5.50.0", + "@typescript-eslint/typescript-estree": "5.51.0", + "@typescript-eslint/utils": "5.51.0", "debug": "^4.3.4", "tsutils": "^3.21.0" }, @@ -2202,9 +2208,9 @@ } }, "node_modules/@typescript-eslint/types": { - "version": "5.50.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.50.0.tgz", - "integrity": "sha512-atruOuJpir4OtyNdKahiHZobPKFvZnBnfDiyEaBf6d9vy9visE7gDjlmhl+y29uxZ2ZDgvXijcungGFjGGex7w==", + "version": "5.51.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.51.0.tgz", + "integrity": "sha512-SqOn0ANn/v6hFn0kjvLwiDi4AzR++CBZz0NV5AnusT2/3y32jdc0G4woXPWHCumWtUXZKPAS27/9vziSsC9jnw==", "dev": true, "engines": { "node": "^12.22.0 || ^14.17.0 || >=16.0.0" @@ -2215,13 +2221,13 @@ } }, "node_modules/@typescript-eslint/typescript-estree": { - "version": "5.50.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.50.0.tgz", - "integrity": "sha512-Gq4zapso+OtIZlv8YNAStFtT6d05zyVCK7Fx3h5inlLBx2hWuc/0465C2mg/EQDDU2LKe52+/jN4f0g9bd+kow==", + "version": "5.51.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.51.0.tgz", + "integrity": "sha512-TSkNupHvNRkoH9FMA3w7TazVFcBPveAAmb7Sz+kArY6sLT86PA5Vx80cKlYmd8m3Ha2SwofM1KwraF24lM9FvA==", "dev": true, "dependencies": { - "@typescript-eslint/types": "5.50.0", - "@typescript-eslint/visitor-keys": "5.50.0", + "@typescript-eslint/types": "5.51.0", + "@typescript-eslint/visitor-keys": "5.51.0", "debug": "^4.3.4", "globby": "^11.1.0", "is-glob": "^4.0.3", @@ -2242,16 +2248,16 @@ } }, "node_modules/@typescript-eslint/utils": { - "version": "5.50.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.50.0.tgz", - "integrity": "sha512-v/AnUFImmh8G4PH0NDkf6wA8hujNNcrwtecqW4vtQ1UOSNBaZl49zP1SHoZ/06e+UiwzHpgb5zP5+hwlYYWYAw==", + "version": "5.51.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.51.0.tgz", + "integrity": "sha512-76qs+5KWcaatmwtwsDJvBk4H76RJQBFe+Gext0EfJdC3Vd2kpY2Pf//OHHzHp84Ciw0/rYoGTDnIAr3uWhhJYw==", "dev": true, "dependencies": { "@types/json-schema": "^7.0.9", "@types/semver": "^7.3.12", - "@typescript-eslint/scope-manager": "5.50.0", - "@typescript-eslint/types": "5.50.0", - "@typescript-eslint/typescript-estree": "5.50.0", + "@typescript-eslint/scope-manager": "5.51.0", + "@typescript-eslint/types": "5.51.0", + "@typescript-eslint/typescript-estree": "5.51.0", "eslint-scope": "^5.1.1", "eslint-utils": "^3.0.0", "semver": "^7.3.7" @@ -2268,12 +2274,12 @@ } }, "node_modules/@typescript-eslint/visitor-keys": { - "version": "5.50.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.50.0.tgz", - "integrity": "sha512-cdMeD9HGu6EXIeGOh2yVW6oGf9wq8asBgZx7nsR/D36gTfQ0odE5kcRYe5M81vjEFAcPeugXrHg78Imu55F6gg==", + "version": "5.51.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.51.0.tgz", + "integrity": "sha512-Oh2+eTdjHjOFjKA27sxESlA87YPSOJafGCR0md5oeMdh1ZcCfAGCIOL216uTBAkAIptvLIfKQhl7lHxMJet4GQ==", "dev": true, "dependencies": { - "@typescript-eslint/types": "5.50.0", + "@typescript-eslint/types": "5.51.0", "eslint-visitor-keys": "^3.3.0" }, "engines": { @@ -2620,26 +2626,6 @@ "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", "integrity": "sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==" }, - "node_modules/array-includes": { - "version": "3.1.6", - "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.1.6.tgz", - "integrity": "sha512-sgTbLvL6cNnw24FnbaDyjmvddQ2ML8arZsgaJhoABMoplz/4QRhtrYS+alr1BUM1Bwp6dhx8vVCBSLG+StwOFw==", - "dev": true, - "peer": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.4", - "es-abstract": "^1.20.4", - "get-intrinsic": "^1.1.3", - "is-string": "^1.0.7" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/array-union": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/array-union/-/array-union-2.1.0.tgz", @@ -2649,44 +2635,6 @@ "node": ">=8" } }, - "node_modules/array.prototype.flat": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/array.prototype.flat/-/array.prototype.flat-1.3.1.tgz", - "integrity": "sha512-roTU0KWIOmJ4DRLmwKd19Otg0/mT3qPNt0Qb3GWW8iObuZXxrjB/pzn0R3hqpRSWg4HCwqx+0vwOnWnvlOyeIA==", - "dev": true, - "peer": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.4", - "es-abstract": "^1.20.4", - "es-shim-unscopables": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/array.prototype.flatmap": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/array.prototype.flatmap/-/array.prototype.flatmap-1.3.1.tgz", - "integrity": "sha512-8UGn9O1FDVvMNB0UlLv4voxRMze7+FpHyF5mSMRjWHUMlpoDViniy05870VlxhfgTnLbpuwTzvD76MTtWxB/mQ==", - "dev": true, - "peer": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.4", - "es-abstract": "^1.20.4", - "es-shim-unscopables": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/asap": { "version": "2.0.6", "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", @@ -2699,28 +2647,16 @@ "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==", "dev": true }, - "node_modules/available-typed-arrays": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.5.tgz", - "integrity": "sha512-DMD0KiN46eipeziST1LPP/STfDU0sufISXmjSgvVsoU2tqxctQeASejWcfNtxYKqETM1UxQ8sp2OrSBWpHY6sw==", - "dev": true, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/babel-jest": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/babel-jest/-/babel-jest-29.4.1.tgz", - "integrity": "sha512-xBZa/pLSsF/1sNpkgsiT3CmY7zV1kAsZ9OxxtrFqYucnOuRftXAfcJqcDVyOPeN4lttWTwhLdu0T9f8uvoPEUg==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/babel-jest/-/babel-jest-29.4.2.tgz", + "integrity": "sha512-vcghSqhtowXPG84posYkkkzcZsdayFkubUgbE3/1tuGbX7AQtwCkkNA/wIbB0BMjuCPoqTkiDyKN7Ty7d3uwNQ==", "dev": true, "dependencies": { - "@jest/transform": "^29.4.1", + "@jest/transform": "^29.4.2", "@types/babel__core": "^7.1.14", "babel-plugin-istanbul": "^6.1.1", - "babel-preset-jest": "^29.4.0", + "babel-preset-jest": "^29.4.2", "chalk": "^4.0.0", "graceful-fs": "^4.2.9", "slash": "^3.0.0" @@ -2765,9 +2701,9 @@ } }, "node_modules/babel-plugin-jest-hoist": { - "version": "29.4.0", - "resolved": "https://registry.npmjs.org/babel-plugin-jest-hoist/-/babel-plugin-jest-hoist-29.4.0.tgz", - "integrity": "sha512-a/sZRLQJEmsmejQ2rPEUe35nO1+C9dc9O1gplH1SXmJxveQSRUYdBk8yGZG/VOUuZs1u2aHZJusEGoRMbhhwCg==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/babel-plugin-jest-hoist/-/babel-plugin-jest-hoist-29.4.2.tgz", + "integrity": "sha512-5HZRCfMeWypFEonRbEkwWXtNS1sQK159LhRVyRuLzyfVBxDy/34Tr/rg4YVi0SScSJ4fqeaR/OIeceJ/LaQ0pQ==", "dev": true, "dependencies": { "@babel/template": "^7.3.3", @@ -2803,12 +2739,12 @@ } }, "node_modules/babel-preset-jest": { - "version": "29.4.0", - "resolved": "https://registry.npmjs.org/babel-preset-jest/-/babel-preset-jest-29.4.0.tgz", - "integrity": "sha512-fUB9vZflUSM3dO/6M2TCAepTzvA4VkOvl67PjErcrQMGt9Eve7uazaeyCZ2th3UtI7ljpiBJES0F7A1vBRsLZA==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/babel-preset-jest/-/babel-preset-jest-29.4.2.tgz", + "integrity": "sha512-ecWdaLY/8JyfUDr0oELBMpj3R5I1L6ZqG+kRJmwqfHtLWuPrJStR0LUkvUhfykJWTsXXMnohsayN/twltBbDrQ==", "dev": true, "dependencies": { - "babel-plugin-jest-hoist": "^29.4.0", + "babel-plugin-jest-hoist": "^29.4.2", "babel-preset-current-node-syntax": "^1.0.0" }, "engines": { @@ -3064,9 +3000,9 @@ } }, "node_modules/caniuse-lite": { - "version": "1.0.30001450", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001450.tgz", - "integrity": "sha512-qMBmvmQmFXaSxexkjjfMvD5rnDL0+m+dUMZKoDYsGG8iZN29RuYh9eRoMvKsT6uMAWlyUUGDEQGJJYjzCIO9ew==", + "version": "1.0.30001451", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001451.tgz", + "integrity": "sha512-XY7UbUpGRatZzoRft//5xOa69/1iGJRBlrieH6QYrkKLIFn3m7OVEJ81dSrKoy2BnKsdbX5cLrOispZNYo9v2w==", "dev": true, "funding": [ { @@ -3314,12 +3250,6 @@ "typedarray": "^0.0.6" } }, - "node_modules/confusing-browser-globals": { - "version": "1.0.11", - "resolved": "https://registry.npmjs.org/confusing-browser-globals/-/confusing-browser-globals-1.0.11.tgz", - "integrity": "sha512-JsPKdmh8ZkmnHxDk55FZ1TqVLvEQTvoByJZRN9jzI0UjxK/QgAmsphz7PGtqgPieQZ/CQcHWXCR7ATDNhGe+YA==", - "dev": true - }, "node_modules/consola": { "version": "2.15.3", "resolved": "https://registry.npmjs.org/consola/-/consola-2.15.3.tgz", @@ -3472,22 +3402,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/define-properties": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.1.4.tgz", - "integrity": "sha512-uckOqKcfaVvtBdsVkdPv3XjveQJsNQqmhXgRi8uhvWWuPYZCNlzT8qAyblUgNoXdHdjMTzAqeGjAoli8f+bzPA==", - "dev": true, - "dependencies": { - "has-property-descriptors": "^1.0.0", - "object-keys": "^1.1.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/delayed-stream": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", @@ -3543,9 +3457,9 @@ } }, "node_modules/diff-sequences": { - "version": "29.3.1", - "resolved": "https://registry.npmjs.org/diff-sequences/-/diff-sequences-29.3.1.tgz", - "integrity": "sha512-hlM3QR272NXCi4pq+N4Kok4kOp6EsgOM3ZSpJI7Da3UAs+Ttsi8MRmB6trM/lhyzUxGfOgnpkHtgqm5Q/CTcfQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/diff-sequences/-/diff-sequences-29.4.2.tgz", + "integrity": "sha512-R6P0Y6PrsH3n4hUXxL3nns0rbRk6Q33js3ygJBeEpbzLzgcNuJ61+u0RXasFpTKISw99TxUzFnumSnRLsjhLaw==", "dev": true, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" @@ -3581,9 +3495,9 @@ "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==" }, "node_modules/electron-to-chromium": { - "version": "1.4.286", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.286.tgz", - "integrity": "sha512-Vp3CVhmYpgf4iXNKAucoQUDcCrBQX3XLBtwgFqP9BUXuucgvAV9zWp1kYU7LL9j4++s9O+12cb3wMtN4SJy6UQ==", + "version": "1.4.294", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.294.tgz", + "integrity": "sha512-PuHZB3jEN7D8WPPjLmBQAsqQz8tWHlkkB4n0E2OYw8RwVdmBYV0Wn+rUFH8JqYyIRb4HQhhedgxlZL163wqLrQ==", "dev": true }, "node_modules/emittery": { @@ -3634,18 +3548,6 @@ "node": ">=10.13.0" } }, - "node_modules/enquirer": { - "version": "2.3.6", - "resolved": "https://registry.npmjs.org/enquirer/-/enquirer-2.3.6.tgz", - "integrity": "sha512-yjNnPr315/FjS4zIsUxYguYUPP2e1NK4d7E7ZOLiyYCcbFBiTMyID+2wvm2w6+pZ/odMA7cRkjhsPbltwBOrLg==", - "dev": true, - "dependencies": { - "ansi-colors": "^4.1.1" - }, - "engines": { - "node": ">=8.6" - } - }, "node_modules/error-ex": { "version": "1.3.2", "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", @@ -3655,100 +3557,12 @@ "is-arrayish": "^0.2.1" } }, - "node_modules/es-abstract": { - "version": "1.21.1", - "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.21.1.tgz", - "integrity": "sha512-QudMsPOz86xYz/1dG1OuGBKOELjCh99IIWHLzy5znUB6j8xG2yMA7bfTV86VSqKF+Y/H08vQPR+9jyXpuC6hfg==", - "dev": true, - "dependencies": { - "available-typed-arrays": "^1.0.5", - "call-bind": "^1.0.2", - "es-set-tostringtag": "^2.0.1", - "es-to-primitive": "^1.2.1", - "function-bind": "^1.1.1", - "function.prototype.name": "^1.1.5", - "get-intrinsic": "^1.1.3", - "get-symbol-description": "^1.0.0", - "globalthis": "^1.0.3", - "gopd": "^1.0.1", - "has": "^1.0.3", - "has-property-descriptors": "^1.0.0", - "has-proto": "^1.0.1", - "has-symbols": "^1.0.3", - "internal-slot": "^1.0.4", - "is-array-buffer": "^3.0.1", - "is-callable": "^1.2.7", - "is-negative-zero": "^2.0.2", - "is-regex": "^1.1.4", - "is-shared-array-buffer": "^1.0.2", - "is-string": "^1.0.7", - "is-typed-array": "^1.1.10", - "is-weakref": "^1.0.2", - "object-inspect": "^1.12.2", - "object-keys": "^1.1.1", - "object.assign": "^4.1.4", - "regexp.prototype.flags": "^1.4.3", - "safe-regex-test": "^1.0.0", - "string.prototype.trimend": "^1.0.6", - "string.prototype.trimstart": "^1.0.6", - "typed-array-length": "^1.0.4", - "unbox-primitive": "^1.0.2", - "which-typed-array": "^1.1.9" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/es-module-lexer": { "version": "0.9.3", "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-0.9.3.tgz", "integrity": "sha512-1HQ2M2sPtxwnvOvT1ZClHyQDiggdNjURWpY2we6aMKCQiUVxTmVs2UYPLIrD84sS+kMdUwfBSylbJPwNnBrnHQ==", "dev": true }, - "node_modules/es-set-tostringtag": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.0.1.tgz", - "integrity": "sha512-g3OMbtlwY3QewlqAiMLI47KywjWZoEytKr8pf6iTC8uJq5bIAH52Z9pnQ8pVL6whrCto53JZDuUIsifGeLorTg==", - "dev": true, - "dependencies": { - "get-intrinsic": "^1.1.3", - "has": "^1.0.3", - "has-tostringtag": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/es-shim-unscopables": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/es-shim-unscopables/-/es-shim-unscopables-1.0.0.tgz", - "integrity": "sha512-Jm6GPcCdC30eMLbZ2x8z2WuRwAws3zTBBKuusffYVUrNj/GVSUAZ+xKMaUpfNDR5IbyNA5LJbaecoUVbmUcB1w==", - "dev": true, - "peer": true, - "dependencies": { - "has": "^1.0.3" - } - }, - "node_modules/es-to-primitive": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.1.tgz", - "integrity": "sha512-QCOllgZJtaUo9miYBcLChTUaHNjJF3PYs1VidD7AwiEj1kYxKeQTctLAezAOH5ZKRH0g2IgPn6KwB4IT8iRpvA==", - "dev": true, - "dependencies": { - "is-callable": "^1.1.4", - "is-date-object": "^1.0.1", - "is-symbol": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/escalade": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", @@ -3776,49 +3590,50 @@ } }, "node_modules/eslint": { - "version": "8.2.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.2.0.tgz", - "integrity": "sha512-erw7XmM+CLxTOickrimJ1SiF55jiNlVSp2qqm0NuBWPtHYQCegD5ZMaW0c3i5ytPqL+SSLaCxdvQXFPLJn+ABw==", + "version": "8.33.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.33.0.tgz", + "integrity": "sha512-WjOpFQgKK8VrCnAtl8We0SUOy/oVZ5NHykyMiagV1M9r8IFpIJX7DduK6n1mpfhlG7T1NLWm2SuD8QB7KFySaA==", "dev": true, "dependencies": { - "@eslint/eslintrc": "^1.0.4", - "@humanwhocodes/config-array": "^0.6.0", + "@eslint/eslintrc": "^1.4.1", + "@humanwhocodes/config-array": "^0.11.8", + "@humanwhocodes/module-importer": "^1.0.1", + "@nodelib/fs.walk": "^1.2.8", "ajv": "^6.10.0", "chalk": "^4.0.0", "cross-spawn": "^7.0.2", "debug": "^4.3.2", "doctrine": "^3.0.0", - "enquirer": "^2.3.5", "escape-string-regexp": "^4.0.0", - "eslint-scope": "^6.0.0", + "eslint-scope": "^7.1.1", "eslint-utils": "^3.0.0", - "eslint-visitor-keys": "^3.0.0", - "espree": "^9.0.0", + "eslint-visitor-keys": "^3.3.0", + "espree": "^9.4.0", "esquery": "^1.4.0", "esutils": "^2.0.2", "fast-deep-equal": "^3.1.3", "file-entry-cache": "^6.0.1", - "functional-red-black-tree": "^1.0.1", - "glob-parent": "^6.0.1", - "globals": "^13.6.0", - "ignore": "^4.0.6", + "find-up": "^5.0.0", + "glob-parent": "^6.0.2", + "globals": "^13.19.0", + "grapheme-splitter": "^1.0.4", + "ignore": "^5.2.0", "import-fresh": "^3.0.0", "imurmurhash": "^0.1.4", "is-glob": "^4.0.0", + "is-path-inside": "^3.0.3", + "js-sdsl": "^4.1.4", "js-yaml": "^4.1.0", "json-stable-stringify-without-jsonify": "^1.0.1", "levn": "^0.4.1", "lodash.merge": "^4.6.2", - "minimatch": "^3.0.4", + "minimatch": "^3.1.2", "natural-compare": "^1.4.0", "optionator": "^0.9.1", - "progress": "^2.0.0", "regexpp": "^3.2.0", - "semver": "^7.2.1", "strip-ansi": "^6.0.1", "strip-json-comments": "^3.1.0", - "text-table": "^0.2.0", - "v8-compile-cache": "^2.0.3" + "text-table": "^0.2.0" }, "bin": { "eslint": "bin/eslint.js" @@ -3830,198 +3645,39 @@ "url": "https://opencollective.com/eslint" } }, - "node_modules/eslint-config-airbnb-base": { - "version": "15.0.0", - "resolved": "https://registry.npmjs.org/eslint-config-airbnb-base/-/eslint-config-airbnb-base-15.0.0.tgz", - "integrity": "sha512-xaX3z4ZZIcFLvh2oUNvcX5oEofXda7giYmuplVxoOg5A7EXJMrUyqRgR+mhDhPK8LZ4PttFOBvCYDbX3sUoUig==", - "dev": true, - "dependencies": { - "confusing-browser-globals": "^1.0.10", - "object.assign": "^4.1.2", - "object.entries": "^1.1.5", - "semver": "^6.3.0" - }, - "engines": { - "node": "^10.12.0 || >=12.0.0" - }, - "peerDependencies": { - "eslint": "^7.32.0 || ^8.2.0", - "eslint-plugin-import": "^2.25.2" - } - }, - "node_modules/eslint-config-airbnb-base/node_modules/semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", + "node_modules/eslint-config-prettier": { + "version": "8.6.0", + "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-8.6.0.tgz", + "integrity": "sha512-bAF0eLpLVqP5oEVUFKpMA+NnRFICwn9X8B5jrR9FcqnYBuPbqWEjTEspPWMj5ye6czoSLDweCzSo3Ko7gGrZaA==", "dev": true, "bin": { - "semver": "bin/semver.js" - } - }, - "node_modules/eslint-config-airbnb-typescript": { - "version": "17.0.0", - "resolved": "https://registry.npmjs.org/eslint-config-airbnb-typescript/-/eslint-config-airbnb-typescript-17.0.0.tgz", - "integrity": "sha512-elNiuzD0kPAPTXjFWg+lE24nMdHMtuxgYoD30OyMD6yrW1AhFZPAg27VX7d3tzOErw+dgJTNWfRSDqEcXb4V0g==", - "dev": true, - "dependencies": { - "eslint-config-airbnb-base": "^15.0.0" + "eslint-config-prettier": "bin/cli.js" }, "peerDependencies": { - "@typescript-eslint/eslint-plugin": "^5.13.0", - "@typescript-eslint/parser": "^5.0.0", - "eslint": "^7.32.0 || ^8.2.0", - "eslint-plugin-import": "^2.25.3" - } - }, - "node_modules/eslint-import-resolver-node": { - "version": "0.3.7", - "resolved": "https://registry.npmjs.org/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.7.tgz", - "integrity": "sha512-gozW2blMLJCeFpBwugLTGyvVjNoeo1knonXAcatC6bjPBZitotxdWf7Gimr25N4c0AAOo4eOUfaG82IJPDpqCA==", - "dev": true, - "peer": true, - "dependencies": { - "debug": "^3.2.7", - "is-core-module": "^2.11.0", - "resolve": "^1.22.1" - } - }, - "node_modules/eslint-import-resolver-node/node_modules/debug": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", - "dev": true, - "peer": true, - "dependencies": { - "ms": "^2.1.1" + "eslint": ">=7.0.0" } }, - "node_modules/eslint-module-utils": { - "version": "2.7.4", - "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.7.4.tgz", - "integrity": "sha512-j4GT+rqzCoRKHwURX7pddtIPGySnX9Si/cgMI5ztrcqOPtk5dDEeZ34CQVPphnqkJytlc97Vuk05Um2mJ3gEQA==", + "node_modules/eslint-plugin-prettier": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-4.2.1.tgz", + "integrity": "sha512-f/0rXLXUt0oFYs8ra4w49wYZBG5GKZpAYsJSm6rnYL5uVDjd+zowwMwVZHnAjf4edNrKpCDYfXDgmRE/Ak7QyQ==", "dev": true, - "peer": true, "dependencies": { - "debug": "^3.2.7" + "prettier-linter-helpers": "^1.0.0" }, "engines": { - "node": ">=4" + "node": ">=12.0.0" + }, + "peerDependencies": { + "eslint": ">=7.28.0", + "prettier": ">=2.0.0" }, "peerDependenciesMeta": { - "eslint": { + "eslint-config-prettier": { "optional": true } } }, - "node_modules/eslint-module-utils/node_modules/debug": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", - "dev": true, - "peer": true, - "dependencies": { - "ms": "^2.1.1" - } - }, - "node_modules/eslint-plugin-import": { - "version": "2.27.5", - "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.27.5.tgz", - "integrity": "sha512-LmEt3GVofgiGuiE+ORpnvP+kAm3h6MLZJ4Q5HCyHADofsb4VzXFsRiWj3c0OFiV+3DWFh0qg3v9gcPlfc3zRow==", - "dev": true, - "peer": true, - "dependencies": { - "array-includes": "^3.1.6", - "array.prototype.flat": "^1.3.1", - "array.prototype.flatmap": "^1.3.1", - "debug": "^3.2.7", - "doctrine": "^2.1.0", - "eslint-import-resolver-node": "^0.3.7", - "eslint-module-utils": "^2.7.4", - "has": "^1.0.3", - "is-core-module": "^2.11.0", - "is-glob": "^4.0.3", - "minimatch": "^3.1.2", - "object.values": "^1.1.6", - "resolve": "^1.22.1", - "semver": "^6.3.0", - "tsconfig-paths": "^3.14.1" - }, - "engines": { - "node": ">=4" - }, - "peerDependencies": { - "eslint": "^2 || ^3 || ^4 || ^5 || ^6 || ^7.2.0 || ^8" - } - }, - "node_modules/eslint-plugin-import/node_modules/debug": { - "version": "3.2.7", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz", - "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==", - "dev": true, - "peer": true, - "dependencies": { - "ms": "^2.1.1" - } - }, - "node_modules/eslint-plugin-import/node_modules/doctrine": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", - "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", - "dev": true, - "peer": true, - "dependencies": { - "esutils": "^2.0.2" - }, - "engines": { - "node": ">=0.10.0" - } - }, - "node_modules/eslint-plugin-import/node_modules/json5": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/json5/-/json5-1.0.2.tgz", - "integrity": "sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA==", - "dev": true, - "peer": true, - "dependencies": { - "minimist": "^1.2.0" - }, - "bin": { - "json5": "lib/cli.js" - } - }, - "node_modules/eslint-plugin-import/node_modules/semver": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", - "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", - "dev": true, - "peer": true, - "bin": { - "semver": "bin/semver.js" - } - }, - "node_modules/eslint-plugin-import/node_modules/strip-bom": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", - "integrity": "sha512-vavAMRXOgBVNF6nyEEmL3DBK19iRpDcoIwW+swQ+CbGiu7lju6t+JklA1MHweoWtadgt4ISVUsXLyDq34ddcwA==", - "dev": true, - "peer": true, - "engines": { - "node": ">=4" - } - }, - "node_modules/eslint-plugin-import/node_modules/tsconfig-paths": { - "version": "3.14.1", - "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.14.1.tgz", - "integrity": "sha512-fxDhWnFSLt3VuTwtvJt5fpwxBHg5AdKWMsgcPOOIilyjymcYVZoCQF8fvFRezCNfblEXmi+PcM1eYHeOAgXCOQ==", - "dev": true, - "peer": true, - "dependencies": { - "@types/json5": "^0.0.29", - "json5": "^1.0.1", - "minimist": "^1.2.6", - "strip-bom": "^3.0.0" - } - }, "node_modules/eslint-scope": { "version": "5.1.1", "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", @@ -4104,9 +3760,9 @@ } }, "node_modules/eslint/node_modules/eslint-scope": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-6.0.0.tgz", - "integrity": "sha512-uRDL9MWmQCkaFus8RF5K9/L/2fn+80yoW3jkD53l4shjCh26fCtvJGasxjUqP5OT87SYTxCVA3BwTUzuELx9kA==", + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-7.1.1.tgz", + "integrity": "sha512-QKQM/UXpIiHcLqJ5AOyIW7XZmzjkzQXYE54n1++wb0u9V/abW3l9uQnxX8Z5Xd18xyKIMTUAyQ0k1e8pz6LUrw==", "dev": true, "dependencies": { "esrecurse": "^4.3.0", @@ -4137,15 +3793,6 @@ "node": ">=10.13.0" } }, - "node_modules/eslint/node_modules/ignore": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", - "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", - "dev": true, - "engines": { - "node": ">= 4" - } - }, "node_modules/eslint/node_modules/json-schema-traverse": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", @@ -4292,16 +3939,16 @@ } }, "node_modules/expect": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/expect/-/expect-29.4.1.tgz", - "integrity": "sha512-OKrGESHOaMxK3b6zxIq9SOW8kEXztKff/Dvg88j4xIJxur1hspEbedVkR3GpHe5LO+WB2Qw7OWN0RMTdp6as5A==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/expect/-/expect-29.4.2.tgz", + "integrity": "sha512-+JHYg9O3hd3RlICG90OPVjRkPBoiUH7PxvDVMnRiaq1g6JUgZStX514erMl0v2Dc5SkfVbm7ztqbd6qHHPn+mQ==", "dev": true, "dependencies": { - "@jest/expect-utils": "^29.4.1", - "jest-get-type": "^29.2.0", - "jest-matcher-utils": "^29.4.1", - "jest-message-util": "^29.4.1", - "jest-util": "^29.4.1" + "@jest/expect-utils": "^29.4.2", + "jest-get-type": "^29.4.2", + "jest-matcher-utils": "^29.4.2", + "jest-message-util": "^29.4.2", + "jest-util": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" @@ -4386,6 +4033,12 @@ "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", "dev": true }, + "node_modules/fast-diff": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/fast-diff/-/fast-diff-1.2.0.tgz", + "integrity": "sha512-xJuoT5+L99XlZ8twedaRf6Ax2TgQVxvgZOYoPKqZufmJib0tL2tegPBOZb1pVNgIhlqDlA0eO0c3wBvQcmzx4w==", + "dev": true + }, "node_modules/fast-glob": { "version": "3.2.12", "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.12.tgz", @@ -4515,6 +4168,22 @@ "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" }, + "node_modules/find-up": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", + "integrity": "sha512-78/PXT1wlLLDgTzDs7sjq9hzz0vXD+zn+7wypEe4fXQxCmdmqfGsEPQxmiCSQI3ajFV91bVSsvNtrJRiW6nGng==", + "dev": true, + "dependencies": { + "locate-path": "^6.0.0", + "path-exists": "^4.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/flat-cache": { "version": "3.0.4", "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-3.0.4.tgz", @@ -4549,15 +4218,6 @@ "integrity": "sha512-5nqDSxl8nn5BSNxyR3n4I6eDmbolI6WT+QqR547RwxQapgjQBmtktdP+HTBb/a/zLsbzERTONyUB5pefh5TtjQ==", "dev": true }, - "node_modules/for-each": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", - "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", - "dev": true, - "dependencies": { - "is-callable": "^1.1.3" - } - }, "node_modules/fork-ts-checker-webpack-plugin": { "version": "7.3.0", "resolved": "https://registry.npmjs.org/fork-ts-checker-webpack-plugin/-/fork-ts-checker-webpack-plugin-7.3.0.tgz", @@ -4712,46 +4372,13 @@ "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==" }, - "node_modules/function.prototype.name": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/function.prototype.name/-/function.prototype.name-1.1.5.tgz", - "integrity": "sha512-uN7m/BzVKQnCUF/iW8jYea67v++2u7m5UgENbHRtdDVclOUP+FMPlCNdmk0h/ysGyo2tavMJEDqJAkJdRa1vMA==", + "node_modules/gensync": { + "version": "1.0.0-beta.2", + "resolved": "https://registry.npmjs.org/gensync/-/gensync-1.0.0-beta.2.tgz", + "integrity": "sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==", "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3", - "es-abstract": "^1.19.0", - "functions-have-names": "^1.2.2" - }, "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/functional-red-black-tree": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz", - "integrity": "sha512-dsKNQNdj6xA3T+QlADDA7mOSlX0qiMINjn0cgr+eGHGsbSHzTabcIogz2+p/iqP1Xs6EP/sS2SbqH+brGTbq0g==", - "dev": true - }, - "node_modules/functions-have-names": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/functions-have-names/-/functions-have-names-1.2.3.tgz", - "integrity": "sha512-xckBUXyTIqT97tq2x2AMb+g163b5JFysYk0x4qxNFwbfQkmNZoiRHb6sPzI9/QV33WeuvVYBUIiD4NzNIyqaRQ==", - "dev": true, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/gensync": { - "version": "1.0.0-beta.2", - "resolved": "https://registry.npmjs.org/gensync/-/gensync-1.0.0-beta.2.tgz", - "integrity": "sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==", - "dev": true, - "engines": { - "node": ">=6.9.0" + "node": ">=6.9.0" } }, "node_modules/get-caller-file": { @@ -4797,22 +4424,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/get-symbol-description": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/get-symbol-description/-/get-symbol-description-1.0.0.tgz", - "integrity": "sha512-2EmdH1YvIQiZpltCNgkuiUnyukzxM/R6NDJX31Ke3BG1Nq5b0S2PhX59UKi9vZpPDQVdqn+1IcaAwnzTT5vCjw==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "get-intrinsic": "^1.1.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/glob": { "version": "7.2.3", "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", @@ -4866,21 +4477,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/globalthis": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/globalthis/-/globalthis-1.0.3.tgz", - "integrity": "sha512-sFdI5LyBiNTHjRd7cGPWapiHWMOXKyuBNX/cWJ3NfzrZQVa8GI/8cofCl74AOVqq9W5kNmguTIzJ/1s2gyI9wA==", - "dev": true, - "dependencies": { - "define-properties": "^1.1.3" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/globby": { "version": "11.1.0", "resolved": "https://registry.npmjs.org/globby/-/globby-11.1.0.tgz", @@ -4901,18 +4497,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/gopd": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.0.1.tgz", - "integrity": "sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==", - "dev": true, - "dependencies": { - "get-intrinsic": "^1.1.3" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/graceful-fs": { "version": "4.2.10", "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.10.tgz", @@ -4936,15 +4520,6 @@ "node": ">= 0.4.0" } }, - "node_modules/has-bigints": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/has-bigints/-/has-bigints-1.0.2.tgz", - "integrity": "sha512-tSvCKtBr9lkF0Ex0aQiP9N+OpV4zi2r/Nee5VkRDbaqv35RLYMzbwQfFSZZH0kR+Rd6302UJZ2p/bJCEoR3VoQ==", - "dev": true, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -4953,30 +4528,6 @@ "node": ">=8" } }, - "node_modules/has-property-descriptors": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.0.tgz", - "integrity": "sha512-62DVLZGoiEBDHQyqG4w9xCuZ7eJEwNmJRWw2VY84Oedb7WFcA27fiEVe8oUQx9hAUJ4ekurquucTGwsyO1XGdQ==", - "dev": true, - "dependencies": { - "get-intrinsic": "^1.1.1" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-proto": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.0.1.tgz", - "integrity": "sha512-7qE+iP+O+bgF9clE5+UoBFzE65mlBiVj3tKCrlNQ0Ogwm0BjpT/gK4SlLYDMybDh5I3TCTKnPPa0oMG7JDYrhg==", - "dev": true, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/has-symbols": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", @@ -4988,21 +4539,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/has-tostringtag": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.0.tgz", - "integrity": "sha512-kFjcSNhnlGV1kyoGk7OXKSawH5JOb/LzUc5w9B02hOTO0dfFRjbHQKvg1d6cf3HbeUmtU9VbbV3qzZ2Teh97WQ==", - "dev": true, - "dependencies": { - "has-symbols": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/hexoid": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/hexoid/-/hexoid-1.0.0.tgz", @@ -5199,20 +4735,6 @@ "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", "dev": true }, - "node_modules/internal-slot": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/internal-slot/-/internal-slot-1.0.4.tgz", - "integrity": "sha512-tA8URYccNzMo94s5MQZgH8NB/XTa6HsOo0MLfXTKKEnHVVdegzaQoFZ7Jp44bdvLvY2waT5dc+j5ICEswhi7UQ==", - "dev": true, - "dependencies": { - "get-intrinsic": "^1.1.3", - "has": "^1.0.3", - "side-channel": "^1.0.4" - }, - "engines": { - "node": ">= 0.4" - } - }, "node_modules/interpret": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.4.0.tgz", @@ -5230,38 +4752,12 @@ "node": ">= 0.10" } }, - "node_modules/is-array-buffer": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/is-array-buffer/-/is-array-buffer-3.0.1.tgz", - "integrity": "sha512-ASfLknmY8Xa2XtB4wmbz13Wu202baeA18cJBCeCy0wXUHZF0IPyVEXqKEcd+t2fNSLLL1vC6k7lxZEojNbISXQ==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "get-intrinsic": "^1.1.3", - "is-typed-array": "^1.1.10" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/is-arrayish": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", "integrity": "sha512-zz06S8t0ozoDXMG+ube26zeCTNXcKIPJZJi8hBrF4idCLms4CG9QtK7qBl1boi5ODzFpjswb5JPmHCbMpjaYzg==", "dev": true }, - "node_modules/is-bigint": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/is-bigint/-/is-bigint-1.0.4.tgz", - "integrity": "sha512-zB9CruMamjym81i2JZ3UMn54PKGsQzsJeo6xvN3HJJ4CAsQNB6iRutp2To77OfCNuoxspsIhzaPoO1zyCEhFOg==", - "dev": true, - "dependencies": { - "has-bigints": "^1.0.1" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/is-binary-path": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-2.1.0.tgz", @@ -5274,34 +4770,6 @@ "node": ">=8" } }, - "node_modules/is-boolean-object": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/is-boolean-object/-/is-boolean-object-1.1.2.tgz", - "integrity": "sha512-gDYaKHJmnj4aWxyj6YHyXVpdQawtVLHU5cb+eztPGczf6cjuTdwve5ZIEfgXqH4e57An1D1AKf8CZ3kYrQRqYA==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "has-tostringtag": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-callable": { - "version": "1.2.7", - "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz", - "integrity": "sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==", - "dev": true, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/is-core-module": { "version": "2.11.0", "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.11.0.tgz", @@ -5314,21 +4782,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/is-date-object": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.5.tgz", - "integrity": "sha512-9YQaSxsAiSwcvS33MBk3wTCVnWK+HhF8VZR2jRxehM16QcVOdHqPn4VPHmRK4lSr38n9JriurInLcP90xsYNfQ==", - "dev": true, - "dependencies": { - "has-tostringtag": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/is-extglob": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", @@ -5377,18 +4830,6 @@ "node": ">=8" } }, - "node_modules/is-negative-zero": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/is-negative-zero/-/is-negative-zero-2.0.2.tgz", - "integrity": "sha512-dqJvarLawXsFbNDeJW7zAz8ItJ9cd28YufuuFzh0G8pNHjJMnY08Dv7sYX2uF5UpQOwieAeOExEYAWWfu7ZZUA==", - "dev": true, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/is-number": { "version": "7.0.0", "resolved": "https://registry.npmjs.org/is-number/-/is-number-7.0.0.tgz", @@ -5398,47 +4839,13 @@ "node": ">=0.12.0" } }, - "node_modules/is-number-object": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/is-number-object/-/is-number-object-1.0.7.tgz", - "integrity": "sha512-k1U0IRzLMo7ZlYIfzRu23Oh6MiIFasgpb9X76eqfFZAqwH44UI4KTBvBYIZ1dSL9ZzChTB9ShHfLkR4pdW5krQ==", + "node_modules/is-path-inside": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-3.0.3.tgz", + "integrity": "sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ==", "dev": true, - "dependencies": { - "has-tostringtag": "^1.0.0" - }, "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-regex": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.1.4.tgz", - "integrity": "sha512-kvRdxDsxZjhzUX07ZnLydzS1TU/TJlTUHHY4YLL87e37oUA49DfkLqgy+VjFocowy29cKvcSiu+kIv728jTTVg==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "has-tostringtag": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-shared-array-buffer": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-shared-array-buffer/-/is-shared-array-buffer-1.0.2.tgz", - "integrity": "sha512-sqN2UDu1/0y6uvXyStCOzyhAjCSlHceFoMKJW8W9EU9cvic/QdsZ0kEU93HEy3IUEFZIiH/3w+AH/UQbPHNdhA==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" + "node": ">=8" } }, "node_modules/is-stream": { @@ -5453,55 +4860,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/is-string": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/is-string/-/is-string-1.0.7.tgz", - "integrity": "sha512-tE2UXzivje6ofPW7l23cjDOMa09gb7xlAqG6jG5ej6uPV32TlWP3NKPigtaGeHNu9fohccRYvIiZMfOOnOYUtg==", - "dev": true, - "dependencies": { - "has-tostringtag": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-symbol": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.4.tgz", - "integrity": "sha512-C/CPBqKWnvdcxqIARxyOh4v1UUEOCHpgDa0WYgpKDFMszcrPcffg5uhwSgPCLD2WWxmq6isisz87tzT01tuGhg==", - "dev": true, - "dependencies": { - "has-symbols": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/is-typed-array": { - "version": "1.1.10", - "resolved": "https://registry.npmjs.org/is-typed-array/-/is-typed-array-1.1.10.tgz", - "integrity": "sha512-PJqgEHiWZvMpaFZ3uTc8kHPM4+4ADTlDniuQL7cU/UDA0Ql7F70yGfHph3cLNe+c9toaigv+DFzTJKhc2CtO6A==", - "dev": true, - "dependencies": { - "available-typed-arrays": "^1.0.5", - "call-bind": "^1.0.2", - "for-each": "^0.3.3", - "gopd": "^1.0.1", - "has-tostringtag": "^1.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/is-unicode-supported": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/is-unicode-supported/-/is-unicode-supported-0.1.0.tgz", @@ -5514,18 +4872,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/is-weakref": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-weakref/-/is-weakref-1.0.2.tgz", - "integrity": "sha512-qctsuLZmIQ0+vSSMfoVvyFe2+GSEvnmZ2ezTup1SBse9+twCCeial6EEi3Nc2KFcf6+qz2FBPnjXsk8xhKSaPQ==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/isarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", @@ -5656,9 +5002,9 @@ } }, "node_modules/jest-changed-files": { - "version": "29.4.0", - "resolved": "https://registry.npmjs.org/jest-changed-files/-/jest-changed-files-29.4.0.tgz", - "integrity": "sha512-rnI1oPxgFghoz32Y8eZsGJMjW54UlqT17ycQeCEktcxxwqqKdlj9afl8LNeO0Pbu+h2JQHThQP0BzS67eTRx4w==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-changed-files/-/jest-changed-files-29.4.2.tgz", + "integrity": "sha512-Qdd+AXdqD16PQa+VsWJpxR3kN0JyOCX1iugQfx5nUgAsI4gwsKviXkpclxOK9ZnwaY2IQVHz+771eAvqeOlfuw==", "dev": true, "dependencies": { "execa": "^5.0.0", @@ -5669,28 +5015,28 @@ } }, "node_modules/jest-circus": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-circus/-/jest-circus-29.4.1.tgz", - "integrity": "sha512-v02NuL5crMNY4CGPHBEflLzl4v91NFb85a+dH9a1pUNx6Xjggrd8l9pPy4LZ1VYNRXlb+f65+7O/MSIbLir6pA==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-circus/-/jest-circus-29.4.2.tgz", + "integrity": "sha512-wW3ztp6a2P5c1yOc1Cfrt5ozJ7neWmqeXm/4SYiqcSriyisgq63bwFj1NuRdSR5iqS0CMEYwSZd89ZA47W9zUg==", "dev": true, "dependencies": { - "@jest/environment": "^29.4.1", - "@jest/expect": "^29.4.1", - "@jest/test-result": "^29.4.1", - "@jest/types": "^29.4.1", + "@jest/environment": "^29.4.2", + "@jest/expect": "^29.4.2", + "@jest/test-result": "^29.4.2", + "@jest/types": "^29.4.2", "@types/node": "*", "chalk": "^4.0.0", "co": "^4.6.0", "dedent": "^0.7.0", "is-generator-fn": "^2.0.0", - "jest-each": "^29.4.1", - "jest-matcher-utils": "^29.4.1", - "jest-message-util": "^29.4.1", - "jest-runtime": "^29.4.1", - "jest-snapshot": "^29.4.1", - "jest-util": "^29.4.1", + "jest-each": "^29.4.2", + "jest-matcher-utils": "^29.4.2", + "jest-message-util": "^29.4.2", + "jest-runtime": "^29.4.2", + "jest-snapshot": "^29.4.2", + "jest-util": "^29.4.2", "p-limit": "^3.1.0", - "pretty-format": "^29.4.1", + "pretty-format": "^29.4.2", "slash": "^3.0.0", "stack-utils": "^2.0.3" }, @@ -5715,21 +5061,21 @@ } }, "node_modules/jest-cli": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-cli/-/jest-cli-29.4.1.tgz", - "integrity": "sha512-jz7GDIhtxQ37M+9dlbv5K+/FVcIo1O/b1sX3cJgzlQUf/3VG25nvuWzlDC4F1FLLzUThJeWLu8I7JF9eWpuURQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-cli/-/jest-cli-29.4.2.tgz", + "integrity": "sha512-b+eGUtXq/K2v7SH3QcJvFvaUaCDS1/YAZBYz0m28Q/Ppyr+1qNaHmVYikOrbHVbZqYQs2IeI3p76uy6BWbXq8Q==", "dev": true, "dependencies": { - "@jest/core": "^29.4.1", - "@jest/test-result": "^29.4.1", - "@jest/types": "^29.4.1", + "@jest/core": "^29.4.2", + "@jest/test-result": "^29.4.2", + "@jest/types": "^29.4.2", "chalk": "^4.0.0", "exit": "^0.1.2", "graceful-fs": "^4.2.9", "import-local": "^3.0.2", - "jest-config": "^29.4.1", - "jest-util": "^29.4.1", - "jest-validate": "^29.4.1", + "jest-config": "^29.4.2", + "jest-util": "^29.4.2", + "jest-validate": "^29.4.2", "prompts": "^2.0.1", "yargs": "^17.3.1" }, @@ -5765,31 +5111,31 @@ } }, "node_modules/jest-config": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-config/-/jest-config-29.4.1.tgz", - "integrity": "sha512-g7p3q4NuXiM4hrS4XFATTkd+2z0Ml2RhFmFPM8c3WyKwVDNszbl4E7cV7WIx1YZeqqCtqbtTtZhGZWJlJqngzg==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-config/-/jest-config-29.4.2.tgz", + "integrity": "sha512-919CtnXic52YM0zW4C1QxjG6aNueX1kBGthuMtvFtRTAxhKfJmiXC9qwHmi6o2josjbDz8QlWyY55F1SIVmCWA==", "dev": true, "dependencies": { "@babel/core": "^7.11.6", - "@jest/test-sequencer": "^29.4.1", - "@jest/types": "^29.4.1", - "babel-jest": "^29.4.1", + "@jest/test-sequencer": "^29.4.2", + "@jest/types": "^29.4.2", + "babel-jest": "^29.4.2", "chalk": "^4.0.0", "ci-info": "^3.2.0", "deepmerge": "^4.2.2", "glob": "^7.1.3", "graceful-fs": "^4.2.9", - "jest-circus": "^29.4.1", - "jest-environment-node": "^29.4.1", - "jest-get-type": "^29.2.0", - "jest-regex-util": "^29.2.0", - "jest-resolve": "^29.4.1", - "jest-runner": "^29.4.1", - "jest-util": "^29.4.1", - "jest-validate": "^29.4.1", + "jest-circus": "^29.4.2", + "jest-environment-node": "^29.4.2", + "jest-get-type": "^29.4.2", + "jest-regex-util": "^29.4.2", + "jest-resolve": "^29.4.2", + "jest-runner": "^29.4.2", + "jest-util": "^29.4.2", + "jest-validate": "^29.4.2", "micromatch": "^4.0.4", "parse-json": "^5.2.0", - "pretty-format": "^29.4.1", + "pretty-format": "^29.4.2", "slash": "^3.0.0", "strip-json-comments": "^3.1.1" }, @@ -5826,15 +5172,15 @@ } }, "node_modules/jest-diff": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-diff/-/jest-diff-29.4.1.tgz", - "integrity": "sha512-uazdl2g331iY56CEyfbNA0Ut7Mn2ulAG5vUaEHXycf1L6IPyuImIxSz4F0VYBKi7LYIuxOwTZzK3wh5jHzASMw==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-diff/-/jest-diff-29.4.2.tgz", + "integrity": "sha512-EK8DSajVtnjx9sa1BkjZq3mqChm2Cd8rIzdXkQMA8e0wuXq53ypz6s5o5V8HRZkoEt2ywJ3eeNWFKWeYr8HK4g==", "dev": true, "dependencies": { "chalk": "^4.0.0", - "diff-sequences": "^29.3.1", - "jest-get-type": "^29.2.0", - "pretty-format": "^29.4.1" + "diff-sequences": "^29.4.2", + "jest-get-type": "^29.4.2", + "pretty-format": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" @@ -5857,9 +5203,9 @@ } }, "node_modules/jest-docblock": { - "version": "29.2.0", - "resolved": "https://registry.npmjs.org/jest-docblock/-/jest-docblock-29.2.0.tgz", - "integrity": "sha512-bkxUsxTgWQGbXV5IENmfiIuqZhJcyvF7tU4zJ/7ioTutdz4ToB5Yx6JOFBpgI+TphRY4lhOyCWGNH/QFQh5T6A==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-docblock/-/jest-docblock-29.4.2.tgz", + "integrity": "sha512-dV2JdahgClL34Y5vLrAHde3nF3yo2jKRH+GIYJuCpfqwEJZcikzeafVTGAjbOfKPG17ez9iWXwUYp7yefeCRag==", "dev": true, "dependencies": { "detect-newline": "^3.0.0" @@ -5869,16 +5215,16 @@ } }, "node_modules/jest-each": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-each/-/jest-each-29.4.1.tgz", - "integrity": "sha512-QlYFiX3llJMWUV0BtWht/esGEz9w+0i7BHwODKCze7YzZzizgExB9MOfiivF/vVT0GSQ8wXLhvHXh3x2fVD4QQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-each/-/jest-each-29.4.2.tgz", + "integrity": "sha512-trvKZb0JYiCndc55V1Yh0Luqi7AsAdDWpV+mKT/5vkpnnFQfuQACV72IoRV161aAr6kAVIBpmYzwhBzm34vQkA==", "dev": true, "dependencies": { - "@jest/types": "^29.4.1", + "@jest/types": "^29.4.2", "chalk": "^4.0.0", - "jest-get-type": "^29.2.0", - "jest-util": "^29.4.1", - "pretty-format": "^29.4.1" + "jest-get-type": "^29.4.2", + "jest-util": "^29.4.2", + "pretty-format": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" @@ -5901,46 +5247,46 @@ } }, "node_modules/jest-environment-node": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-environment-node/-/jest-environment-node-29.4.1.tgz", - "integrity": "sha512-x/H2kdVgxSkxWAIlIh9MfMuBa0hZySmfsC5lCsWmWr6tZySP44ediRKDUiNggX/eHLH7Cd5ZN10Rw+XF5tXsqg==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-environment-node/-/jest-environment-node-29.4.2.tgz", + "integrity": "sha512-MLPrqUcOnNBc8zTOfqBbxtoa8/Ee8tZ7UFW7hRDQSUT+NGsvS96wlbHGTf+EFAT9KC3VNb7fWEM6oyvmxtE/9w==", "dev": true, "dependencies": { - "@jest/environment": "^29.4.1", - "@jest/fake-timers": "^29.4.1", - "@jest/types": "^29.4.1", + "@jest/environment": "^29.4.2", + "@jest/fake-timers": "^29.4.2", + "@jest/types": "^29.4.2", "@types/node": "*", - "jest-mock": "^29.4.1", - "jest-util": "^29.4.1" + "jest-mock": "^29.4.2", + "jest-util": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/jest-get-type": { - "version": "29.2.0", - "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-29.2.0.tgz", - "integrity": "sha512-uXNJlg8hKFEnDgFsrCjznB+sTxdkuqiCL6zMgA75qEbAJjJYTs9XPrvDctrEig2GDow22T/LvHgO57iJhXB/UA==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-get-type/-/jest-get-type-29.4.2.tgz", + "integrity": "sha512-vERN30V5i2N6lqlFu4ljdTqQAgrkTFMC9xaIIfOPYBw04pufjXRty5RuXBiB1d72tGbURa/UgoiHB90ruOSivg==", "dev": true, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/jest-haste-map": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-haste-map/-/jest-haste-map-29.4.1.tgz", - "integrity": "sha512-imTjcgfVVTvg02khXL11NNLTx9ZaofbAWhilrMg/G8dIkp+HYCswhxf0xxJwBkfhWb3e8dwbjuWburvxmcr58w==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-haste-map/-/jest-haste-map-29.4.2.tgz", + "integrity": "sha512-WkUgo26LN5UHPknkezrBzr7lUtV1OpGsp+NfXbBwHztsFruS3gz+AMTTBcEklvi8uPzpISzYjdKXYZQJXBnfvw==", "dev": true, "dependencies": { - "@jest/types": "^29.4.1", + "@jest/types": "^29.4.2", "@types/graceful-fs": "^4.1.3", "@types/node": "*", "anymatch": "^3.0.3", "fb-watchman": "^2.0.0", "graceful-fs": "^4.2.9", - "jest-regex-util": "^29.2.0", - "jest-util": "^29.4.1", - "jest-worker": "^29.4.1", + "jest-regex-util": "^29.4.2", + "jest-util": "^29.4.2", + "jest-worker": "^29.4.2", "micromatch": "^4.0.4", "walker": "^1.0.8" }, @@ -5952,28 +5298,28 @@ } }, "node_modules/jest-leak-detector": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-leak-detector/-/jest-leak-detector-29.4.1.tgz", - "integrity": "sha512-akpZv7TPyGMnH2RimOCgy+hPmWZf55EyFUvymQ4LMsQP8xSPlZumCPtXGoDhFNhUE2039RApZkTQDKU79p/FiQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-leak-detector/-/jest-leak-detector-29.4.2.tgz", + "integrity": "sha512-Wa62HuRJmWXtX9F00nUpWlrbaH5axeYCdyRsOs/+Rb1Vb6+qWTlB5rKwCCRKtorM7owNwKsyJ8NRDUcZ8ghYUA==", "dev": true, "dependencies": { - "jest-get-type": "^29.2.0", - "pretty-format": "^29.4.1" + "jest-get-type": "^29.4.2", + "pretty-format": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/jest-matcher-utils": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-matcher-utils/-/jest-matcher-utils-29.4.1.tgz", - "integrity": "sha512-k5h0u8V4nAEy6lSACepxL/rw78FLDkBnXhZVgFneVpnJONhb2DhZj/Gv4eNe+1XqQ5IhgUcqj745UwH0HJmMnA==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-matcher-utils/-/jest-matcher-utils-29.4.2.tgz", + "integrity": "sha512-EZaAQy2je6Uqkrm6frnxBIdaWtSYFoR8SVb2sNLAtldswlR/29JAgx+hy67llT3+hXBaLB0zAm5UfeqerioZyg==", "dev": true, "dependencies": { "chalk": "^4.0.0", - "jest-diff": "^29.4.1", - "jest-get-type": "^29.2.0", - "pretty-format": "^29.4.1" + "jest-diff": "^29.4.2", + "jest-get-type": "^29.4.2", + "pretty-format": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" @@ -5996,18 +5342,18 @@ } }, "node_modules/jest-message-util": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-29.4.1.tgz", - "integrity": "sha512-H4/I0cXUaLeCw6FM+i4AwCnOwHRgitdaUFOdm49022YD5nfyr8C/DrbXOBEyJaj+w/y0gGJ57klssOaUiLLQGQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-29.4.2.tgz", + "integrity": "sha512-SElcuN4s6PNKpOEtTInjOAA8QvItu0iugkXqhYyguRvQoXapg5gN+9RQxLAkakChZA7Y26j6yUCsFWN+hlKD6g==", "dev": true, "dependencies": { "@babel/code-frame": "^7.12.13", - "@jest/types": "^29.4.1", + "@jest/types": "^29.4.2", "@types/stack-utils": "^2.0.0", "chalk": "^4.0.0", "graceful-fs": "^4.2.9", "micromatch": "^4.0.4", - "pretty-format": "^29.4.1", + "pretty-format": "^29.4.2", "slash": "^3.0.0", "stack-utils": "^2.0.3" }, @@ -6032,14 +5378,14 @@ } }, "node_modules/jest-mock": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-mock/-/jest-mock-29.4.1.tgz", - "integrity": "sha512-MwA4hQ7zBOcgVCVnsM8TzaFLVUD/pFWTfbkY953Y81L5ret3GFRZtmPmRFAjKQSdCKoJvvqOu6Bvfpqlwwb0dQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-mock/-/jest-mock-29.4.2.tgz", + "integrity": "sha512-x1FSd4Gvx2yIahdaIKoBjwji6XpboDunSJ95RpntGrYulI1ByuYQCKN/P7hvk09JB74IonU3IPLdkutEWYt++g==", "dev": true, "dependencies": { - "@jest/types": "^29.4.1", + "@jest/types": "^29.4.2", "@types/node": "*", - "jest-util": "^29.4.1" + "jest-util": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" @@ -6063,26 +5409,26 @@ } }, "node_modules/jest-regex-util": { - "version": "29.2.0", - "resolved": "https://registry.npmjs.org/jest-regex-util/-/jest-regex-util-29.2.0.tgz", - "integrity": "sha512-6yXn0kg2JXzH30cr2NlThF+70iuO/3irbaB4mh5WyqNIvLLP+B6sFdluO1/1RJmslyh/f9osnefECflHvTbwVA==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-regex-util/-/jest-regex-util-29.4.2.tgz", + "integrity": "sha512-XYZXOqUl1y31H6VLMrrUL1ZhXuiymLKPz0BO1kEeR5xER9Tv86RZrjTm74g5l9bPJQXA/hyLdaVPN/sdqfteig==", "dev": true, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" } }, "node_modules/jest-resolve": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-resolve/-/jest-resolve-29.4.1.tgz", - "integrity": "sha512-j/ZFNV2lm9IJ2wmlq1uYK0Y/1PiyDq9g4HEGsNTNr3viRbJdV+8Lf1SXIiLZXFvyiisu0qUyIXGBnw+OKWkJwQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-resolve/-/jest-resolve-29.4.2.tgz", + "integrity": "sha512-RtKWW0mbR3I4UdkOrW7552IFGLYQ5AF9YrzD0FnIOkDu0rAMlA5/Y1+r7lhCAP4nXSBTaE7ueeqj6IOwZpgoqw==", "dev": true, "dependencies": { "chalk": "^4.0.0", "graceful-fs": "^4.2.9", - "jest-haste-map": "^29.4.1", + "jest-haste-map": "^29.4.2", "jest-pnp-resolver": "^1.2.2", - "jest-util": "^29.4.1", - "jest-validate": "^29.4.1", + "jest-util": "^29.4.2", + "jest-validate": "^29.4.2", "resolve": "^1.20.0", "resolve.exports": "^2.0.0", "slash": "^3.0.0" @@ -6092,13 +5438,13 @@ } }, "node_modules/jest-resolve-dependencies": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-resolve-dependencies/-/jest-resolve-dependencies-29.4.1.tgz", - "integrity": "sha512-Y3QG3M1ncAMxfjbYgtqNXC5B595zmB6e//p/qpA/58JkQXu/IpLDoLeOa8YoYfsSglBKQQzNUqtfGJJT/qLmJg==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-resolve-dependencies/-/jest-resolve-dependencies-29.4.2.tgz", + "integrity": "sha512-6pL4ptFw62rjdrPk7rRpzJYgcRqRZNsZTF1VxVTZMishbO6ObyWvX57yHOaNGgKoADtAHRFYdHQUEvYMJATbDg==", "dev": true, "dependencies": { - "jest-regex-util": "^29.2.0", - "jest-snapshot": "^29.4.1" + "jest-regex-util": "^29.4.2", + "jest-snapshot": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" @@ -6121,30 +5467,30 @@ } }, "node_modules/jest-runner": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-runner/-/jest-runner-29.4.1.tgz", - "integrity": "sha512-8d6XXXi7GtHmsHrnaqBKWxjKb166Eyj/ksSaUYdcBK09VbjPwIgWov1VwSmtupCIz8q1Xv4Qkzt/BTo3ZqiCeg==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-runner/-/jest-runner-29.4.2.tgz", + "integrity": "sha512-wqwt0drm7JGjwdH+x1XgAl+TFPH7poowMguPQINYxaukCqlczAcNLJiK+OLxUxQAEWMdy+e6nHZlFHO5s7EuRg==", "dev": true, "dependencies": { - "@jest/console": "^29.4.1", - "@jest/environment": "^29.4.1", - "@jest/test-result": "^29.4.1", - "@jest/transform": "^29.4.1", - "@jest/types": "^29.4.1", + "@jest/console": "^29.4.2", + "@jest/environment": "^29.4.2", + "@jest/test-result": "^29.4.2", + "@jest/transform": "^29.4.2", + "@jest/types": "^29.4.2", "@types/node": "*", "chalk": "^4.0.0", "emittery": "^0.13.1", "graceful-fs": "^4.2.9", - "jest-docblock": "^29.2.0", - "jest-environment-node": "^29.4.1", - "jest-haste-map": "^29.4.1", - "jest-leak-detector": "^29.4.1", - "jest-message-util": "^29.4.1", - "jest-resolve": "^29.4.1", - "jest-runtime": "^29.4.1", - "jest-util": "^29.4.1", - "jest-watcher": "^29.4.1", - "jest-worker": "^29.4.1", + "jest-docblock": "^29.4.2", + "jest-environment-node": "^29.4.2", + "jest-haste-map": "^29.4.2", + "jest-leak-detector": "^29.4.2", + "jest-message-util": "^29.4.2", + "jest-resolve": "^29.4.2", + "jest-runtime": "^29.4.2", + "jest-util": "^29.4.2", + "jest-watcher": "^29.4.2", + "jest-worker": "^29.4.2", "p-limit": "^3.1.0", "source-map-support": "0.5.13" }, @@ -6188,31 +5534,31 @@ } }, "node_modules/jest-runtime": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-runtime/-/jest-runtime-29.4.1.tgz", - "integrity": "sha512-UXTMU9uKu2GjYwTtoAw5rn4STxWw/nadOfW7v1sx6LaJYa3V/iymdCLQM6xy3+7C6mY8GfX22vKpgxY171UIoA==", - "dev": true, - "dependencies": { - "@jest/environment": "^29.4.1", - "@jest/fake-timers": "^29.4.1", - "@jest/globals": "^29.4.1", - "@jest/source-map": "^29.2.0", - "@jest/test-result": "^29.4.1", - "@jest/transform": "^29.4.1", - "@jest/types": "^29.4.1", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-runtime/-/jest-runtime-29.4.2.tgz", + "integrity": "sha512-3fque9vtpLzGuxT9eZqhxi+9EylKK/ESfhClv4P7Y9sqJPs58LjVhTt8jaMp/pRO38agll1CkSu9z9ieTQeRrw==", + "dev": true, + "dependencies": { + "@jest/environment": "^29.4.2", + "@jest/fake-timers": "^29.4.2", + "@jest/globals": "^29.4.2", + "@jest/source-map": "^29.4.2", + "@jest/test-result": "^29.4.2", + "@jest/transform": "^29.4.2", + "@jest/types": "^29.4.2", "@types/node": "*", "chalk": "^4.0.0", "cjs-module-lexer": "^1.0.0", "collect-v8-coverage": "^1.0.0", "glob": "^7.1.3", "graceful-fs": "^4.2.9", - "jest-haste-map": "^29.4.1", - "jest-message-util": "^29.4.1", - "jest-mock": "^29.4.1", - "jest-regex-util": "^29.2.0", - "jest-resolve": "^29.4.1", - "jest-snapshot": "^29.4.1", - "jest-util": "^29.4.1", + "jest-haste-map": "^29.4.2", + "jest-message-util": "^29.4.2", + "jest-mock": "^29.4.2", + "jest-regex-util": "^29.4.2", + "jest-resolve": "^29.4.2", + "jest-snapshot": "^29.4.2", + "jest-util": "^29.4.2", "semver": "^7.3.5", "slash": "^3.0.0", "strip-bom": "^4.0.0" @@ -6238,9 +5584,9 @@ } }, "node_modules/jest-snapshot": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-snapshot/-/jest-snapshot-29.4.1.tgz", - "integrity": "sha512-l4iV8EjGgQWVz3ee/LR9sULDk2pCkqb71bjvlqn+qp90lFwpnulHj4ZBT8nm1hA1C5wowXLc7MGnw321u0tsYA==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-snapshot/-/jest-snapshot-29.4.2.tgz", + "integrity": "sha512-PdfubrSNN5KwroyMH158R23tWcAXJyx4pvSvWls1dHoLCaUhGul9rsL3uVjtqzRpkxlkMavQjGuWG1newPgmkw==", "dev": true, "dependencies": { "@babel/core": "^7.11.6", @@ -6249,23 +5595,23 @@ "@babel/plugin-syntax-typescript": "^7.7.2", "@babel/traverse": "^7.7.2", "@babel/types": "^7.3.3", - "@jest/expect-utils": "^29.4.1", - "@jest/transform": "^29.4.1", - "@jest/types": "^29.4.1", + "@jest/expect-utils": "^29.4.2", + "@jest/transform": "^29.4.2", + "@jest/types": "^29.4.2", "@types/babel__traverse": "^7.0.6", "@types/prettier": "^2.1.5", "babel-preset-current-node-syntax": "^1.0.0", "chalk": "^4.0.0", - "expect": "^29.4.1", + "expect": "^29.4.2", "graceful-fs": "^4.2.9", - "jest-diff": "^29.4.1", - "jest-get-type": "^29.2.0", - "jest-haste-map": "^29.4.1", - "jest-matcher-utils": "^29.4.1", - "jest-message-util": "^29.4.1", - "jest-util": "^29.4.1", + "jest-diff": "^29.4.2", + "jest-get-type": "^29.4.2", + "jest-haste-map": "^29.4.2", + "jest-matcher-utils": "^29.4.2", + "jest-message-util": "^29.4.2", + "jest-util": "^29.4.2", "natural-compare": "^1.4.0", - "pretty-format": "^29.4.1", + "pretty-format": "^29.4.2", "semver": "^7.3.5" }, "engines": { @@ -6289,12 +5635,12 @@ } }, "node_modules/jest-util": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-29.4.1.tgz", - "integrity": "sha512-bQy9FPGxVutgpN4VRc0hk6w7Hx/m6L53QxpDreTZgJd9gfx/AV2MjyPde9tGyZRINAUrSv57p2inGBu2dRLmkQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-29.4.2.tgz", + "integrity": "sha512-wKnm6XpJgzMUSRFB7YF48CuwdzuDIHenVuoIb1PLuJ6F+uErZsuDkU+EiExkChf6473XcawBrSfDSnXl+/YG4g==", "dev": true, "dependencies": { - "@jest/types": "^29.4.1", + "@jest/types": "^29.4.2", "@types/node": "*", "chalk": "^4.0.0", "ci-info": "^3.2.0", @@ -6322,17 +5668,17 @@ } }, "node_modules/jest-validate": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-validate/-/jest-validate-29.4.1.tgz", - "integrity": "sha512-qNZXcZQdIQx4SfUB/atWnI4/I2HUvhz8ajOSYUu40CSmf9U5emil8EDHgE7M+3j9/pavtk3knlZBDsgFvv/SWw==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-validate/-/jest-validate-29.4.2.tgz", + "integrity": "sha512-tto7YKGPJyFbhcKhIDFq8B5od+eVWD/ySZ9Tvcp/NGCvYA4RQbuzhbwYWtIjMT5W5zA2W0eBJwu4HVw34d5G6Q==", "dev": true, "dependencies": { - "@jest/types": "^29.4.1", + "@jest/types": "^29.4.2", "camelcase": "^6.2.0", "chalk": "^4.0.0", - "jest-get-type": "^29.2.0", + "jest-get-type": "^29.4.2", "leven": "^3.1.0", - "pretty-format": "^29.4.1" + "pretty-format": "^29.4.2" }, "engines": { "node": "^14.15.0 || ^16.10.0 || >=18.0.0" @@ -6367,18 +5713,18 @@ } }, "node_modules/jest-watcher": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-watcher/-/jest-watcher-29.4.1.tgz", - "integrity": "sha512-vFOzflGFs27nU6h8dpnVRER3O2rFtL+VMEwnG0H3KLHcllLsU8y9DchSh0AL/Rg5nN1/wSiQ+P4ByMGpuybaVw==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-watcher/-/jest-watcher-29.4.2.tgz", + "integrity": "sha512-onddLujSoGiMJt+tKutehIidABa175i/Ays+QvKxCqBwp7fvxP3ZhKsrIdOodt71dKxqk4sc0LN41mWLGIK44w==", "dev": true, "dependencies": { - "@jest/test-result": "^29.4.1", - "@jest/types": "^29.4.1", + "@jest/test-result": "^29.4.2", + "@jest/types": "^29.4.2", "@types/node": "*", "ansi-escapes": "^4.2.1", "chalk": "^4.0.0", "emittery": "^0.13.1", - "jest-util": "^29.4.1", + "jest-util": "^29.4.2", "string-length": "^4.0.1" }, "engines": { @@ -6402,13 +5748,13 @@ } }, "node_modules/jest-worker": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-29.4.1.tgz", - "integrity": "sha512-O9doU/S1EBe+yp/mstQ0VpPwpv0Clgn68TkNwGxL6/usX/KUW9Arnn4ag8C3jc6qHcXznhsT5Na1liYzAsuAbQ==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-29.4.2.tgz", + "integrity": "sha512-VIuZA2hZmFyRbchsUCHEehoSf2HEl0YVF8SDJqtPnKorAaBuh42V8QsLnde0XP5F6TyCynGPEGgBOn3Fc+wZGw==", "dev": true, "dependencies": { "@types/node": "*", - "jest-util": "^29.4.1", + "jest-util": "^29.4.2", "merge-stream": "^2.0.0", "supports-color": "^8.0.0" }, @@ -6431,6 +5777,16 @@ "url": "https://github.com/chalk/supports-color?sponsor=1" } }, + "node_modules/js-sdsl": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/js-sdsl/-/js-sdsl-4.3.0.tgz", + "integrity": "sha512-mifzlm2+5nZ+lEcLJMoBK0/IH/bDg8XnJfd/Wq6IP+xoCjLZsTOnV2QpxlVbX9bMnkl5PdEjNtBJ9Cj1NjifhQ==", + "dev": true, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/js-sdsl" + } + }, "node_modules/js-tokens": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", @@ -6555,6 +5911,21 @@ "node": ">=6.11.5" } }, + "node_modules/locate-path": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-6.0.0.tgz", + "integrity": "sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==", + "dev": true, + "dependencies": { + "p-locate": "^5.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/lodash": { "version": "4.17.21", "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", @@ -6790,9 +6161,9 @@ } }, "node_modules/minimist": { - "version": "1.2.7", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.7.tgz", - "integrity": "sha512-bzfL1YUZsP41gmu/qjrEk0Q6i2ix/cVeAhbCbqH9u3zYutS1cLg00qhrD0M2MVdCcx4Sc0UpP2eBWo9rotpq6g==", + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.8.tgz", + "integrity": "sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==", "funding": { "url": "https://github.com/sponsors/ljharb" } @@ -6904,9 +6275,9 @@ "dev": true }, "node_modules/node-releases": { - "version": "2.0.9", - "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.9.tgz", - "integrity": "sha512-2xfmOrRkGogbTK9R6Leda0DGiXeY3p2NJpy4+gNCffdUvV6mdEJnaDEic1i3Ec2djAo8jWYoJMR5PB0MSMpxUA==", + "version": "2.0.10", + "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.10.tgz", + "integrity": "sha512-5GFldHPXVG/YZmFzJvKK2zDSzPKhEp0+ZR5SVaoSag9fsL5YgHbUHDfnG5494ISANDcK4KwPXAx2xqVEydmd7w==", "dev": true }, "node_modules/normalize-path": { @@ -6938,14 +6309,6 @@ "node": ">=0.10.0" } }, - "node_modules/object-hash": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/object-hash/-/object-hash-3.0.0.tgz", - "integrity": "sha512-RSn9F68PjH9HqtltsSnqYC1XXoWe9Bju5+213R98cNGttag9q9yAOTzdbsqvIa7aNm5WffBZFpWYr2aWrklWAw==", - "engines": { - "node": ">= 6" - } - }, "node_modules/object-inspect": { "version": "1.12.3", "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.3.tgz", @@ -6954,65 +6317,6 @@ "url": "https://github.com/sponsors/ljharb" } }, - "node_modules/object-keys": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", - "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==", - "dev": true, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/object.assign": { - "version": "4.1.4", - "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.4.tgz", - "integrity": "sha512-1mxKf0e58bvyjSCtKYY4sRe9itRk3PJpquJOjeIkz885CczcI4IvJJDLPS72oowuSh+pBxUFROpX+TU++hxhZQ==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.4", - "has-symbols": "^1.0.3", - "object-keys": "^1.1.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/object.entries": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/object.entries/-/object.entries-1.1.6.tgz", - "integrity": "sha512-leTPzo4Zvg3pmbQ3rDK69Rl8GQvIqMWubrkxONG9/ojtFE2rD9fjMKfSI5BxW3osRH1m6VdzmqK8oAY9aT4x5w==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.4", - "es-abstract": "^1.20.4" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/object.values": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/object.values/-/object.values-1.1.6.tgz", - "integrity": "sha512-FVVTkD1vENCsAcwNs9k6jea2uHC/X0+JcjG8YA60FN5CMaJmG95wT9jek/xX9nornqGRrBkKtzuAu2wuHpKqvw==", - "dev": true, - "peer": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.4", - "es-abstract": "^1.20.4" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/on-finished": { "version": "2.4.1", "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.4.1.tgz", @@ -7144,6 +6448,21 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/p-locate": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-5.0.0.tgz", + "integrity": "sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==", + "dev": true, + "dependencies": { + "p-limit": "^3.0.2" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/p-try": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz", @@ -7347,13 +6666,40 @@ "node": ">= 0.8.0" } }, + "node_modules/prettier": { + "version": "2.8.4", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-2.8.4.tgz", + "integrity": "sha512-vIS4Rlc2FNh0BySk3Wkd6xmwxB0FpOndW5fisM5H8hsZSxU2VWVB5CWIkIjWvrHjIhxk2g3bfMKM87zNTrZddw==", + "dev": true, + "bin": { + "prettier": "bin-prettier.js" + }, + "engines": { + "node": ">=10.13.0" + }, + "funding": { + "url": "https://github.com/prettier/prettier?sponsor=1" + } + }, + "node_modules/prettier-linter-helpers": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/prettier-linter-helpers/-/prettier-linter-helpers-1.0.0.tgz", + "integrity": "sha512-GbK2cP9nraSSUF9N2XwUwqfzlAFlMNYYl+ShE/V+H8a9uNl/oUqB1w2EL54Jh0OlyRSd8RfWYJ3coVS4TROP2w==", + "dev": true, + "dependencies": { + "fast-diff": "^1.1.2" + }, + "engines": { + "node": ">=6.0.0" + } + }, "node_modules/pretty-format": { - "version": "29.4.1", - "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-29.4.1.tgz", - "integrity": "sha512-dt/Z761JUVsrIKaY215o1xQJBGlSmTx/h4cSqXqjHLnU1+Kt+mavVE7UgqJJO5ukx5HjSswHfmXz4LjS2oIJfg==", + "version": "29.4.2", + "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-29.4.2.tgz", + "integrity": "sha512-qKlHR8yFVCbcEWba0H0TOC8dnLlO4vPlyEjRPw31FZ2Rupy9nLa8ZLbYny8gWEl8CkEhJqAE6IzdNELTBVcBEg==", "dev": true, "dependencies": { - "@jest/schemas": "^29.4.0", + "@jest/schemas": "^29.4.2", "ansi-styles": "^5.0.0", "react-is": "^18.0.0" }, @@ -7378,15 +6724,6 @@ "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz", "integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==" }, - "node_modules/progress": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz", - "integrity": "sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==", - "dev": true, - "engines": { - "node": ">=0.4.0" - } - }, "node_modules/prompts": { "version": "2.4.2", "resolved": "https://registry.npmjs.org/prompts/-/prompts-2.4.2.tgz", @@ -7550,23 +6887,6 @@ "resolved": "https://registry.npmjs.org/reflect-metadata/-/reflect-metadata-0.1.13.tgz", "integrity": "sha512-Ts1Y/anZELhSsjMcU605fU9RE4Oi3p5ORujwbIKXfWa+0Zxs510Qrmrce5/Jowq3cHSZSJqBjypxmHarc+vEWg==" }, - "node_modules/regexp.prototype.flags": { - "version": "1.4.3", - "resolved": "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.4.3.tgz", - "integrity": "sha512-fjggEOO3slI6Wvgjwflkc4NFRCTZAu5CnNfBd5qOMYhWdn67nJBBu34/TkD++eeFmd8C9r9jfXJ27+nSiRkSUA==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.3", - "functions-have-names": "^1.2.2" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/regexpp": { "version": "3.2.0", "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-3.2.0.tgz", @@ -7750,20 +7070,6 @@ } ] }, - "node_modules/safe-regex-test": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.0.0.tgz", - "integrity": "sha512-JBUUzyOgEwXQY1NuPtvcj/qcBDbDmEvWufhlnXZIm75DEHp+afM1r1ujJpJsV/gSM4t59tpDyPi1sd6ZaPFfsA==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "get-intrinsic": "^1.1.3", - "is-regex": "^1.1.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/safer-buffer": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", @@ -8110,34 +7416,6 @@ "node": ">=8" } }, - "node_modules/string.prototype.trimend": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/string.prototype.trimend/-/string.prototype.trimend-1.0.6.tgz", - "integrity": "sha512-JySq+4mrPf9EsDBEDYMOb/lM7XQLulwg5R/m1r0PXEFqrV0qHvl58sdTilSXtKOflCsK2E8jxf+GKC0T07RWwQ==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.4", - "es-abstract": "^1.20.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/string.prototype.trimstart": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/string.prototype.trimstart/-/string.prototype.trimstart-1.0.6.tgz", - "integrity": "sha512-omqjMDaY92pbn5HOX7f9IccLA+U1tA9GvtU4JrodiXFfYB7jPzzHpRzpglLAjtUV6bB557zwClJezTqnAiYnQA==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "define-properties": "^1.1.4", - "es-abstract": "^1.20.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/strip-ansi": { "version": "6.0.1", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", @@ -8686,20 +7964,6 @@ "node": ">= 0.6" } }, - "node_modules/typed-array-length": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/typed-array-length/-/typed-array-length-1.0.4.tgz", - "integrity": "sha512-KjZypGq+I/H7HI5HlOoGHkWUUGq+Q0TPhQurLbyrVrvnKTBgzLhIJ7j6J/XTQOi0d1RjyZ0wdas8bKs2p0x3Ng==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "for-each": "^0.3.3", - "is-typed-array": "^1.1.9" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/typedarray": { "version": "0.0.6", "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", @@ -8729,21 +7993,6 @@ "node": ">=8" } }, - "node_modules/unbox-primitive": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/unbox-primitive/-/unbox-primitive-1.0.2.tgz", - "integrity": "sha512-61pPlCD9h51VoreyJ0BReideM3MDKMKnh6+V9L08331ipq6Q8OFXZYiqP6n/tbHx4s5I9uRhcye6BrbkizkBDw==", - "dev": true, - "dependencies": { - "call-bind": "^1.0.2", - "has-bigints": "^1.0.2", - "has-symbols": "^1.0.3", - "which-boxed-primitive": "^1.0.2" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/universalify": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/universalify/-/universalify-2.0.0.tgz", @@ -8809,20 +8058,6 @@ "node": ">= 0.4.0" } }, - "node_modules/uuid": { - "version": "9.0.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.0.tgz", - "integrity": "sha512-MXcSTerfPa4uqyzStbRoTgt5XIe3x5+42+q1sDuy3R5MDk66URdLMOZe5aPX/SQd+kuYAh0FdP/pO28IkQyTeg==", - "bin": { - "uuid": "dist/bin/uuid" - } - }, - "node_modules/v8-compile-cache": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz", - "integrity": "sha512-l8lCEmLcLYZh4nbunNZvQCJc5pv7+RCwa8q/LdUx8u7lsWvPDKmpodJAJNwkAhJC//dFY48KuIEmjtd4RViDrA==", - "dev": true - }, "node_modules/v8-compile-cache-lib": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz", @@ -8982,42 +8217,6 @@ "node": ">= 8" } }, - "node_modules/which-boxed-primitive": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/which-boxed-primitive/-/which-boxed-primitive-1.0.2.tgz", - "integrity": "sha512-bwZdv0AKLpplFY2KZRX6TvyuN7ojjr7lwkg6ml0roIy9YeuSr7JS372qlNW18UQYzgYK9ziGcerWqZOmEn9VNg==", - "dev": true, - "dependencies": { - "is-bigint": "^1.0.1", - "is-boolean-object": "^1.1.0", - "is-number-object": "^1.0.4", - "is-string": "^1.0.5", - "is-symbol": "^1.0.3" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/which-typed-array": { - "version": "1.1.9", - "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.9.tgz", - "integrity": "sha512-w9c4xkx6mPidwp7180ckYWfMmvxpjlZuIudNtDf4N/tTAUB8VJbX25qZoAsrtGuYNnGw3pa0AXgbGKRB8/EceA==", - "dev": true, - "dependencies": { - "available-typed-arrays": "^1.0.5", - "call-bind": "^1.0.2", - "for-each": "^0.3.3", - "gopd": "^1.0.1", - "has-tostringtag": "^1.0.0", - "is-typed-array": "^1.1.10" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/windows-release": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/windows-release/-/windows-release-4.0.0.tgz", @@ -9113,16 +8312,16 @@ "dev": true }, "node_modules/write-file-atomic": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-5.0.0.tgz", - "integrity": "sha512-R7NYMnHSlV42K54lwY9lvW6MnSm1HSJqZL3xiSgi9E7//FYaI74r2G0rd+/X6VAMkHEdzxQaU5HUOXWUz5kA/w==", + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-4.0.2.tgz", + "integrity": "sha512-7KxauUdBmSdWnmpaGFg+ppNjKF8uNLry8LyzjauQDOVONfFLNKrKvQOxZ/VuTIcS/gge/YNahf5RIIQWTSarlg==", "dev": true, "dependencies": { "imurmurhash": "^0.1.4", "signal-exit": "^3.0.7" }, "engines": { - "node": "^14.17.0 || ^16.13.0 || >=18.0.0" + "node": "^12.13.0 || ^14.15.0 || >=16.0.0" } }, "node_modules/xtend": { diff --git a/server/package.json b/server/package.json index cda54ae..ec15c8a 100644 --- a/server/package.json +++ b/server/package.json @@ -6,6 +6,7 @@ "license": "MIT", "scripts": { "build": "nest build", + "format": "prettier --write \"src/**/*.ts\" \"test/**/*.ts\"", "start": "nest start", "start:dev": "nest start --watch", "start:debug": "nest start --debug --watch", @@ -33,12 +34,13 @@ "@types/jest": "29.2.4", "@types/node": "18.11.18", "@types/supertest": "^2.0.11", - "@typescript-eslint/eslint-plugin": "^5.50.0", - "@typescript-eslint/parser": "^5.50.0", - "eslint": "^8.2.0", - "eslint-config-airbnb-base": "^15.0.0", - "eslint-config-airbnb-typescript": "^17.0.0", + "@typescript-eslint/eslint-plugin": "^5.0.0", + "@typescript-eslint/parser": "^5.0.0", + "eslint": "^8.0.1", + "eslint-config-prettier": "^8.3.0", + "eslint-plugin-prettier": "^4.0.0", "jest": "29.3.1", + "prettier": "^2.3.2", "source-map-support": "^0.5.20", "supertest": "^6.1.3", "ts-jest": "29.0.3", diff --git a/server/src/app.controller.spec.ts b/server/src/app.controller.spec.ts new file mode 100644 index 0000000..d22f389 --- /dev/null +++ b/server/src/app.controller.spec.ts @@ -0,0 +1,22 @@ +import { Test, TestingModule } from '@nestjs/testing'; +import { AppController } from './app.controller'; +import { AppService } from './app.service'; + +describe('AppController', () => { + let appController: AppController; + + beforeEach(async () => { + const app: TestingModule = await Test.createTestingModule({ + controllers: [AppController], + providers: [AppService], + }).compile(); + + appController = app.get(AppController); + }); + + describe('root', () => { + it('should return "Hello World!"', () => { + expect(appController.getHello()).toBe('Hello World!'); + }); + }); +}); diff --git a/server/src/app.controller.ts b/server/src/app.controller.ts index 81e3721..cce879e 100644 --- a/server/src/app.controller.ts +++ b/server/src/app.controller.ts @@ -1,8 +1,8 @@ import { Controller, Get } from '@nestjs/common'; -import AppService from './app.service'; +import { AppService } from './app.service'; @Controller() -class AppController { +export class AppController { constructor(private readonly appService: AppService) {} @Get() @@ -10,5 +10,3 @@ class AppController { return this.appService.getHello(); } } - -export default AppController; diff --git a/server/src/app.module.ts b/server/src/app.module.ts index 7c7ce14..8662803 100644 --- a/server/src/app.module.ts +++ b/server/src/app.module.ts @@ -1,12 +1,10 @@ import { Module } from '@nestjs/common'; -import AppController from './app.controller'; -import AppService from './app.service'; +import { AppController } from './app.controller'; +import { AppService } from './app.service'; @Module({ imports: [], controllers: [AppController], providers: [AppService], }) -class AppModule {} - -export default AppModule; +export class AppModule {} diff --git a/server/src/app.service.ts b/server/src/app.service.ts index 17c14bc..927d7cc 100644 --- a/server/src/app.service.ts +++ b/server/src/app.service.ts @@ -1,10 +1,8 @@ import { Injectable } from '@nestjs/common'; @Injectable() -class AppService { +export class AppService { getHello(): string { return 'Hello World!'; } } - -export default AppService; diff --git a/server/src/main.ts b/server/src/main.ts index 2705ff8..f045237 100644 --- a/server/src/main.ts +++ b/server/src/main.ts @@ -1,9 +1,9 @@ import { NestFactory } from '@nestjs/core'; -import AppModule from './app.module'; +import { AppModule } from './app.module'; +import * as process from 'process'; async function bootstrap(): Promise { const app = await NestFactory.create(AppModule); - app.enableCors(); await app.listen(process.env.PORT || 3000); } diff --git a/server/test/app.e2e-spec.ts b/server/test/app.e2e-spec.ts new file mode 100644 index 0000000..0012dcd --- /dev/null +++ b/server/test/app.e2e-spec.ts @@ -0,0 +1,24 @@ +import { Test, TestingModule } from '@nestjs/testing'; +import { INestApplication } from '@nestjs/common'; +import * as request from 'supertest'; +import { AppModule } from '../src/app.module'; + +describe('AppController (e2e)', () => { + let app: INestApplication; + + beforeEach(async () => { + const moduleFixture: TestingModule = await Test.createTestingModule({ + imports: [AppModule], + }).compile(); + + app = moduleFixture.createNestApplication(); + await app.init(); + }); + + it('/ (GET)', () => { + return request(app.getHttpServer()) + .get('/') + .expect(200) + .expect('Hello World!'); + }); +}); diff --git a/server/test/jest-e2e.json b/server/test/jest-e2e.json new file mode 100644 index 0000000..e9d912f --- /dev/null +++ b/server/test/jest-e2e.json @@ -0,0 +1,9 @@ +{ + "moduleFileExtensions": ["js", "json", "ts"], + "rootDir": ".", + "testEnvironment": "node", + "testRegex": ".e2e-spec.ts$", + "transform": { + "^.+\\.(t|j)s$": "ts-jest" + } +} From be66a604fcd84aa6a293512a629991ecbd95025e Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sat, 11 Feb 2023 00:45:11 +0300 Subject: [PATCH 041/196] feat: add monsters attack, player death --- client/src/index.html | 10 +- client/src/scripts/components/crone.ts | 77 +++++- client/src/scripts/components/dave.ts | 6 +- client/src/scripts/components/game.ts | 33 +-- client/src/scripts/components/monster.ts | 23 +- client/src/scripts/components/zombie.ts | 56 +++- client/src/scripts/controllers/playLevel.ts | 267 ++++++++++++++------ client/src/styles/crone.css | 7 + client/src/styles/level.css | 27 +- client/src/styles/zombie.css | 7 + client/src/types/dave.ts | 1 + client/src/types/monster.ts | 31 +++ 12 files changed, 396 insertions(+), 149 deletions(-) create mode 100644 client/src/types/monster.ts diff --git a/client/src/index.html b/client/src/index.html index f809063..97cb270 100644 --- a/client/src/index.html +++ b/client/src/index.html @@ -6,13 +6,5 @@ RS Clone - -
-
-
- -
-
-
- + diff --git a/client/src/scripts/components/crone.ts b/client/src/scripts/components/crone.ts index 5452147..3b7b64a 100644 --- a/client/src/scripts/components/crone.ts +++ b/client/src/scripts/components/crone.ts @@ -1,5 +1,9 @@ +/* eslint-disable class-methods-use-this */ import '@styles/crone'; -import { LeftFeet } from '../../types/game'; +import { LeftFeet, Offset, Rect } from '../../types/game'; +import { + Bullet, BulletMove, MonsterAttack, MonsterMove, MonsterState, +} from '../../types/monster'; import Monster from './monster'; class Crone extends Monster { @@ -27,14 +31,83 @@ class Crone extends Monster { sprite: HTMLElement = document.createElement('div'); - constructor(leftFeet: LeftFeet) { + bullet: Bullet[] = []; + + bulletOffsetX = 20; + + bulletOffsetY = 10; + + bulletW = 20; + + bulletH = 10; + + constructor(leftFeet: LeftFeet, levelArea: HTMLElement) { super(); this.sprite.classList.add('crone'); this.x = leftFeet.x; this.y = leftFeet.y - this.h; this.sprite.style.width = `${this.w}px`; this.sprite.style.height = `${this.h}px`; + this.state = MonsterState.MOVING; + this.moveDir = Math.random() > 0.5 ? MonsterMove.LEFT : MonsterMove.RIGHT; this.setPosition(); + this.levelArea = levelArea; + } + + attack(): void { + if (this.state === MonsterState.ATTACKING) { + if (this.attackDir === MonsterAttack.LEFT) { + this.createBullet( + { + x: this.x + this.bulletOffsetX, + y: this.y + this.bulletOffsetY, + w: this.bulletW, + h: this.bulletH, + }, + BulletMove.LEFT, + ); + } else if (this.attackDir === MonsterAttack.RIGHT) { + this.createBullet( + { + x: this.x + this.w - this.bulletOffsetX, + y: this.y + this.bulletOffsetY, + w: this.bulletW, + h: this.bulletH, + }, + BulletMove.RIGHT, + ); + } + setTimeout(() => { + this.state = MonsterState.MOVING; + }, 500); + } + } + + createBullet(area: Rect, bulletDir: BulletMove): void { + const bullet: Bullet = { + area, + sprite: document.createElement('div'), + }; + bullet.area = area; + bullet.sprite = document.createElement('div'); + bullet.sprite.classList.add('crone_bullet'); + bullet.sprite.style.width = `${area.w}px`; + bullet.sprite.style.height = `${area.h}px`; + bullet.sprite.style.transform = `translate(${area.x}px, ${area.y}px)`; + bullet.movedDir = bulletDir; + this.bullet.push(bullet); + this.levelArea.append(bullet.sprite); + } + + removeBullet(bullet: Bullet): void { + bullet.sprite.remove(); + this.bullet.splice(this.bullet.indexOf(bullet), 1); + } + + moveBullet(bullet: Bullet, offset: Offset): void { + bullet.area.x += offset[0]; + bullet.area.y += offset[1]; + bullet.sprite.style.transform = `translate(${bullet.area.x}px, ${bullet.area.y}px)`; } } diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index 7b35dd6..bf901f3 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -29,8 +29,12 @@ class Player { stepSize = 8; + shootOffsetY = 10; + jumpStartVelocity = 8; + lives = 3; + constructor(leftFeet: LeftFeet) { this.sprite.classList.add('player'); this.x = leftFeet.x; @@ -70,7 +74,7 @@ class Player { offset: Offset, ): void { const fromX: number = this.x + this.w / 2; - const fromY: number = this.y + this.h / 2; + const fromY: number = this.y + this.h / 2 - this.shootOffsetY; const ctx: CanvasRenderingContext2D | null = canvas.getContext('2d'); if (ctx) { diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index d582adf..40b023a 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -41,10 +41,6 @@ class GameView { dave: Player; - canvas: HTMLCanvasElement = document.createElement('canvas'); - - canvasData: ImageData; - constructor() { this.levelArea.classList.add('level-area'); this.levelArea.style.width = `${this.levelAreaW}px`; @@ -57,23 +53,8 @@ class GameView { this.playerArea.style.height = `${this.playerAreaH}px`; this.playerArea.style.left = `${this.viewAreaW / 2 - this.playerAreaW / 2}px`; this.playerArea.style.top = `${this.viewAreaH / 2 - this.playerAreaH / 2}px`; - - this.canvas.width = this.levelAreaW; - this.canvas.height = this.levelAreaH; - this.canvas.style.position = 'absolute'; - this.canvas.style.top = '0'; - this.canvas.style.left = '0'; - this.levelArea.append(this.canvas); - const ctx: CanvasRenderingContext2D = this.canvas.getContext('2d')!; - this.canvasData = ctx.getImageData( - 0, - 0, - this.canvas.width, - this.canvas.height, - ); - this.viewArea.append(this.levelArea, this.playerArea); - document.querySelectorAll('.opacity_side')[0]?.after(this.viewArea); + document.querySelector('body')?.append(this.viewArea); } loadLevelEntities(): void { @@ -82,16 +63,17 @@ class GameView { this.platforms = this.loadBorders(LevelEntity.PLATFORM); this.showPlatforms(); this.loadCharacters(LevelEntity.ZOMBIE).forEach((leftFeet) => { - this.monsters.push(new Zombie(leftFeet)); + this.monsters.push(new Zombie(leftFeet, this.levelArea)); }); this.loadCharacters(LevelEntity.CRONE).forEach((leftFeet) => { - this.monsters.push(new Crone(leftFeet)); + this.monsters.push(new Crone(leftFeet, this.levelArea)); }); this.showMonsters(); this.dave = new Player(this.loadCharacters(LevelEntity.DAVE)[0]); this.insertPlayer(); this.correctLevelPosition(); this.levelArea.classList.add('level1'); + console.log('asd'); } loadBorders(entityType: LevelEntity): Rect[] { @@ -219,6 +201,13 @@ class GameView { monster.removeSprite(); this.monsters.splice(this.monsters.indexOf(monster), 1); } + + resetLevel(): void { + this.walls = []; + this.platforms = []; + this.monsters = []; + this.levelArea.innerHTML = ''; + } } export default GameView; diff --git a/client/src/scripts/components/monster.ts b/client/src/scripts/components/monster.ts index 9e35739..069d4f2 100644 --- a/client/src/scripts/components/monster.ts +++ b/client/src/scripts/components/monster.ts @@ -1,4 +1,5 @@ import { LeftFeet } from '../../types/game'; +import { MonsterAttack, MonsterMove, MonsterState } from '../../types/monster'; class Monster { x: number; @@ -9,13 +10,11 @@ class Monster { h: number; - movingLeft: boolean; + state: MonsterState; - movingRight: boolean; + moveDir: MonsterMove; - movingUp: boolean; - - movingDown: boolean; + attackDir: MonsterAttack; stepSize: number; @@ -29,6 +28,10 @@ class Monster { sprite: HTMLElement; + attackElement: HTMLElement; + + levelArea: HTMLElement; + constructor() { this.sprite = document.createElement('div'); } @@ -38,12 +41,10 @@ class Monster { } swapMoving(): void { - if (this.movingRight) { - this.movingRight = false; - this.movingLeft = true; - } else if (this.movingLeft) { - this.movingRight = true; - this.movingLeft = false; + if (this.moveDir === MonsterMove.RIGHT) { + this.moveDir = MonsterMove.LEFT; + } else if (this.moveDir === MonsterMove.LEFT) { + this.moveDir = MonsterMove.RIGHT; } } diff --git a/client/src/scripts/components/zombie.ts b/client/src/scripts/components/zombie.ts index d59e14d..1f46bc8 100644 --- a/client/src/scripts/components/zombie.ts +++ b/client/src/scripts/components/zombie.ts @@ -1,5 +1,8 @@ import '@styles/zombie'; -import { LeftFeet } from '../../types/game'; +import { LeftFeet, Rect } from '../../types/game'; +import { + Bullet, MonsterAttack, MonsterMove, MonsterState, +} from '../../types/monster'; import Monster from './monster'; class Zombie extends Monster { @@ -31,14 +34,63 @@ class Zombie extends Monster { sprite: HTMLElement = document.createElement('div'); - constructor(leftFeet: LeftFeet) { + bullet: Bullet | undefined; + + constructor(leftFeet: LeftFeet, levelArea: HTMLElement) { super(); this.sprite.classList.add('zombie'); this.x = leftFeet.x; this.y = leftFeet.y - this.h; this.sprite.style.width = `${this.w}px`; this.sprite.style.height = `${this.h}px`; + this.state = MonsterState.MOVING; + this.moveDir = Math.random() > 0.5 ? MonsterMove.LEFT : MonsterMove.RIGHT; this.setPosition(); + this.levelArea = levelArea; + } + + attack(): void { + if (this.state === MonsterState.ATTACKING) { + if (this.attackDir === MonsterAttack.LEFT) { + this.createBullet({ + x: this.x - this.w, + y: this.y, + w: this.w * 2, + h: this.h, + }); + } else if (this.attackDir === MonsterAttack.RIGHT) { + this.createBullet({ + x: this.x, + y: this.y, + w: this.w * 2, + h: this.h, + }); + } + setTimeout(() => { + this.state = MonsterState.MOVING; + this.removeBullet(); + }, 500); + } + } + + createBullet(area: Rect): void { + const bullet: Bullet = { + area, + sprite: document.createElement('div'), + }; + bullet.area = area; + bullet.sprite = document.createElement('div'); + bullet.sprite.classList.add('zombie_bullet'); + bullet.sprite.style.width = `${area.w}px`; + bullet.sprite.style.height = `${area.h}px`; + bullet.sprite.style.transform = `translate(${area.x}px, ${area.y}px)`; + this.bullet = bullet; + this.levelArea.append(bullet.sprite); + } + + removeBullet(): void { + this.bullet?.sprite.remove(); + this.bullet = undefined; } } diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index 76b103e..ddf5081 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -8,12 +8,20 @@ import { import Player from '../components/dave'; import Zombie from '../components/zombie'; import GameView, { Monster } from '../components/game'; +import { + BulletMove, MonsterAttack, MonsterMove, MonsterState, +} from '../../types/monster'; +import Crone from '../components/crone'; class PlayLevel { gameView: GameView; dave: Player; + monsterAnimationTimer: number; + + daveAnimationTimer: number; + constructor() { this.gameView = new GameView(); } @@ -23,7 +31,7 @@ class PlayLevel { this.dave = this.gameView.dave; this.animate(); this.setListener(); - this.animateZombies(); + this.animateMonsters(); } getHorizontalDiffMovingLeftRight(): Offset { @@ -204,57 +212,101 @@ class PlayLevel { return [0, 0]; } - animate(): void { + animate(fps = 60): void { + const fpsInterval: number = 1000 / fps; + let then: number = Date.now(); const tick = (): void => { - if (this.dave.state !== DaveState.STANDING) { - let dX = 0; - let dY = 0; - if (this.dave.state === DaveState.RUNNING) { - if (this.isDaveHasToFall()) { - this.dave.state = DaveState.FALLING; - } else { - [dX, dY] = this.getHorizontalDiffMovingLeftRight(); + this.daveAnimationTimer = requestAnimationFrame(tick); + + const now: number = Date.now(); + const elapsed: number = now - then; + if (elapsed > fpsInterval) { + then = now - (elapsed % fpsInterval); + if (this.dave.state !== DaveState.STANDING) { + let dX = 0; + let dY = 0; + if (this.dave.state === DaveState.RUNNING) { + if (this.isDaveHasToFall()) { + this.dave.state = DaveState.FALLING; + } else { + [dX, dY] = this.getHorizontalDiffMovingLeftRight(); + } + } else if (this.dave.state === DaveState.FALLING) { + [dX, dY] = this.getDiffFalling(); + } else if (this.dave.state === DaveState.JUMPING_UP) { + [dX, dY] = this.getDiffJumping(); + } else if (this.dave.state === DaveState.JUMPING_DOWN) { + [dX, dY] = this.getDiffStartJumpingDown(); + } else if (this.dave.state === DaveState.SHOOTING) { + [dX, dY] = this.getDiffShooting(); } - } else if (this.dave.state === DaveState.FALLING) { - [dX, dY] = this.getDiffFalling(); - } else if (this.dave.state === DaveState.JUMPING_UP) { - [dX, dY] = this.getDiffJumping(); - } else if (this.dave.state === DaveState.JUMPING_DOWN) { - [dX, dY] = this.getDiffStartJumpingDown(); - } else if (this.dave.state === DaveState.SHOOTING) { - [dX, dY] = this.getDiffShooting(); + this.dave.correctPosByDiff( + dX, + dY, + this.gameView.levelAreaW, + this.gameView.levelAreaH, + ); + this.gameView.correctLevelPosition(); + } else if (this.isDaveHasToFall()) { + this.dave.state = DaveState.FALLING; } - - this.dave.correctPosByDiff( - dX, - dY, - this.gameView.levelAreaW, - this.gameView.levelAreaH, - ); - this.gameView.correctLevelPosition(); - } else if (this.isDaveHasToFall()) { - this.dave.state = DaveState.FALLING; + this.dave.setView(); + this.moveBullets(); } - this.dave.setView(); - this.dave.showShootLine( - this.gameView.canvas, - this.gameView.canvasData, - this.calcEndOfLineShoot(), - ); - requestAnimationFrame(tick); }; tick(); } + moveBullets(): void { + this.gameView.monsters.forEach((monster) => { + if (monster instanceof Crone) { + monster.bullet.forEach((bullet) => { + const dX = bullet.movedDir === BulletMove.LEFT + ? -this.dave.stepSize + : this.dave.stepSize; + const dY = 0; + const fullRect: Rect = { + x: bullet.area.x + ((dX < 0) ? dX : 0), + y: bullet.area.y, + w: bullet.area.w + ((dX > 0) ? dX : 0), + h: bullet.area.h, + }; + if (this.checkAttackDave(fullRect)) { + this.dave.state = DaveState.DEAD; + this.restartLevel(); + } + if (this.isCrossWithWalls(fullRect).length === 0) { + (monster).moveBullet(bullet, [dX, dY]); + } else { + (monster).removeBullet(bullet); + } + }); + } else if ( + (monster instanceof Zombie) + && monster.bullet + && this.checkAttackDave(monster.bullet.area)) { + this.dave.state = DaveState.DEAD; + this.restartLevel(); + } + }); + } + + checkAttackDave(bullet: Rect): boolean { + return !!this.isRectCrossWithRect(bullet, this.dave); + } + + isRectCrossWithRect(rect1: Rect, rect2: Rect): boolean { + return !!((rect1.x < rect2.x + rect2.w + && rect1.x + rect1.w > rect2.x + && rect1.y < rect2.y + rect2.h + && rect1.h + rect1.y > rect2.y + )); + } + isCrossWithWalls(rectCommon: Rect): Rect[] { const crossWalls: Rect[] = []; for (let i = 0; i < this.gameView.walls.length; i += 1) { - if ( - rectCommon.x < this.gameView.walls[i].x + this.gameView.walls[i].w - && rectCommon.x + rectCommon.w > this.gameView.walls[i].x - && rectCommon.y < this.gameView.walls[i].y + this.gameView.walls[i].h - && rectCommon.h + rectCommon.y > this.gameView.walls[i].y - ) { + if (this.isRectCrossWithRect(rectCommon, this.gameView.walls[i])) { crossWalls.push(this.gameView.walls[i]); } } @@ -400,53 +452,88 @@ class PlayLevel { }); } - animateZombies(): void { - setInterval(() => { + animateMonsters(): void { + this.monsterAnimationTimer = window.setInterval(() => { for (let i = 0; i < this.gameView.monsters.length; i += 1) { const monster = this.gameView.monsters[i]; - if (monster.moveTicks === monster.moveTicksMax) { - monster.moveTicks -= 1; - let dX = 0; - if (monster.movingRight) { - dX = monster.stepSize; - } else if (monster.movingLeft) { - dX = -monster.stepSize; + if (monster.state === MonsterState.MOVING) { + this.moveMonster(monster); + } + } + }, 50); + } + + moveMonster(monster: Monster): void { + if (monster.moveTicks === monster.moveTicksMax) { + monster.moveTicks -= 1; + let dX = 0; + if (monster.moveDir === MonsterMove.RIGHT) { + dX = monster.stepSize; + } else if (monster.moveDir === MonsterMove.LEFT) { + dX = -monster.stepSize; + } + if (this.isCrossWithWalls({ + x: monster.x + ((dX < 0) ? dX : 0), + y: monster.y, + w: monster.w + ((dX > 0) ? dX : 0), + h: monster.h, + }).length === 0) { + const daveIsNear: Position = this.isDaveNearMonster(monster); + const whereIsDave: Position = this.isDaveVisibleToMonster(monster); + if (monster instanceof Crone) { + const shootOrNot: boolean = Math.random() > 0.90; + if (shootOrNot) { + if (whereIsDave === Position.LEFT) { + monster.state = MonsterState.ATTACKING; + monster.attackDir = MonsterAttack.LEFT; + (monster).attack(); + } else if (whereIsDave === Position.RIGHT) { + monster.state = MonsterState.ATTACKING; + monster.attackDir = MonsterAttack.RIGHT; + (monster).attack(); + } } - if (this.isCrossWithWalls({ - x: monster.x + ((dX < 0) ? dX : 0), - y: monster.y, - w: monster.w + ((dX > 0) ? dX : 0), - h: monster.h, - }).length === 0) { - const whereIsDave: Position = this.isDaveNearMonster(monster); - if ( - (whereIsDave === Position.LEFT && monster.movingRight) - || (whereIsDave === Position.RIGHT && monster.movingLeft) - ) { - if (monster.randomSteps > 0) { - monster.x += dX; - monster.randomSteps -= 1; - } else { - monster.swapMoving(); - monster.setRandomSteps(); - } - } else { + } + if (daveIsNear === Position.NONE) { + if ( + (whereIsDave === Position.LEFT + && monster.moveDir === MonsterMove.RIGHT) + || (whereIsDave === Position.RIGHT + && monster.moveDir === MonsterMove.LEFT) + ) { + if (monster.randomSteps > 0) { monster.x += dX; + monster.randomSteps -= 1; + } else { + monster.swapMoving(); + monster.setRandomSteps(); } } else { - monster.swapMoving(); + monster.x += dX; + } + } else if (monster instanceof Zombie) { + if (daveIsNear === Position.LEFT) { + monster.state = MonsterState.ATTACKING; + monster.attackDir = MonsterAttack.LEFT; + (monster).attack(); + } else if (daveIsNear === Position.RIGHT) { + monster.state = MonsterState.ATTACKING; + monster.attackDir = MonsterAttack.RIGHT; + (monster).attack(); } - monster.setPosition(); - } else if (monster.moveTicks === 0) { - monster.moveTicks = monster.moveTicksMax; - } else if (monster.moveTicks < monster.moveTicksMax) { - monster.moveTicks -= 1; } + } else { + monster.swapMoving(); } - }, 50); + monster.setPosition(); + } else if (monster.moveTicks === 0) { + monster.moveTicks = monster.moveTicksMax; + } else if (monster.moveTicks < monster.moveTicksMax) { + monster.moveTicks -= 1; + } } - isDaveNearMonster(monster: Monster): Position { + isDaveVisibleToMonster(monster: Monster): Position { const diffX: number = this.dave.x - monster.x; const diffY: number = this.dave.y - monster.y; if (Math.abs(diffX) > this.gameView.viewAreaW / 2 @@ -458,6 +545,18 @@ class PlayLevel { return Position.LEFT; } + isDaveNearMonster(monster: Monster): Position { + const diffX: number = this.dave.x - monster.x; + const diffY: number = this.dave.y - monster.y; + if (Math.abs(diffX) > this.dave.w + || Math.abs(diffY) > Math.min(this.dave.h, monster.h)) { + return Position.NONE; + } if (diffX > 0) { + return Position.RIGHT; + } + return Position.LEFT; + } + calcEndOfLineShoot(): Offset { let dX = 0; let dY = 0; @@ -512,7 +611,8 @@ class PlayLevel { daveShoot(): void { const fromX: number = this.dave.x + this.dave.w / 2; - const fromY: number = this.dave.y + this.dave.h / 2; + const fromY: number = this.dave.y + this.dave.h / 2 + - this.dave.shootOffsetY; const [dX, dY] = this.calcEndOfLineShoot(); let closestWall: Rect | undefined; this.gameView.walls.forEach((wall) => { @@ -636,6 +736,17 @@ class PlayLevel { } return false; } + + restartLevel(): void { + clearInterval(this.monsterAnimationTimer); + cancelAnimationFrame(this.daveAnimationTimer); + this.gameView.resetLevel(); + this.gameView.loadLevelEntities(); + this.dave = this.gameView.dave; + this.animate(); + this.setListener(); + this.animateMonsters(); + } } export default PlayLevel; diff --git a/client/src/styles/crone.css b/client/src/styles/crone.css index a3df570..9efafc7 100644 --- a/client/src/styles/crone.css +++ b/client/src/styles/crone.css @@ -8,3 +8,10 @@ .crone.attacked { background-color: green; } + +.crone_bullet { + position: absolute; + top: 0; + left: 0; + background-color:blue; +} diff --git a/client/src/styles/level.css b/client/src/styles/level.css index f3f017b..0d41175 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -1,6 +1,7 @@ body { overflow: hidden; height: 100vw; + background-color: #ccc; } #container { @@ -12,12 +13,12 @@ body { position: relative; background-color: white; opacity: 1; + overflow: hidden; + margin: 100px auto; } .player-area { position: absolute; - - /* border: 1px dashed green; */ } .level-area { @@ -30,26 +31,4 @@ body { .wall { position: absolute; - - /* background-color: black; */ -} - -.opacity { - background: rgb(200 200 150 / 95%); - z-index: 10; - position: relative; -} - -.opacity_side { - flex-grow: 1; -} - -.opacity_top { - width: 100%; - height: 100px; -} - -.opacity_bottom { - width: 100%; - height: 100%; } diff --git a/client/src/styles/zombie.css b/client/src/styles/zombie.css index 0f75814..4c7ca7b 100644 --- a/client/src/styles/zombie.css +++ b/client/src/styles/zombie.css @@ -8,3 +8,10 @@ .zombie.attacked { background-color: crimson; } + +.zombie_bullet { + position: absolute; + top: 0; + left: 0; + background-color:blueviolet; +} diff --git a/client/src/types/dave.ts b/client/src/types/dave.ts index 4f4955c..3dff843 100644 --- a/client/src/types/dave.ts +++ b/client/src/types/dave.ts @@ -7,6 +7,7 @@ export enum DaveState { SHOOTING, RECHARGING, STUCK, + DEAD, } export enum DaveMove { diff --git a/client/src/types/monster.ts b/client/src/types/monster.ts new file mode 100644 index 0000000..2315fae --- /dev/null +++ b/client/src/types/monster.ts @@ -0,0 +1,31 @@ +import { Rect } from './game'; + +export enum MonsterState { + STANDING, + MOVING, + JUMPING_DOWN, + JUMPING_UP, + ATTACKING, +} + +export enum MonsterMove { + LEFT, + RIGHT, + NONE, +} + +export enum MonsterAttack { + LEFT, + RIGHT, +} + +export type Bullet = { + area: Rect; + sprite: HTMLElement; + movedDir?: BulletMove; +}; + +export enum BulletMove { + LEFT, + RIGHT, +} From d8092a943386f4f92d094c69e2e627d885de58df Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sat, 11 Feb 2023 01:41:23 +0300 Subject: [PATCH 042/196] feat: add MongoDB connection --- server/package-lock.json | 1457 +++++++++++++++++++++++++++++++++++++- server/package.json | 2 + server/src/app.module.ts | 16 +- 3 files changed, 1463 insertions(+), 12 deletions(-) diff --git a/server/package-lock.json b/server/package-lock.json index d28f1f7..8fa3354 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -10,7 +10,9 @@ "license": "MIT", "dependencies": { "@nestjs/common": "^9.0.0", + "@nestjs/config": "^2.3.1", "@nestjs/core": "^9.0.0", + "@nestjs/mongoose": "^9.2.1", "@nestjs/platform-express": "^9.0.0", "reflect-metadata": "^0.1.13", "rxjs": "^7.2.0" @@ -196,6 +198,1150 @@ "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", "dev": true }, + "node_modules/@aws-crypto/ie11-detection": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/ie11-detection/-/ie11-detection-3.0.0.tgz", + "integrity": "sha512-341lBBkiY1DfDNKai/wXM3aujNBkXR7tq1URPQDL9wi3AUbI80NR74uF1TXHMm7po1AcnFk8iu2S2IeU/+/A+Q==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^1.11.1" + } + }, + "node_modules/@aws-crypto/ie11-detection/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "optional": true, + "peer": true + }, + "node_modules/@aws-crypto/sha256-browser": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/sha256-browser/-/sha256-browser-3.0.0.tgz", + "integrity": "sha512-8VLmW2B+gjFbU5uMeqtQM6Nj0/F1bro80xQXCW6CQBWgosFWXTx77aeOF5CAIAmbOK64SdMBJdNr6J41yP5mvQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-crypto/ie11-detection": "^3.0.0", + "@aws-crypto/sha256-js": "^3.0.0", + "@aws-crypto/supports-web-crypto": "^3.0.0", + "@aws-crypto/util": "^3.0.0", + "@aws-sdk/types": "^3.222.0", + "@aws-sdk/util-locate-window": "^3.0.0", + "@aws-sdk/util-utf8-browser": "^3.0.0", + "tslib": "^1.11.1" + } + }, + "node_modules/@aws-crypto/sha256-browser/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "optional": true, + "peer": true + }, + "node_modules/@aws-crypto/sha256-js": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/sha256-js/-/sha256-js-3.0.0.tgz", + "integrity": "sha512-PnNN7os0+yd1XvXAy23CFOmTbMaDxgxXtTKHybrJ39Y8kGzBATgBFibWJKH6BhytLI/Zyszs87xCOBNyBig6vQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-crypto/util": "^3.0.0", + "@aws-sdk/types": "^3.222.0", + "tslib": "^1.11.1" + } + }, + "node_modules/@aws-crypto/sha256-js/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "optional": true, + "peer": true + }, + "node_modules/@aws-crypto/supports-web-crypto": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/supports-web-crypto/-/supports-web-crypto-3.0.0.tgz", + "integrity": "sha512-06hBdMwUAb2WFTuGG73LSC0wfPu93xWwo5vL2et9eymgmu3Id5vFAHBbajVWiGhPO37qcsdCap/FqXvJGJWPIg==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^1.11.1" + } + }, + "node_modules/@aws-crypto/supports-web-crypto/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "optional": true, + "peer": true + }, + "node_modules/@aws-crypto/util": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/@aws-crypto/util/-/util-3.0.0.tgz", + "integrity": "sha512-2OJlpeJpCR48CC8r+uKVChzs9Iungj9wkZrl8Z041DWEWvyIHILYKCPNzJghKsivj+S3mLo6BVc7mBNzdxA46w==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "^3.222.0", + "@aws-sdk/util-utf8-browser": "^3.0.0", + "tslib": "^1.11.1" + } + }, + "node_modules/@aws-crypto/util/node_modules/tslib": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz", + "integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg==", + "optional": true, + "peer": true + }, + "node_modules/@aws-sdk/abort-controller": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/abort-controller/-/abort-controller-3.267.0.tgz", + "integrity": "sha512-5R7OSnHFV/f+qQpMf1RuSQoVdXroK94Vl6naWjMOAhMyofHykVhEok9hmFPac86AVx8rVX/vuA7u9GKI6/EE7g==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/client-cognito-identity": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/client-cognito-identity/-/client-cognito-identity-3.267.0.tgz", + "integrity": "sha512-jEE5aw7wp7VhiaU0vCbNQbEIhiaNZnBhRj+vJVCd2HQBI9IVLVXAoyExWxLruAXKEO+A1w1df+fwZAOo0M7aQQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-crypto/sha256-browser": "3.0.0", + "@aws-crypto/sha256-js": "3.0.0", + "@aws-sdk/client-sts": "3.267.0", + "@aws-sdk/config-resolver": "3.267.0", + "@aws-sdk/credential-provider-node": "3.267.0", + "@aws-sdk/fetch-http-handler": "3.267.0", + "@aws-sdk/hash-node": "3.267.0", + "@aws-sdk/invalid-dependency": "3.267.0", + "@aws-sdk/middleware-content-length": "3.267.0", + "@aws-sdk/middleware-endpoint": "3.267.0", + "@aws-sdk/middleware-host-header": "3.267.0", + "@aws-sdk/middleware-logger": "3.267.0", + "@aws-sdk/middleware-recursion-detection": "3.267.0", + "@aws-sdk/middleware-retry": "3.267.0", + "@aws-sdk/middleware-serde": "3.267.0", + "@aws-sdk/middleware-signing": "3.267.0", + "@aws-sdk/middleware-stack": "3.267.0", + "@aws-sdk/middleware-user-agent": "3.267.0", + "@aws-sdk/node-config-provider": "3.267.0", + "@aws-sdk/node-http-handler": "3.267.0", + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/smithy-client": "3.267.0", + "@aws-sdk/types": "3.267.0", + "@aws-sdk/url-parser": "3.267.0", + "@aws-sdk/util-base64": "3.208.0", + "@aws-sdk/util-body-length-browser": "3.188.0", + "@aws-sdk/util-body-length-node": "3.208.0", + "@aws-sdk/util-defaults-mode-browser": "3.267.0", + "@aws-sdk/util-defaults-mode-node": "3.267.0", + "@aws-sdk/util-endpoints": "3.267.0", + "@aws-sdk/util-retry": "3.267.0", + "@aws-sdk/util-user-agent-browser": "3.267.0", + "@aws-sdk/util-user-agent-node": "3.267.0", + "@aws-sdk/util-utf8": "3.254.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/client-sso": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/client-sso/-/client-sso-3.267.0.tgz", + "integrity": "sha512-/475/mT0gYhimpCdK4iZW+eX0DT6mkTgVk5P9ARpQGzEblFM6i2pE7GQnlGeLyHVOtA0cNAyGrWUuj2pyigUaA==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-crypto/sha256-browser": "3.0.0", + "@aws-crypto/sha256-js": "3.0.0", + "@aws-sdk/config-resolver": "3.267.0", + "@aws-sdk/fetch-http-handler": "3.267.0", + "@aws-sdk/hash-node": "3.267.0", + "@aws-sdk/invalid-dependency": "3.267.0", + "@aws-sdk/middleware-content-length": "3.267.0", + "@aws-sdk/middleware-endpoint": "3.267.0", + "@aws-sdk/middleware-host-header": "3.267.0", + "@aws-sdk/middleware-logger": "3.267.0", + "@aws-sdk/middleware-recursion-detection": "3.267.0", + "@aws-sdk/middleware-retry": "3.267.0", + "@aws-sdk/middleware-serde": "3.267.0", + "@aws-sdk/middleware-stack": "3.267.0", + "@aws-sdk/middleware-user-agent": "3.267.0", + "@aws-sdk/node-config-provider": "3.267.0", + "@aws-sdk/node-http-handler": "3.267.0", + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/smithy-client": "3.267.0", + "@aws-sdk/types": "3.267.0", + "@aws-sdk/url-parser": "3.267.0", + "@aws-sdk/util-base64": "3.208.0", + "@aws-sdk/util-body-length-browser": "3.188.0", + "@aws-sdk/util-body-length-node": "3.208.0", + "@aws-sdk/util-defaults-mode-browser": "3.267.0", + "@aws-sdk/util-defaults-mode-node": "3.267.0", + "@aws-sdk/util-endpoints": "3.267.0", + "@aws-sdk/util-retry": "3.267.0", + "@aws-sdk/util-user-agent-browser": "3.267.0", + "@aws-sdk/util-user-agent-node": "3.267.0", + "@aws-sdk/util-utf8": "3.254.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/client-sso-oidc": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/client-sso-oidc/-/client-sso-oidc-3.267.0.tgz", + "integrity": "sha512-Jdq0v0mJSJbG/CKLfHC1L0cjCot48Y6lLMQV1lfkYE65xD0ZSs8Gl7P/T391ZH7cLO6ifVoPdsYnwzhi1ZPXSQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-crypto/sha256-browser": "3.0.0", + "@aws-crypto/sha256-js": "3.0.0", + "@aws-sdk/config-resolver": "3.267.0", + "@aws-sdk/fetch-http-handler": "3.267.0", + "@aws-sdk/hash-node": "3.267.0", + "@aws-sdk/invalid-dependency": "3.267.0", + "@aws-sdk/middleware-content-length": "3.267.0", + "@aws-sdk/middleware-endpoint": "3.267.0", + "@aws-sdk/middleware-host-header": "3.267.0", + "@aws-sdk/middleware-logger": "3.267.0", + "@aws-sdk/middleware-recursion-detection": "3.267.0", + "@aws-sdk/middleware-retry": "3.267.0", + "@aws-sdk/middleware-serde": "3.267.0", + "@aws-sdk/middleware-stack": "3.267.0", + "@aws-sdk/middleware-user-agent": "3.267.0", + "@aws-sdk/node-config-provider": "3.267.0", + "@aws-sdk/node-http-handler": "3.267.0", + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/smithy-client": "3.267.0", + "@aws-sdk/types": "3.267.0", + "@aws-sdk/url-parser": "3.267.0", + "@aws-sdk/util-base64": "3.208.0", + "@aws-sdk/util-body-length-browser": "3.188.0", + "@aws-sdk/util-body-length-node": "3.208.0", + "@aws-sdk/util-defaults-mode-browser": "3.267.0", + "@aws-sdk/util-defaults-mode-node": "3.267.0", + "@aws-sdk/util-endpoints": "3.267.0", + "@aws-sdk/util-retry": "3.267.0", + "@aws-sdk/util-user-agent-browser": "3.267.0", + "@aws-sdk/util-user-agent-node": "3.267.0", + "@aws-sdk/util-utf8": "3.254.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/client-sts": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/client-sts/-/client-sts-3.267.0.tgz", + "integrity": "sha512-bJ+SwJZAP3DuDUgToDV89HsB80IhSfB1rhzLG9csqs6h7uMLO8H1/fymElYKT4VMMAA+rpWJ3pznyGiCK7w28A==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-crypto/sha256-browser": "3.0.0", + "@aws-crypto/sha256-js": "3.0.0", + "@aws-sdk/config-resolver": "3.267.0", + "@aws-sdk/credential-provider-node": "3.267.0", + "@aws-sdk/fetch-http-handler": "3.267.0", + "@aws-sdk/hash-node": "3.267.0", + "@aws-sdk/invalid-dependency": "3.267.0", + "@aws-sdk/middleware-content-length": "3.267.0", + "@aws-sdk/middleware-endpoint": "3.267.0", + "@aws-sdk/middleware-host-header": "3.267.0", + "@aws-sdk/middleware-logger": "3.267.0", + "@aws-sdk/middleware-recursion-detection": "3.267.0", + "@aws-sdk/middleware-retry": "3.267.0", + "@aws-sdk/middleware-sdk-sts": "3.267.0", + "@aws-sdk/middleware-serde": "3.267.0", + "@aws-sdk/middleware-signing": "3.267.0", + "@aws-sdk/middleware-stack": "3.267.0", + "@aws-sdk/middleware-user-agent": "3.267.0", + "@aws-sdk/node-config-provider": "3.267.0", + "@aws-sdk/node-http-handler": "3.267.0", + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/smithy-client": "3.267.0", + "@aws-sdk/types": "3.267.0", + "@aws-sdk/url-parser": "3.267.0", + "@aws-sdk/util-base64": "3.208.0", + "@aws-sdk/util-body-length-browser": "3.188.0", + "@aws-sdk/util-body-length-node": "3.208.0", + "@aws-sdk/util-defaults-mode-browser": "3.267.0", + "@aws-sdk/util-defaults-mode-node": "3.267.0", + "@aws-sdk/util-endpoints": "3.267.0", + "@aws-sdk/util-retry": "3.267.0", + "@aws-sdk/util-user-agent-browser": "3.267.0", + "@aws-sdk/util-user-agent-node": "3.267.0", + "@aws-sdk/util-utf8": "3.254.0", + "fast-xml-parser": "4.0.11", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/config-resolver": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/config-resolver/-/config-resolver-3.267.0.tgz", + "integrity": "sha512-UMvJY548xOkamU9ZuZk336VX9r3035CAbttagiPJ/FXy9S8jcQ7N722PAovtxs69nNBQf56cmWsnOHphLCGG9w==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/signature-v4": "3.267.0", + "@aws-sdk/types": "3.267.0", + "@aws-sdk/util-config-provider": "3.208.0", + "@aws-sdk/util-middleware": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-cognito-identity": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-cognito-identity/-/credential-provider-cognito-identity-3.267.0.tgz", + "integrity": "sha512-H97VsbiTcb4tbY/LQMZNglJIHt7CHso7RtGgctmdsEA7Rha79fV/egF0Vqo2OQHDgEEpgQDWCeHbXO1P5ibR/A==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/client-cognito-identity": "3.267.0", + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-env": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-env/-/credential-provider-env-3.267.0.tgz", + "integrity": "sha512-oiem2UtaFe4CQHscUCImJjPhYWd4iF8fqXhlq6BqHs1wsO6A0vnIUGh+Srut/2q7Xeegl/SRU34HK0hh8JCbxg==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-imds": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-imds/-/credential-provider-imds-3.267.0.tgz", + "integrity": "sha512-Afd5+LdJ9QyeI5L4iyVmI4MLV+0JBtRLmRy0LdinwJaP0DyKyv9+uaIaorKfWihQpe8hwjEfQWTlTz2A3JMJtw==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/node-config-provider": "3.267.0", + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/types": "3.267.0", + "@aws-sdk/url-parser": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-ini": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-ini/-/credential-provider-ini-3.267.0.tgz", + "integrity": "sha512-pHHlqZqZXA4cTssTyRmbYtrjxS2BEy2KFYHEEHNUrd82pUHnj70n+lrpVnT5pRhPPDacpNzxq0KZGeNgmETpbw==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/credential-provider-env": "3.267.0", + "@aws-sdk/credential-provider-imds": "3.267.0", + "@aws-sdk/credential-provider-process": "3.267.0", + "@aws-sdk/credential-provider-sso": "3.267.0", + "@aws-sdk/credential-provider-web-identity": "3.267.0", + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/shared-ini-file-loader": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-node": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-node/-/credential-provider-node-3.267.0.tgz", + "integrity": "sha512-uo8VyZ/L8HBXskYZC65bR1ZUJ5mBn8JarrGHt6vMG2A+uM7AuryTsKn2wdhPfuCUGKuQLXmix5K4VW/wzq11kQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/credential-provider-env": "3.267.0", + "@aws-sdk/credential-provider-imds": "3.267.0", + "@aws-sdk/credential-provider-ini": "3.267.0", + "@aws-sdk/credential-provider-process": "3.267.0", + "@aws-sdk/credential-provider-sso": "3.267.0", + "@aws-sdk/credential-provider-web-identity": "3.267.0", + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/shared-ini-file-loader": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-process": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-process/-/credential-provider-process-3.267.0.tgz", + "integrity": "sha512-pd1OOB1Mm+QdPv3sPfO+1G8HBaPAAYXxjLcOK5z/myBeZAsLR12Xcaft4RR1XWwXXKEQqq42cbAINWQdyVykqQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/shared-ini-file-loader": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-sso": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-sso/-/credential-provider-sso-3.267.0.tgz", + "integrity": "sha512-JqwxelzeRhVdloNi+VUUXhJdziTtNrrwMuhds9wj4KPfl1S2EIzkRxHSjwDz1wtSyuIPOOo6pPJiaVbwvLpkVg==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/client-sso": "3.267.0", + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/shared-ini-file-loader": "3.267.0", + "@aws-sdk/token-providers": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/credential-provider-web-identity": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-provider-web-identity/-/credential-provider-web-identity-3.267.0.tgz", + "integrity": "sha512-za5UsQmj3sYRhd4h5eStj3GCHHfAAjfx2x5FmgQ9ldOp+s0wHEqSL1g+OL9v6o8otf9JnWha+wfUYq3yVGfufQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/credential-providers": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/credential-providers/-/credential-providers-3.267.0.tgz", + "integrity": "sha512-Og70E1eHGcxShMbrmm8lOepF82Hg5Fe7WXv0pnUKFFUxr+pf89bCjxGwktZIDM7ZMMXGIyladeIgTjsJkhpjRQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/client-cognito-identity": "3.267.0", + "@aws-sdk/client-sso": "3.267.0", + "@aws-sdk/client-sts": "3.267.0", + "@aws-sdk/credential-provider-cognito-identity": "3.267.0", + "@aws-sdk/credential-provider-env": "3.267.0", + "@aws-sdk/credential-provider-imds": "3.267.0", + "@aws-sdk/credential-provider-ini": "3.267.0", + "@aws-sdk/credential-provider-node": "3.267.0", + "@aws-sdk/credential-provider-process": "3.267.0", + "@aws-sdk/credential-provider-sso": "3.267.0", + "@aws-sdk/credential-provider-web-identity": "3.267.0", + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/shared-ini-file-loader": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/fetch-http-handler": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/fetch-http-handler/-/fetch-http-handler-3.267.0.tgz", + "integrity": "sha512-u8v8OvWvLVfifmETCAj+DCTot900AsdO1b+N+O8nXiTm2v99rtEoNRJW+no/5vJKNqR+95OAz4NWjFep8nzseg==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/querystring-builder": "3.267.0", + "@aws-sdk/types": "3.267.0", + "@aws-sdk/util-base64": "3.208.0", + "tslib": "^2.3.1" + } + }, + "node_modules/@aws-sdk/hash-node": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/hash-node/-/hash-node-3.267.0.tgz", + "integrity": "sha512-N3xeChdJg4V4jh2vrRN521EMJYxjUOo/LpvpisFyQHE/p31AfcOLb05upYFoYLvyeder9RHBIyNsvvnMYYoCsA==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "3.267.0", + "@aws-sdk/util-buffer-from": "3.208.0", + "@aws-sdk/util-utf8": "3.254.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/invalid-dependency": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/invalid-dependency/-/invalid-dependency-3.267.0.tgz", + "integrity": "sha512-I95IR/eDLC54+9qrL6uh64nhpLVHwxxbBhhEUZKDACp86eXulO8T/DOwUX31ps4+2lI7tbEhQT7f9WDOO3fN8Q==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + } + }, + "node_modules/@aws-sdk/is-array-buffer": { + "version": "3.201.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/is-array-buffer/-/is-array-buffer-3.201.0.tgz", + "integrity": "sha512-UPez5qLh3dNgt0DYnPD/q0mVJY84rA17QE26hVNOW3fAji8W2wrwrxdacWOxyXvlxWsVRcKmr+lay1MDqpAMfg==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/middleware-content-length": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-content-length/-/middleware-content-length-3.267.0.tgz", + "integrity": "sha512-b6MBIK12iwcATKnWIhsh50xWVMmZOXZFIo9D4io6D+JM6j/U+GZrSWqxhHzb3SjavuwVgA2hwq4mUCh2WJPJKA==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/middleware-endpoint": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-endpoint/-/middleware-endpoint-3.267.0.tgz", + "integrity": "sha512-pGICM/qlQVfixtfKZt8zHq54KvLG2MmOAgNWj2MXB7oirPs/3rC9Kz9ITFXJgjlRFyfssgP/feKhs2yZkI8lhw==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/middleware-serde": "3.267.0", + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/signature-v4": "3.267.0", + "@aws-sdk/types": "3.267.0", + "@aws-sdk/url-parser": "3.267.0", + "@aws-sdk/util-config-provider": "3.208.0", + "@aws-sdk/util-middleware": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/middleware-host-header": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-host-header/-/middleware-host-header-3.267.0.tgz", + "integrity": "sha512-D8TfjMeuQXTsB7Ni8liMmNqb3wz+T6t/tYUHtsMo0j++94KAPPj1rhkkTAjR4Rc+IYGCS4YyyCuCXjGB6gkjnA==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/middleware-logger": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-logger/-/middleware-logger-3.267.0.tgz", + "integrity": "sha512-wnLeZYWbgGCuNmRl0Pmky0cSXBWmMTaQBgq90WfwyM0V8wzcoeaovTWA5/qe8oJzusOgUMFoVia4Ew20k3lu8w==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/middleware-recursion-detection": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-recursion-detection/-/middleware-recursion-detection-3.267.0.tgz", + "integrity": "sha512-NCBkTLxaW7XtfQoVBqQCaQZqec5XDtEylkw7g0tGjYDcl934fzu3ciH9MsJ34QFe9slYM6g4v+eC9f1w9K/19g==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/middleware-retry": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-retry/-/middleware-retry-3.267.0.tgz", + "integrity": "sha512-MiiNtddZXVhtSAnJFyChwNxnhzMYmv6qWl8qgSjuIOw9SczkHPCoANTfUdRlzG6RfPYhgYtzMGqqnrficJ6mVg==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/service-error-classification": "3.267.0", + "@aws-sdk/types": "3.267.0", + "@aws-sdk/util-middleware": "3.267.0", + "@aws-sdk/util-retry": "3.267.0", + "tslib": "^2.3.1", + "uuid": "^8.3.2" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/middleware-retry/node_modules/uuid": { + "version": "8.3.2", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz", + "integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==", + "optional": true, + "peer": true, + "bin": { + "uuid": "dist/bin/uuid" + } + }, + "node_modules/@aws-sdk/middleware-sdk-sts": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-sdk-sts/-/middleware-sdk-sts-3.267.0.tgz", + "integrity": "sha512-JLDNNvV7Hr0CQrf1vSmflvPbfDFIx5lFf8tY7DZwYWEE920ZzbJTfUsTW9iZHJGeIe8dAQX1tmfYL68+++nvEQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/middleware-signing": "3.267.0", + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/signature-v4": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/middleware-serde": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-serde/-/middleware-serde-3.267.0.tgz", + "integrity": "sha512-9qspxiZs+JShukzKMAameBSubfvtUOGZviu9GT5OfRekY2dBbwWcfchP2WvlwxZ/CcC+GwO1HcPqKDCMGsNoow==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/middleware-signing": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-signing/-/middleware-signing-3.267.0.tgz", + "integrity": "sha512-thkFEBiFW0M/73dIzl7hQmyAONb8zyD2ZYUFyGm7cIM60sRDUKejPHV6Izonll+HbBZgiBdwUi42uu8O+LfFGQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/signature-v4": "3.267.0", + "@aws-sdk/types": "3.267.0", + "@aws-sdk/util-middleware": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/middleware-stack": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-stack/-/middleware-stack-3.267.0.tgz", + "integrity": "sha512-52uH3JO3ceI15dgzt8gU7lpJf59qbRUQYJ7pAmTMiHtyEawZ39Puv6sGheY3fAffhqd/aQvup6wn18Q1fRIQUA==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/middleware-user-agent": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/middleware-user-agent/-/middleware-user-agent-3.267.0.tgz", + "integrity": "sha512-eaReMnoB1Cx3OY8WDSiUMNDz/EkdAo4w/m3d5CizckKQNmB29gUrgyFs7g7sHTcShQAduZzlsfRPzc6NmKYaWQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/node-config-provider": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/node-config-provider/-/node-config-provider-3.267.0.tgz", + "integrity": "sha512-wNX+Cu0x+kllng253j5dvmLm4opDRr7YehJ0rNGAV24X+UPJPluN9HrBFly+z4+bH16TpJEPKx7AayiWZGFE1w==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/shared-ini-file-loader": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/node-http-handler": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/node-http-handler/-/node-http-handler-3.267.0.tgz", + "integrity": "sha512-wtt3O+e8JEKaLFtmQd74HSZj2TyiApPkwMJ3R50hyboVswt8RcdMWdFbzLnPVpT1AqskG3fMECSKbu8AC/xvBQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/abort-controller": "3.267.0", + "@aws-sdk/protocol-http": "3.267.0", + "@aws-sdk/querystring-builder": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/property-provider": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/property-provider/-/property-provider-3.267.0.tgz", + "integrity": "sha512-/BD1Zar9PCQSV8VZTAWOJmtojAeMIl16ljZX3Kix84r45qqNNxuPST2AhNVN+p97Js4x9kBFCHkdFOpW94wr4Q==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/protocol-http": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/protocol-http/-/protocol-http-3.267.0.tgz", + "integrity": "sha512-8HhOZXMCZ0nsJC/FoifX7YrTYGP91tCpSxIHkr7HxQcTdBMI7QakMtIIWK9Qjsy6tUI98aAdEo5PNCbzdpozmQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/querystring-builder": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/querystring-builder/-/querystring-builder-3.267.0.tgz", + "integrity": "sha512-SKo8V3oPV1wZy4r4lccH7R2LT0PUK/WGaXkKR30wyrtDjJRWVJDYef9ysOpRP+adCTt3G5XO0SzyPQUW5dXYVA==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "3.267.0", + "@aws-sdk/util-uri-escape": "3.201.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/querystring-parser": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/querystring-parser/-/querystring-parser-3.267.0.tgz", + "integrity": "sha512-Krq36GXqEfRfzJ9wOzkkzpbb4SWjgSYydTIgK6KtKapme0HPcB24kmmsjsUVuHzKuQMCHHDRWm+b47iBmHGpSQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/service-error-classification": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/service-error-classification/-/service-error-classification-3.267.0.tgz", + "integrity": "sha512-fOWg7bcItmJqD/YQbGvN9o03ucoBzvWNTQEB81mLKMSKr1Cf/ms0f8oa94LlImgqjjfjvAqHh6rUBTpSmSEyaw==", + "optional": true, + "peer": true, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/shared-ini-file-loader": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/shared-ini-file-loader/-/shared-ini-file-loader-3.267.0.tgz", + "integrity": "sha512-Jz9R5hXKSk+aRoBKi4Bnf6T/FZUBYrIibbLnhiNxpQ1FY9mTggJR/rxuIdOE23LtfW+CRqqEYOtAtmC1oYE6tw==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/signature-v4": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/signature-v4/-/signature-v4-3.267.0.tgz", + "integrity": "sha512-Je1e7rum2zvxa3jWfwq4E+fyBdFJmSJAwGtWYz3+/rWipwXFlSAPeSVqtNjHdfzakgabvzLp7aesG4yQTrO2YQ==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/is-array-buffer": "3.201.0", + "@aws-sdk/types": "3.267.0", + "@aws-sdk/util-hex-encoding": "3.201.0", + "@aws-sdk/util-middleware": "3.267.0", + "@aws-sdk/util-uri-escape": "3.201.0", + "@aws-sdk/util-utf8": "3.254.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/smithy-client": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/smithy-client/-/smithy-client-3.267.0.tgz", + "integrity": "sha512-WdgXHqKmFQIkAWETO/I5boX9u6QbMLC4X74OVSBaBLhRjqYmvolMFtNrQzvSKGB3FaxAN9Do41amC0mGoeLC8A==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/middleware-stack": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/token-providers": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/token-providers/-/token-providers-3.267.0.tgz", + "integrity": "sha512-CGayGrPl4ONG4RuGbNv+QS4oVuItx4hK2FCbFS7d6V7h53rkDrcFd34NsvbicQ2KVFobE7fKs6ZaripJbJbLHA==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/client-sso-oidc": "3.267.0", + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/shared-ini-file-loader": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/types": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/types/-/types-3.267.0.tgz", + "integrity": "sha512-fICTbSeIfXlTHnciQgDt37R0kXoKxgh0a3prnLWVvTcmf7NFujdZmg5YTAZT3KJJ7SuKsIgnI8azBYioVY8BVQ==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/url-parser": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/url-parser/-/url-parser-3.267.0.tgz", + "integrity": "sha512-xoQ5Fd11moiE82QTL9GGE6e73SFuD0Wi73tA75TAwKuY12OP5vDJ4oBC86A1G2T+OzeHJQmYyqiA5j48CzqB6A==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/querystring-parser": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + } + }, + "node_modules/@aws-sdk/util-base64": { + "version": "3.208.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-base64/-/util-base64-3.208.0.tgz", + "integrity": "sha512-PQniZph5A6N7uuEOQi+1hnMz/FSOK/8kMFyFO+4DgA1dZ5pcKcn5wiFwHkcTb/BsgVqQa3Jx0VHNnvhlS8JyTg==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/util-buffer-from": "3.208.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/util-body-length-browser": { + "version": "3.188.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-body-length-browser/-/util-body-length-browser-3.188.0.tgz", + "integrity": "sha512-8VpnwFWXhnZ/iRSl9mTf+VKOX9wDE8QtN4bj9pBfxwf90H1X7E8T6NkiZD3k+HubYf2J94e7DbeHs7fuCPW5Qg==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^2.3.1" + } + }, + "node_modules/@aws-sdk/util-body-length-node": { + "version": "3.208.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-body-length-node/-/util-body-length-node-3.208.0.tgz", + "integrity": "sha512-3zj50e5g7t/MQf53SsuuSf0hEELzMtD8RX8C76f12OSRo2Bca4FLLYHe0TZbxcfQHom8/hOaeZEyTyMogMglqg==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/util-buffer-from": { + "version": "3.208.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-buffer-from/-/util-buffer-from-3.208.0.tgz", + "integrity": "sha512-7L0XUixNEFcLUGPeBF35enCvB9Xl+K6SQsmbrPk1P3mlV9mguWSDQqbOBwY1Ir0OVbD6H/ZOQU7hI/9RtRI0Zw==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/is-array-buffer": "3.201.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/util-config-provider": { + "version": "3.208.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-config-provider/-/util-config-provider-3.208.0.tgz", + "integrity": "sha512-DSRqwrERUsT34ug+anlMBIFooBEGwM8GejC7q00Y/9IPrQy50KnG5PW2NiTjuLKNi7pdEOlwTSEocJE15eDZIg==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/util-defaults-mode-browser": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-defaults-mode-browser/-/util-defaults-mode-browser-3.267.0.tgz", + "integrity": "sha512-MgrqpedA58HVR8RpT2A42//5Lb3M0JwEiYlDaA7EvIVsMx1NzO+cng4MDJi03YBAP5hwCVQmO9Sf5Au4dm+m0g==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/types": "3.267.0", + "bowser": "^2.11.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">= 10.0.0" + } + }, + "node_modules/@aws-sdk/util-defaults-mode-node": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-defaults-mode-node/-/util-defaults-mode-node-3.267.0.tgz", + "integrity": "sha512-JyFk95T77sGM4q386id/mDt9/7HvoQySAygPyv/lj//WEJJIRKiefB277CKKJPT8nRAsO4mIyAT+YO/xGCxkQA==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/config-resolver": "3.267.0", + "@aws-sdk/credential-provider-imds": "3.267.0", + "@aws-sdk/node-config-provider": "3.267.0", + "@aws-sdk/property-provider": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">= 10.0.0" + } + }, + "node_modules/@aws-sdk/util-endpoints": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-endpoints/-/util-endpoints-3.267.0.tgz", + "integrity": "sha512-c6miY83Eo0erqXY+YiS2sOg3izURqvaWHd9przJzBQea9XRCN4ANT2P8AhoC0BPIORutaaOSoCSp/crHG0XLLg==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/util-hex-encoding": { + "version": "3.201.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-hex-encoding/-/util-hex-encoding-3.201.0.tgz", + "integrity": "sha512-7t1vR1pVxKx0motd3X9rI3m/xNp78p3sHtP5yo4NP4ARpxyJ0fokBomY8ScaH2D/B+U5o9ARxldJUdMqyBlJcA==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/util-locate-window": { + "version": "3.208.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-locate-window/-/util-locate-window-3.208.0.tgz", + "integrity": "sha512-iua1A2+P7JJEDHVgvXrRJSvsnzG7stYSGQnBVphIUlemwl6nN5D+QrgbjECtrbxRz8asYFHSzhdhECqN+tFiBg==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/util-middleware": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-middleware/-/util-middleware-3.267.0.tgz", + "integrity": "sha512-7nvqBZVz3RdwYv6lU958g6sWI2Qt8lzxDVn0uwfnPH+fAiX7Ln1Hen2A0XeW5cL5uYUJy6wNM5cyfTzFZosE0A==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/util-retry": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-retry/-/util-retry-3.267.0.tgz", + "integrity": "sha512-ZXo1ICG2HgxkIZWlnPteh2R90kwmhRwvbP282CwrrYgTKuMZmW2R/+o6vqhWyPkjoNFN/pno0FxuDA3IYau3Sw==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/service-error-classification": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">= 14.0.0" + } + }, + "node_modules/@aws-sdk/util-uri-escape": { + "version": "3.201.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-uri-escape/-/util-uri-escape-3.201.0.tgz", + "integrity": "sha512-TeTWbGx4LU2c5rx0obHeDFeO9HvwYwQtMh1yniBz00pQb6Qt6YVOETVQikRZ+XRQwEyCg/dA375UplIpiy54mA==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/util-user-agent-browser": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-user-agent-browser/-/util-user-agent-browser-3.267.0.tgz", + "integrity": "sha512-SmI6xInnPPa0gFhCqhtWOUMTxLeRbm7X5HXzeprhK1d8aNNlUVyALAV7K8ovIjnv3a97lIJSekyb78oTuYITCA==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/types": "3.267.0", + "bowser": "^2.11.0", + "tslib": "^2.3.1" + } + }, + "node_modules/@aws-sdk/util-user-agent-node": { + "version": "3.267.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-user-agent-node/-/util-user-agent-node-3.267.0.tgz", + "integrity": "sha512-nfmyffA1yIypJ30CIMO6Tc16t8dFJzdztzoowjmnfb8/LzTZECERM3GICq0DvZDPfSo+jbuz634VtS2K7tVZjA==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/node-config-provider": "3.267.0", + "@aws-sdk/types": "3.267.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + }, + "peerDependencies": { + "aws-crt": ">=1.0.0" + }, + "peerDependenciesMeta": { + "aws-crt": { + "optional": true + } + } + }, + "node_modules/@aws-sdk/util-utf8": { + "version": "3.254.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-utf8/-/util-utf8-3.254.0.tgz", + "integrity": "sha512-14Kso/eIt5/qfIBmhEL9L1IfyUqswjSTqO2mY7KOzUZ9SZbwn3rpxmtkhmATkRjD7XIlLKaxBkI7tU9Zjzj8Kw==", + "optional": true, + "peer": true, + "dependencies": { + "@aws-sdk/util-buffer-from": "3.208.0", + "tslib": "^2.3.1" + }, + "engines": { + "node": ">=14.0.0" + } + }, + "node_modules/@aws-sdk/util-utf8-browser": { + "version": "3.259.0", + "resolved": "https://registry.npmjs.org/@aws-sdk/util-utf8-browser/-/util-utf8-browser-3.259.0.tgz", + "integrity": "sha512-UvFa/vR+e19XookZF8RzFZBrw2EUkQWxiBW0yYQAhvk3C+QVGl0H3ouca8LDBlBfQKXwmW3huo/59H8rwb1wJw==", + "optional": true, + "peer": true, + "dependencies": { + "tslib": "^2.3.1" + } + }, "node_modules/@babel/code-frame": { "version": "7.18.6", "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.18.6.tgz", @@ -1541,6 +2687,22 @@ } } }, + "node_modules/@nestjs/config": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/@nestjs/config/-/config-2.3.1.tgz", + "integrity": "sha512-Ckzel0NZ9CWhNsLfE1hxfDuxJuEbhQvGxSlmZ1/X8awjRmAA/g3kT6M1+MO1SHj1wMtPyUfd9WpwkiqFbiwQgA==", + "dependencies": { + "dotenv": "16.0.3", + "dotenv-expand": "10.0.0", + "lodash": "4.17.21", + "uuid": "9.0.0" + }, + "peerDependencies": { + "@nestjs/common": "^7.0.0 || ^8.0.0 || ^9.0.0", + "reflect-metadata": "^0.1.13", + "rxjs": "^6.0.0 || ^7.2.0" + } + }, "node_modules/@nestjs/core": { "version": "9.3.8", "resolved": "https://registry.npmjs.org/@nestjs/core/-/core-9.3.8.tgz", @@ -1578,6 +2740,18 @@ } } }, + "node_modules/@nestjs/mongoose": { + "version": "9.2.1", + "resolved": "https://registry.npmjs.org/@nestjs/mongoose/-/mongoose-9.2.1.tgz", + "integrity": "sha512-tMK5kKFjQnNVhqJDw1wa352z+VsODOFznTn74xSzrziof03qS+O6rLU4q1kMx0B4AmFbADf03GOdpvBc9bMWqw==", + "peerDependencies": { + "@nestjs/common": "^8.0.0 || ^9.0.0", + "@nestjs/core": "^8.0.0 || ^9.0.0", + "mongoose": "^6.0.2", + "reflect-metadata": "^0.1.12", + "rxjs": "^7.0.0" + } + }, "node_modules/@nestjs/platform-express": { "version": "9.3.8", "resolved": "https://registry.npmjs.org/@nestjs/platform-express/-/platform-express-9.3.8.tgz", @@ -2019,8 +3193,7 @@ "node_modules/@types/node": { "version": "18.11.18", "resolved": "https://registry.npmjs.org/@types/node/-/node-18.11.18.tgz", - "integrity": "sha512-DHQpWGjyQKSHj3ebjFI/wRKcqQcdR+MoFBygntYOZytCqNfkd2ZC4ARDJ2DQqhjH5p85Nnd3jhUJIXrszFX/JA==", - "dev": true + "integrity": "sha512-DHQpWGjyQKSHj3ebjFI/wRKcqQcdR+MoFBygntYOZytCqNfkd2ZC4ARDJ2DQqhjH5p85Nnd3jhUJIXrszFX/JA==" }, "node_modules/@types/parse-json": { "version": "4.0.0", @@ -2087,6 +3260,22 @@ "@types/superagent": "*" } }, + "node_modules/@types/webidl-conversions": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/@types/webidl-conversions/-/webidl-conversions-7.0.0.tgz", + "integrity": "sha512-xTE1E+YF4aWPJJeUzaZI5DRntlkY3+BCVJi0axFptnjGmAoWxkyREIh/XMrfxVLejwQxMCfDXdICo0VLxThrog==", + "peer": true + }, + "node_modules/@types/whatwg-url": { + "version": "8.2.2", + "resolved": "https://registry.npmjs.org/@types/whatwg-url/-/whatwg-url-8.2.2.tgz", + "integrity": "sha512-FtQu10RWgn3D9U4aazdwIE2yzphmTJREDqNdODHrbrZmmMqI0vMheC/6NE/J1Yveaj8H+ela+YwWTjq5PGmuhA==", + "peer": true, + "dependencies": { + "@types/node": "*", + "@types/webidl-conversions": "*" + } + }, "node_modules/@types/yargs": { "version": "17.0.22", "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-17.0.22.tgz", @@ -2764,7 +3953,6 @@ "version": "1.5.1", "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.5.1.tgz", "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==", - "dev": true, "funding": [ { "type": "github", @@ -2850,6 +4038,13 @@ "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" }, + "node_modules/bowser": { + "version": "2.11.0", + "resolved": "https://registry.npmjs.org/bowser/-/bowser-2.11.0.tgz", + "integrity": "sha512-AlcaJBi/pqqJBIQ8U9Mcpc9i8Aqxn88Skv5d+xBX006BY5u8N3mGLHa5Lgppa7L/HfwgwLgZ6NYs+Ag6uUmJRA==", + "optional": true, + "peer": true + }, "node_modules/brace-expansion": { "version": "1.1.11", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", @@ -2921,11 +4116,22 @@ "node-int64": "^0.4.0" } }, + "node_modules/bson": { + "version": "4.7.2", + "resolved": "https://registry.npmjs.org/bson/-/bson-4.7.2.tgz", + "integrity": "sha512-Ry9wCtIZ5kGqkJoi6aD8KjxFZEx78guTQDnpXWiNthsxzrxAK/i8E6pCHAIZTbaEFWcOCvbecMukfK7XUvyLpQ==", + "peer": true, + "dependencies": { + "buffer": "^5.6.0" + }, + "engines": { + "node": ">=6.9.0" + } + }, "node_modules/buffer": { "version": "5.7.1", "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.7.1.tgz", "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==", - "dev": true, "funding": [ { "type": "github", @@ -3356,7 +4562,6 @@ "version": "4.3.4", "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.4.tgz", "integrity": "sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ==", - "dev": true, "dependencies": { "ms": "2.1.2" }, @@ -3489,6 +4694,22 @@ "node": ">=6.0.0" } }, + "node_modules/dotenv": { + "version": "16.0.3", + "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.0.3.tgz", + "integrity": "sha512-7GO6HghkA5fYG9TYnNxi14/7K9f5occMlp3zXAuSxn7CKCxt9xbNWG7yF8hTCSUchlfWSe3uLmlPfigevRItzQ==", + "engines": { + "node": ">=12" + } + }, + "node_modules/dotenv-expand": { + "version": "10.0.0", + "resolved": "https://registry.npmjs.org/dotenv-expand/-/dotenv-expand-10.0.0.tgz", + "integrity": "sha512-GopVGCpVS1UKH75VKHGuQFqS1Gusej0z4FyQkPdwjil2gNIv+LNsqBlboOzpJFZKVT95GkCyWJbBSdFEFUWI2A==", + "engines": { + "node": ">=12" + } + }, "node_modules/ee-first": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", @@ -4072,6 +5293,23 @@ "resolved": "https://registry.npmjs.org/fast-safe-stringify/-/fast-safe-stringify-2.1.1.tgz", "integrity": "sha512-W+KJc2dmILlPplD/H4K9l9LcAHAfPtP6BY84uVLXQ6Evcz9Lcg33Y2z1IVblT6xdY54PXYVHEv+0Wpq8Io6zkA==" }, + "node_modules/fast-xml-parser": { + "version": "4.0.11", + "resolved": "https://registry.npmjs.org/fast-xml-parser/-/fast-xml-parser-4.0.11.tgz", + "integrity": "sha512-4aUg3aNRR/WjQAcpceODG1C3x3lFANXRo8+1biqfieHmg9pyMt7qB4lQV/Ta6sJCTbA5vfD8fnA8S54JATiFUA==", + "optional": true, + "peer": true, + "dependencies": { + "strnum": "^1.0.5" + }, + "bin": { + "fxparser": "src/cli/cli.js" + }, + "funding": { + "type": "paypal", + "url": "https://paypal.me/naturalintelligence" + } + }, "node_modules/fastq": { "version": "1.15.0", "resolved": "https://registry.npmjs.org/fastq/-/fastq-1.15.0.tgz", @@ -4593,7 +5831,6 @@ "version": "1.2.1", "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==", - "dev": true, "funding": [ { "type": "github", @@ -4744,6 +5981,12 @@ "node": ">= 0.10" } }, + "node_modules/ip": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ip/-/ip-2.0.0.tgz", + "integrity": "sha512-WKa+XuLG1A1R0UWhl2+1XQSi+fZWMsYKffMZTTYsiZaUD8k2yDAj5atimTUD2TZkyCkNEeYE5NhFZmupOGtjYQ==", + "peer": true + }, "node_modules/ipaddr.js": { "version": "1.9.1", "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", @@ -5865,6 +7108,15 @@ "graceful-fs": "^4.1.6" } }, + "node_modules/kareem": { + "version": "2.5.1", + "resolved": "https://registry.npmjs.org/kareem/-/kareem-2.5.1.tgz", + "integrity": "sha512-7jFxRVm+jD+rkq3kY0iZDJfsO2/t4BBPeEb2qKn2lR/9KhuksYk5hxzfRYWMPV8P/x2d0kHD306YyWLzjjH+uA==", + "peer": true, + "engines": { + "node": ">=12.0.0" + } + }, "node_modules/kleur": { "version": "3.0.3", "resolved": "https://registry.npmjs.org/kleur/-/kleur-3.0.3.tgz", @@ -5929,8 +7181,7 @@ "node_modules/lodash": { "version": "4.17.21", "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.21.tgz", - "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==", - "dev": true + "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==" }, "node_modules/lodash.memoize": { "version": "4.1.2", @@ -6068,6 +7319,13 @@ "node": ">= 4.0.0" } }, + "node_modules/memory-pager": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/memory-pager/-/memory-pager-1.5.0.tgz", + "integrity": "sha512-ZS4Bp4r/Zoeq6+NLJpP+0Zzm0pR8whtGPf1XExKLJBAczGMnSi3It14OiNCStjQjM6NU1okjQGSxgEZN8eBYKg==", + "optional": true, + "peer": true + }, "node_modules/merge-descriptors": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", @@ -6179,11 +7437,121 @@ "mkdirp": "bin/cmd.js" } }, + "node_modules/mongodb": { + "version": "4.13.0", + "resolved": "https://registry.npmjs.org/mongodb/-/mongodb-4.13.0.tgz", + "integrity": "sha512-+taZ/bV8d1pYuHL4U+gSwkhmDrwkWbH1l4aah4YpmpscMwgFBkufIKxgP/G7m87/NUuQzc2Z75ZTI7ZOyqZLbw==", + "peer": true, + "dependencies": { + "bson": "^4.7.0", + "mongodb-connection-string-url": "^2.5.4", + "socks": "^2.7.1" + }, + "engines": { + "node": ">=12.9.0" + }, + "optionalDependencies": { + "@aws-sdk/credential-providers": "^3.186.0", + "saslprep": "^1.0.3" + } + }, + "node_modules/mongodb-connection-string-url": { + "version": "2.6.0", + "resolved": "https://registry.npmjs.org/mongodb-connection-string-url/-/mongodb-connection-string-url-2.6.0.tgz", + "integrity": "sha512-WvTZlI9ab0QYtTYnuMLgobULWhokRjtC7db9LtcVfJ+Hsnyr5eo6ZtNAt3Ly24XZScGMelOcGtm7lSn0332tPQ==", + "peer": true, + "dependencies": { + "@types/whatwg-url": "^8.2.1", + "whatwg-url": "^11.0.0" + } + }, + "node_modules/mongodb-connection-string-url/node_modules/tr46": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-3.0.0.tgz", + "integrity": "sha512-l7FvfAHlcmulp8kr+flpQZmVwtu7nfRV7NZujtN0OqES8EL4O4e0qqzL0DC5gAvx/ZC/9lk6rhcUwYvkBnBnYA==", + "peer": true, + "dependencies": { + "punycode": "^2.1.1" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/mongodb-connection-string-url/node_modules/webidl-conversions": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-7.0.0.tgz", + "integrity": "sha512-VwddBukDzu71offAQR975unBIGqfKZpM+8ZX6ySk8nYhVoo5CYaZyzt3YBvYtRtO+aoGlqxPg/B87NGVZ/fu6g==", + "peer": true, + "engines": { + "node": ">=12" + } + }, + "node_modules/mongodb-connection-string-url/node_modules/whatwg-url": { + "version": "11.0.0", + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-11.0.0.tgz", + "integrity": "sha512-RKT8HExMpoYx4igMiVMY83lN6UeITKJlBQ+vR/8ZJ8OCdSiN3RwCq+9gH0+Xzj0+5IrM6i4j/6LuvzbZIQgEcQ==", + "peer": true, + "dependencies": { + "tr46": "^3.0.0", + "webidl-conversions": "^7.0.0" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/mongoose": { + "version": "6.9.1", + "resolved": "https://registry.npmjs.org/mongoose/-/mongoose-6.9.1.tgz", + "integrity": "sha512-hOz1ZWV0w6WEVLrj89Wpk7PXDYtDDF6k7/NX79lY5iKqeFtZsceBXW8xW59YFNcW5O3cH32hQ8IbDlhgyBsDMA==", + "peer": true, + "dependencies": { + "bson": "^4.7.0", + "kareem": "2.5.1", + "mongodb": "4.13.0", + "mpath": "0.9.0", + "mquery": "4.0.3", + "ms": "2.1.3", + "sift": "16.0.1" + }, + "engines": { + "node": ">=12.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/mongoose" + } + }, + "node_modules/mongoose/node_modules/ms": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", + "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", + "peer": true + }, + "node_modules/mpath": { + "version": "0.9.0", + "resolved": "https://registry.npmjs.org/mpath/-/mpath-0.9.0.tgz", + "integrity": "sha512-ikJRQTk8hw5DEoFVxHG1Gn9T/xcjtdnOKIU1JTmGjZZlg9LST2mBLmcX3/ICIbgJydT2GOc15RnNy5mHmzfSew==", + "peer": true, + "engines": { + "node": ">=4.0.0" + } + }, + "node_modules/mquery": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/mquery/-/mquery-4.0.3.tgz", + "integrity": "sha512-J5heI+P08I6VJ2Ky3+33IpCdAvlYGTSUjwTPxkAr8i8EoduPMBX2OY/wa3IKZIQl7MU4SbFk8ndgSKyB/cl1zA==", + "peer": true, + "dependencies": { + "debug": "4.x" + }, + "engines": { + "node": ">=12.0.0" + } + }, "node_modules/ms": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz", - "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", - "dev": true + "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==" }, "node_modules/multer": { "version": "1.4.4-lts.1", @@ -6763,7 +8131,6 @@ "version": "2.3.0", "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.0.tgz", "integrity": "sha512-rRV+zQD8tVFys26lAGR9WUuS4iUAngJScM+ZRSKtvl5tKeZ2t5bvdNFdNHBW9FWR4guGHlgmsZ1G7BSm2wTbuA==", - "dev": true, "engines": { "node": ">=6" } @@ -7075,6 +8442,19 @@ "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" }, + "node_modules/saslprep": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/saslprep/-/saslprep-1.0.3.tgz", + "integrity": "sha512-/MY/PEMbk2SuY5sScONwhUDsV2p77Znkb/q3nSVstq/yQzYJOH/Azh29p9oJLsl3LnQwSvZDKagDGBsBwSooag==", + "optional": true, + "peer": true, + "dependencies": { + "sparse-bitfield": "^3.0.3" + }, + "engines": { + "node": ">=6" + } + }, "node_modules/schema-utils": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.1.1.tgz", @@ -7277,6 +8657,12 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/sift": { + "version": "16.0.1", + "resolved": "https://registry.npmjs.org/sift/-/sift-16.0.1.tgz", + "integrity": "sha512-Wv6BjQ5zbhW7VFefWusVP33T/EM0vYikCaQ2qR8yULbsilAT8/wQaXvuQ3ptGLpoKx+lihJE3y2UTgKDyyNHZQ==", + "peer": true + }, "node_modules/signal-exit": { "version": "3.0.7", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", @@ -7298,6 +8684,30 @@ "node": ">=8" } }, + "node_modules/smart-buffer": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/smart-buffer/-/smart-buffer-4.2.0.tgz", + "integrity": "sha512-94hK0Hh8rPqQl2xXc3HsaBoOXKV20MToPkcXvwbISWLEs+64sBq5kFgn2kJDHb1Pry9yrP0dxrCI9RRci7RXKg==", + "peer": true, + "engines": { + "node": ">= 6.0.0", + "npm": ">= 3.0.0" + } + }, + "node_modules/socks": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/socks/-/socks-2.7.1.tgz", + "integrity": "sha512-7maUZy1N7uo6+WVEX6psASxtNlKaNVMlGQKkG/63nEDdLOWNbiUMoLK7X4uYoLhQstau72mLgfEWcXcwsaHbYQ==", + "peer": true, + "dependencies": { + "ip": "^2.0.0", + "smart-buffer": "^4.2.0" + }, + "engines": { + "node": ">= 10.13.0", + "npm": ">= 3.0.0" + } + }, "node_modules/source-map": { "version": "0.7.4", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.7.4.tgz", @@ -7333,6 +8743,16 @@ "deprecated": "Please use @jridgewell/sourcemap-codec instead", "dev": true }, + "node_modules/sparse-bitfield": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/sparse-bitfield/-/sparse-bitfield-3.0.3.tgz", + "integrity": "sha512-kvzhi7vqKTfkh0PZU+2D2PIllw2ymqJKujUcyPMd9Y75Nv4nPbGJZXNhxsgdQab2BmlDct1YnfQCguEvHr7VsQ==", + "optional": true, + "peer": true, + "dependencies": { + "memory-pager": "^1.0.2" + } + }, "node_modules/sprintf-js": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", @@ -7458,6 +8878,13 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/strnum": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/strnum/-/strnum-1.0.5.tgz", + "integrity": "sha512-J8bbNyKKXl5qYcR36TIO8W3mVGVHrmmxsd5PAItGkmyzwJvybiw2IVq5nqd0i4LSNSkB/sx9VHllbfFdr9k1JA==", + "optional": true, + "peer": true + }, "node_modules/superagent": { "version": "8.0.9", "resolved": "https://registry.npmjs.org/superagent/-/superagent-8.0.9.tgz", @@ -8058,6 +9485,14 @@ "node": ">= 0.4.0" } }, + "node_modules/uuid": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.0.tgz", + "integrity": "sha512-MXcSTerfPa4uqyzStbRoTgt5XIe3x5+42+q1sDuy3R5MDk66URdLMOZe5aPX/SQd+kuYAh0FdP/pO28IkQyTeg==", + "bin": { + "uuid": "dist/bin/uuid" + } + }, "node_modules/v8-compile-cache-lib": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz", diff --git a/server/package.json b/server/package.json index ec15c8a..7ce78ea 100644 --- a/server/package.json +++ b/server/package.json @@ -21,7 +21,9 @@ }, "dependencies": { "@nestjs/common": "^9.0.0", + "@nestjs/config": "^2.3.1", "@nestjs/core": "^9.0.0", + "@nestjs/mongoose": "^9.2.1", "@nestjs/platform-express": "^9.0.0", "reflect-metadata": "^0.1.13", "rxjs": "^7.2.0" diff --git a/server/src/app.module.ts b/server/src/app.module.ts index 8662803..7e8019f 100644 --- a/server/src/app.module.ts +++ b/server/src/app.module.ts @@ -1,9 +1,23 @@ import { Module } from '@nestjs/common'; import { AppController } from './app.controller'; import { AppService } from './app.service'; +import { MongooseModule } from '@nestjs/mongoose'; +import { ConfigModule } from '@nestjs/config'; +import * as process from 'process'; @Module({ - imports: [], + imports: [ + ConfigModule.forRoot({ + envFilePath: '.env', + }), + MongooseModule.forRoot( + process.env.MONGODB_CONNECTION_URL || 'mongodb://127.0.0.1:27017', + { + useNewUrlParser: true, + useUnifiedTopology: true, + }, + ), + ], controllers: [AppController], providers: [AppService], }) From 312e05e47cd01e00f67316299f483a4364abd08c Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sat, 11 Feb 2023 02:10:29 +0300 Subject: [PATCH 043/196] feat: create user model and schema --- server/package-lock.json | 10 ++++++- server/package.json | 4 ++- server/src/models/scheme/user.schema.ts | 35 +++++++++++++++++++++++++ server/src/types/enums/authProviders.ts | 3 +++ server/src/types/interfaces/user.ts | 8 ++++++ 5 files changed, 58 insertions(+), 2 deletions(-) create mode 100644 server/src/models/scheme/user.schema.ts create mode 100644 server/src/types/enums/authProviders.ts create mode 100644 server/src/types/interfaces/user.ts diff --git a/server/package-lock.json b/server/package-lock.json index 8fa3354..21e7961 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -15,7 +15,8 @@ "@nestjs/mongoose": "^9.2.1", "@nestjs/platform-express": "^9.0.0", "reflect-metadata": "^0.1.13", - "rxjs": "^7.2.0" + "rxjs": "^7.2.0", + "uuid": "^9.0.0" }, "devDependencies": { "@nestjs/cli": "^9.0.0", @@ -25,6 +26,7 @@ "@types/jest": "29.2.4", "@types/node": "18.11.18", "@types/supertest": "^2.0.11", + "@types/uuid": "^9.0.0", "@typescript-eslint/eslint-plugin": "^5.0.0", "@typescript-eslint/parser": "^5.0.0", "eslint": "^8.0.1", @@ -3260,6 +3262,12 @@ "@types/superagent": "*" } }, + "node_modules/@types/uuid": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-9.0.0.tgz", + "integrity": "sha512-kr90f+ERiQtKWMz5rP32ltJ/BtULDI5RVO0uavn1HQUOwjx0R1h0rnDYNL0CepF1zL5bSY6FISAfd9tOdDhU5Q==", + "dev": true + }, "node_modules/@types/webidl-conversions": { "version": "7.0.0", "resolved": "https://registry.npmjs.org/@types/webidl-conversions/-/webidl-conversions-7.0.0.tgz", diff --git a/server/package.json b/server/package.json index 7ce78ea..4e8f4d2 100644 --- a/server/package.json +++ b/server/package.json @@ -26,7 +26,8 @@ "@nestjs/mongoose": "^9.2.1", "@nestjs/platform-express": "^9.0.0", "reflect-metadata": "^0.1.13", - "rxjs": "^7.2.0" + "rxjs": "^7.2.0", + "uuid": "^9.0.0" }, "devDependencies": { "@nestjs/cli": "^9.0.0", @@ -36,6 +37,7 @@ "@types/jest": "29.2.4", "@types/node": "18.11.18", "@types/supertest": "^2.0.11", + "@types/uuid": "^9.0.0", "@typescript-eslint/eslint-plugin": "^5.0.0", "@typescript-eslint/parser": "^5.0.0", "eslint": "^8.0.1", diff --git a/server/src/models/scheme/user.schema.ts b/server/src/models/scheme/user.schema.ts new file mode 100644 index 0000000..edae557 --- /dev/null +++ b/server/src/models/scheme/user.schema.ts @@ -0,0 +1,35 @@ +import { Document } from 'mongoose'; +import { Prop, Schema, SchemaFactory } from '@nestjs/mongoose'; +import { v4 as UUIDv4 } from 'uuid'; +import { IUser } from '../../types/interfaces/user'; +import { AuthProvider } from '../../types/enums/authProviders'; + +@Schema({ collection: 'users' }) +export class User extends Document implements IUser { + @Prop({ + type: String, + isRequired: true, + default: UUIDv4, + }) + _id: string; + + @Prop({ + type: String, + isRequired: true, + }) + username: string; + + @Prop({ + type: String, + isRequired: false, + }) + password?: string; + + @Prop({ + type: String, + isRequired: true, + }) + authProvider: AuthProvider; +} + +export const UserSchema = SchemaFactory.createForClass(User); diff --git a/server/src/types/enums/authProviders.ts b/server/src/types/enums/authProviders.ts new file mode 100644 index 0000000..efe0613 --- /dev/null +++ b/server/src/types/enums/authProviders.ts @@ -0,0 +1,3 @@ +export enum AuthProvider { + PASSWORD = 'jwt', +} diff --git a/server/src/types/interfaces/user.ts b/server/src/types/interfaces/user.ts new file mode 100644 index 0000000..133185b --- /dev/null +++ b/server/src/types/interfaces/user.ts @@ -0,0 +1,8 @@ +import { AuthProvider } from '../enums/authProviders'; + +export interface IUser { + readonly _id: string; + readonly username: string; + readonly password?: string; + readonly authProvider: AuthProvider; +} From 1a31ab4188fbb68515c3f5d9af86b9dad7ea0617 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sat, 11 Feb 2023 14:48:56 +0300 Subject: [PATCH 044/196] feat: create user service with CRUD operations --- server/src/app.module.ts | 2 + .../dto/requests/createUserRequestDto.ts | 3 ++ server/src/types/dto/responses/userDto.ts | 3 ++ server/src/user/user.module.ts | 14 +++++++ server/src/user/user.service.ts | 37 +++++++++++++++++++ 5 files changed, 59 insertions(+) create mode 100644 server/src/types/dto/requests/createUserRequestDto.ts create mode 100644 server/src/types/dto/responses/userDto.ts create mode 100644 server/src/user/user.module.ts create mode 100644 server/src/user/user.service.ts diff --git a/server/src/app.module.ts b/server/src/app.module.ts index 7e8019f..20d0d6a 100644 --- a/server/src/app.module.ts +++ b/server/src/app.module.ts @@ -3,6 +3,7 @@ import { AppController } from './app.controller'; import { AppService } from './app.service'; import { MongooseModule } from '@nestjs/mongoose'; import { ConfigModule } from '@nestjs/config'; +import { UserModule } from './user/user.module'; import * as process from 'process'; @Module({ @@ -17,6 +18,7 @@ import * as process from 'process'; useUnifiedTopology: true, }, ), + UserModule, ], controllers: [AppController], providers: [AppService], diff --git a/server/src/types/dto/requests/createUserRequestDto.ts b/server/src/types/dto/requests/createUserRequestDto.ts new file mode 100644 index 0000000..7cc8f25 --- /dev/null +++ b/server/src/types/dto/requests/createUserRequestDto.ts @@ -0,0 +1,3 @@ +import { IUser } from '../../interfaces/user'; + +export type CreateUserRequestDto = Readonly>; diff --git a/server/src/types/dto/responses/userDto.ts b/server/src/types/dto/responses/userDto.ts new file mode 100644 index 0000000..a84edb7 --- /dev/null +++ b/server/src/types/dto/responses/userDto.ts @@ -0,0 +1,3 @@ +import { IUser } from '../../interfaces/user'; + +export type UserDto = Readonly>; diff --git a/server/src/user/user.module.ts b/server/src/user/user.module.ts new file mode 100644 index 0000000..1b6e41f --- /dev/null +++ b/server/src/user/user.module.ts @@ -0,0 +1,14 @@ +import { Module } from '@nestjs/common'; +import { UserService } from './user.service'; +import { MongooseModule } from '@nestjs/mongoose'; +import { User, UserSchema } from '../models/scheme/user.schema'; +import { UserController } from './user.controller'; + +@Module({ + imports: [ + MongooseModule.forFeature([{ name: User.name, schema: UserSchema }]), + ], + providers: [UserService], + controllers: [UserController], +}) +export class UserModule {} diff --git a/server/src/user/user.service.ts b/server/src/user/user.service.ts new file mode 100644 index 0000000..16a4a9a --- /dev/null +++ b/server/src/user/user.service.ts @@ -0,0 +1,37 @@ +import { Injectable } from '@nestjs/common'; +import { InjectModel } from '@nestjs/mongoose'; +import { Model } from 'mongoose'; +import { User } from '../models/scheme/user.schema'; +import { CreateUserRequestDto } from '../types/dto/requests/createUserRequestDto'; +import { UserDto } from '../types/dto/responses/userDto'; + +@Injectable() +export class UserService { + constructor( + @InjectModel(User.name) private readonly userModel: Model, + ) {} + + async findAll(): Promise { + return await this.userModel.find().exec(); + } + + async findOne(id: string): Promise { + return await this.userModel.findOne({ _id: id }).exec(); + } + + async create(requestDto: CreateUserRequestDto): Promise { + const newUser = new this.userModel(requestDto); + return await newUser.save(); + } + + async update( + id: string, + user: CreateUserRequestDto, + ): Promise { + return this.userModel.findByIdAndUpdate(id, user, { new: true }); + } + + async delete(id: string): Promise { + return this.userModel.findByIdAndDelete(id); + } +} From 90c8ae82ce27f38c81d2b08c113b9c705b516015 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sat, 11 Feb 2023 02:10:29 +0300 Subject: [PATCH 045/196] feat: create user model and schema --- server/package-lock.json | 10 ++++++- server/package.json | 4 ++- server/src/models/scheme/user.schema.ts | 35 +++++++++++++++++++++++++ server/src/types/enums/authProviders.ts | 3 +++ server/src/types/interfaces/user.ts | 8 ++++++ 5 files changed, 58 insertions(+), 2 deletions(-) create mode 100644 server/src/models/scheme/user.schema.ts create mode 100644 server/src/types/enums/authProviders.ts create mode 100644 server/src/types/interfaces/user.ts diff --git a/server/package-lock.json b/server/package-lock.json index 8fa3354..21e7961 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -15,7 +15,8 @@ "@nestjs/mongoose": "^9.2.1", "@nestjs/platform-express": "^9.0.0", "reflect-metadata": "^0.1.13", - "rxjs": "^7.2.0" + "rxjs": "^7.2.0", + "uuid": "^9.0.0" }, "devDependencies": { "@nestjs/cli": "^9.0.0", @@ -25,6 +26,7 @@ "@types/jest": "29.2.4", "@types/node": "18.11.18", "@types/supertest": "^2.0.11", + "@types/uuid": "^9.0.0", "@typescript-eslint/eslint-plugin": "^5.0.0", "@typescript-eslint/parser": "^5.0.0", "eslint": "^8.0.1", @@ -3260,6 +3262,12 @@ "@types/superagent": "*" } }, + "node_modules/@types/uuid": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-9.0.0.tgz", + "integrity": "sha512-kr90f+ERiQtKWMz5rP32ltJ/BtULDI5RVO0uavn1HQUOwjx0R1h0rnDYNL0CepF1zL5bSY6FISAfd9tOdDhU5Q==", + "dev": true + }, "node_modules/@types/webidl-conversions": { "version": "7.0.0", "resolved": "https://registry.npmjs.org/@types/webidl-conversions/-/webidl-conversions-7.0.0.tgz", diff --git a/server/package.json b/server/package.json index 7ce78ea..4e8f4d2 100644 --- a/server/package.json +++ b/server/package.json @@ -26,7 +26,8 @@ "@nestjs/mongoose": "^9.2.1", "@nestjs/platform-express": "^9.0.0", "reflect-metadata": "^0.1.13", - "rxjs": "^7.2.0" + "rxjs": "^7.2.0", + "uuid": "^9.0.0" }, "devDependencies": { "@nestjs/cli": "^9.0.0", @@ -36,6 +37,7 @@ "@types/jest": "29.2.4", "@types/node": "18.11.18", "@types/supertest": "^2.0.11", + "@types/uuid": "^9.0.0", "@typescript-eslint/eslint-plugin": "^5.0.0", "@typescript-eslint/parser": "^5.0.0", "eslint": "^8.0.1", diff --git a/server/src/models/scheme/user.schema.ts b/server/src/models/scheme/user.schema.ts new file mode 100644 index 0000000..edae557 --- /dev/null +++ b/server/src/models/scheme/user.schema.ts @@ -0,0 +1,35 @@ +import { Document } from 'mongoose'; +import { Prop, Schema, SchemaFactory } from '@nestjs/mongoose'; +import { v4 as UUIDv4 } from 'uuid'; +import { IUser } from '../../types/interfaces/user'; +import { AuthProvider } from '../../types/enums/authProviders'; + +@Schema({ collection: 'users' }) +export class User extends Document implements IUser { + @Prop({ + type: String, + isRequired: true, + default: UUIDv4, + }) + _id: string; + + @Prop({ + type: String, + isRequired: true, + }) + username: string; + + @Prop({ + type: String, + isRequired: false, + }) + password?: string; + + @Prop({ + type: String, + isRequired: true, + }) + authProvider: AuthProvider; +} + +export const UserSchema = SchemaFactory.createForClass(User); diff --git a/server/src/types/enums/authProviders.ts b/server/src/types/enums/authProviders.ts new file mode 100644 index 0000000..67e012c --- /dev/null +++ b/server/src/types/enums/authProviders.ts @@ -0,0 +1,3 @@ +export enum AuthProvider { + LOCAL = 'local', +} diff --git a/server/src/types/interfaces/user.ts b/server/src/types/interfaces/user.ts new file mode 100644 index 0000000..133185b --- /dev/null +++ b/server/src/types/interfaces/user.ts @@ -0,0 +1,8 @@ +import { AuthProvider } from '../enums/authProviders'; + +export interface IUser { + readonly _id: string; + readonly username: string; + readonly password?: string; + readonly authProvider: AuthProvider; +} From 913fde22cfe391f2a45dcdb350ecbcf75ecb7e19 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sat, 11 Feb 2023 18:13:28 +0300 Subject: [PATCH 046/196] feat: create a selection controller for the desired animation --- .../src/scripts/controllers/playAnimator.ts | 74 +++++++++++++++++++ 1 file changed, 74 insertions(+) create mode 100644 client/src/scripts/controllers/playAnimator.ts diff --git a/client/src/scripts/controllers/playAnimator.ts b/client/src/scripts/controllers/playAnimator.ts new file mode 100644 index 0000000..86530fe --- /dev/null +++ b/client/src/scripts/controllers/playAnimator.ts @@ -0,0 +1,74 @@ +import { IPlayerAnimator } from '../../types/interfaces/playerAnimator'; +import Direction from '../../types/enums/directions'; + +class PlayAnimator implements IPlayerAnimator { + constructor(private readonly playerBlock: HTMLElement) { + + } + + stand(direction: Direction): void { + this.playerBlock.removeAttribute('class'); + this.playerBlock.setAttribute( + 'class', + `players-animate-stand-${direction}`, + ); + } + + move(direction: Direction): void { + this.playerBlock.removeAttribute('class'); + this.playerBlock.setAttribute( + 'class', + `players-animate-move-${direction}`, + ); + } + + jump(direction: Direction): void { + this.playerBlock.removeAttribute('class'); + this.playerBlock.setAttribute( + 'class', + `players-animate-jump-${direction}`, + ); + } + + fall(direction: Direction): void { + this.playerBlock.removeAttribute('class'); + this.playerBlock.setAttribute( + 'class', + `players-animate-fall-${direction}`, + ); + } + + look(direction: Direction): void { + this.playerBlock.removeAttribute('class'); + this.playerBlock.setAttribute( + 'class', + `players-animate-look-${direction}`, + ); + } + + shoot(direction: Direction): void { + this.playerBlock.removeAttribute('class'); + this.playerBlock.setAttribute( + 'class', + `players-animate-shoot-${direction}`, + ); + } + + reload(): void { + this.playerBlock.removeAttribute('class'); + this.playerBlock.setAttribute( + 'class', + 'players-animate-reload', + ); + } + + exit(): void { + this.playerBlock.removeAttribute('class'); + this.playerBlock.setAttribute( + 'class', + 'players-animate-exit', + ); + } +} + +export default PlayAnimator; From 22b55c9a5496849837cf28d9c324405292d27453 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sat, 11 Feb 2023 18:15:10 +0300 Subject: [PATCH 047/196] feat: add a sprite for the main character animation --- client/src/assets/sprites/dave_sprites.png | Bin 0 -> 13960 bytes 1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 client/src/assets/sprites/dave_sprites.png diff --git a/client/src/assets/sprites/dave_sprites.png b/client/src/assets/sprites/dave_sprites.png new file mode 100644 index 0000000000000000000000000000000000000000..07f8bcf17fa7fc4803d771035e912b2c67e551be GIT binary patch literal 13960 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 literal 0 HcmV?d00001 From 27e0e1c48490af93bb2c294816a457f7947d2fd4 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sat, 11 Feb 2023 18:17:10 +0300 Subject: [PATCH 048/196] feat: add an interface for select the desired animation --- client/src/types/interfaces/playerAnimator.ts | 12 ++++++++++++ 1 file changed, 12 insertions(+) create mode 100644 client/src/types/interfaces/playerAnimator.ts diff --git a/client/src/types/interfaces/playerAnimator.ts b/client/src/types/interfaces/playerAnimator.ts new file mode 100644 index 0000000..de3f0b0 --- /dev/null +++ b/client/src/types/interfaces/playerAnimator.ts @@ -0,0 +1,12 @@ +import Direction from '../enums/directions'; + +export interface IPlayerAnimator { + stand(direction: Direction): void + move(direction: Direction): void + jump(direction: Direction): void + fall(direction: Direction): void + reload(): void + shoot(direction: Direction): void + look(direction: Direction): void + exit(): void +} From 12bf459acccc36cd806fa77ef6ad090230eeefcb Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sat, 11 Feb 2023 18:18:49 +0300 Subject: [PATCH 049/196] =?UTF-8?q?feat:=20=D0=B0dd=20enum=20to=20select?= =?UTF-8?q?=20animation=20direction?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- client/src/types/enums/directions.ts | 12 ++++++++++++ 1 file changed, 12 insertions(+) create mode 100644 client/src/types/enums/directions.ts diff --git a/client/src/types/enums/directions.ts b/client/src/types/enums/directions.ts new file mode 100644 index 0000000..2059431 --- /dev/null +++ b/client/src/types/enums/directions.ts @@ -0,0 +1,12 @@ +enum Direction { + LEFT = 'left', + RIGHT = 'right', + UP = 'up', + DOWN = 'down', + TOP_RIGHT = 'topRight', + TOP_LEFT = 'topLeft', + DOWN_RIGHT = 'downRight', + DOWN_LEFT = 'downLeft', +} + +export default Direction; From bf18917d99e11fef6d995fff2b2f5acb748a07c7 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sat, 11 Feb 2023 18:24:00 +0300 Subject: [PATCH 050/196] feat: add animation styles and its keyframes --- client/src/index.ts | 15 +- client/src/styles/dave.css | 7 +- client/src/styles/playerAnimation.scss | 145 +++++++++++ .../src/styles/playerAnimationKeyframes.scss | 229 ++++++++++++++++++ 4 files changed, 380 insertions(+), 16 deletions(-) create mode 100644 client/src/styles/playerAnimation.scss create mode 100644 client/src/styles/playerAnimationKeyframes.scss diff --git a/client/src/index.ts b/client/src/index.ts index fd7c0a9..bc37ed1 100644 --- a/client/src/index.ts +++ b/client/src/index.ts @@ -1,19 +1,6 @@ import '@styles/main'; +import '@styles/playerAnimation'; import PlayLevel from './scripts/controllers/playLevel'; const playLevel = new PlayLevel(); playLevel.startGame(); - -( - async (): Promise => { - const text = await fetch( - `${process.env.API_URL}`, - { - method: 'GET', - }, - ) - .then((res) => res.text()); - - console.log(text); - } -)(); diff --git a/client/src/styles/dave.css b/client/src/styles/dave.css index 21b52f9..3f42a68 100644 --- a/client/src/styles/dave.css +++ b/client/src/styles/dave.css @@ -1,6 +1,9 @@ +@import "./playerAnimation"; + .player { position: absolute; + background: url("../assets/sprites/dave_sprites.png") 0 0; + background-size: 5257px; top: 0; left: 0; - background-color: brown; -} \ No newline at end of file +} diff --git a/client/src/styles/playerAnimation.scss b/client/src/styles/playerAnimation.scss new file mode 100644 index 0000000..52451d5 --- /dev/null +++ b/client/src/styles/playerAnimation.scss @@ -0,0 +1,145 @@ +@import "playerAnimationKeyframes"; + +$bg-size: 5257px; + +.players { + &-animate-stand-left { + background: url("../assets/sprites/dave_sprites.png") -583px 0; + background-size: $bg-size; + } + + &-animate-stand-right { + background: url("../assets/sprites/dave_sprites.png") 0 0; + background-size: $bg-size; + } + + &-animate { + background: url("../assets/sprites/dave_sprites.png"); + background-size: $bg-size; + animation-timing-function: steps(1); + + &-move-left { + background: url("../assets/sprites/dave_sprites.png"); + animation: move-left 0.5s ease-in-out infinite; + background-size: $bg-size; + animation-timing-function: steps(1); + } + + &-move-right { + background: url("../assets/sprites/dave_sprites.png"); + animation: move-right 0.5s ease-in-out infinite; + background-size: $bg-size; + animation-timing-function: steps(1); + } + + &-jump { + &-left { + background: url("../assets/sprites/dave_sprites.png"); + animation: jump-left 0.7s ease-in-out; + background-size: $bg-size; + animation-timing-function: steps(1); + } + + &-right { + background: url("../assets/sprites/dave_sprites.png"); + animation: jump-right 0.7s ease-in-out; + background-size: $bg-size; + animation-timing-function: steps(1); + } + } + &-fall { + &-left { + background: url("../assets/sprites/dave_sprites.png"); + animation: fall-left 0.7s ease-in-out infinite; + background-size: $bg-size; + animation-timing-function: steps(1); + } + + &-right { + background: url("../assets/sprites/dave_sprites.png"); + animation: fall-right 0.7s ease-in-out infinite; + background-size: $bg-size; + animation-timing-function: steps(1); + } + } + + &-look { + &-topRight { + background: url("../assets/sprites/dave_sprites.png") -2552px 0; + width: 73px !important; + background-size: $bg-size; + } + + &-topLeft { + background: url("../assets/sprites/dave_sprites.png") -3043px 0; + width: 73px !important; + background-size: $bg-size; + } + &-downRight { + background: url("../assets/sprites/dave_sprites.png") -2696px 0; + width: 73px !important; + background-size: $bg-size; + } + + &-downLeft { + background: url("../assets/sprites/dave_sprites.png") -3179px 0; + width: 69px !important; + background-size: $bg-size; + } + } + &-shoot { + &-left { + background: url("../assets/sprites/dave_sprites.png"); + animation: shoot-left 0.5s ease-in-out infinite; + background-size: $bg-size; + animation-timing-function: steps(1); + } + + &-right { + background: url("../assets/sprites/dave_sprites.png"); + animation: shoot-right 0.5s ease-in-out infinite; + background-size: $bg-size; + animation-timing-function: steps(1); + } + + &-topRight { + background: url("../assets/sprites/dave_sprites.png"); + animation: shoot-top-right 0.5s ease-in-out infinite; + background-size: $bg-size; + animation-timing-function: steps(1); + } + + &-topLeft { + background: url("../assets/sprites/dave_sprites.png"); + animation: shoot-top-left 0.5s ease-in-out infinite; + background-size: $bg-size; + animation-timing-function: steps(1); + } + &-downRight { + background: url("../assets/sprites/dave_sprites.png"); + animation: shoot-down-right 0.5s ease-in-out infinite; + background-size: $bg-size; + animation-timing-function: steps(1); + } + + &-downLeft { + background: url("../assets/sprites/dave_sprites.png"); + animation: shoot-down-left 0.5s ease-in-out infinite; + background-size: $bg-size; + animation-timing-function: steps(1); + } + } + &-exit { + background: url("../assets/sprites/dave_sprites.png"); + animation: exit 1s ease-in-out infinite; + background-size: $bg-size; + animation-timing-function: steps(1); + } + &-reload { + background: url("../assets/sprites/dave_sprites.png"); + animation: reload 0.5s ease-in-out infinite; + background-size: $bg-size; + animation-timing-function: steps(1); + } + } +} diff --git a/client/src/styles/playerAnimationKeyframes.scss b/client/src/styles/playerAnimationKeyframes.scss new file mode 100644 index 0000000..6bbec9d --- /dev/null +++ b/client/src/styles/playerAnimationKeyframes.scss @@ -0,0 +1,229 @@ +@keyframes move-left { + 0% { + background-position: -644px 0; + width: 78px; + } + + 25% { + background-position: -714px 0; + width: 78px; + } + + 50% { + background-position: -783px 0; + width: 78px; + } + + 75% { + background-position: -854px 0; + width: 78px; + } +} + +@keyframes move-right { + 0% { + background-position: -69px 0; + width: 78px; + } + + 25% { + background-position: -144px 0; + width: 78px; + } + + 50% { + background-position: -212px 0; + width: 78px; + } + + 75% { + background-position: -282px 0; + width: 78px; + } +} + +@keyframes jump-left { + 0% { + background-position: -355px 0; + width: 78px; + } + + 25% { + background-position: -432px 0; + width: 78px; + } + + 50% { + background-position: -498px 0; + width: 78px; + } +} + +@keyframes jump-right { + 0% { + background-position: -923px 0; + width: 78px; + } + + 25% { + background-position: -996px 0; + width: 78px; + } + + 50% { + background-position: -1067px 0; + width: 78px; + } +} + +@keyframes fall-left { + + 0% { + background-position: -432px 0; + width: 78px; + } + + 50% { + background-position: -498px 0; + width: 78px; + } +} + +@keyframes fall-right { + + 0% { + background-position: -996px 0; + width: 78px; + } + + 50% { + background-position: -1067px 0; + width: 78px; + } +} + +@keyframes fall-right { + + 0% { + background-position: -996px 0; + width: 78px; + } + + 50% { + background-position: -1067px 0; + width: 78px; + } +} + +@keyframes reload { + + 0% { + background-position: -1152px 0; + width: 78px; + } + + 50% { + background-position: -1220px 0; + width: 69px; + } +} + +@keyframes shoot-right{ + + 0% { + background-position: -2381px 0; + width: 82px; + } + + 50% { + background-position: -2473px 0; + width: 82px; + } +} + +@keyframes shoot-top-right{ + + 0% { + background-position: -2552px 0; + width: 75px; + } + + 50% { + background-position: -2619px 0; + width: 75px; + } +} + +@keyframes shoot-down-right{ + + 0% { + background-position: -2696px 0; + width: 75px; + } + + 50% { + background-position: -2773px 0; + width: 70px; + } +} + +@keyframes shoot-left{ + + 0% { + background-position: -2845px 0; + width: 78px; + } + + 50% { + background-position: -2945px 0; + width: 78px; + } +} + +@keyframes shoot-top-left{ + + 0% { + background-position: -3043px 0; + width: 75px; + } + + 50% { + background-position: -3121px 0; + width: 56px; + } +} + +@keyframes shoot-down-left{ + + 0% { + background-position: -3179px 0; + width: 69px; + } + + 50% { + background-position: -3250px 0; + width: 70px; + } +} + +@keyframes exit { + 0% { + background-position: -3323px 0; + width: 78px; + } + + 25% { + background-position: -3400px 0; + width: 78px; + } + + 50% { + background-position: -3470px 0; + width: 78px; + } + + 75% { + background-position: -3545px 0; + width: 63px; + } +} From 5610ade2833ea7ab8eb94e0c3a5bd9679c96dae8 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sat, 11 Feb 2023 18:33:44 +0300 Subject: [PATCH 051/196] refactor: refactor apply stylint --- client/src/styles/playerAnimation.scss | 6 +++++ .../src/styles/playerAnimationKeyframes.scss | 22 +++++-------------- 2 files changed, 12 insertions(+), 16 deletions(-) diff --git a/client/src/styles/playerAnimation.scss b/client/src/styles/playerAnimation.scss index 52451d5..c3406d0 100644 --- a/client/src/styles/playerAnimation.scss +++ b/client/src/styles/playerAnimation.scss @@ -47,6 +47,7 @@ $bg-size: 5257px; animation-timing-function: steps(1); } } + &-fall { &-left { background: url("../assets/sprites/dave_sprites.png"); @@ -75,6 +76,7 @@ $bg-size: 5257px; width: 73px !important; background-size: $bg-size; } + &-downRight { background: url("../assets/sprites/dave_sprites.png") -2696px 0; width: 73px !important; @@ -87,6 +89,7 @@ $bg-size: 5257px; background-size: $bg-size; } } + &-shoot { &-left { background: url("../assets/sprites/dave_sprites.png"); @@ -115,6 +118,7 @@ $bg-size: 5257px; background-size: $bg-size; animation-timing-function: steps(1); } + &-downRight { background: url("../assets/sprites/dave_sprites.png"); animation: shoot-down-right 0.5s ease-in-out infinite; @@ -129,12 +133,14 @@ $bg-size: 5257px; animation-timing-function: steps(1); } } + &-exit { background: url("../assets/sprites/dave_sprites.png"); animation: exit 1s ease-in-out infinite; background-size: $bg-size; animation-timing-function: steps(1); } + &-reload { background: url("../assets/sprites/dave_sprites.png"); animation: reload 0.5s ease-in-out infinite; diff --git a/client/src/styles/playerAnimationKeyframes.scss b/client/src/styles/playerAnimationKeyframes.scss index 6bbec9d..154842f 100644 --- a/client/src/styles/playerAnimationKeyframes.scss +++ b/client/src/styles/playerAnimationKeyframes.scss @@ -77,7 +77,6 @@ } @keyframes fall-left { - 0% { background-position: -432px 0; width: 78px; @@ -90,7 +89,6 @@ } @keyframes fall-right { - 0% { background-position: -996px 0; width: 78px; @@ -103,7 +101,6 @@ } @keyframes fall-right { - 0% { background-position: -996px 0; width: 78px; @@ -116,7 +113,6 @@ } @keyframes reload { - 0% { background-position: -1152px 0; width: 78px; @@ -128,8 +124,7 @@ } } -@keyframes shoot-right{ - +@keyframes shoot-right { 0% { background-position: -2381px 0; width: 82px; @@ -141,8 +136,7 @@ } } -@keyframes shoot-top-right{ - +@keyframes shoot-top-right { 0% { background-position: -2552px 0; width: 75px; @@ -154,8 +148,7 @@ } } -@keyframes shoot-down-right{ - +@keyframes shoot-down-right { 0% { background-position: -2696px 0; width: 75px; @@ -167,8 +160,7 @@ } } -@keyframes shoot-left{ - +@keyframes shoot-left { 0% { background-position: -2845px 0; width: 78px; @@ -180,8 +172,7 @@ } } -@keyframes shoot-top-left{ - +@keyframes shoot-top-left { 0% { background-position: -3043px 0; width: 75px; @@ -193,8 +184,7 @@ } } -@keyframes shoot-down-left{ - +@keyframes shoot-down-left { 0% { background-position: -3179px 0; width: 69px; From 8fea2e8046692ea9383193ec3635d428dca49e45 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sat, 11 Feb 2023 18:42:21 +0300 Subject: [PATCH 052/196] fix: import scss --- client/src/index.ts | 1 - client/src/styles/main.scss | 12 +++++++----- 2 files changed, 7 insertions(+), 6 deletions(-) diff --git a/client/src/index.ts b/client/src/index.ts index bc37ed1..249dc76 100644 --- a/client/src/index.ts +++ b/client/src/index.ts @@ -1,5 +1,4 @@ import '@styles/main'; -import '@styles/playerAnimation'; import PlayLevel from './scripts/controllers/playLevel'; const playLevel = new PlayLevel(); diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index 5bb33ba..16a43f3 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -1,5 +1,7 @@ -* { - margin: 0; - padding: 0; - box-sizing: border-box; -} +@import "playerAnimation"; + +* { + margin: 0; + padding: 0; + box-sizing: border-box; +} From 654951ca6196038cc1b486cf1820316cc4b27a69 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sat, 11 Feb 2023 19:02:42 +0300 Subject: [PATCH 053/196] fix: base styles are not erase --- .../src/scripts/controllers/playAnimator.ts | 40 +++++++++++++++---- client/src/styles/dave.css | 2 +- client/src/styles/playerAnimation.scss | 4 +- 3 files changed, 35 insertions(+), 11 deletions(-) diff --git a/client/src/scripts/controllers/playAnimator.ts b/client/src/scripts/controllers/playAnimator.ts index 86530fe..0157f92 100644 --- a/client/src/scripts/controllers/playAnimator.ts +++ b/client/src/scripts/controllers/playAnimator.ts @@ -7,66 +7,90 @@ class PlayAnimator implements IPlayerAnimator { } stand(direction: Direction): void { + const classes = this.playerBlock.classList.toString() + .replace(/players-[^\s]+/g, '') + .trim(); this.playerBlock.removeAttribute('class'); this.playerBlock.setAttribute( 'class', - `players-animate-stand-${direction}`, + `${classes} players-animate-stand-${direction}`, ); } move(direction: Direction): void { + const classes = this.playerBlock.classList.toString() + .replace(/players-[^\s]+/g, '') + .trim(); this.playerBlock.removeAttribute('class'); this.playerBlock.setAttribute( 'class', - `players-animate-move-${direction}`, + `${classes} players-animate-move-${direction}`.trim(), ); } jump(direction: Direction): void { + const classes = this.playerBlock.classList.toString() + .replace(/players-[^\s]+/g, '') + .trim(); this.playerBlock.removeAttribute('class'); this.playerBlock.setAttribute( 'class', - `players-animate-jump-${direction}`, + `${classes} players-animate-jump-${direction}`.trim(), ); } fall(direction: Direction): void { + const classes = this.playerBlock.classList.toString() + .replace(/players-[^\s]+/g, '') + .trim(); this.playerBlock.removeAttribute('class'); this.playerBlock.setAttribute( 'class', - `players-animate-fall-${direction}`, + `${classes} players-animate-fall-${direction}`.trim(), ); } look(direction: Direction): void { + const classes = this.playerBlock.classList.toString() + .replace(/players-[^\s]+/g, '') + .trim(); this.playerBlock.removeAttribute('class'); this.playerBlock.setAttribute( 'class', - `players-animate-look-${direction}`, + `${classes} players-animate-look-${direction}`.trim(), ); } shoot(direction: Direction): void { + const classes = this.playerBlock.classList.toString() + .replace(/players-[^\s]+/g, '') + .trim(); this.playerBlock.removeAttribute('class'); this.playerBlock.setAttribute( 'class', - `players-animate-shoot-${direction}`, + `${classes} players-animate-shoot-${direction}`.trim(), ); } reload(): void { + const classes = this.playerBlock.classList.toString() + .replace(/players-[^\s]+/g, '') + .trim(); this.playerBlock.removeAttribute('class'); this.playerBlock.setAttribute( 'class', - 'players-animate-reload', + `${classes} players-animate-reload`.trim(), ); } exit(): void { + const classes = this.playerBlock.classList.toString() + .replace(/players-[^\s]+/g, '') + .trim(); this.playerBlock.removeAttribute('class'); this.playerBlock.setAttribute( 'class', - 'players-animate-exit', + `${classes} players-animate-exit`.trim(), ); } } diff --git a/client/src/styles/dave.css b/client/src/styles/dave.css index 3f42a68..d4590d3 100644 --- a/client/src/styles/dave.css +++ b/client/src/styles/dave.css @@ -2,7 +2,7 @@ .player { position: absolute; - background: url("../assets/sprites/dave_sprites.png") 0 0; + background-image: url("../assets/sprites/dave_sprites.png"); background-size: 5257px; top: 0; left: 0; diff --git a/client/src/styles/playerAnimation.scss b/client/src/styles/playerAnimation.scss index c3406d0..c3de066 100644 --- a/client/src/styles/playerAnimation.scss +++ b/client/src/styles/playerAnimation.scss @@ -4,12 +4,12 @@ $bg-size: 5257px; .players { &-animate-stand-left { - background: url("../assets/sprites/dave_sprites.png") -583px 0; + background-position: -583px 0; background-size: $bg-size; } &-animate-stand-right { - background: url("../assets/sprites/dave_sprites.png") 0 0; + background-position: 0 0; background-size: $bg-size; } From a4b8629e8f6431d43c5f464451c9d8ef4f7db0cc Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sat, 11 Feb 2023 19:53:44 +0300 Subject: [PATCH 054/196] feat: add game score door with loot --- client/src/assets/levels/level1.ts | 68 ++++++++-------- client/src/assets/levels/loot1.png | Bin 0 -> 2948 bytes client/src/assets/levels/loot2.png | Bin 0 -> 2984 bytes client/src/assets/levels/loot4.png | Bin 0 -> 2993 bytes client/src/assets/levels/opendoor.png | Bin 0 -> 3269 bytes client/src/scripts/components/crone.ts | 7 ++ client/src/scripts/components/game.ts | 85 +++++++++++++++++++- client/src/scripts/components/zombie.ts | 4 + client/src/scripts/controllers/playLevel.ts | 32 +++++++- client/src/styles/crone.css | 2 + client/src/styles/dave.css | 1 + client/src/styles/level.css | 27 +++++++ client/src/styles/zombie.css | 2 + client/src/types/game.ts | 31 ++++++- 14 files changed, 218 insertions(+), 41 deletions(-) create mode 100644 client/src/assets/levels/loot1.png create mode 100644 client/src/assets/levels/loot2.png create mode 100644 client/src/assets/levels/loot4.png create mode 100644 client/src/assets/levels/opendoor.png diff --git a/client/src/assets/levels/level1.ts b/client/src/assets/levels/level1.ts index 4a6e6ba..bd88585 100644 --- a/client/src/assets/levels/level1.ts +++ b/client/src/assets/levels/level1.ts @@ -1,36 +1,36 @@ -export const LEVEL1 = `0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 0 Z 0 0 1 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 2 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 C 0 0 0 0 1 0 1 0 0 0 0 0 0 0 Z 0 0 0 0 0 Z 0 0 0 0 0 2 2 2 2 0 C 0 1 -0 0 0 0 0 0 2 2 2 2 0 0 0 0 0 0 0 0 2 1 2 2 2 1 1 1 1 1 1 1 1 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 -0 0 0 0 2 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 C 0 1 0 0 0 0 0 0 0 1 0 0 0 0 Z 0 0 Z 0 0 0 0 0 0 0 0 0 Z 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 1 1 1 1 1 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 2 2 2 1 1 1 1 1 1 1 1 1 1 1 1 -0 0 0 0 0 2 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 0 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 2 2 2 0 C 0 0 0 1 0 0 0 0 0 1 0 0 0 0 0 C 0 0 0 0 2 2 2 0 Z 0 0 0 0 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 1 1 1 1 1 1 1 1 1 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 2 2 1 1 1 1 1 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 1 0 0 0 1 0 0 0 0 0 Z 0 0 0 Z 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 1 1 1 1 1 1 1 1 1 1 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 2 2 1 1 1 1 1 1 -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 -0 0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 2 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 -0 0 0 0 0 0 2 0 1 1 0 0 0 0 0 0 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 2 0 0 0 0 0 1 -0 0 0 0 2 2 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 2 2 0 0 0 0 0 0 0 0 2 2 2 2 2 0 0 0 0 1 -0 0 0 0 0 0 0 0 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 Z 0 0 0 0 0 0 Z 0 0 Z 0 0 0 0 0 0 0 0 0 0 0 Z 2 2 2 2 2 2 2 0 Z 0 1 -0 D 0 0 0 0 0 0 1 1 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 -1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0`; +export const LEVEL1 = `0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W 1 +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W 0 Z 0 0 W 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P P 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 2 0 C 0 0 0 0 W 0 W 0 0 0 0 0 0 0 Z 0 0 0 0 0 Z 0 0 0 0 0 P P P P 0 C 0 W +0 0 0 0 0 0 P P P P 0 0 0 0 0 0 0 0 P W P P P W W W W W W W W 0 W W W W W W W W W W W W W W W W W W W W W W W W W W W W +0 0 0 0 P 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W +0 0 P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W +0 0 P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W +0 0 0 P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 2 0 C 0 W 0 0 0 0 0 0 0 W 0 0 0 0 Z 0 0 Z 0 0 0 0 0 0 0 0 0 Z 0 0 4 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P W W W W W 0 0 0 0 0 0 0 W W W W W W W W W W P P P W W W W W W W W W W W W +0 0 0 0 0 P 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P 0 0 0 0 0 0 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P 0 0 0 0 0 0 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 P 0 0 0 0 0 0 0 0 P W P P P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P 0 0 0 0 0 0 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P 0 0 0 0 0 0 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 1 C 0 0 0 W 0 0 0 0 0 W 0 0 0 1 0 C 0 0 0 0 P P P 0 Z 0 0 0 0 0 0 1 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W W W W W W W W W W 0 0 0 0 0 W W W W W W W W W W W W W W W W W P P P W W W W W W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 1 0 0 0 0 0 W 0 0 0 W 0 0 0 0 0 Z 0 0 0 Z 0 0 0 0 0 0 0 P P P 0 0 1 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W W W W W W W W W W W 0 0 0 W W W W W W W W W W W W W W W W W W P P P W W W W W W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P 0 0 0 0 0 W +0 0 0 0 0 0 0 0 0 W 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P 0 0 0 0 0 W +0 0 0 0 0 0 P 0 W W 0 0 0 0 0 0 0 0 W W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P 0 0 0 0 0 W +0 0 0 0 P P 0 0 W W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P 0 0 0 0 0 0 0 0 P P P P P 0 0 0 0 W +0 0 0 0 0 0 0 0 W W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 Z 0 0 0 0 0 0 Z 0 1 Z 0 0 0 0 0 0 0 0 0 0 0 Z P P P P P P P 0 Z 0 W +0 D 0 0 0 0 0 0 W W 0 0 0 0 0 0 0 W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W +W W W W W W W W W W W W W W W W W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0`; export const LEVEL2 = ''; diff --git a/client/src/assets/levels/loot1.png b/client/src/assets/levels/loot1.png new file mode 100644 index 0000000000000000000000000000000000000000..996c5f357359242e0c529b84e8fe7da1e5c3df26 GIT binary patch literal 2948 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 literal 0 HcmV?d00001 diff --git a/client/src/assets/levels/opendoor.png b/client/src/assets/levels/opendoor.png new file mode 100644 index 0000000000000000000000000000000000000000..29f850900cea78a9a7de40701dc60829e05a56f7 GIT binary patch literal 3269 zcmX|Dc{CL47k+0@GgFpq6Ovuo648gkAQ`fZv4?DB-}gZpBuW_B*T#~qp-7oz%aWZa zvSuftu@71L>3qNQ-Sgh(Iq$jmKKD8AU+-g#t_D4V69E9A*F@jI9<%jv5@08ek&1BV zJ0`d%+RO)lQ!IZI0y47B0)WtQQd7fV96fwJd>lPIc{SD4cs;#6?44Zi0T4KvZ4h9Z zNM%==q~2pRRvlieNOcVZ`~oCcJCj)+(=%Z6kck=98X1i+W@S5*g*IvlA4H(Dqi2X0 z$qp({qHo6-S;+n3883Q!KZvrry8mszb}?)5pcmK2h(E(DoUoAR4CJwq*A<3&;`Pui z9d&pp8+wYCmuaD^$$_pFfHfLiV5skF!E+ou0S)L?{70B-`A;%8nw z1tDNT`z6D6R?vPHyf%1q7Xgw0aK(kF@`F-(u(GA8LU}bSb0X0(GbwsmE4nhYv2kiIr%eZz{c9t4Bt$XYlW%}QiRDKKF6Pxnkm47 zUZm0PJq-ZoUjN4z!2q~H3=@5=a`N;?R#GEF z)<^EzMkLhc#0}JG!N%)Mswd{~=McGPQ&cz%8x@9W-@c~dB%aBbW~%xqB}czF#cUC_ z?1?;KeKx1*Z0#dBtx7wL#fDEI`iyPdFn=!$nI1>WZ-bV3hA-eSzX@aQywXn&p44hcC52V$(|m>cq23qsa6b7&^y&ANVYI}jpAgy^y(*-?-mMAbNP#R!z%F-5ICb)Hc zpMzE6NxZ2E)dWU@-n0FV=DBKCh1Td9ZFrs_wjhaFOZJ}fJnf6;(yHmiQvIHioUgFb zXocsuHQk8*7)gVu5*8W1456M(cD1eoiTuIO8BPvPR7c4r-x~Nt#Ci49ƚKTa+! zE=6nwoTh(7AJK-ky~yFh5zJ9^wwgmSUAvI(OKN(%;pK1ATt_{i=~D}K1RxexYARGFO3*q-Z8#kc+=<&X0`87mp%jJJ)yku--amc^IdhD=;B zTqc>PGZiws-W8W+mbLh2x=pgqu*QoFh-@3Uk4mi^tRPl0R!*$S@7U}J?YQmqad)3% z<{rA{do9G<*RR{()w6cFU|OcRq@|>J$;5%nA=f8+Qx;ixi_pcK>Ys`0P%`VC;YT6_$ zO5X9mV|Hi1?!4ZcEa9A?%WmysE#^~oUBT80N{aV>_b$;WeNuux4|*O|Us%sSsaP)% zIux27dh#G=|Jv`a!}#5XY1{_;x-OkH&joCnQfR zv8kSh)0^>lCwep@H@Nofu8cc~XY{jm!m`6RJ!!iPyH$bUoT&(_z-E%Y~P_SZau!_>HBMA&hNba9Z1fu zSXaB1OfsHaN)8K*+ErgqW%gwegs(oHYZ-1)d_3y|U3AU3k~NoMnBr?!K0luK9=Wj8 z+m#b=-AvYu5F!_u#++KIJRiZUijh34H(%tg!_BhsFf&q5y*@8CPrss?tabg_Lbh@8 zj@-nx`)a=(AL-rn`*a1ahZVyma6Ef2u&HBwW9U1nZ^UavLOv-gDJvgK@03y{_U&@@ z#cDl!F|kDYIoyI&u4Rt%{5ZHKfelFj$vTemMj(vG(T$|NJiJ8Z-2cq zX@B%{PvBHIdq^GOHHQ59%`iF8Y<-HqLHz@}K#T!0;F6Rjw&rf2)7rrOF2}CQltavn zDb{Gi88^NWhm9C`@j^{3+(ah1B&nmzy?pETdpkCp&1yNnOZURKwS2#*dmOaugPGDL8*UHeW+ zTB&_27HHy9r+$Ciec)I4L_DW0S53o0=mc3KK(93?KKMoO$sKjdva_#;>-ejNhDx{_ z_G;{Tw1Ve+Cf;K-b2TI2t>pk! zKaxbg8&NU0j`HJaem3_VZjJitKcN(|MLF5J%8Fmp z$8l8cgLD^5eakurwZ0r>r0*~7YAb5T=J&;T%e7k1Eqs<_waHnnTrXx-Or#zOR(PurX(qhQbfh6_e=DyIt z^DD={O93!sxTRDu@$9ixzZzF=pTyJ ziih;<`oUp8GQ4sYS0kJqT_60)=$ry_(EY)S-qGz2yNpr@Z#|eIh<{)bZ}mfTto~QxgwHYD2NA4 zC;%Z(vL=1F$9;i^(edxjNQV~hinq~!^>zym68cihI~5JGjvZL!g_l>FzAaUPV^lk|E>mq9UhCrc){}xioY*o6a@`na&C0=YI2nr zx?}NTbCu)M8_ERP}mA%Q}I5gFDZ { + item.sprite.remove(); + }); + this.bullet = []; + } + moveBullet(bullet: Bullet, offset: Offset): void { bullet.area.x += offset[0]; bullet.area.y += offset[1]; diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 40b023a..92680d7 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -1,6 +1,8 @@ import '@styles/level'; -import { Rect, LevelEntity, LeftFeet } from '../../types/game'; +import { + Rect, LevelEntity, LeftFeet, Door, DoorSize, LootSize, Loot, +} from '../../types/game'; import Player from './dave'; import Zombie from './zombie'; import { LEVEL1 } from '../../assets/levels/level1'; @@ -39,8 +41,16 @@ class GameView { monsters: Monster[] = []; + doors: Door[] = []; + dave: Player; + loot: Loot[] = []; + + godMode = false; + + score: number; + constructor() { this.levelArea.classList.add('level-area'); this.levelArea.style.width = `${this.levelAreaW}px`; @@ -69,6 +79,9 @@ class GameView { this.monsters.push(new Crone(leftFeet, this.levelArea)); }); this.showMonsters(); + this.loadDoors(LevelEntity.DOOR1); + this.loadDoors(LevelEntity.DOOR2); + this.loadDoors(LevelEntity.DOOR4); this.dave = new Player(this.loadCharacters(LevelEntity.DAVE)[0]); this.insertPlayer(); this.correctLevelPosition(); @@ -129,6 +142,40 @@ class GameView { return characters; } + loadDoors(entityType: LevelEntity): void { + LEVEL1.split('\n').forEach((line, indx) => { + const arrLine = line.split(' '); + for (let i = 0; i < arrLine.length; i += 1) { + if (arrLine[i] === entityType) { + const loot = { + area: { + x: i * this.tileSize + DoorSize.W / 2, + y: (indx + 1) * this.tileSize - DoorSize.H + 10, + w: LootSize.W, + h: LootSize.H, + }, + sprite: document.createElement('div'), + grabbed: false, + bonus: parseInt(entityType, 10) * 100, + }; + const door: Door = { + area: { + x: i * this.tileSize, + y: (indx + 1) * this.tileSize - DoorSize.H, + w: DoorSize.W, + h: DoorSize.H, + }, + sprite: document.createElement('div'), + loot, + opened: false, + }; + this.doors.push(door); + } + } + }); + this.showClosedDoors(); + } + showWalls(): void { this.walls.forEach((item) => { const elem: HTMLElement = document.createElement('div'); @@ -163,6 +210,39 @@ class GameView { }); } + showClosedDoors(): void { + this.doors.forEach((door) => { + door.sprite.classList.add('door'); + door.sprite.style.width = `${door.area.w}px`; + door.sprite.style.height = `${door.area.h}px`; + door.sprite.style.left = `${door.area.x}px`; + door.sprite.style.top = `${door.area.y}px`; + door.loot.sprite.classList.add('loot'); + door.loot.sprite.classList.add(`loot${door.loot.bonus}`); + door.loot.sprite.style.width = `${door.loot.area.w}px`; + door.loot.sprite.style.height = `${door.loot.area.h}px`; + door.loot.sprite.style.left = `${door.loot.area.x}px`; + door.loot.sprite.style.top = `${door.loot.area.y}px`; + }); + } + + openDoor(door: Door): void { + door.opened = true; + this.levelArea.append(door.sprite); + this.levelArea.append(door.loot.sprite); + this.loot.push(door.loot); + } + + grabLoot(loot: Loot): void { + loot.grabbed = true; + loot.sprite.classList.remove(`loot${loot.bonus}`); + loot.sprite.innerHTML = `${loot.bonus}`; + setTimeout(() => { + loot.sprite.remove(); + this.loot.splice(this.loot.indexOf(loot), 1); + }, 2000); + } + correctLevelPosition(): void { const daveViewX = this.dave.x + this.levelAreaX; const rAreaX = this.viewAreaW / 2 + this.playerAreaW / 2 - this.dave.w; @@ -197,7 +277,8 @@ class GameView { this.levelArea.style.transform = `translate(${this.levelAreaX}px, ${this.levelAreaY}px)`; } - removeZombie(monster: Monster): void { + removeMonster(monster: Monster): void { + monster.removeAllBullets(); monster.removeSprite(); this.monsters.splice(this.monsters.indexOf(monster), 1); } diff --git a/client/src/scripts/components/zombie.ts b/client/src/scripts/components/zombie.ts index 1f46bc8..8878829 100644 --- a/client/src/scripts/components/zombie.ts +++ b/client/src/scripts/components/zombie.ts @@ -92,6 +92,10 @@ class Zombie extends Monster { this.bullet?.sprite.remove(); this.bullet = undefined; } + + removeAllBullets(): void { + this.removeBullet(); + } } export default Zombie; diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index ddf5081..fe60034 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -252,6 +252,7 @@ class PlayLevel { } this.dave.setView(); this.moveBullets(); + this.checkLoot(); } }; tick(); @@ -271,7 +272,7 @@ class PlayLevel { w: bullet.area.w + ((dX > 0) ? dX : 0), h: bullet.area.h, }; - if (this.checkAttackDave(fullRect)) { + if (!this.gameView.godMode && this.checkAttackDave(fullRect)) { this.dave.state = DaveState.DEAD; this.restartLevel(); } @@ -283,6 +284,7 @@ class PlayLevel { }); } else if ( (monster instanceof Zombie) + && !this.gameView.godMode && monster.bullet && this.checkAttackDave(monster.bullet.area)) { this.dave.state = DaveState.DEAD; @@ -291,6 +293,14 @@ class PlayLevel { }); } + checkLoot(): void { + this.gameView.loot.forEach((loot) => { + if (!loot.grabbed && this.isRectCrossWithRect(loot.area, this.dave)) { + this.gameView.grabLoot(loot); + } + }); + } + checkAttackDave(bullet: Rect): boolean { return !!this.isRectCrossWithRect(bullet, this.dave); } @@ -394,7 +404,17 @@ class PlayLevel { break; case 'ArrowUp': if (this.dave.state === DaveState.STANDING) { - this.dave.shoot = DaveShoot.UP; + let foundDoor = false; + this.gameView.doors.forEach((door) => { + if (!door.opened + && this.isRectCrossWithRect(door.area, this.dave)) { + this.gameView.openDoor(door); + foundDoor = true; + } + }); + if (!foundDoor) { + this.dave.shoot = DaveShoot.UP; + } } break; case 'ArrowDown': @@ -430,6 +450,12 @@ class PlayLevel { }, 50); } break; + case 'KeyG': + if (e.ctrlKey) { + e.preventDefault(); + this.gameView.godMode = !this.gameView.godMode; + } + break; default: this.dave.setView(); break; @@ -648,7 +674,7 @@ class PlayLevel { ) { closestMonster.getAttacked(); if (closestMonster.health === 0) { - this.gameView.removeZombie(closestMonster); + this.gameView.removeMonster(closestMonster); } } } diff --git a/client/src/styles/crone.css b/client/src/styles/crone.css index 9efafc7..7445f1a 100644 --- a/client/src/styles/crone.css +++ b/client/src/styles/crone.css @@ -3,6 +3,7 @@ top: 0; left: 0; background-color:cadetblue; + z-index: 10; } .crone.attacked { @@ -14,4 +15,5 @@ top: 0; left: 0; background-color:blue; + z-index: 10; } diff --git a/client/src/styles/dave.css b/client/src/styles/dave.css index 21b52f9..d058fad 100644 --- a/client/src/styles/dave.css +++ b/client/src/styles/dave.css @@ -3,4 +3,5 @@ top: 0; left: 0; background-color: brown; + z-index: 100; } \ No newline at end of file diff --git a/client/src/styles/level.css b/client/src/styles/level.css index 0d41175..76ae01e 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -32,3 +32,30 @@ body { .wall { position: absolute; } + +.door { + position: absolute; + width: 96px; + height: 144px; + background: url("./../assets/levels/opendoor.png") no-repeat no-repeat; + z-index: 1; +} + +.loot { + position: absolute; + width: 40px; + height: 32px; + z-index: 2; +} + +.loot100 { + background: url("./../assets/levels/loot1.png") no-repeat no-repeat; +} + +.loot200 { + background: url("./../assets/levels/loot2.png") no-repeat no-repeat; +} + +.loot400 { + background: url("./../assets/levels/loot4.png") no-repeat no-repeat; +} diff --git a/client/src/styles/zombie.css b/client/src/styles/zombie.css index 4c7ca7b..3ddc028 100644 --- a/client/src/styles/zombie.css +++ b/client/src/styles/zombie.css @@ -3,6 +3,7 @@ top: 0; left: 0; background-color: burlywood; + z-index: 10; } .zombie.attacked { @@ -14,4 +15,5 @@ top: 0; left: 0; background-color:blueviolet; + z-index: 10; } diff --git a/client/src/types/game.ts b/client/src/types/game.ts index 08c05d4..4bf2e08 100644 --- a/client/src/types/game.ts +++ b/client/src/types/game.ts @@ -11,11 +11,14 @@ export type LeftFeet = { }; export enum LevelEntity { - WALL = '1', - PLATFORM = '2', + WALL = 'W', + PLATFORM = 'P', ZOMBIE = 'Z', DAVE = 'D', CRONE = 'C', + DOOR1 = '1', + DOOR2 = '2', + DOOR4 = '4', } export type Offset = [number, number]; @@ -31,3 +34,27 @@ export enum Position { LEFT, RIGHT, } + +export type Door = { + area: Rect; + sprite: HTMLElement; + loot: Loot; + opened: boolean; +}; + +export type Loot = { + area: Rect; + sprite: HTMLElement; + grabbed: boolean; + bonus: number; +}; + +export enum DoorSize { + W = 96, + H = 144, +} + +export enum LootSize { + W = 40, + H = 36, +} From a090199cd183902daefa3bca51886d8b76694606 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sat, 11 Feb 2023 20:43:31 +0300 Subject: [PATCH 055/196] feat: create user service --- server/src/app.module.ts | 2 + server/src/errors/userAlreadyExists.ts | 12 ++++ server/src/errors/userNotFoundError.ts | 7 ++ server/src/user/user.module.ts | 12 ++++ server/src/user/user.service.ts | 97 ++++++++++++++++++++++++++ 5 files changed, 130 insertions(+) create mode 100644 server/src/errors/userAlreadyExists.ts create mode 100644 server/src/errors/userNotFoundError.ts create mode 100644 server/src/user/user.module.ts create mode 100644 server/src/user/user.service.ts diff --git a/server/src/app.module.ts b/server/src/app.module.ts index 7e8019f..20d0d6a 100644 --- a/server/src/app.module.ts +++ b/server/src/app.module.ts @@ -3,6 +3,7 @@ import { AppController } from './app.controller'; import { AppService } from './app.service'; import { MongooseModule } from '@nestjs/mongoose'; import { ConfigModule } from '@nestjs/config'; +import { UserModule } from './user/user.module'; import * as process from 'process'; @Module({ @@ -17,6 +18,7 @@ import * as process from 'process'; useUnifiedTopology: true, }, ), + UserModule, ], controllers: [AppController], providers: [AppService], diff --git a/server/src/errors/userAlreadyExists.ts b/server/src/errors/userAlreadyExists.ts new file mode 100644 index 0000000..8ba7064 --- /dev/null +++ b/server/src/errors/userAlreadyExists.ts @@ -0,0 +1,12 @@ +import { IUser } from '../types/interfaces/user'; + +export class UserAlreadyExists extends Error { + constructor( + username: IUser['username'], + authProvider: IUser['authProvider'], + ) { + super( + `User with username: '${username}' and auth provider: '${authProvider}' already exists.`, + ); + } +} diff --git a/server/src/errors/userNotFoundError.ts b/server/src/errors/userNotFoundError.ts new file mode 100644 index 0000000..e84e2e2 --- /dev/null +++ b/server/src/errors/userNotFoundError.ts @@ -0,0 +1,7 @@ +import { IUser } from '../types/interfaces/user'; + +export class UserNotFoundError extends Error { + constructor(userId: IUser['_id']) { + super(`User with id: '${userId}' not found.`); + } +} diff --git a/server/src/user/user.module.ts b/server/src/user/user.module.ts new file mode 100644 index 0000000..1a99e84 --- /dev/null +++ b/server/src/user/user.module.ts @@ -0,0 +1,12 @@ +import { Module } from '@nestjs/common'; +import { UserService } from './user.service'; +import { MongooseModule } from '@nestjs/mongoose'; +import { User, UserSchema } from '../models/scheme/user.schema'; + +@Module({ + imports: [ + MongooseModule.forFeature([{ name: User.name, schema: UserSchema }]), + ], + providers: [UserService], +}) +export class UserModule {} diff --git a/server/src/user/user.service.ts b/server/src/user/user.service.ts new file mode 100644 index 0000000..3341e6d --- /dev/null +++ b/server/src/user/user.service.ts @@ -0,0 +1,97 @@ +import { Injectable } from '@nestjs/common'; +import { User } from '../models/scheme/user.schema'; +import { InjectModel } from '@nestjs/mongoose'; +import { Model } from 'mongoose'; +import { IUser } from '../types/interfaces/user'; +import { UserNotFoundError } from '../errors/userNotFoundError'; +import { UserAlreadyExists } from '../errors/userAlreadyExists'; +import { AuthProvider } from '../types/enums/authProviders'; + +@Injectable() +export class UserService { + constructor( + @InjectModel(User.name) private readonly userModel: Model, + ) {} + + async findAll(page: number, limit: number): Promise { + const startIndex = (page - 1) * (limit <= 100 ? limit : 100); + return this.userModel.find({}).skip(startIndex).limit(limit).exec(); + } + + async findOne(id: IUser['_id']): Promise { + const result = await this.userModel.findOne({ _id: id }).exec(); + + if (!result) { + throw new UserNotFoundError(id); + } + + return result; + } + + async create(user: Omit): Promise { + await this.validateUser(user); + + const createdUser = new this.userModel(user); + return createdUser.save(); + } + + async update( + id: IUser['_id'], + newUser: Omit, + ): Promise { + const targetUser = await this.userModel.findOne({ _id: id }).exec(); + + if (!targetUser) { + throw new UserNotFoundError(id); + } + + await this.validateUser(newUser); + + await targetUser + .update( + { + _id: id, + ...newUser, + }, + { new: true }, + ) + .exec(); + await targetUser.save(); + + return targetUser; + } + + async delete(id: IUser['_id']): Promise { + const targetUser = await this.userModel.findOne({ _id: id }).exec(); + + if (!targetUser) { + throw new UserNotFoundError(id); + } + + await targetUser.remove(); + await targetUser.save(); + + return targetUser; + } + + private async validateUser(user: Omit): Promise { + if (user.username.trim().length < 3) { + throw new Error('The username must be more than 3 characters.'); + } + + if (!(user.authProvider === AuthProvider.LOCAL)) { + throw new Error('Invalid auth provider.'); + } + + const duplicate = await this.userModel + .findOne({ + username: user.username, + authProvider: user.authProvider, + }) + .exec(); + + if (duplicate) { + throw new UserAlreadyExists(user.username, user.authProvider); + } + } +} From d1e060f83a01320fd35e78c285bc115661e396a6 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sat, 11 Feb 2023 23:58:36 +0300 Subject: [PATCH 056/196] feat: add player animation --- client/src/assets/sprites/dave_sprites.png | Bin 13960 -> 22049 bytes client/src/scripts/components/dave.ts | 79 ++++++++++++++++----- 2 files changed, 61 insertions(+), 18 deletions(-) diff --git a/client/src/assets/sprites/dave_sprites.png b/client/src/assets/sprites/dave_sprites.png index 07f8bcf17fa7fc4803d771035e912b2c67e551be..a0ed95c30f5de2c05ea8af0993d846b3465d2a38 100644 GIT binary patch literal 22049 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 literal 13960 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 diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index bf901f3..0cd604b 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -5,13 +5,15 @@ import { import { DaveLook, DaveMove, DaveShoot, DaveState, } from '../../types/dave'; +import PlayAnimator from '../controllers/playAnimator'; +import Direction from '../../types/enums/directions'; class Player { x = 0; y = 0; - w = 64; + w = 72; h = 96; @@ -35,6 +37,8 @@ class Player { lives = 3; + animation: PlayAnimator; + constructor(leftFeet: LeftFeet) { this.sprite.classList.add('player'); this.x = leftFeet.x; @@ -42,29 +46,68 @@ class Player { this.sprite.style.width = `${this.w}px`; this.sprite.style.height = `${this.h}px`; this.setPosition(); + this.animation = new PlayAnimator(this.sprite); } setView(): void { if (this.state === DaveState.FALLING) { - if (this.look === DaveLook.LEFT) { - this.sprite.innerHTML = ''; - } else if (this.look === DaveLook.RIGHT) { - this.sprite.innerHTML = ''; - } + this.animation.fall( + this.look === DaveLook.LEFT + ? Direction.RIGHT + : Direction.LEFT, + ); } else if (this.state === DaveState.JUMPING_UP) { - if (this.look === DaveLook.LEFT) { - this.sprite.innerHTML = ''; - } else if (this.look === DaveLook.RIGHT) { - this.sprite.innerHTML = ''; + this.animation.jump( + this.look === DaveLook.LEFT + ? Direction.RIGHT + : Direction.LEFT, + ); + } else if (this.state === DaveState.SHOOTING) { + if (this.shoot === DaveShoot.UP) { + this.animation.shoot( + this.look === DaveLook.LEFT + ? Direction.TOP_LEFT + : Direction.TOP_RIGHT, + ); + } else if (this.shoot === DaveShoot.DOWN) { + this.animation.shoot( + this.look === DaveLook.LEFT + ? Direction.DOWN_LEFT + : Direction.DOWN_RIGHT, + ); + } else { + this.animation.shoot( + this.look === DaveLook.LEFT + ? Direction.LEFT + : Direction.RIGHT, + ); + } + } else if (this.state === DaveState.RUNNING) { + this.animation.move( + this.look === DaveLook.LEFT + ? Direction.LEFT + : Direction.RIGHT, + ); + } else if (this.state === DaveState.STANDING) { + if (this.shoot === DaveShoot.UP) { + this.animation.look( + this.look === DaveLook.LEFT + ? Direction.TOP_LEFT + : Direction.TOP_RIGHT, + ); + } else if (this.shoot === DaveShoot.DOWN) { + this.animation.look( + this.look === DaveLook.LEFT + ? Direction.DOWN_LEFT + : Direction.DOWN_RIGHT, + ); + } else { + this.animation.look( + this.look === DaveLook.LEFT + ? Direction.LEFT + : Direction.RIGHT, + ); } - } else if (this.shoot === DaveShoot.UP) { - this.sprite.innerHTML = 'Shooting UP'; - } else if (this.shoot === DaveShoot.DOWN) { - this.sprite.innerHTML = 'Shooting DOWN'; - } else if (this.look === DaveLook.LEFT) { - this.sprite.innerHTML = ''; - } else if (this.look === DaveLook.RIGHT) { - this.sprite.innerHTML = ''; } } From 41086cd14f89cb0d5b4bbe4a58a0306202741289 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sun, 12 Feb 2023 00:36:18 +0300 Subject: [PATCH 057/196] fix: fix visual bug associate with the state of stand to the left and right side --- .../src/scripts/controllers/playAnimator.ts | 11 ---------- client/src/styles/playerAnimation.scss | 21 ++++++++++--------- client/src/types/interfaces/playerAnimator.ts | 1 - 3 files changed, 11 insertions(+), 22 deletions(-) diff --git a/client/src/scripts/controllers/playAnimator.ts b/client/src/scripts/controllers/playAnimator.ts index 0157f92..3f889bc 100644 --- a/client/src/scripts/controllers/playAnimator.ts +++ b/client/src/scripts/controllers/playAnimator.ts @@ -6,17 +6,6 @@ class PlayAnimator implements IPlayerAnimator { } - stand(direction: Direction): void { - const classes = this.playerBlock.classList.toString() - .replace(/players-[^\s]+/g, '') - .trim(); - this.playerBlock.removeAttribute('class'); - this.playerBlock.setAttribute( - 'class', - `${classes} players-animate-stand-${direction}`, - ); - } - move(direction: Direction): void { const classes = this.playerBlock.classList.toString() .replace(/players-[^\s]+/g, '') diff --git a/client/src/styles/playerAnimation.scss b/client/src/styles/playerAnimation.scss index c3de066..b7042cc 100644 --- a/client/src/styles/playerAnimation.scss +++ b/client/src/styles/playerAnimation.scss @@ -3,16 +3,6 @@ $bg-size: 5257px; .players { - &-animate-stand-left { - background-position: -583px 0; - background-size: $bg-size; - } - - &-animate-stand-right { - background-position: 0 0; - background-size: $bg-size; - } - &-animate { background: url("../assets/sprites/dave_sprites.png"); background-size: $bg-size; @@ -65,6 +55,17 @@ $bg-size: 5257px; } &-look { + &-left { + background-position: -583px 0; + width: 60px !important; + background-size: $bg-size; + } + + &-right { + background-position: 0 0; + background-size: $bg-size; + } + &-topRight { background: url("../assets/sprites/dave_sprites.png") -2552px 0; width: 73px !important; diff --git a/client/src/types/interfaces/playerAnimator.ts b/client/src/types/interfaces/playerAnimator.ts index de3f0b0..b83d896 100644 --- a/client/src/types/interfaces/playerAnimator.ts +++ b/client/src/types/interfaces/playerAnimator.ts @@ -1,7 +1,6 @@ import Direction from '../enums/directions'; export interface IPlayerAnimator { - stand(direction: Direction): void move(direction: Direction): void jump(direction: Direction): void fall(direction: Direction): void From 724c8e17c0a645b194a843f3542fd124dfc8223e Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sun, 12 Feb 2023 00:58:13 +0300 Subject: [PATCH 058/196] feat: add game over screen, info on score and lives --- client/src/assets/levels/gameover.png | Bin 0 -> 3815 bytes client/src/scripts/components/crone.ts | 2 ++ client/src/scripts/components/dave.ts | 2 -- client/src/scripts/components/game.ts | 33 ++++++++++++++------ client/src/scripts/components/monster.ts | 2 ++ client/src/scripts/components/zombie.ts | 2 ++ client/src/scripts/controllers/playLevel.ts | 28 +++++++++++------ client/src/styles/level.css | 25 +++++++++++++-- 8 files changed, 70 insertions(+), 24 deletions(-) create mode 100644 client/src/assets/levels/gameover.png diff --git a/client/src/assets/levels/gameover.png b/client/src/assets/levels/gameover.png new file mode 100644 index 0000000000000000000000000000000000000000..876b7378bfcdaac90813c6f297ab7508e2590665 GIT binary patch literal 3815 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 literal 0 HcmV?d00001 diff --git a/client/src/scripts/components/crone.ts b/client/src/scripts/components/crone.ts index 161e5d5..1e89477 100644 --- a/client/src/scripts/components/crone.ts +++ b/client/src/scripts/components/crone.ts @@ -41,6 +41,8 @@ class Crone extends Monster { bulletH = 10; + bonus = 100; + constructor(leftFeet: LeftFeet, levelArea: HTMLElement) { super(); this.sprite.classList.add('crone'); diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index bf901f3..485c14b 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -33,8 +33,6 @@ class Player { jumpStartVelocity = 8; - lives = 3; - constructor(leftFeet: LeftFeet) { this.sprite.classList.add('player'); this.x = leftFeet.x; diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 92680d7..9447902 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -27,8 +27,6 @@ class GameView { viewAreaH = 630; - playerArea: HTMLElement = document.createElement('div'); - playerAreaW = 128; playerAreaH = 256; @@ -49,7 +47,11 @@ class GameView { godMode = false; - score: number; + score = 0; + + lives = 3; + + scoreElement: HTMLElement; constructor() { this.levelArea.classList.add('level-area'); @@ -58,12 +60,9 @@ class GameView { this.viewArea.classList.add('view-area'); this.viewArea.style.width = `${this.viewAreaW}px`; this.viewArea.style.height = `${this.viewAreaH}px`; - this.playerArea.classList.add('player-area'); - this.playerArea.style.width = `${this.playerAreaW}px`; - this.playerArea.style.height = `${this.playerAreaH}px`; - this.playerArea.style.left = `${this.viewAreaW / 2 - this.playerAreaW / 2}px`; - this.playerArea.style.top = `${this.viewAreaH / 2 - this.playerAreaH / 2}px`; - this.viewArea.append(this.levelArea, this.playerArea); + this.scoreElement = document.createElement('div'); + this.scoreElement.classList.add('score'); + this.viewArea.append(this.levelArea, this.scoreElement); document.querySelector('body')?.append(this.viewArea); } @@ -86,7 +85,7 @@ class GameView { this.insertPlayer(); this.correctLevelPosition(); this.levelArea.classList.add('level1'); - console.log('asd'); + this.updateScoreOnScreen(); } loadBorders(entityType: LevelEntity): Rect[] { @@ -235,6 +234,8 @@ class GameView { grabLoot(loot: Loot): void { loot.grabbed = true; + this.score += loot.bonus; + this.updateScoreOnScreen(); loot.sprite.classList.remove(`loot${loot.bonus}`); loot.sprite.innerHTML = `${loot.bonus}`; setTimeout(() => { @@ -280,6 +281,8 @@ class GameView { removeMonster(monster: Monster): void { monster.removeAllBullets(); monster.removeSprite(); + this.score += monster.bonus; + this.updateScoreOnScreen(); this.monsters.splice(this.monsters.indexOf(monster), 1); } @@ -289,6 +292,16 @@ class GameView { this.monsters = []; this.levelArea.innerHTML = ''; } + + updateScoreOnScreen(): void { + this.scoreElement.innerHTML = `Lives: ${this.lives}
Score: ${this.score}`; + } + + gameOver(): void { + const gameOver: HTMLElement = document.createElement('div'); + gameOver.classList.add('game-over'); + this.viewArea.append(gameOver); + } } export default GameView; diff --git a/client/src/scripts/components/monster.ts b/client/src/scripts/components/monster.ts index 069d4f2..8147f54 100644 --- a/client/src/scripts/components/monster.ts +++ b/client/src/scripts/components/monster.ts @@ -32,6 +32,8 @@ class Monster { levelArea: HTMLElement; + bonus: number; + constructor() { this.sprite = document.createElement('div'); } diff --git a/client/src/scripts/components/zombie.ts b/client/src/scripts/components/zombie.ts index 8878829..4e24fdc 100644 --- a/client/src/scripts/components/zombie.ts +++ b/client/src/scripts/components/zombie.ts @@ -36,6 +36,8 @@ class Zombie extends Monster { bullet: Bullet | undefined; + bonus = 100; + constructor(leftFeet: LeftFeet, levelArea: HTMLElement) { super(); this.sprite.classList.add('zombie'); diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index fe60034..4450fe9 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -273,8 +273,7 @@ class PlayLevel { h: bullet.area.h, }; if (!this.gameView.godMode && this.checkAttackDave(fullRect)) { - this.dave.state = DaveState.DEAD; - this.restartLevel(); + this.daveGoesDead(); } if (this.isCrossWithWalls(fullRect).length === 0) { (monster).moveBullet(bullet, [dX, dY]); @@ -287,12 +286,17 @@ class PlayLevel { && !this.gameView.godMode && monster.bullet && this.checkAttackDave(monster.bullet.area)) { - this.dave.state = DaveState.DEAD; - this.restartLevel(); + this.daveGoesDead(); } }); } + daveGoesDead(): void { + this.dave.state = DaveState.DEAD; + this.gameView.lives -= 1; + this.restartLevel(); + } + checkLoot(): void { this.gameView.loot.forEach((loot) => { if (!loot.grabbed && this.isRectCrossWithRect(loot.area, this.dave)) { @@ -766,12 +770,16 @@ class PlayLevel { restartLevel(): void { clearInterval(this.monsterAnimationTimer); cancelAnimationFrame(this.daveAnimationTimer); - this.gameView.resetLevel(); - this.gameView.loadLevelEntities(); - this.dave = this.gameView.dave; - this.animate(); - this.setListener(); - this.animateMonsters(); + if (this.gameView.lives > 0) { + this.gameView.resetLevel(); + this.gameView.loadLevelEntities(); + this.dave = this.gameView.dave; + this.animate(); + this.setListener(); + this.animateMonsters(); + } else { + this.gameView.gameOver(); + } } } diff --git a/client/src/styles/level.css b/client/src/styles/level.css index 76ae01e..c1809bf 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -1,7 +1,9 @@ +@import url('https://fonts.cdnfonts.com/css/perfect-dos-vga-437'); + body { overflow: hidden; height: 100vw; - background-color: #ccc; + background-color: #cccccc; } #container { @@ -11,7 +13,7 @@ body { .view-area { position: relative; - background-color: white; + background-color: #ffffff; opacity: 1; overflow: hidden; margin: 100px auto; @@ -59,3 +61,22 @@ body { .loot400 { background: url("./../assets/levels/loot4.png") no-repeat no-repeat; } + +.score { + font-family: 'Perfect DOS VGA 437', sans-serif; + position: absolute; + top: 10px; + left: 10px; + color: #C62828; + font-size: 18px; + background-color: rgb(250, 250, 250, 70%); +} + +.game-over { + position: absolute; + top: 200px; + width: 457px; + height: 120px; + left: 251px; + background: url("./../assets/levels/gameover.png") no-repeat no-repeat; +} From ea825a7531f9b3418b45d7465821f14343c0e830 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 16:15:28 +0300 Subject: [PATCH 059/196] refactor: move modules into ./modules --- server/src/{ => modules/app}/app.controller.spec.ts | 0 server/src/{ => modules/app}/app.controller.ts | 0 server/src/{ => modules/app}/app.module.ts | 0 server/src/{ => modules/app}/app.service.ts | 0 server/src/{ => modules}/user/user.module.ts | 2 +- server/src/{ => modules}/user/user.service.ts | 10 +++++----- 6 files changed, 6 insertions(+), 6 deletions(-) rename server/src/{ => modules/app}/app.controller.spec.ts (100%) rename server/src/{ => modules/app}/app.controller.ts (100%) rename server/src/{ => modules/app}/app.module.ts (100%) rename server/src/{ => modules/app}/app.service.ts (100%) rename server/src/{ => modules}/user/user.module.ts (81%) rename server/src/{ => modules}/user/user.service.ts (87%) diff --git a/server/src/app.controller.spec.ts b/server/src/modules/app/app.controller.spec.ts similarity index 100% rename from server/src/app.controller.spec.ts rename to server/src/modules/app/app.controller.spec.ts diff --git a/server/src/app.controller.ts b/server/src/modules/app/app.controller.ts similarity index 100% rename from server/src/app.controller.ts rename to server/src/modules/app/app.controller.ts diff --git a/server/src/app.module.ts b/server/src/modules/app/app.module.ts similarity index 100% rename from server/src/app.module.ts rename to server/src/modules/app/app.module.ts diff --git a/server/src/app.service.ts b/server/src/modules/app/app.service.ts similarity index 100% rename from server/src/app.service.ts rename to server/src/modules/app/app.service.ts diff --git a/server/src/user/user.module.ts b/server/src/modules/user/user.module.ts similarity index 81% rename from server/src/user/user.module.ts rename to server/src/modules/user/user.module.ts index 1a99e84..e254c15 100644 --- a/server/src/user/user.module.ts +++ b/server/src/modules/user/user.module.ts @@ -1,7 +1,7 @@ import { Module } from '@nestjs/common'; import { UserService } from './user.service'; import { MongooseModule } from '@nestjs/mongoose'; -import { User, UserSchema } from '../models/scheme/user.schema'; +import { User, UserSchema } from '../../models/scheme/user.schema'; @Module({ imports: [ diff --git a/server/src/user/user.service.ts b/server/src/modules/user/user.service.ts similarity index 87% rename from server/src/user/user.service.ts rename to server/src/modules/user/user.service.ts index 3341e6d..4e3aa4b 100644 --- a/server/src/user/user.service.ts +++ b/server/src/modules/user/user.service.ts @@ -1,11 +1,11 @@ import { Injectable } from '@nestjs/common'; -import { User } from '../models/scheme/user.schema'; +import { User } from '../../models/scheme/user.schema'; import { InjectModel } from '@nestjs/mongoose'; import { Model } from 'mongoose'; -import { IUser } from '../types/interfaces/user'; -import { UserNotFoundError } from '../errors/userNotFoundError'; -import { UserAlreadyExists } from '../errors/userAlreadyExists'; -import { AuthProvider } from '../types/enums/authProviders'; +import { IUser } from '../../types/interfaces/user'; +import { UserNotFoundError } from '../../errors/userNotFoundError'; +import { UserAlreadyExists } from '../../errors/userAlreadyExists'; +import { AuthProvider } from '../../types/enums/authProviders'; @Injectable() export class UserService { From 643cd03c120a096600479e88299e9bfb9bdbd134 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 16:25:41 +0300 Subject: [PATCH 060/196] refactor: errors replace on HttpException --- server/src/errors/userAlreadyExists.ts | 13 +++++++++++-- server/src/errors/userNotFoundError.ts | 19 ++++++++++++++++--- 2 files changed, 27 insertions(+), 5 deletions(-) diff --git a/server/src/errors/userAlreadyExists.ts b/server/src/errors/userAlreadyExists.ts index 8ba7064..f97e981 100644 --- a/server/src/errors/userAlreadyExists.ts +++ b/server/src/errors/userAlreadyExists.ts @@ -1,12 +1,21 @@ import { IUser } from '../types/interfaces/user'; +import { HttpException, HttpStatus } from '@nestjs/common'; -export class UserAlreadyExists extends Error { +export class UserAlreadyExists extends HttpException { constructor( username: IUser['username'], authProvider: IUser['authProvider'], ) { super( - `User with username: '${username}' and auth provider: '${authProvider}' already exists.`, + { + statusCode: HttpStatus.CONFLICT, + message: 'This user already exists in current authorization provider.', + user: { + username, + authProvider, + }, + }, + HttpStatus.CONFLICT, ); } } diff --git a/server/src/errors/userNotFoundError.ts b/server/src/errors/userNotFoundError.ts index e84e2e2..7a857cb 100644 --- a/server/src/errors/userNotFoundError.ts +++ b/server/src/errors/userNotFoundError.ts @@ -1,7 +1,20 @@ import { IUser } from '../types/interfaces/user'; +import { HttpException, HttpStatus } from '@nestjs/common'; -export class UserNotFoundError extends Error { - constructor(userId: IUser['_id']) { - super(`User with id: '${userId}' not found.`); +export class UserNotFoundError extends HttpException { + constructor(user: IUser) { + super( + { + statusCode: HttpStatus.NOT_FOUND, + message: + 'The requested user was not found or does not exist in the current authorization provider.', + user: { + id: user._id, + username: user.username, + authProvider: user.authProvider, + }, + }, + HttpStatus.NOT_FOUND, + ); } } From dbd38c95b818c9962968c170d4e470f272e040ca Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 16:28:11 +0300 Subject: [PATCH 061/196] fix: fix default value for MongoDB connection URI --- server/src/modules/app/app.module.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/server/src/modules/app/app.module.ts b/server/src/modules/app/app.module.ts index 20d0d6a..473c751 100644 --- a/server/src/modules/app/app.module.ts +++ b/server/src/modules/app/app.module.ts @@ -3,8 +3,7 @@ import { AppController } from './app.controller'; import { AppService } from './app.service'; import { MongooseModule } from '@nestjs/mongoose'; import { ConfigModule } from '@nestjs/config'; -import { UserModule } from './user/user.module'; -import * as process from 'process'; +import { UserModule } from '../user/user.module'; @Module({ imports: [ @@ -12,7 +11,8 @@ import * as process from 'process'; envFilePath: '.env', }), MongooseModule.forRoot( - process.env.MONGODB_CONNECTION_URL || 'mongodb://127.0.0.1:27017', + process.env.MONGODB_CONNECTION_URL || + 'mongodb://127.0.0.1:27017/rs-clone', { useNewUrlParser: true, useUnifiedTopology: true, From 495f2f55eca887499efb295d44e52d615b3ca4b0 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 16:30:07 +0300 Subject: [PATCH 062/196] fix: fix UserNotFoundError --- server/src/errors/userNotFoundError.ts | 13 ++++++++----- server/src/modules/user/user.service.ts | 13 ++++++++++--- 2 files changed, 18 insertions(+), 8 deletions(-) diff --git a/server/src/errors/userNotFoundError.ts b/server/src/errors/userNotFoundError.ts index 7a857cb..ed9567b 100644 --- a/server/src/errors/userNotFoundError.ts +++ b/server/src/errors/userNotFoundError.ts @@ -2,16 +2,19 @@ import { IUser } from '../types/interfaces/user'; import { HttpException, HttpStatus } from '@nestjs/common'; export class UserNotFoundError extends HttpException { - constructor(user: IUser) { + constructor(user: Partial) { super( { statusCode: HttpStatus.NOT_FOUND, message: 'The requested user was not found or does not exist in the current authorization provider.', - user: { - id: user._id, - username: user.username, - authProvider: user.authProvider, + error: 'Not Found', + errorData: { + user: { + id: user._id, + username: user.username, + authProvider: user.authProvider, + }, }, }, HttpStatus.NOT_FOUND, diff --git a/server/src/modules/user/user.service.ts b/server/src/modules/user/user.service.ts index 4e3aa4b..4675c4e 100644 --- a/server/src/modules/user/user.service.ts +++ b/server/src/modules/user/user.service.ts @@ -22,7 +22,9 @@ export class UserService { const result = await this.userModel.findOne({ _id: id }).exec(); if (!result) { - throw new UserNotFoundError(id); + throw new UserNotFoundError({ + _id: id, + }); } return result; @@ -42,7 +44,10 @@ export class UserService { const targetUser = await this.userModel.findOne({ _id: id }).exec(); if (!targetUser) { - throw new UserNotFoundError(id); + throw new UserNotFoundError({ + _id: id, + ...newUser, + }); } await this.validateUser(newUser); @@ -65,7 +70,9 @@ export class UserService { const targetUser = await this.userModel.findOne({ _id: id }).exec(); if (!targetUser) { - throw new UserNotFoundError(id); + throw new UserNotFoundError({ + _id: id, + }); } await targetUser.remove(); From 40c9fe8def1b1043c0195afb5341af82762daa84 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 16:58:59 +0300 Subject: [PATCH 063/196] fix: fix UserAlreadyExists --- server/src/errors/userAlreadyExists.ts | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/server/src/errors/userAlreadyExists.ts b/server/src/errors/userAlreadyExists.ts index f97e981..038eb93 100644 --- a/server/src/errors/userAlreadyExists.ts +++ b/server/src/errors/userAlreadyExists.ts @@ -10,9 +10,12 @@ export class UserAlreadyExists extends HttpException { { statusCode: HttpStatus.CONFLICT, message: 'This user already exists in current authorization provider.', - user: { - username, - authProvider, + error: 'Conflict', + errorData: { + user: { + username, + authProvider, + }, }, }, HttpStatus.CONFLICT, From 7607662828387671134b1525bc8ff1d11ff85f55 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 16:59:31 +0300 Subject: [PATCH 064/196] refactor: replace DTO --- server/src/types/dto/requests/createUserRequestDto.ts | 3 --- server/src/types/dto/responses/userDto.ts | 3 --- server/src/types/dto/user/createUserDto.ts | 3 +++ server/src/types/dto/user/updateUserDto.ts | 3 +++ 4 files changed, 6 insertions(+), 6 deletions(-) delete mode 100644 server/src/types/dto/requests/createUserRequestDto.ts delete mode 100644 server/src/types/dto/responses/userDto.ts create mode 100644 server/src/types/dto/user/createUserDto.ts create mode 100644 server/src/types/dto/user/updateUserDto.ts diff --git a/server/src/types/dto/requests/createUserRequestDto.ts b/server/src/types/dto/requests/createUserRequestDto.ts deleted file mode 100644 index 7cc8f25..0000000 --- a/server/src/types/dto/requests/createUserRequestDto.ts +++ /dev/null @@ -1,3 +0,0 @@ -import { IUser } from '../../interfaces/user'; - -export type CreateUserRequestDto = Readonly>; diff --git a/server/src/types/dto/responses/userDto.ts b/server/src/types/dto/responses/userDto.ts deleted file mode 100644 index a84edb7..0000000 --- a/server/src/types/dto/responses/userDto.ts +++ /dev/null @@ -1,3 +0,0 @@ -import { IUser } from '../../interfaces/user'; - -export type UserDto = Readonly>; diff --git a/server/src/types/dto/user/createUserDto.ts b/server/src/types/dto/user/createUserDto.ts new file mode 100644 index 0000000..d9729b6 --- /dev/null +++ b/server/src/types/dto/user/createUserDto.ts @@ -0,0 +1,3 @@ +import { IUser } from '../../interfaces/user'; + +export type CreateUserRequestDto = Omit; diff --git a/server/src/types/dto/user/updateUserDto.ts b/server/src/types/dto/user/updateUserDto.ts new file mode 100644 index 0000000..e0ee4d6 --- /dev/null +++ b/server/src/types/dto/user/updateUserDto.ts @@ -0,0 +1,3 @@ +import { CreateUserRequestDto } from './createUserDto'; + +export type UpdateUserRequestDto = CreateUserRequestDto; From 3b68c2acb3803cac97b2675cf696a9a2e61dd7a5 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 17:00:06 +0300 Subject: [PATCH 065/196] refactor: bootstrap function --- server/src/main.ts | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/server/src/main.ts b/server/src/main.ts index f045237..ea371bb 100644 --- a/server/src/main.ts +++ b/server/src/main.ts @@ -1,9 +1,11 @@ import { NestFactory } from '@nestjs/core'; -import { AppModule } from './app.module'; -import * as process from 'process'; +import { AppModule } from './modules/app/app.module'; async function bootstrap(): Promise { const app = await NestFactory.create(AppModule); + + app.enableCors(); + await app.listen(process.env.PORT || 3000); } From 6b580f4a34dcbb5e5b307c0715fe463d2bcc1f25 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 17:00:37 +0300 Subject: [PATCH 066/196] refactor: apply DTO for user service --- server/src/modules/user/user.service.ts | 51 ++++++++++++++++--------- 1 file changed, 33 insertions(+), 18 deletions(-) diff --git a/server/src/modules/user/user.service.ts b/server/src/modules/user/user.service.ts index 4675c4e..3bcebdc 100644 --- a/server/src/modules/user/user.service.ts +++ b/server/src/modules/user/user.service.ts @@ -1,4 +1,4 @@ -import { Injectable } from '@nestjs/common'; +import { BadRequestException, Injectable } from '@nestjs/common'; import { User } from '../../models/scheme/user.schema'; import { InjectModel } from '@nestjs/mongoose'; import { Model } from 'mongoose'; @@ -6,6 +6,8 @@ import { IUser } from '../../types/interfaces/user'; import { UserNotFoundError } from '../../errors/userNotFoundError'; import { UserAlreadyExists } from '../../errors/userAlreadyExists'; import { AuthProvider } from '../../types/enums/authProviders'; +import { CreateUserRequestDto } from '../../types/dto/user/createUserDto'; +import { UpdateUserRequestDto } from '../../types/dto/user/updateUserDto'; @Injectable() export class UserService { @@ -18,7 +20,7 @@ export class UserService { return this.userModel.find({}).skip(startIndex).limit(limit).exec(); } - async findOne(id: IUser['_id']): Promise { + async findOne(id: IUser['_id']): Promise { const result = await this.userModel.findOne({ _id: id }).exec(); if (!result) { @@ -30,7 +32,7 @@ export class UserService { return result; } - async create(user: Omit): Promise { + async create(user: CreateUserRequestDto): Promise { await this.validateUser(user); const createdUser = new this.userModel(user); @@ -39,8 +41,8 @@ export class UserService { async update( id: IUser['_id'], - newUser: Omit, - ): Promise { + newUser: UpdateUserRequestDto, + ): Promise { const targetUser = await this.userModel.findOne({ _id: id }).exec(); if (!targetUser) { @@ -50,7 +52,7 @@ export class UserService { }); } - await this.validateUser(newUser); + await this.validateUser(newUser, true); await targetUser .update( @@ -63,10 +65,13 @@ export class UserService { .exec(); await targetUser.save(); - return targetUser; + return { + _id: id, + ...newUser, + }; } - async delete(id: IUser['_id']): Promise { + async delete(id: IUser['_id']): Promise { const targetUser = await this.userModel.findOne({ _id: id }).exec(); if (!targetUser) { @@ -76,26 +81,36 @@ export class UserService { } await targetUser.remove(); - await targetUser.save(); return targetUser; } - private async validateUser(user: Omit): Promise { + private async validateUser( + user: CreateUserRequestDto | UpdateUserRequestDto, + skipDuplicateCheck = false, + ): Promise { + let duplicate = false; + if (user.username.trim().length < 3) { - throw new Error('The username must be more than 3 characters.'); + throw new BadRequestException( + 'The username must be more than 3 characters.', + ); } if (!(user.authProvider === AuthProvider.LOCAL)) { - throw new Error('Invalid auth provider.'); + throw new BadRequestException('Invalid auth provider.'); } - const duplicate = await this.userModel - .findOne({ - username: user.username, - authProvider: user.authProvider, - }) - .exec(); + if (!skipDuplicateCheck) { + const existUser = await this.userModel + .findOne({ + username: user.username, + authProvider: user.authProvider, + }) + .exec(); + + duplicate = !!existUser; + } if (duplicate) { throw new UserAlreadyExists(user.username, user.authProvider); From ccebd71596263acf8f7ca493450fa904551d8415 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sun, 12 Feb 2023 17:01:29 +0300 Subject: [PATCH 067/196] feat: add death animation layer --- client/src/scripts/components/dave.ts | 9 +++++++++ client/src/scripts/controllers/playLevel.ts | 12 ++++++++++-- client/src/styles/dave.css | 13 ++++++++++++- 3 files changed, 31 insertions(+), 3 deletions(-) diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index 38b51a3..2b4edec 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -37,6 +37,8 @@ class Player { animation: PlayAnimator; + deathLayer: HTMLElement; + constructor(leftFeet: LeftFeet) { this.sprite.classList.add('player'); this.x = leftFeet.x; @@ -45,6 +47,9 @@ class Player { this.sprite.style.height = `${this.h}px`; this.setPosition(); this.animation = new PlayAnimator(this.sprite); + this.deathLayer = document.createElement('div'); + this.deathLayer.classList.add('death-layer'); + this.sprite.append(this.deathLayer); } setView(): void { @@ -155,6 +160,10 @@ class Player { setPosition(): void { this.sprite.style.transform = `translate(${this.x}px, ${this.y}px)`; } + + showDeathLayer(): void { + this.deathLayer.style.display = 'block'; + } } export default Player; diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index 4450fe9..890fd49 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -292,9 +292,14 @@ class PlayLevel { } daveGoesDead(): void { + this.dave.showDeathLayer(); this.dave.state = DaveState.DEAD; this.gameView.lives -= 1; - this.restartLevel(); + this.stopGame(); + this.gameView.updateScoreOnScreen(); + setTimeout(() => { + this.restartLevel(); + }, 3000); } checkLoot(): void { @@ -767,9 +772,12 @@ class PlayLevel { return false; } - restartLevel(): void { + stopGame(): void { clearInterval(this.monsterAnimationTimer); cancelAnimationFrame(this.daveAnimationTimer); + } + + restartLevel(): void { if (this.gameView.lives > 0) { this.gameView.resetLevel(); this.gameView.loadLevelEntities(); diff --git a/client/src/styles/dave.css b/client/src/styles/dave.css index 84232ac..45eb596 100644 --- a/client/src/styles/dave.css +++ b/client/src/styles/dave.css @@ -7,4 +7,15 @@ top: 0; left: 0; z-index: 100; -} \ No newline at end of file +} + +.death-layer { + position: absolute; + top: -20px; + left: -40px; + width: 144px; + height: 144px; + z-index: 101; + background-color: crimson; + display: none; +} From 83bfbd4185d7036fbc7d907881fdfccb22ec01a4 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 17:02:07 +0300 Subject: [PATCH 068/196] refactor: remove unused spec files --- server/src/modules/app/app.controller.spec.ts | 22 ----------------- server/test/app.e2e-spec.ts | 24 ------------------- 2 files changed, 46 deletions(-) delete mode 100644 server/src/modules/app/app.controller.spec.ts delete mode 100644 server/test/app.e2e-spec.ts diff --git a/server/src/modules/app/app.controller.spec.ts b/server/src/modules/app/app.controller.spec.ts deleted file mode 100644 index d22f389..0000000 --- a/server/src/modules/app/app.controller.spec.ts +++ /dev/null @@ -1,22 +0,0 @@ -import { Test, TestingModule } from '@nestjs/testing'; -import { AppController } from './app.controller'; -import { AppService } from './app.service'; - -describe('AppController', () => { - let appController: AppController; - - beforeEach(async () => { - const app: TestingModule = await Test.createTestingModule({ - controllers: [AppController], - providers: [AppService], - }).compile(); - - appController = app.get(AppController); - }); - - describe('root', () => { - it('should return "Hello World!"', () => { - expect(appController.getHello()).toBe('Hello World!'); - }); - }); -}); diff --git a/server/test/app.e2e-spec.ts b/server/test/app.e2e-spec.ts deleted file mode 100644 index 0012dcd..0000000 --- a/server/test/app.e2e-spec.ts +++ /dev/null @@ -1,24 +0,0 @@ -import { Test, TestingModule } from '@nestjs/testing'; -import { INestApplication } from '@nestjs/common'; -import * as request from 'supertest'; -import { AppModule } from '../src/app.module'; - -describe('AppController (e2e)', () => { - let app: INestApplication; - - beforeEach(async () => { - const moduleFixture: TestingModule = await Test.createTestingModule({ - imports: [AppModule], - }).compile(); - - app = moduleFixture.createNestApplication(); - await app.init(); - }); - - it('/ (GET)', () => { - return request(app.getHttpServer()) - .get('/') - .expect(200) - .expect('Hello World!'); - }); -}); From 91df9ad199b84b05119bd1e6be3243c96dcd2326 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 17:18:02 +0300 Subject: [PATCH 069/196] feat: create auth module --- server/src/modules/auth/auth.module.ts | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 server/src/modules/auth/auth.module.ts diff --git a/server/src/modules/auth/auth.module.ts b/server/src/modules/auth/auth.module.ts new file mode 100644 index 0000000..7459c06 --- /dev/null +++ b/server/src/modules/auth/auth.module.ts @@ -0,0 +1,4 @@ +import { Module } from '@nestjs/common'; + +@Module({}) +export class AuthModule {} From 472dd32e459f11f965c64f69b8e49b2867373b18 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 17:54:34 +0300 Subject: [PATCH 070/196] feat: create auth service --- server/src/modules/app/app.module.ts | 2 ++ server/src/modules/auth/auth.module.ts | 5 ++++- server/src/modules/auth/auth.service.ts | 4 ++++ 3 files changed, 10 insertions(+), 1 deletion(-) create mode 100644 server/src/modules/auth/auth.service.ts diff --git a/server/src/modules/app/app.module.ts b/server/src/modules/app/app.module.ts index 473c751..51cbe88 100644 --- a/server/src/modules/app/app.module.ts +++ b/server/src/modules/app/app.module.ts @@ -4,6 +4,7 @@ import { AppService } from './app.service'; import { MongooseModule } from '@nestjs/mongoose'; import { ConfigModule } from '@nestjs/config'; import { UserModule } from '../user/user.module'; +import { AuthModule } from '../auth/auth.module'; @Module({ imports: [ @@ -19,6 +20,7 @@ import { UserModule } from '../user/user.module'; }, ), UserModule, + AuthModule, ], controllers: [AppController], providers: [AppService], diff --git a/server/src/modules/auth/auth.module.ts b/server/src/modules/auth/auth.module.ts index 7459c06..b754151 100644 --- a/server/src/modules/auth/auth.module.ts +++ b/server/src/modules/auth/auth.module.ts @@ -1,4 +1,7 @@ import { Module } from '@nestjs/common'; +import { AuthService } from './auth.service'; -@Module({}) +@Module({ + providers: [AuthService], +}) export class AuthModule {} diff --git a/server/src/modules/auth/auth.service.ts b/server/src/modules/auth/auth.service.ts new file mode 100644 index 0000000..a41c649 --- /dev/null +++ b/server/src/modules/auth/auth.service.ts @@ -0,0 +1,4 @@ +import { Injectable } from '@nestjs/common'; + +@Injectable() +export class AuthService {} From 3d6c9ccc33f9b9553cd5af9ed731cfa92651d54c Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 17:54:55 +0300 Subject: [PATCH 071/196] refactor: replace Omit on Pick --- server/src/types/dto/user/createUserDto.ts | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/server/src/types/dto/user/createUserDto.ts b/server/src/types/dto/user/createUserDto.ts index d9729b6..49d86f3 100644 --- a/server/src/types/dto/user/createUserDto.ts +++ b/server/src/types/dto/user/createUserDto.ts @@ -1,3 +1,6 @@ import { IUser } from '../../interfaces/user'; -export type CreateUserRequestDto = Omit; +export type CreateUserRequestDto = Pick< + IUser, + 'username' | 'password' | 'authProvider' +>; From 0f7fa827670d5bf065e847572acc29eb8eb2d25d Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 18:29:03 +0300 Subject: [PATCH 072/196] feat: create register with local provider --- server/package-lock.json | 73 ++++++++++++++++++- server/package.json | 1 + .../middlewares/authValidationMiddleware.ts | 25 +++++++ server/src/modules/app/app.module.ts | 10 ++- server/src/modules/auth/auth.module.ts | 12 ++- server/src/modules/auth/auth.service.ts | 58 ++++++++++++++- server/src/types/dto/user/authUserDto.ts | 9 +++ server/src/types/interfaces/userJwtPayload.ts | 8 ++ 8 files changed, 188 insertions(+), 8 deletions(-) create mode 100644 server/src/middlewares/authValidationMiddleware.ts create mode 100644 server/src/types/dto/user/authUserDto.ts create mode 100644 server/src/types/interfaces/userJwtPayload.ts diff --git a/server/package-lock.json b/server/package-lock.json index 21e7961..04fa2ff 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -12,6 +12,7 @@ "@nestjs/common": "^9.0.0", "@nestjs/config": "^2.3.1", "@nestjs/core": "^9.0.0", + "@nestjs/jwt": "^10.0.2", "@nestjs/mongoose": "^9.2.1", "@nestjs/platform-express": "^9.0.0", "reflect-metadata": "^0.1.13", @@ -2742,6 +2743,18 @@ } } }, + "node_modules/@nestjs/jwt": { + "version": "10.0.2", + "resolved": "https://registry.npmjs.org/@nestjs/jwt/-/jwt-10.0.2.tgz", + "integrity": "sha512-MLxjCSbO7C9fN2hst5kpIhnJAgglJmrKppXAXqElB8A9ip3ZuCowMDjjmNWWJyfOzE98NV0E0iEQGE2StMUC+Q==", + "dependencies": { + "@types/jsonwebtoken": "9.0.1", + "jsonwebtoken": "9.0.0" + }, + "peerDependencies": { + "@nestjs/common": "^8.0.0 || ^9.0.0" + } + }, "node_modules/@nestjs/mongoose": { "version": "9.2.1", "resolved": "https://registry.npmjs.org/@nestjs/mongoose/-/mongoose-9.2.1.tgz", @@ -3186,6 +3199,14 @@ "integrity": "sha512-wOuvG1SN4Us4rez+tylwwwCV1psiNVOkJeM3AUWUNWg/jDQY2+HE/444y5gc+jBmRqASOm2Oeh5c1axHobwRKQ==", "dev": true }, + "node_modules/@types/jsonwebtoken": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/@types/jsonwebtoken/-/jsonwebtoken-9.0.1.tgz", + "integrity": "sha512-c5ltxazpWabia/4UzhIoaDcIza4KViOQhdbjRlfcIGVnsE3c3brkz9Z+F/EeJIECOQP7W7US2hNE930cWWkPiw==", + "dependencies": { + "@types/node": "*" + } + }, "node_modules/@types/mime": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/@types/mime/-/mime-3.0.1.tgz", @@ -4159,6 +4180,11 @@ "ieee754": "^1.1.13" } }, + "node_modules/buffer-equal-constant-time": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz", + "integrity": "sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==" + }, "node_modules/buffer-from": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", @@ -4718,6 +4744,14 @@ "node": ">=12" } }, + "node_modules/ecdsa-sig-formatter": { + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/ecdsa-sig-formatter/-/ecdsa-sig-formatter-1.0.11.tgz", + "integrity": "sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==", + "dependencies": { + "safe-buffer": "^5.0.1" + } + }, "node_modules/ee-first": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", @@ -7116,6 +7150,40 @@ "graceful-fs": "^4.1.6" } }, + "node_modules/jsonwebtoken": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-9.0.0.tgz", + "integrity": "sha512-tuGfYXxkQGDPnLJ7SibiQgVgeDgfbPq2k2ICcbgqW8WxWLBAxKQM/ZCu/IT8SOSwmaYl4dpTFCW5xZv7YbbWUw==", + "dependencies": { + "jws": "^3.2.2", + "lodash": "^4.17.21", + "ms": "^2.1.1", + "semver": "^7.3.8" + }, + "engines": { + "node": ">=12", + "npm": ">=6" + } + }, + "node_modules/jwa": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/jwa/-/jwa-1.4.1.tgz", + "integrity": "sha512-qiLX/xhEEFKUAJ6FiBMbes3w9ATzyk5W7Hvzpa/SLYdxNtng+gcurvrI7TbACjIXlsJyr05/S1oUhZrc63evQA==", + "dependencies": { + "buffer-equal-constant-time": "1.0.1", + "ecdsa-sig-formatter": "1.0.11", + "safe-buffer": "^5.0.1" + } + }, + "node_modules/jws": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/jws/-/jws-3.2.2.tgz", + "integrity": "sha512-YHlZCB6lMTllWDtSPHz/ZXTsi8S00usEV6v1tjq8tOUZzw7DpSDWVXjXDre6ed1w/pd495ODpHZYSdkRTsa0HA==", + "dependencies": { + "jwa": "^1.4.1", + "safe-buffer": "^5.0.1" + } + }, "node_modules/kareem": { "version": "2.5.1", "resolved": "https://registry.npmjs.org/kareem/-/kareem-2.5.1.tgz", @@ -8516,7 +8584,6 @@ "version": "7.3.8", "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.8.tgz", "integrity": "sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==", - "dev": true, "dependencies": { "lru-cache": "^6.0.0" }, @@ -8531,7 +8598,6 @@ "version": "6.0.0", "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", - "dev": true, "dependencies": { "yallist": "^4.0.0" }, @@ -8542,8 +8608,7 @@ "node_modules/semver/node_modules/yallist": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", - "dev": true + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==" }, "node_modules/send": { "version": "0.18.0", diff --git a/server/package.json b/server/package.json index 4e8f4d2..0e60ee5 100644 --- a/server/package.json +++ b/server/package.json @@ -23,6 +23,7 @@ "@nestjs/common": "^9.0.0", "@nestjs/config": "^2.3.1", "@nestjs/core": "^9.0.0", + "@nestjs/jwt": "^10.0.2", "@nestjs/mongoose": "^9.2.1", "@nestjs/platform-express": "^9.0.0", "reflect-metadata": "^0.1.13", diff --git a/server/src/middlewares/authValidationMiddleware.ts b/server/src/middlewares/authValidationMiddleware.ts new file mode 100644 index 0000000..1393010 --- /dev/null +++ b/server/src/middlewares/authValidationMiddleware.ts @@ -0,0 +1,25 @@ +import { HttpStatus, Injectable, NestMiddleware } from '@nestjs/common'; +import { NextFunction, Request, Response } from 'express'; +import { RegisterUserRequestDto } from '../types/dto/user/authUserDto'; + +@Injectable() +export class AuthValidationMiddleware implements NestMiddleware { + use(req: Request, res: Response, next: NextFunction): unknown { + const user: RegisterUserRequestDto = req.body; + if (!user.username) { + return res.status(HttpStatus.BAD_REQUEST).send({ + statusCode: '400', + message: `The 'username' field must be provided.`, + error: 'Bad Request', + }); + } + if (!user.password) { + return res.status(HttpStatus.BAD_REQUEST).send({ + statusCode: '400', + message: `The 'password' field must be provided.`, + error: 'Bad Request', + }); + } + next(); + } +} diff --git a/server/src/modules/app/app.module.ts b/server/src/modules/app/app.module.ts index 51cbe88..063cfc6 100644 --- a/server/src/modules/app/app.module.ts +++ b/server/src/modules/app/app.module.ts @@ -1,10 +1,12 @@ -import { Module } from '@nestjs/common'; +import { MiddlewareConsumer, Module } from '@nestjs/common'; import { AppController } from './app.controller'; import { AppService } from './app.service'; import { MongooseModule } from '@nestjs/mongoose'; import { ConfigModule } from '@nestjs/config'; import { UserModule } from '../user/user.module'; import { AuthModule } from '../auth/auth.module'; +import { AuthValidationMiddleware } from '../../middlewares/authValidationMiddleware'; +import { AuthController } from '../auth/auth.controller'; @Module({ imports: [ @@ -25,4 +27,8 @@ import { AuthModule } from '../auth/auth.module'; controllers: [AppController], providers: [AppService], }) -export class AppModule {} +export class AppModule { + configure(consumer: MiddlewareConsumer): void { + consumer.apply(AuthValidationMiddleware).forRoutes(AuthController); + } +} diff --git a/server/src/modules/auth/auth.module.ts b/server/src/modules/auth/auth.module.ts index b754151..c5c7555 100644 --- a/server/src/modules/auth/auth.module.ts +++ b/server/src/modules/auth/auth.module.ts @@ -1,7 +1,17 @@ import { Module } from '@nestjs/common'; import { AuthService } from './auth.service'; +import { UserService } from '../user/user.service'; +import { JwtService } from '@nestjs/jwt'; +import { ConfigService } from '@nestjs/config'; +import { MongooseModule } from '@nestjs/mongoose'; +import { User, UserSchema } from '../../models/scheme/user.schema'; +import { AuthController } from './auth.controller'; @Module({ - providers: [AuthService], + imports: [ + MongooseModule.forFeature([{ name: User.name, schema: UserSchema }]), + ], + providers: [AuthService, UserService, JwtService, ConfigService], + controllers: [AuthController], }) export class AuthModule {} diff --git a/server/src/modules/auth/auth.service.ts b/server/src/modules/auth/auth.service.ts index a41c649..6efdf15 100644 --- a/server/src/modules/auth/auth.service.ts +++ b/server/src/modules/auth/auth.service.ts @@ -1,4 +1,60 @@ import { Injectable } from '@nestjs/common'; +import { JwtService } from '@nestjs/jwt'; +import { ConfigService } from '@nestjs/config'; +import { UserService } from '../user/user.service'; +import { + RegisterUserRequestDto, + RegisterUserResponseDto, +} from '../../types/dto/user/authUserDto'; +import { AuthProvider } from '../../types/enums/authProviders'; +import { IUser } from '../../types/interfaces/user'; +import { UserJwtPayload } from '../../types/interfaces/userJwtPayload'; @Injectable() -export class AuthService {} +export class AuthService { + constructor( + private readonly userService: UserService, + private readonly jwtService: JwtService, + private readonly config: ConfigService, + ) {} + + async register( + user: RegisterUserRequestDto, + authProvider: AuthProvider, + ): Promise { + switch (authProvider) { + case AuthProvider.LOCAL: + return await this.registerLocal(user); + } + } + + private async registerLocal( + user: RegisterUserRequestDto, + ): Promise { + const newUser = await this.userService.create({ + authProvider: AuthProvider.LOCAL, + ...user, + }); + const accessToken = this.createJwtToken(newUser); + + return { + _id: newUser._id, + username: newUser.username, + authProvider: newUser.authProvider, + accessToken, + }; + } + + private createJwtToken(user: IUser): string { + const payload: UserJwtPayload = { + id: user._id, + username: user.username, + authProvider: user.authProvider, + }; + + return this.jwtService.sign(payload, { + secret: this.config.get('JWT_SECRET') || 'super-secret-key', + expiresIn: this.config.get('JWT_EXPIRES_IN') || '24h', + }); + } +} diff --git a/server/src/types/dto/user/authUserDto.ts b/server/src/types/dto/user/authUserDto.ts new file mode 100644 index 0000000..4755611 --- /dev/null +++ b/server/src/types/dto/user/authUserDto.ts @@ -0,0 +1,9 @@ +import { IUser } from '../../interfaces/user'; + +export type LoginUserRequestDto = Pick; +export type RegisterUserRequestDto = LoginUserRequestDto; + +export type LoginUserResponseDto = { + accessToken: string; +} & Pick; +export type RegisterUserResponseDto = LoginUserResponseDto; diff --git a/server/src/types/interfaces/userJwtPayload.ts b/server/src/types/interfaces/userJwtPayload.ts new file mode 100644 index 0000000..87bf46a --- /dev/null +++ b/server/src/types/interfaces/userJwtPayload.ts @@ -0,0 +1,8 @@ +import { IUser } from './user'; +import { JwtPayload } from 'jsonwebtoken'; + +export interface UserJwtPayload extends JwtPayload { + readonly id: IUser['_id']; + readonly username: IUser['username']; + readonly authProvider: IUser['authProvider']; +} From 7c3c876906a9183c1a75d13f0a8daf3686fd9447 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 18:49:55 +0300 Subject: [PATCH 073/196] feat: create login with local provider --- server/src/modules/auth/auth.service.ts | 44 ++++++++++++++++++++++++- server/src/modules/user/user.service.ts | 18 ++++++++++ 2 files changed, 61 insertions(+), 1 deletion(-) diff --git a/server/src/modules/auth/auth.service.ts b/server/src/modules/auth/auth.service.ts index 6efdf15..f841ed6 100644 --- a/server/src/modules/auth/auth.service.ts +++ b/server/src/modules/auth/auth.service.ts @@ -1,8 +1,10 @@ -import { Injectable } from '@nestjs/common'; +import { Injectable, UnauthorizedException } from '@nestjs/common'; import { JwtService } from '@nestjs/jwt'; import { ConfigService } from '@nestjs/config'; import { UserService } from '../user/user.service'; import { + LoginUserRequestDto, + LoginUserResponseDto, RegisterUserRequestDto, RegisterUserResponseDto, } from '../../types/dto/user/authUserDto'; @@ -28,9 +30,20 @@ export class AuthService { } } + async login( + user: LoginUserRequestDto, + authProvider: AuthProvider, + ): Promise { + switch (authProvider) { + case AuthProvider.LOCAL: + return await this.loginLocal(user); + } + } + private async registerLocal( user: RegisterUserRequestDto, ): Promise { + // TODO: Encrypt your password first. const newUser = await this.userService.create({ authProvider: AuthProvider.LOCAL, ...user, @@ -45,6 +58,35 @@ export class AuthService { }; } + private async loginLocal( + user: LoginUserRequestDto, + ): Promise { + let targetUser: IUser; + let accessToken: string; + + try { + targetUser = await this.userService.findByUserNameAndAuthProvider( + user.username, + AuthProvider.LOCAL, + ); + accessToken = this.createJwtToken(targetUser); + } catch (e: unknown) { + throw new UnauthorizedException('User not found or password incorrect.'); + } + + // TODO: Use compare function for encrypted password + if (!(user.password === targetUser.password)) { + throw new UnauthorizedException('User not found or password incorrect.'); + } + + return { + _id: targetUser._id, + username: targetUser.username, + authProvider: targetUser.authProvider, + accessToken, + }; + } + private createJwtToken(user: IUser): string { const payload: UserJwtPayload = { id: user._id, diff --git a/server/src/modules/user/user.service.ts b/server/src/modules/user/user.service.ts index 3bcebdc..966b267 100644 --- a/server/src/modules/user/user.service.ts +++ b/server/src/modules/user/user.service.ts @@ -32,6 +32,24 @@ export class UserService { return result; } + async findByUserNameAndAuthProvider( + username: IUser['username'], + authProvider: IUser['authProvider'], + ): Promise { + const result = await this.userModel + .findOne({ username, authProvider }) + .exec(); + + if (!result) { + throw new UserNotFoundError({ + username, + authProvider, + }); + } + + return result; + } + async create(user: CreateUserRequestDto): Promise { await this.validateUser(user); From a059489a9fd44a92a317a9731af0d04f3aa45c1a Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 21:06:36 +0300 Subject: [PATCH 074/196] feat: add password encrypt --- server/package-lock.json | 341 ++++++++++++++++++++++-- server/package.json | 2 + server/src/modules/auth/auth.service.ts | 29 +- 3 files changed, 344 insertions(+), 28 deletions(-) diff --git a/server/package-lock.json b/server/package-lock.json index 04fa2ff..cc9da76 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -15,6 +15,7 @@ "@nestjs/jwt": "^10.0.2", "@nestjs/mongoose": "^9.2.1", "@nestjs/platform-express": "^9.0.0", + "bcrypt": "^5.1.0", "reflect-metadata": "^0.1.13", "rxjs": "^7.2.0", "uuid": "^9.0.0" @@ -23,6 +24,7 @@ "@nestjs/cli": "^9.0.0", "@nestjs/schematics": "^9.0.0", "@nestjs/testing": "^9.0.0", + "@types/bcrypt": "^5.0.0", "@types/express": "^4.17.13", "@types/jest": "29.2.4", "@types/node": "18.11.18", @@ -2599,6 +2601,39 @@ "node": ">=8" } }, + "node_modules/@mapbox/node-pre-gyp": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/@mapbox/node-pre-gyp/-/node-pre-gyp-1.0.10.tgz", + "integrity": "sha512-4ySo4CjzStuprMwk35H5pPbkymjv1SF3jGLj6rAHp/xT/RF7TL7bd9CTm1xDY49K2qF7jmR/g7k+SkLETP6opA==", + "dependencies": { + "detect-libc": "^2.0.0", + "https-proxy-agent": "^5.0.0", + "make-dir": "^3.1.0", + "node-fetch": "^2.6.7", + "nopt": "^5.0.0", + "npmlog": "^5.0.1", + "rimraf": "^3.0.2", + "semver": "^7.3.5", + "tar": "^6.1.11" + }, + "bin": { + "node-pre-gyp": "bin/node-pre-gyp" + } + }, + "node_modules/@mapbox/node-pre-gyp/node_modules/rimraf": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-3.0.2.tgz", + "integrity": "sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==", + "dependencies": { + "glob": "^7.1.3" + }, + "bin": { + "rimraf": "bin.js" + }, + "funding": { + "url": "https://github.com/sponsors/isaacs" + } + }, "node_modules/@nestjs/cli": { "version": "9.2.0", "resolved": "https://registry.npmjs.org/@nestjs/cli/-/cli-9.2.0.tgz", @@ -3076,6 +3111,15 @@ "@babel/types": "^7.3.0" } }, + "node_modules/@types/bcrypt": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/@types/bcrypt/-/bcrypt-5.0.0.tgz", + "integrity": "sha512-agtcFKaruL8TmcvqbndlqHPSJgsolhf/qPWchFlgnW1gECTN/nKbFcoFnvKAQRFfKbh+BO6A3SWdJu9t+xF3Lw==", + "dev": true, + "dependencies": { + "@types/node": "*" + } + }, "node_modules/@types/body-parser": { "version": "1.19.2", "resolved": "https://registry.npmjs.org/@types/body-parser/-/body-parser-1.19.2.tgz", @@ -3666,6 +3710,11 @@ "integrity": "sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ==", "dev": true }, + "node_modules/abbrev": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz", + "integrity": "sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==" + }, "node_modules/accepts": { "version": "1.3.8", "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.8.tgz", @@ -3717,6 +3766,17 @@ "node": ">=0.4.0" } }, + "node_modules/agent-base": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-6.0.2.tgz", + "integrity": "sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==", + "dependencies": { + "debug": "4" + }, + "engines": { + "node": ">= 6.0.0" + } + }, "node_modules/ajv": { "version": "8.12.0", "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.12.0.tgz", @@ -3790,7 +3850,6 @@ "version": "5.0.1", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz", "integrity": "sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==", - "dev": true, "engines": { "node": ">=8" } @@ -3827,6 +3886,36 @@ "resolved": "https://registry.npmjs.org/append-field/-/append-field-1.0.0.tgz", "integrity": "sha512-klpgFSWLW1ZEs8svjfb7g4qWY0YS5imI82dTg+QahUvJ8YqAY0P10Uk8tTyh9ZGuYEZEMaeJYCF5BFuX552hsw==" }, + "node_modules/aproba": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/aproba/-/aproba-2.0.0.tgz", + "integrity": "sha512-lYe4Gx7QT+MKGbDsA+Z+he/Wtef0BiwDOlK/XkBrdfsh9J/jPPXbX0tE9x9cl27Tmu5gg3QUbUrQYa/y+KOHPQ==" + }, + "node_modules/are-we-there-yet": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/are-we-there-yet/-/are-we-there-yet-2.0.0.tgz", + "integrity": "sha512-Ci/qENmwHnsYo9xKIcUJN5LeDKdJ6R1Z1j9V/J5wyq8nh/mYPEpIKJbBZXtZjG04HiK7zV/p6Vs9952MrMeUIw==", + "dependencies": { + "delegates": "^1.0.0", + "readable-stream": "^3.6.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/are-we-there-yet/node_modules/readable-stream": { + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.0.tgz", + "integrity": "sha512-BViHy7LKeTz4oNnkcLJ+lVSL6vpiFeX6/d3oSH8zCW7UxP2onchk+vTGB143xuFjHS3deTgkKoXXymXqymiIdA==", + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, "node_modules/arg": { "version": "4.1.3", "resolved": "https://registry.npmjs.org/arg/-/arg-4.1.3.tgz", @@ -3975,8 +4064,7 @@ "node_modules/balanced-match": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", - "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", - "dev": true + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==" }, "node_modules/base64-js": { "version": "1.5.1", @@ -3997,6 +4085,19 @@ } ] }, + "node_modules/bcrypt": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/bcrypt/-/bcrypt-5.1.0.tgz", + "integrity": "sha512-RHBS7HI5N5tEnGTmtR/pppX0mmDSBpQ4aCBsj7CEQfYXDcO74A8sIBYcJMuCsis2E81zDxeENYhv66oZwLiA+Q==", + "hasInstallScript": true, + "dependencies": { + "@mapbox/node-pre-gyp": "^1.0.10", + "node-addon-api": "^5.0.0" + }, + "engines": { + "node": ">= 10.0.0" + } + }, "node_modules/binary-extensions": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-2.2.0.tgz", @@ -4078,7 +4179,6 @@ "version": "1.1.11", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", - "dev": true, "dependencies": { "balanced-match": "^1.0.0", "concat-map": "0.0.1" @@ -4310,6 +4410,14 @@ "fsevents": "~2.3.2" } }, + "node_modules/chownr": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/chownr/-/chownr-2.0.0.tgz", + "integrity": "sha512-bIomtDF5KGpdogkLd9VspvFzk9KfpyyGlS8YFVZl7TGPBHL5snIOnxeshwVgPteQ9b4Eydl+pVbIyE1DcvCWgQ==", + "engines": { + "node": ">=10" + } + }, "node_modules/chrome-trace-event": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/chrome-trace-event/-/chrome-trace-event-1.0.3.tgz", @@ -4443,6 +4551,14 @@ "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" }, + "node_modules/color-support": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-support/-/color-support-1.1.3.tgz", + "integrity": "sha512-qiBjkpbMLO/HL68y+lh4q0/O1MZFj2RX6X/KmMa3+gJD3z+WwI1ZzDHysvqHGS3mP6mznPckpXmw1nI9cJjyRg==", + "bin": { + "color-support": "bin.js" + } + }, "node_modules/combined-stream": { "version": "1.0.8", "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", @@ -4473,8 +4589,7 @@ "node_modules/concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", - "dev": true + "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==" }, "node_modules/concat-stream": { "version": "1.6.2", @@ -4495,6 +4610,11 @@ "resolved": "https://registry.npmjs.org/consola/-/consola-2.15.3.tgz", "integrity": "sha512-9vAdYbHj6x2fLKC4+oPH0kFzY/orMZyG2Aj+kNylHxKGJ/Ed4dpNyAQYwJOdqO4zdM7XpVHmyejQDcQHrnuXbw==" }, + "node_modules/console-control-strings": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/console-control-strings/-/console-control-strings-1.1.0.tgz", + "integrity": "sha512-ty/fTekppD2fIwRvnZAVdeOiGd1c7YXEixbgJTNzqcxJWKQnjJ/V1bNEEE6hygpM3WjwHFUVK6HTjWSzV4a8sQ==" + }, "node_modules/content-disposition": { "version": "0.5.4", "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.4.tgz", @@ -4650,6 +4770,11 @@ "node": ">=0.4.0" } }, + "node_modules/delegates": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delegates/-/delegates-1.0.0.tgz", + "integrity": "sha512-bd2L678uiWATM6m5Z1VzNCErI3jiGzt6HGY8OVICs40JQq/HALfbyNJmp0UDakEY4pMMaN0Ly5om/B1VI/+xfQ==" + }, "node_modules/depd": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", @@ -4667,6 +4792,14 @@ "npm": "1.2.8000 || >= 1.4.16" } }, + "node_modules/detect-libc": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/detect-libc/-/detect-libc-2.0.1.tgz", + "integrity": "sha512-463v3ZeIrcWtdgIg6vI6XUncguvr2TnGl4SzDXinkt9mSLpBJKXT3mW6xT3VQdDN11+WVs29pgvivTc4Lp8v+w==", + "engines": { + "node": ">=8" + } + }, "node_modules/detect-newline": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/detect-newline/-/detect-newline-3.1.0.tgz", @@ -4778,8 +4911,7 @@ "node_modules/emoji-regex": { "version": "8.0.0", "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-8.0.0.tgz", - "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", - "dev": true + "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==" }, "node_modules/encodeurl": { "version": "1.0.2", @@ -5621,6 +5753,33 @@ "node": ">=14.14" } }, + "node_modules/fs-minipass": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/fs-minipass/-/fs-minipass-2.1.0.tgz", + "integrity": "sha512-V/JgOLFCS+R6Vcq0slCuaeWEdNC3ouDlJMNIsacH2VtALiu9mV4LPrHc5cDl8k5aw6J8jwgWWpiTo5RYhmIzvg==", + "dependencies": { + "minipass": "^3.0.0" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/fs-minipass/node_modules/minipass": { + "version": "3.3.6", + "resolved": "https://registry.npmjs.org/minipass/-/minipass-3.3.6.tgz", + "integrity": "sha512-DxiNidxSEK+tHG6zOIklvNOwm3hvCrbUrdtzY74U6HKTJxvIDfOUL5W5P2Ghd3DTkhhKPYGqeNUIh5qcM4YBfw==", + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/fs-minipass/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==" + }, "node_modules/fs-monkey": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/fs-monkey/-/fs-monkey-1.0.3.tgz", @@ -5630,8 +5789,7 @@ "node_modules/fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==", - "dev": true + "integrity": "sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==" }, "node_modules/fsevents": { "version": "2.3.2", @@ -5652,6 +5810,25 @@ "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==" }, + "node_modules/gauge": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/gauge/-/gauge-3.0.2.tgz", + "integrity": "sha512-+5J6MS/5XksCuXq++uFRsnUd7Ovu1XenbeuIuNRJxYWjgQbPuFhT14lAvsWfqfAmnwluf1OwMjz39HjfLPci0Q==", + "dependencies": { + "aproba": "^1.0.3 || ^2.0.0", + "color-support": "^1.1.2", + "console-control-strings": "^1.0.0", + "has-unicode": "^2.0.1", + "object-assign": "^4.1.1", + "signal-exit": "^3.0.0", + "string-width": "^4.2.3", + "strip-ansi": "^6.0.1", + "wide-align": "^1.1.2" + }, + "engines": { + "node": ">=10" + } + }, "node_modules/gensync": { "version": "1.0.0-beta.2", "resolved": "https://registry.npmjs.org/gensync/-/gensync-1.0.0-beta.2.tgz", @@ -5708,7 +5885,6 @@ "version": "7.2.3", "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz", "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==", - "dev": true, "dependencies": { "fs.realpath": "^1.0.0", "inflight": "^1.0.4", @@ -5819,6 +5995,11 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/has-unicode": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/has-unicode/-/has-unicode-2.0.1.tgz", + "integrity": "sha512-8Rf9Y83NBReMnx0gFzA8JImQACstCYWUplepDa9xprwwtmgEZUF0h/i5xSA625zB/I37EtrswSST6OXxwaaIJQ==" + }, "node_modules/hexoid": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/hexoid/-/hexoid-1.0.0.tgz", @@ -5849,6 +6030,18 @@ "node": ">= 0.8" } }, + "node_modules/https-proxy-agent": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-5.0.1.tgz", + "integrity": "sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA==", + "dependencies": { + "agent-base": "6", + "debug": "4" + }, + "engines": { + "node": ">= 6" + } + }, "node_modules/human-signals": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/human-signals/-/human-signals-2.1.0.tgz", @@ -5945,7 +6138,6 @@ "version": "1.0.6", "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", "integrity": "sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==", - "dev": true, "dependencies": { "once": "^1.3.0", "wrappy": "1" @@ -6080,7 +6272,6 @@ "version": "3.0.0", "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-3.0.0.tgz", "integrity": "sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==", - "dev": true, "engines": { "node": ">=8" } @@ -7340,7 +7531,6 @@ "version": "3.1.0", "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-3.1.0.tgz", "integrity": "sha512-g3FeP20LNwhALb/6Cz6Dd4F2ngze0jz7tbzrD2wAV+o9FeNHe4rL+yK2md0J/fiSf1sa1ADhXqi5+oVwOM/eGw==", - "dev": true, "dependencies": { "semver": "^6.0.0" }, @@ -7355,7 +7545,6 @@ "version": "6.3.0", "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", "integrity": "sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==", - "dev": true, "bin": { "semver": "bin/semver.js" } @@ -7486,7 +7675,6 @@ "version": "3.1.2", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz", "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==", - "dev": true, "dependencies": { "brace-expansion": "^1.1.7" }, @@ -7502,6 +7690,42 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/minipass": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/minipass/-/minipass-4.0.3.tgz", + "integrity": "sha512-OW2r4sQ0sI+z5ckEt5c1Tri4xTgZwYDxpE54eqWlQloQRoWtXjqt9udJ5Z4dSv7wK+nfFI7FRXyCpBSft+gpFw==", + "engines": { + "node": ">=8" + } + }, + "node_modules/minizlib": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/minizlib/-/minizlib-2.1.2.tgz", + "integrity": "sha512-bAxsR8BVfj60DWXHE3u30oHzfl4G7khkSuPW+qvpd7jFRHm7dLxOjUk1EHACJ/hxLY8phGJ0YhYHZo7jil7Qdg==", + "dependencies": { + "minipass": "^3.0.0", + "yallist": "^4.0.0" + }, + "engines": { + "node": ">= 8" + } + }, + "node_modules/minizlib/node_modules/minipass": { + "version": "3.3.6", + "resolved": "https://registry.npmjs.org/minipass/-/minipass-3.3.6.tgz", + "integrity": "sha512-DxiNidxSEK+tHG6zOIklvNOwm3hvCrbUrdtzY74U6HKTJxvIDfOUL5W5P2Ghd3DTkhhKPYGqeNUIh5qcM4YBfw==", + "dependencies": { + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/minizlib/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==" + }, "node_modules/mkdirp": { "version": "0.5.6", "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.6.tgz", @@ -7684,6 +7908,11 @@ "integrity": "sha512-AGK2yQKIjRuqnc6VkX2Xj5d+QW8xZ87pa1UK6yA6ouUyuxfHuMP6umE5QK7UmTeOAymo+Zx1Fxiuw9rVx8taHQ==", "dev": true }, + "node_modules/node-addon-api": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/node-addon-api/-/node-addon-api-5.1.0.tgz", + "integrity": "sha512-eh0GgfEkpnoWDq+VY8OyvYhFEzBk6jIYbRKdIlyTiAXIVJ8PyBaKb0rp7oDtoddbdoHWhq8wwr+XZ81F1rpNdA==" + }, "node_modules/node-emoji": { "version": "1.11.0", "resolved": "https://registry.npmjs.org/node-emoji/-/node-emoji-1.11.0.tgz", @@ -7724,6 +7953,20 @@ "integrity": "sha512-5GFldHPXVG/YZmFzJvKK2zDSzPKhEp0+ZR5SVaoSag9fsL5YgHbUHDfnG5494ISANDcK4KwPXAx2xqVEydmd7w==", "dev": true }, + "node_modules/nopt": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/nopt/-/nopt-5.0.0.tgz", + "integrity": "sha512-Tbj67rffqceeLpcRXrT7vKAN8CwfPeIBgM7E6iBkmKLV7bEMwpGgYLGv0jACUsECaa/vuxP0IjEont6umdMgtQ==", + "dependencies": { + "abbrev": "1" + }, + "bin": { + "nopt": "bin/nopt.js" + }, + "engines": { + "node": ">=6" + } + }, "node_modules/normalize-path": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", @@ -7745,6 +7988,17 @@ "node": ">=8" } }, + "node_modules/npmlog": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/npmlog/-/npmlog-5.0.1.tgz", + "integrity": "sha512-AqZtDUWOMKs1G/8lwylVjrdYgqA4d9nu8hc+0gzRxlDb1I10+FHBGMXs6aiQHFdCUUlqH99MUMuLfzWDNDtfxw==", + "dependencies": { + "are-we-there-yet": "^2.0.0", + "console-control-strings": "^1.1.0", + "gauge": "^3.0.0", + "set-blocking": "^2.0.0" + } + }, "node_modules/object-assign": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", @@ -7776,7 +8030,6 @@ "version": "1.4.0", "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==", - "dev": true, "dependencies": { "wrappy": "1" } @@ -7967,7 +8220,6 @@ "version": "1.0.1", "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", "integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==", - "dev": true, "engines": { "node": ">=0.10.0" } @@ -8674,6 +8926,11 @@ "node": ">= 0.8.0" } }, + "node_modules/set-blocking": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", + "integrity": "sha512-KiKBS8AnWGEyLzofFfmvKwpdPzqiy16LvQfK3yv/fVH7Bj13/wl3JSR1J+rfgRE9q7xUJK4qvgS8raSOeLUehw==" + }, "node_modules/setprototypeof": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", @@ -8739,8 +8996,7 @@ "node_modules/signal-exit": { "version": "3.0.7", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", - "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==", - "dev": true + "integrity": "sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==" }, "node_modules/sisteransi": { "version": "1.0.5", @@ -8899,7 +9155,6 @@ "version": "4.2.3", "resolved": "https://registry.npmjs.org/string-width/-/string-width-4.2.3.tgz", "integrity": "sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==", - "dev": true, "dependencies": { "emoji-regex": "^8.0.0", "is-fullwidth-code-point": "^3.0.0", @@ -8913,7 +9168,6 @@ "version": "6.0.1", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-6.0.1.tgz", "integrity": "sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==", - "dev": true, "dependencies": { "ansi-regex": "^5.0.1" }, @@ -9045,6 +9299,38 @@ "node": ">=6" } }, + "node_modules/tar": { + "version": "6.1.13", + "resolved": "https://registry.npmjs.org/tar/-/tar-6.1.13.tgz", + "integrity": "sha512-jdIBIN6LTIe2jqzay/2vtYLlBHa3JF42ot3h1dW8Q0PaAG4v8rm0cvpVePtau5C6OKXGGcgO9q2AMNSWxiLqKw==", + "dependencies": { + "chownr": "^2.0.0", + "fs-minipass": "^2.0.0", + "minipass": "^4.0.0", + "minizlib": "^2.1.1", + "mkdirp": "^1.0.3", + "yallist": "^4.0.0" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/tar/node_modules/mkdirp": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-1.0.4.tgz", + "integrity": "sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw==", + "bin": { + "mkdirp": "bin/cmd.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/tar/node_modules/yallist": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==" + }, "node_modules/terser": { "version": "5.16.3", "resolved": "https://registry.npmjs.org/terser/-/terser-5.16.3.tgz", @@ -9725,6 +10011,14 @@ "node": ">= 8" } }, + "node_modules/wide-align": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/wide-align/-/wide-align-1.1.5.tgz", + "integrity": "sha512-eDMORYaPNZ4sQIuuYPDHdQvf4gyCF9rEEV/yPxGfwPkRodwEgiMUUXTx/dex+Me0wxx53S+NgUHaP7y3MGlDmg==", + "dependencies": { + "string-width": "^1.0.2 || 2 || 3 || 4" + } + }, "node_modules/windows-release": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/windows-release/-/windows-release-4.0.0.tgz", @@ -9816,8 +10110,7 @@ "node_modules/wrappy": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", - "dev": true + "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==" }, "node_modules/write-file-atomic": { "version": "4.0.2", diff --git a/server/package.json b/server/package.json index 0e60ee5..6950574 100644 --- a/server/package.json +++ b/server/package.json @@ -26,6 +26,7 @@ "@nestjs/jwt": "^10.0.2", "@nestjs/mongoose": "^9.2.1", "@nestjs/platform-express": "^9.0.0", + "bcrypt": "^5.1.0", "reflect-metadata": "^0.1.13", "rxjs": "^7.2.0", "uuid": "^9.0.0" @@ -34,6 +35,7 @@ "@nestjs/cli": "^9.0.0", "@nestjs/schematics": "^9.0.0", "@nestjs/testing": "^9.0.0", + "@types/bcrypt": "^5.0.0", "@types/express": "^4.17.13", "@types/jest": "29.2.4", "@types/node": "18.11.18", diff --git a/server/src/modules/auth/auth.service.ts b/server/src/modules/auth/auth.service.ts index f841ed6..291cbe0 100644 --- a/server/src/modules/auth/auth.service.ts +++ b/server/src/modules/auth/auth.service.ts @@ -1,4 +1,8 @@ -import { Injectable, UnauthorizedException } from '@nestjs/common'; +import { + BadRequestException, + Injectable, + UnauthorizedException, +} from '@nestjs/common'; import { JwtService } from '@nestjs/jwt'; import { ConfigService } from '@nestjs/config'; import { UserService } from '../user/user.service'; @@ -11,9 +15,13 @@ import { import { AuthProvider } from '../../types/enums/authProviders'; import { IUser } from '../../types/interfaces/user'; import { UserJwtPayload } from '../../types/interfaces/userJwtPayload'; +import * as bcrypt from 'bcrypt'; @Injectable() export class AuthService { + private readonly saltRounds = + Number(process.env.PASWORD_HASH_SALT_ROUNDS) || 10; + constructor( private readonly userService: UserService, private readonly jwtService: JwtService, @@ -43,10 +51,17 @@ export class AuthService { private async registerLocal( user: RegisterUserRequestDto, ): Promise { - // TODO: Encrypt your password first. + if (!user.password) { + throw new BadRequestException( + 'For a local authorization provider, a password must be provided.', + ); + } + + const encryptedPassword = await bcrypt.hash(user.password, this.saltRounds); const newUser = await this.userService.create({ authProvider: AuthProvider.LOCAL, ...user, + password: encryptedPassword, }); const accessToken = this.createJwtToken(newUser); @@ -64,6 +79,12 @@ export class AuthService { let targetUser: IUser; let accessToken: string; + if (!user.password) { + throw new BadRequestException( + 'For a local authorization provider, a password must be provided.', + ); + } + try { targetUser = await this.userService.findByUserNameAndAuthProvider( user.username, @@ -74,8 +95,8 @@ export class AuthService { throw new UnauthorizedException('User not found or password incorrect.'); } - // TODO: Use compare function for encrypted password - if (!(user.password === targetUser.password)) { + // eslint-disable-next-line @typescript-eslint/no-non-null-assertion + if (!(await bcrypt.compare(user.password, targetUser.password!))) { throw new UnauthorizedException('User not found or password incorrect.'); } From 4172f5faf5ff488d2a638e69155e507c084db05d Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 21:19:55 +0300 Subject: [PATCH 075/196] feat: create auth controller with register and login using local provider --- server/src/modules/auth/auth.controller.ts | 89 ++++++++++++++++++++++ 1 file changed, 89 insertions(+) create mode 100644 server/src/modules/auth/auth.controller.ts diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts new file mode 100644 index 0000000..1591a84 --- /dev/null +++ b/server/src/modules/auth/auth.controller.ts @@ -0,0 +1,89 @@ +import { + BadRequestException, + Body, + Controller, + HttpStatus, + Post, + Query, + Res, + UnauthorizedException, +} from '@nestjs/common'; +import { AuthService } from './auth.service'; +import { + LoginUserRequestDto, + RegisterUserRequestDto, + RegisterUserResponseDto, +} from '../../types/dto/user/authUserDto'; +import { AuthProvider } from '../../types/enums/authProviders'; +import { Response } from 'express'; + +@Controller('auth') +export class AuthController { + constructor(private readonly authService: AuthService) {} + + @Post('register') + async register( + @Res() res: Response, + @Query() { provider }: { provider: AuthProvider }, + @Body() user: RegisterUserRequestDto, + ): Promise { + try { + if (!provider || provider === AuthProvider.LOCAL) { + const registeredUser = await this.authService.register( + { + ...user, + }, + AuthProvider.LOCAL, + ); + + res.cookie('auth_token', registeredUser.accessToken, { + httpOnly: true, + }); + + res.status(HttpStatus.OK).send(registeredUser); + return registeredUser; + } + } catch (e: unknown) { + if (e instanceof Error) { + throw new BadRequestException(e.message); + } + } + + throw new BadRequestException('Invalid auth provider.'); + } + + @Post('login') + async login( + @Res() res: Response, + @Query() { provider }: { provider: AuthProvider }, + @Body() user: LoginUserRequestDto, + ): Promise { + try { + if (!provider || provider === AuthProvider.LOCAL) { + const registeredUser = await this.authService.login( + { + ...user, + }, + AuthProvider.LOCAL, + ); + + res.cookie('auth_token', registeredUser.accessToken, { + httpOnly: true, + }); + + res.status(HttpStatus.OK).send(registeredUser); + return registeredUser; + } + } catch (e: unknown) { + if (e instanceof UnauthorizedException) { + throw new UnauthorizedException(e.message); + } + + if (e instanceof Error) { + throw new BadRequestException(e.message); + } + } + + throw new BadRequestException('Invalid auth provider.'); + } +} From 1e67b96de3cd4db8e10d4b4ffcb20fba32428bef Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 22:10:08 +0300 Subject: [PATCH 076/196] hotfix: update node js version into package.json --- server/package.json | 3 +++ 1 file changed, 3 insertions(+) diff --git a/server/package.json b/server/package.json index 6950574..37a3f28 100644 --- a/server/package.json +++ b/server/package.json @@ -56,6 +56,9 @@ "tsconfig-paths": "4.1.1", "typescript": "^4.7.4" }, + "engines": { + "node": ">=18" + } "jest": { "moduleFileExtensions": [ "js", From f849ac9b6ad66484ce29af4f783d96c65349ddba Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 22:11:47 +0300 Subject: [PATCH 077/196] hotfix: fix a error in package.json --- server/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/package.json b/server/package.json index 37a3f28..596b5a2 100644 --- a/server/package.json +++ b/server/package.json @@ -58,7 +58,7 @@ }, "engines": { "node": ">=18" - } + }, "jest": { "moduleFileExtensions": [ "js", From 63b573e047b5ad3ad9fb8750afa1f6e6efeac6c1 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sun, 12 Feb 2023 23:02:42 +0300 Subject: [PATCH 078/196] feat: add jump-fire-bonus sounds --- client/src/assets/sounds/bonus1.mp3 | Bin 0 -> 7019 bytes client/src/assets/sounds/jump.mp3 | Bin 0 -> 4632 bytes client/src/assets/sounds/land.mp3 | Bin 0 -> 3904 bytes client/src/assets/sounds/reload.mp3 | Bin 0 -> 3422 bytes client/src/assets/sounds/shot.mp3 | Bin 0 -> 8544 bytes client/src/assets/sounds/startgame.mp3 | Bin 0 -> 19855 bytes client/src/assets/sprites/dave_sprites.png | Bin 22049 -> 18059 bytes client/src/scripts/components/dave.ts | 2 +- client/src/scripts/components/game.ts | 13 +++++- client/src/scripts/controllers/playLevel.ts | 7 ++- .../src/styles/playerAnimationKeyframes.scss | 40 +++++++++--------- client/src/types/game.ts | 11 +++++ client/src/types/index.d.ts | 1 + client/webpack.config.js | 4 +- 14 files changed, 53 insertions(+), 25 deletions(-) create mode 100644 client/src/assets/sounds/bonus1.mp3 create mode 100644 client/src/assets/sounds/jump.mp3 create mode 100644 client/src/assets/sounds/land.mp3 create mode 100644 client/src/assets/sounds/reload.mp3 create mode 100644 client/src/assets/sounds/shot.mp3 create mode 100644 client/src/assets/sounds/startgame.mp3 diff --git a/client/src/assets/sounds/bonus1.mp3 b/client/src/assets/sounds/bonus1.mp3 new file mode 100644 index 0000000000000000000000000000000000000000..02d7e1bef0928702886c11f5b2523aede39138c9 GIT binary patch literal 7019 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 b=`uEzaki8dinYKZXaDzE{$JyN%>w@c%Q+hO literal 0 HcmV?d00001 diff --git a/client/src/assets/sounds/land.mp3 b/client/src/assets/sounds/land.mp3 new file mode 100644 index 0000000000000000000000000000000000000000..178eedbd2e255302569c1584c5f56ed1616125e4 GIT binary patch literal 3904 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 literal 0 HcmV?d00001 diff --git a/client/src/assets/sounds/startgame.mp3 b/client/src/assets/sounds/startgame.mp3 new file mode 100644 index 0000000000000000000000000000000000000000..b083ae4e5b27499b3a26fd991b99c4dfa3b929ca GIT binary patch literal 19855 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
N-$2Q9W+WOFt zK>)cXxA|luMM2a{>w@a7#DSjU>CdxT<`&V~kh`bMW>|0dT<4L|@=bQU$$0v=>DHM; zhWB6QCUTW1Zm>*5i==Q#Z7?gFDBlLZr=q;qhTd7YP)EA#+f-V{%vEz{d$zCihTT{3ujqFV1_LS}pWT0*2gZ)pgy@{n)BYZG+lef)aH&^evCrr?9*( zkDAI4Lk~YM-A&9D9jP1*QQ!RWEI`5U?ZOntL+aM5m$BLBPCtdG5H<=x53pp1H59P` zA1O?T;vNAEp8H)&e#ebS59Ka4mQsh>J6yO%BX{<%cGHlgG00h>I+}xFtl6`3i-8jfH)In4Zocc&fVGAZy<># z^`H0$-(2`UcCxL22SeEN?W_CCEt||^(b;Ci{bdi%Zd!b?_B!ccAae1I(Weh1@6tX> z*0Njqv(FDc+IV-%{#!tV!_Vn0< z6;je4%7sJ3iep5Al7856+HAOg@4qRDaIq9F@hud2A0TrO%b7hfhYxYFO=9LCW$Kn6 z%fWC;rDm+1kTSTxnxCY9ij$x1*3%;&Ja8G3fY(vM8xuJma!h=v8$S$17u%mLLA7$; zyj;jE7R9+eZm4v77>v97_QX2>FG81j^d{dmCO4uswk3)mNrdv^6Q-hy^0)jJwmV7ng4?JH^3&d@UCaLcZTV=s|CHs^eLd}o0$X8}4}@H6I! zB)}lIjUhY&Fy^EXQh8W=-1gEb!zpDr|FbRn?u^LXm;T=x!$fddklxjX?o^>NWLv|L z7Z)8!`6iisTs?2Yf5`Auo=+B#Ly>QH{8oNn({75TqY0n@3HW1W#;DQN94rS z8ZXGCjqbTvRtff0wB5KPW(eg&;S{tKJ^%R;3M~W!@-+Q)viZb9P_gcL1|2p+DKGR- zHWg{V&5}mvsf@WK7oMEd^D@+qX9j1F%T6oQu+ULGTGT5uvWZMeRxZGnG>202GB!Nf z`t8KZ`F~FSuBywyXyUr>Ykk-g2?VS_bbivwIk(g6`|}lvz6ywR6Ak81)L5rzD}Ky{ ziwSZ@nZ|FYS4k_646VIQHOM=sfg?=T_@48pU1Jl^FCAdxA-iQ1#Bn^8Y=}E+#HQ?# z?td&Lz5Chi7&alT6l)QS`;t{F%6{5qzkSN%4(jQ!)0u?FRFyRi(dd)4HDl%lfW!)b zHQiZ4E^8PpZLTv)TA~+Jm9mg}N zn3;p~bXwmR0SO@C>`j$iye55X{=pR~c-+fzFri5MD+Ux`5<{1O0I+DQHexC)%o=>O zJqt>(SbYk%|9S0G>oWq<5B0PQUNqA4tLxcg)`673?khNbspS;pd`leNREsVB6onmf z%ivWHWdUN=A_cRhltLd;&H?4veOnB-Uyy$(n3oGQCN|AcUPlSbNhji16~FkUak`%K zH?qGKgPb{W0A1WwVyT}(>n{EcEKlq92RG<>?HHTI>bdxWyC7y~XB)*UVqIcO{Z=n!m^ZH<83^%PznM zL<#ma>=27S#_o{Uf4XF$D*x&(Mz;`K5NJ;JYMDykccT}t2>i|fpR#V3B4V=QwPX-a z^ODVy1AI10@w~Y7{*TAUo-Ef}w9k}>Qn#;PDkj9m*NZ`|lopqZk#Kqe z2owf^!C+x{9T+6Wh?cqn35*RB_*VmnOteJ>3CxihVGJK_1O7!|G#URIinUyac%$;1qt9U&Szne^`&Pht(RB|xb)lY SxM2Rb0KCWS9Pj_PQ}{o;CmyK) literal 0 HcmV?d00001 diff --git a/client/src/assets/sprites/dave_sprites.png b/client/src/assets/sprites/dave_sprites.png index a0ed95c30f5de2c05ea8af0993d846b3465d2a38..6924874f3a63f5c36d846c19d510eb39ecb7f931 100644 GIT binary patch literal 18059 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 literal 22049 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 diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index 2b4edec..d538a0d 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -13,7 +13,7 @@ class Player { y = 0; - w = 72; + w = 68; h = 96; diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 9447902..7a6fd41 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -1,7 +1,12 @@ import '@styles/level'; +import jumpSound from '../../assets/sounds/jump.mp3'; +import landSound from '../../assets/sounds/land.mp3'; +import shotSound from '../../assets/sounds/shot.mp3'; +import bonus1Sound from '../../assets/sounds/bonus1.mp3'; import { - Rect, LevelEntity, LeftFeet, Door, DoorSize, LootSize, Loot, + Rect, LevelEntity, LeftFeet, Door, DoorSize, + LootSize, Loot, SoundType, AllSound, } from '../../types/game'; import Player from './dave'; import Zombie from './zombie'; @@ -53,6 +58,8 @@ class GameView { scoreElement: HTMLElement; + sounds: AllSound = {}; + constructor() { this.levelArea.classList.add('level-area'); this.levelArea.style.width = `${this.levelAreaW}px`; @@ -64,6 +71,10 @@ class GameView { this.scoreElement.classList.add('score'); this.viewArea.append(this.levelArea, this.scoreElement); document.querySelector('body')?.append(this.viewArea); + this.sounds[SoundType.JUMP] = new Audio(jumpSound); + this.sounds[SoundType.LAND] = new Audio(landSound); + this.sounds[SoundType.SHOT] = new Audio(shotSound); + this.sounds[SoundType.BONUS1] = new Audio(bonus1Sound); } loadLevelEntities(): void { diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index 890fd49..d992218 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -1,6 +1,6 @@ /* eslint-disable class-methods-use-this */ import { - Line, Offset, Position, Rect, + Line, Offset, Position, Rect, SoundType, } from '../../types/game'; import { DaveLook, DaveMove, DaveShoot, DaveState, @@ -104,6 +104,7 @@ class PlayLevel { } } if (wallUnder) { + this.gameView.sounds[SoundType.LAND].play(); dY = wallUnder.y - this.dave.h - this.dave.y; this.dave.state = this.dave.move === DaveMove.NONE ? DaveState.STANDING @@ -306,6 +307,7 @@ class PlayLevel { this.gameView.loot.forEach((loot) => { if (!loot.grabbed && this.isRectCrossWithRect(loot.area, this.dave)) { this.gameView.grabLoot(loot); + this.gameView.sounds[SoundType.BONUS1].play(); } }); } @@ -438,6 +440,7 @@ class PlayLevel { this.dave.state = DaveState.JUMPING_DOWN; } else { this.dave.state = DaveState.JUMPING_UP; + this.gameView.sounds[SoundType.JUMP].play(); } this.dave.velocity = this.dave.jumpStartVelocity; } @@ -451,6 +454,8 @@ class PlayLevel { || this.dave.state === DaveState.RECHARGING) { this.dave.state = DaveState.SHOOTING; this.daveShoot(); + this.gameView.sounds[SoundType.SHOT].currentTime = 0; + this.gameView.sounds[SoundType.SHOT].play(); setTimeout(() => { this.dave.state = DaveState.STUCK; setTimeout(() => { diff --git a/client/src/styles/playerAnimationKeyframes.scss b/client/src/styles/playerAnimationKeyframes.scss index 154842f..e361e24 100644 --- a/client/src/styles/playerAnimationKeyframes.scss +++ b/client/src/styles/playerAnimationKeyframes.scss @@ -1,78 +1,78 @@ @keyframes move-left { 0% { background-position: -644px 0; - width: 78px; + width: 72px; } 25% { - background-position: -714px 0; - width: 78px; + background-position: -718px 0; + width: 72px; } 50% { - background-position: -783px 0; - width: 78px; + background-position: -787px 0; + width: 72px; } 75% { - background-position: -854px 0; - width: 78px; + background-position: -857px 0; + width: 72px; } } @keyframes move-right { 0% { background-position: -69px 0; - width: 78px; + width: 72px; } 25% { - background-position: -144px 0; - width: 78px; + background-position: -146px 0; + width: 72px; } 50% { - background-position: -212px 0; - width: 78px; + background-position: -214px 0; + width: 72px; } 75% { - background-position: -282px 0; - width: 78px; + background-position: -284px 0; + width: 72px; } } @keyframes jump-left { 0% { background-position: -355px 0; - width: 78px; + width: 72px; } 25% { background-position: -432px 0; - width: 78px; + width: 72px; } 50% { background-position: -498px 0; - width: 78px; + width: 72px; } } @keyframes jump-right { 0% { background-position: -923px 0; - width: 78px; + width: 72px; } 25% { background-position: -996px 0; - width: 78px; + width: 72px; } 50% { background-position: -1067px 0; - width: 78px; + width: 72px; } } diff --git a/client/src/types/game.ts b/client/src/types/game.ts index 4bf2e08..9216135 100644 --- a/client/src/types/game.ts +++ b/client/src/types/game.ts @@ -58,3 +58,14 @@ export enum LootSize { W = 40, H = 36, } + +export enum SoundType { + JUMP, + SHOT, + LAND, + BONUS1, +} + +export type AllSound = { + [key: string]: HTMLAudioElement; +}; diff --git a/client/src/types/index.d.ts b/client/src/types/index.d.ts index ed4e496..de4c46a 100644 --- a/client/src/types/index.d.ts +++ b/client/src/types/index.d.ts @@ -6,3 +6,4 @@ declare module '*.svg'; declare module '*.ttf'; declare module '*.woff'; declare module '*.woff2'; +declare module '*.mp3'; diff --git a/client/webpack.config.js b/client/webpack.config.js index 47e24f7..52562e1 100644 --- a/client/webpack.config.js +++ b/client/webpack.config.js @@ -124,7 +124,7 @@ module.exports = async (env, argv) => { use: resolveStyleLoaders('sass-loader'), }, { - test: /\.(png|jpe?g|gif|svg|ttf|woff|woff2)$/i, + test: /\.(png|jpe?g|gif|svg|ttf|woff|woff2|mp3)$/i, dependency: { not: ['url'], }, @@ -132,7 +132,7 @@ module.exports = async (env, argv) => { { loader: 'url-loader', options: { - limit: 8192, + limit: 16000, name: '[path][name].[ext]', }, }, From 583c2d4189f30bdc94a4911c42844c339e600410 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 12 Feb 2023 23:17:37 +0300 Subject: [PATCH 079/196] feat: add createdAt field in user model --- server/src/models/scheme/user.schema.ts | 6 ++++++ server/src/types/interfaces/user.ts | 1 + 2 files changed, 7 insertions(+) diff --git a/server/src/models/scheme/user.schema.ts b/server/src/models/scheme/user.schema.ts index edae557..82df955 100644 --- a/server/src/models/scheme/user.schema.ts +++ b/server/src/models/scheme/user.schema.ts @@ -30,6 +30,12 @@ export class User extends Document implements IUser { isRequired: true, }) authProvider: AuthProvider; + + @Prop({ + type: Date, + default: Date.now, + }) + createdAt?: Date; } export const UserSchema = SchemaFactory.createForClass(User); diff --git a/server/src/types/interfaces/user.ts b/server/src/types/interfaces/user.ts index 133185b..41dca2e 100644 --- a/server/src/types/interfaces/user.ts +++ b/server/src/types/interfaces/user.ts @@ -5,4 +5,5 @@ export interface IUser { readonly username: string; readonly password?: string; readonly authProvider: AuthProvider; + readonly createdAt?: Date; } From 387e8dfad017bfd9756f6b71cdf95790382b8dfc Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 13 Feb 2023 01:03:56 +0300 Subject: [PATCH 080/196] feat: create JwtStrategy and JwtAuthGuard --- server/package-lock.json | 117 ++++++++++++++++++ server/package.json | 5 + server/src/guards/jwtAuth.guard.ts | 42 +++++++ server/src/main.ts | 2 + ...leware.ts => authValidation.middleware.ts} | 0 server/src/modules/app/app.controller.ts | 4 +- server/src/modules/app/app.module.ts | 7 +- server/src/modules/auth/auth.module.ts | 8 +- .../modules/auth/strategies/jwtStrategy.ts | 36 ++++++ server/src/modules/user/user.service.ts | 10 ++ 10 files changed, 227 insertions(+), 4 deletions(-) create mode 100644 server/src/guards/jwtAuth.guard.ts rename server/src/middlewares/{authValidationMiddleware.ts => authValidation.middleware.ts} (100%) create mode 100644 server/src/modules/auth/strategies/jwtStrategy.ts diff --git a/server/package-lock.json b/server/package-lock.json index cc9da76..64af101 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -14,8 +14,11 @@ "@nestjs/core": "^9.0.0", "@nestjs/jwt": "^10.0.2", "@nestjs/mongoose": "^9.2.1", + "@nestjs/passport": "^9.0.3", "@nestjs/platform-express": "^9.0.0", "bcrypt": "^5.1.0", + "cookie-parser": "^1.4.6", + "passport-jwt": "^4.0.1", "reflect-metadata": "^0.1.13", "rxjs": "^7.2.0", "uuid": "^9.0.0" @@ -25,9 +28,11 @@ "@nestjs/schematics": "^9.0.0", "@nestjs/testing": "^9.0.0", "@types/bcrypt": "^5.0.0", + "@types/cookie-parser": "^1.4.3", "@types/express": "^4.17.13", "@types/jest": "29.2.4", "@types/node": "18.11.18", + "@types/passport-jwt": "^3.0.8", "@types/supertest": "^2.0.11", "@types/uuid": "^9.0.0", "@typescript-eslint/eslint-plugin": "^5.0.0", @@ -44,6 +49,9 @@ "ts-node": "^10.0.0", "tsconfig-paths": "4.1.1", "typescript": "^4.7.4" + }, + "engines": { + "node": ">=18" } }, "node_modules/@ampproject/remapping": { @@ -2802,6 +2810,15 @@ "rxjs": "^7.0.0" } }, + "node_modules/@nestjs/passport": { + "version": "9.0.3", + "resolved": "https://registry.npmjs.org/@nestjs/passport/-/passport-9.0.3.tgz", + "integrity": "sha512-HplSJaimEAz1IOZEu+pdJHHJhQyBOPAYWXYHfAPQvRqWtw4FJF1VXl1Qtk9dcXQX1eKytDtH+qBzNQc19GWNEg==", + "peerDependencies": { + "@nestjs/common": "^8.0.0 || ^9.0.0", + "passport": "^0.4.0 || ^0.5.0 || ^0.6.0" + } + }, "node_modules/@nestjs/platform-express": { "version": "9.3.8", "resolved": "https://registry.npmjs.org/@nestjs/platform-express/-/platform-express-9.3.8.tgz", @@ -3139,6 +3156,15 @@ "@types/node": "*" } }, + "node_modules/@types/cookie-parser": { + "version": "1.4.3", + "resolved": "https://registry.npmjs.org/@types/cookie-parser/-/cookie-parser-1.4.3.tgz", + "integrity": "sha512-CqSKwFwefj4PzZ5n/iwad/bow2hTCh0FlNAeWLtQM3JA/NX/iYagIpWG2cf1bQKQ2c9gU2log5VUCrn7LDOs0w==", + "dev": true, + "dependencies": { + "@types/express": "*" + } + }, "node_modules/@types/cookiejar": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/@types/cookiejar/-/cookiejar-2.1.2.tgz", @@ -3268,6 +3294,36 @@ "integrity": "sha512-//oorEZjL6sbPcKUaCdIGlIUeH26mgzimjBB77G6XRgnDl/L5wOnpyBGRe/Mmf5CVW3PwEBE1NjiMZ/ssFh4wA==", "dev": true }, + "node_modules/@types/passport": { + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/@types/passport/-/passport-1.0.11.tgz", + "integrity": "sha512-pz1cx9ptZvozyGKKKIPLcVDVHwae4hrH5d6g5J+DkMRRjR3cVETb4jMabhXAUbg3Ov7T22nFHEgaK2jj+5CBpw==", + "dev": true, + "dependencies": { + "@types/express": "*" + } + }, + "node_modules/@types/passport-jwt": { + "version": "3.0.8", + "resolved": "https://registry.npmjs.org/@types/passport-jwt/-/passport-jwt-3.0.8.tgz", + "integrity": "sha512-VKJZDJUAHFhPHHYvxdqFcc5vlDht8Q2pL1/ePvKAgqRThDaCc84lSYOTQmnx3+JIkDlN+2KfhFhXIzlcVT+Pcw==", + "dev": true, + "dependencies": { + "@types/express": "*", + "@types/jsonwebtoken": "*", + "@types/passport-strategy": "*" + } + }, + "node_modules/@types/passport-strategy": { + "version": "0.2.35", + "resolved": "https://registry.npmjs.org/@types/passport-strategy/-/passport-strategy-0.2.35.tgz", + "integrity": "sha512-o5D19Jy2XPFoX2rKApykY15et3Apgax00RRLf0RUotPDUsYrQa7x4howLYr9El2mlUApHmCMv5CZ1IXqKFQ2+g==", + "dev": true, + "dependencies": { + "@types/express": "*", + "@types/passport": "*" + } + }, "node_modules/@types/prettier": { "version": "2.7.2", "resolved": "https://registry.npmjs.org/@types/prettier/-/prettier-2.7.2.tgz", @@ -4648,6 +4704,26 @@ "node": ">= 0.6" } }, + "node_modules/cookie-parser": { + "version": "1.4.6", + "resolved": "https://registry.npmjs.org/cookie-parser/-/cookie-parser-1.4.6.tgz", + "integrity": "sha512-z3IzaNjdwUC2olLIB5/ITd0/setiaFMLYiZJle7xg5Fe9KWAceil7xszYfHHBtDFYLSgJduS2Ty0P1uJdPDJeA==", + "dependencies": { + "cookie": "0.4.1", + "cookie-signature": "1.0.6" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/cookie-parser/node_modules/cookie": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.1.tgz", + "integrity": "sha512-ZwrFkGJxUR3EIoXtO+yVE69Eb7KlixbaeAWfBQB9vVsNn/o+Yw69gBWSSDK825hQNdN+wF8zELf3dFNl/kxkUA==", + "engines": { + "node": ">= 0.6" + } + }, "node_modules/cookie-signature": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", @@ -8207,6 +8283,41 @@ "node": ">= 0.8" } }, + "node_modules/passport": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/passport/-/passport-0.6.0.tgz", + "integrity": "sha512-0fe+p3ZnrWRW74fe8+SvCyf4a3Pb2/h7gFkQ8yTJpAO50gDzlfjZUZTO1k5Eg9kUct22OxHLqDZoKUWRHOh9ug==", + "peer": true, + "dependencies": { + "passport-strategy": "1.x.x", + "pause": "0.0.1", + "utils-merge": "^1.0.1" + }, + "engines": { + "node": ">= 0.4.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/jaredhanson" + } + }, + "node_modules/passport-jwt": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/passport-jwt/-/passport-jwt-4.0.1.tgz", + "integrity": "sha512-UCKMDYhNuGOBE9/9Ycuoyh7vP6jpeTp/+sfMJl7nLff/t6dps+iaeE0hhNkKN8/HZHcJ7lCdOyDxHdDoxoSvdQ==", + "dependencies": { + "jsonwebtoken": "^9.0.0", + "passport-strategy": "^1.0.0" + } + }, + "node_modules/passport-strategy": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/passport-strategy/-/passport-strategy-1.0.0.tgz", + "integrity": "sha512-CB97UUvDKJde2V0KDWWB3lyf6PC3FaZP7YxZ2G8OAtn9p4HI9j9JLP9qjOGZFvyl8uwNT8qM+hGnz/n16NI7oA==", + "engines": { + "node": ">= 0.4.0" + } + }, "node_modules/path-exists": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", @@ -8253,6 +8364,12 @@ "node": ">=8" } }, + "node_modules/pause": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/pause/-/pause-0.0.1.tgz", + "integrity": "sha512-KG8UEiEVkR3wGEb4m5yZkVCzigAD+cVEJck2CzYZO37ZGJfctvVptVO192MwrtPhzONn6go8ylnOdMhKqi4nfg==", + "peer": true + }, "node_modules/picocolors": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.0.0.tgz", diff --git a/server/package.json b/server/package.json index 596b5a2..50f43d5 100644 --- a/server/package.json +++ b/server/package.json @@ -25,8 +25,11 @@ "@nestjs/core": "^9.0.0", "@nestjs/jwt": "^10.0.2", "@nestjs/mongoose": "^9.2.1", + "@nestjs/passport": "^9.0.3", "@nestjs/platform-express": "^9.0.0", "bcrypt": "^5.1.0", + "cookie-parser": "^1.4.6", + "passport-jwt": "^4.0.1", "reflect-metadata": "^0.1.13", "rxjs": "^7.2.0", "uuid": "^9.0.0" @@ -36,9 +39,11 @@ "@nestjs/schematics": "^9.0.0", "@nestjs/testing": "^9.0.0", "@types/bcrypt": "^5.0.0", + "@types/cookie-parser": "^1.4.3", "@types/express": "^4.17.13", "@types/jest": "29.2.4", "@types/node": "18.11.18", + "@types/passport-jwt": "^3.0.8", "@types/supertest": "^2.0.11", "@types/uuid": "^9.0.0", "@typescript-eslint/eslint-plugin": "^5.0.0", diff --git a/server/src/guards/jwtAuth.guard.ts b/server/src/guards/jwtAuth.guard.ts new file mode 100644 index 0000000..d9689fd --- /dev/null +++ b/server/src/guards/jwtAuth.guard.ts @@ -0,0 +1,42 @@ +import { PassportStrategy } from '@nestjs/passport'; +import { Observable } from 'rxjs'; +import { + ExecutionContext, + Injectable, + UnauthorizedException, +} from '@nestjs/common'; +import { JwtStrategy } from '../modules/auth/strategies/jwtStrategy'; +import { Request } from 'express'; +import * as jwt from 'jsonwebtoken'; +import { UserJwtPayload } from '../types/interfaces/userJwtPayload'; +import * as process from 'process'; + +@Injectable() +export class JwtAuthGuard extends PassportStrategy(JwtStrategy) { + async canActivate( + context: ExecutionContext, + ): Promise | Observable> { + try { + await this.authenticate(context.switchToHttp().getRequest()); + + return true; + } catch (e: unknown) { + throw new UnauthorizedException(); + } + } + + async authenticate(req: Request): Promise { + const token = req.cookies?.auth_token; + + if (!token) { + throw new Error('Invalid token'); + } + + const payload = jwt.verify( + token, + process.env.JWT_SECRET || 'super-secret-key', + ) as UserJwtPayload; + + await this.validate(payload); + } +} diff --git a/server/src/main.ts b/server/src/main.ts index ea371bb..5f1c2e2 100644 --- a/server/src/main.ts +++ b/server/src/main.ts @@ -1,9 +1,11 @@ import { NestFactory } from '@nestjs/core'; import { AppModule } from './modules/app/app.module'; +import * as cookieParser from 'cookie-parser'; async function bootstrap(): Promise { const app = await NestFactory.create(AppModule); + app.use(cookieParser()); app.enableCors(); await app.listen(process.env.PORT || 3000); diff --git a/server/src/middlewares/authValidationMiddleware.ts b/server/src/middlewares/authValidation.middleware.ts similarity index 100% rename from server/src/middlewares/authValidationMiddleware.ts rename to server/src/middlewares/authValidation.middleware.ts diff --git a/server/src/modules/app/app.controller.ts b/server/src/modules/app/app.controller.ts index cce879e..d6c43da 100644 --- a/server/src/modules/app/app.controller.ts +++ b/server/src/modules/app/app.controller.ts @@ -1,11 +1,13 @@ -import { Controller, Get } from '@nestjs/common'; +import { Controller, Get, UseGuards } from '@nestjs/common'; import { AppService } from './app.service'; +import { JwtAuthGuard } from '../../guards/jwtAuth.guard'; @Controller() export class AppController { constructor(private readonly appService: AppService) {} @Get() + @UseGuards(JwtAuthGuard) getHello(): string { return this.appService.getHello(); } diff --git a/server/src/modules/app/app.module.ts b/server/src/modules/app/app.module.ts index 063cfc6..1eb5782 100644 --- a/server/src/modules/app/app.module.ts +++ b/server/src/modules/app/app.module.ts @@ -5,8 +5,10 @@ import { MongooseModule } from '@nestjs/mongoose'; import { ConfigModule } from '@nestjs/config'; import { UserModule } from '../user/user.module'; import { AuthModule } from '../auth/auth.module'; -import { AuthValidationMiddleware } from '../../middlewares/authValidationMiddleware'; +import { AuthValidationMiddleware } from '../../middlewares/authValidation.middleware'; import { AuthController } from '../auth/auth.controller'; +import { UserService } from '../user/user.service'; +import { User, UserSchema } from '../../models/scheme/user.schema'; @Module({ imports: [ @@ -21,11 +23,12 @@ import { AuthController } from '../auth/auth.controller'; useUnifiedTopology: true, }, ), + MongooseModule.forFeature([{ name: User.name, schema: UserSchema }]), UserModule, AuthModule, ], controllers: [AppController], - providers: [AppService], + providers: [AppService, UserService], }) export class AppModule { configure(consumer: MiddlewareConsumer): void { diff --git a/server/src/modules/auth/auth.module.ts b/server/src/modules/auth/auth.module.ts index c5c7555..bd16db9 100644 --- a/server/src/modules/auth/auth.module.ts +++ b/server/src/modules/auth/auth.module.ts @@ -1,14 +1,20 @@ import { Module } from '@nestjs/common'; import { AuthService } from './auth.service'; import { UserService } from '../user/user.service'; -import { JwtService } from '@nestjs/jwt'; +import { JwtModule, JwtService } from '@nestjs/jwt'; import { ConfigService } from '@nestjs/config'; import { MongooseModule } from '@nestjs/mongoose'; import { User, UserSchema } from '../../models/scheme/user.schema'; import { AuthController } from './auth.controller'; +import { PassportModule } from '@nestjs/passport'; @Module({ imports: [ + PassportModule, + JwtModule.register({ + secret: process.env.JWT_SECRET || 'super-secret-key', + signOptions: { expiresIn: process.env.JWT_EXPIRES_IN || '24h' }, + }), MongooseModule.forFeature([{ name: User.name, schema: UserSchema }]), ], providers: [AuthService, UserService, JwtService, ConfigService], diff --git a/server/src/modules/auth/strategies/jwtStrategy.ts b/server/src/modules/auth/strategies/jwtStrategy.ts new file mode 100644 index 0000000..e7a1d81 --- /dev/null +++ b/server/src/modules/auth/strategies/jwtStrategy.ts @@ -0,0 +1,36 @@ +import { Injectable, UnauthorizedException } from '@nestjs/common'; +import { ConfigService } from '@nestjs/config'; +import { UserService } from '../../user/user.service'; +import { UserJwtPayload } from '../../../types/interfaces/userJwtPayload'; +import { Strategy } from 'passport-jwt'; +import { IUser } from '../../../types/interfaces/user'; +import { PassportStrategy } from '@nestjs/passport'; +import { Request } from 'express'; + +@Injectable() +export class JwtStrategy extends PassportStrategy(Strategy) { + constructor( + private configService: ConfigService, + private readonly userService: UserService, + ) { + super({ + jwtFromRequest: (req: Request) => { + return req.cookies?.auth_token; + }, + secretOrKey: configService.get('JWT_SECRET') || 'super-secret-key', + }); + } + + async validate(payload: UserJwtPayload): Promise { + const targetUser = await this.userService.find(payload); + + if (!targetUser) { + throw new UnauthorizedException(); + } + + console.log(payload); + console.log(targetUser); + + return targetUser; + } +} diff --git a/server/src/modules/user/user.service.ts b/server/src/modules/user/user.service.ts index 966b267..fb284bb 100644 --- a/server/src/modules/user/user.service.ts +++ b/server/src/modules/user/user.service.ts @@ -15,6 +15,16 @@ export class UserService { @InjectModel(User.name) private readonly userModel: Model, ) {} + async find(filter: object): Promise { + const result = await this.userModel.findOne(filter).exec(); + + if (!result) { + throw new UserNotFoundError(filter); + } + + return result; + } + async findAll(page: number, limit: number): Promise { const startIndex = (page - 1) * (limit <= 100 ? limit : 100); return this.userModel.find({}).skip(startIndex).limit(limit).exec(); From f7abd7ba78c6cbe9618781806be2fa4018224219 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 13 Feb 2023 02:05:09 +0300 Subject: [PATCH 081/196] fix: fix auth controller HTTP exceptions --- server/src/modules/auth/auth.controller.ts | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index 1591a84..a6c82d0 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -1,6 +1,7 @@ import { BadRequestException, Body, + ConflictException, Controller, HttpStatus, Post, @@ -16,6 +17,7 @@ import { } from '../../types/dto/user/authUserDto'; import { AuthProvider } from '../../types/enums/authProviders'; import { Response } from 'express'; +import { UserAlreadyExists } from '../../errors/userAlreadyExists'; @Controller('auth') export class AuthController { @@ -44,6 +46,10 @@ export class AuthController { return registeredUser; } } catch (e: unknown) { + if (e instanceof UserAlreadyExists) { + throw new ConflictException(e.message); + } + if (e instanceof Error) { throw new BadRequestException(e.message); } From 9b12768bc524410e5516ee7abea7cea8c9bcf973 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Mon, 13 Feb 2023 23:18:47 +0300 Subject: [PATCH 082/196] feat: add dave bullet count recharge --- client/src/assets/sounds/empty.mp3 | Bin 0 -> 4749 bytes client/src/assets/sprites/ammo.png | Bin 0 -> 1188 bytes client/src/assets/sprites/dave_sprites.png | Bin 18059 -> 18663 bytes client/src/assets/sprites/knife.png | Bin 0 -> 1012 bytes client/src/scripts/components/dave.ts | 6 + client/src/scripts/components/game.ts | 18 +- client/src/scripts/controllers/playLevel.ts | 173 ++++++++++++++------ client/src/styles/level.css | 47 +++++- client/src/styles/playerAnimation.scss | 2 +- client/src/types/game.ts | 2 + 10 files changed, 193 insertions(+), 55 deletions(-) create mode 100644 client/src/assets/sounds/empty.mp3 create mode 100644 client/src/assets/sprites/ammo.png create mode 100644 client/src/assets/sprites/knife.png diff --git a/client/src/assets/sounds/empty.mp3 b/client/src/assets/sounds/empty.mp3 new file mode 100644 index 0000000000000000000000000000000000000000..1d958f07fc06c71aa642778c3ced8903b02df56e GIT binary patch literal 4749 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 DYnkMk literal 0 HcmV?d00001 diff --git a/client/src/assets/sprites/ammo.png b/client/src/assets/sprites/ammo.png new file mode 100644 index 0000000000000000000000000000000000000000..483386befa461204ed44d561c6b6c5229738852c GIT binary patch literal 1188 zcmah|OK1~87+&#G3tEcc^Wd;ms%Unzd2Gzuq@>xz2HaYcKr0Hm-JLc|-JNxJVzxoW z7pMmdqWC~XK`$bx;6Z#qRrF911Qm;3d>&LPdXS=3sk3PkJs2H+n15!z@B9Dx=b!zZ z9V@5T&#R{>YI>?&Op{rps41XsD)EFDiySh|#ffg5LA|&jTab#Ws0V_SF89GSl+}UF z!?1;-rqWur8+S{q1O@4g>|z*4Hwl}fT3Q`bR{9|ZJ+MzRBJ`&lLp0FT2;CKwypkD* zIjy~D!A!9us}%c{uu8W^L5m|00Ucr)IQk~T7MuuO(iMpBZnHEfL2!SBo=mD+>I89Q zK@ep89>vRXfae)55afAo8Sr^IAL}K?d$@oQ{lm|_sS!%D47L(;zWEG)v7@Gpi z777KX;AfE4$8zCt*wyg)JOtsf2MjDb9>Z>`D2UKjEX~9kGJvZn_nt3k>l%#({b-jwVaT@;4_picscEE&e8rmptDdgdLo7_;Q5VxR= zk(EVgQ>BWXIfRj&Lner4c(AxjGgMTtmz405B%}-*%Z36|VuU6NjHanVIJlf^i}{nW zworoO5@IaCCzG+|BJcGF1EEl&!WEH{*P($cT(!y#cx!UqR?tlnS%j9h1*%C4>7aCF zL93mMSW~aeRcq$rPt@eHBpKFy*gqb+vPHVbb*pVl7S+aw2I+Q-v~|8UrIIhv(77s` z_~DM|z0w~U%23Co^@oZ7GbP5d&hycyAM1C6IXl*b3KJtY6LquVSAHe`OI6}{xW#(%lLtlBNrgk^*w*>>gd>kCs&WI@4q-S`o4Yc#K^9aRigfBI0(PuRt5Bct|YZn!d-t_(EinkGcWn6J*|@kcdZ&5oq&o; i@ju6FOXT?Y+oiXtZ~n(SbsRq97A2MF5HGfE-1Q4K=A6s` literal 0 HcmV?d00001 diff --git a/client/src/assets/sprites/dave_sprites.png b/client/src/assets/sprites/dave_sprites.png index 6924874f3a63f5c36d846c19d510eb39ecb7f931..b8ae47971c273bafee1f4a13b1106549acc1d2fa 100644 GIT binary patch literal 18663 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 K=d#Wzp$Py~c-Q&> literal 18059 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 diff --git a/client/src/assets/sprites/knife.png b/client/src/assets/sprites/knife.png new file mode 100644 index 0000000000000000000000000000000000000000..47a030823fed7251bbb876a837df58a75f299b50 GIT binary patch literal 1012 zcmaJ=F>ljA6n0gRs-iAkNKuB9+W`cz^k6D9>qu;$>MnVE+9`=f97U|FDgo0?>oCRT)*ibJ{>)qHCYH?id$KKP2)8D^SwTW#7l zwq=|6oRwj?)DMBpFzXv>XxSd7sEha9Kw*D>_{1XDQP`cbQ8Ypo_uQ?1gw1}vW%oT> za@dXAXg!rdz{k`=slOk@a;mTcT^a1m&9i6#p`OB?CDk?>NF@7vT{L!iroL<x~d9-u2t5mnj}aSCUbI<&*x!=0bfo}PiOOQ z-+(nkn{^Ym*@)vNKnqJr5RXdOW0wOO!uK)l5 literal 0 HcmV?d00001 diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index d538a0d..35d3e4f 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -39,6 +39,10 @@ class Player { deathLayer: HTMLElement; + bullets = 8; + + bulletsMax = 8; + constructor(leftFeet: LeftFeet) { this.sprite.classList.add('player'); this.x = leftFeet.x; @@ -111,6 +115,8 @@ class Player { : Direction.RIGHT, ); } + } else if (this.state === DaveState.RECHARGING) { + this.animation.reload(); } } diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 7a6fd41..2a680de 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -3,6 +3,8 @@ import jumpSound from '../../assets/sounds/jump.mp3'; import landSound from '../../assets/sounds/land.mp3'; import shotSound from '../../assets/sounds/shot.mp3'; import bonus1Sound from '../../assets/sounds/bonus1.mp3'; +import emptySound from '../../assets/sounds/empty.mp3'; +import reloadSound from '../../assets/sounds/reload.mp3'; import { Rect, LevelEntity, LeftFeet, Door, DoorSize, @@ -60,6 +62,8 @@ class GameView { sounds: AllSound = {}; + ammoElement: HTMLElement; + constructor() { this.levelArea.classList.add('level-area'); this.levelArea.style.width = `${this.levelAreaW}px`; @@ -69,12 +73,16 @@ class GameView { this.viewArea.style.height = `${this.viewAreaH}px`; this.scoreElement = document.createElement('div'); this.scoreElement.classList.add('score'); - this.viewArea.append(this.levelArea, this.scoreElement); + this.ammoElement = document.createElement('div'); + this.ammoElement.classList.add('ammo'); + this.viewArea.append(this.levelArea, this.scoreElement, this.ammoElement); document.querySelector('body')?.append(this.viewArea); this.sounds[SoundType.JUMP] = new Audio(jumpSound); this.sounds[SoundType.LAND] = new Audio(landSound); this.sounds[SoundType.SHOT] = new Audio(shotSound); this.sounds[SoundType.BONUS1] = new Audio(bonus1Sound); + this.sounds[SoundType.EMPTY] = new Audio(emptySound); + this.sounds[SoundType.RELOAD] = new Audio(reloadSound); } loadLevelEntities(): void { @@ -94,6 +102,7 @@ class GameView { this.loadDoors(LevelEntity.DOOR4); this.dave = new Player(this.loadCharacters(LevelEntity.DAVE)[0]); this.insertPlayer(); + this.showAmmo(); this.correctLevelPosition(); this.levelArea.classList.add('level1'); this.updateScoreOnScreen(); @@ -313,6 +322,13 @@ class GameView { gameOver.classList.add('game-over'); this.viewArea.append(gameOver); } + + showAmmo(): void { + for (let i = 0; i <= 8; i += 1) { + this.ammoElement.classList.remove(`ammo${i}`); + } + this.ammoElement.classList.add(`ammo${this.dave.bullets}`); + } } export default GameView; diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index d992218..9b6d914 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -22,6 +22,12 @@ class PlayLevel { daveAnimationTimer: number; + reloadAnimationTimer: number | undefined; + + reloadStartTimer: number | undefined; + + shootTimer: number | undefined; + constructor() { this.gameView = new GameView(); } @@ -223,7 +229,9 @@ class PlayLevel { const elapsed: number = now - then; if (elapsed > fpsInterval) { then = now - (elapsed % fpsInterval); - if (this.dave.state !== DaveState.STANDING) { + if (this.dave.state !== DaveState.STANDING + && this.dave.state !== DaveState.RECHARGING) { + this.resetReloadAnimation(); let dX = 0; let dY = 0; if (this.dave.state === DaveState.RUNNING) { @@ -250,6 +258,19 @@ class PlayLevel { this.gameView.correctLevelPosition(); } else if (this.isDaveHasToFall()) { this.dave.state = DaveState.FALLING; + } else if (this.dave.state === DaveState.STANDING) { + if (!this.reloadStartTimer + && this.dave.bullets < this.dave.bulletsMax) { + this.reloadStart(); + } + if (this.dave.bullets === this.dave.bulletsMax) { + this.resetReloadAnimation(); + } + } else if (this.dave.state === DaveState.RECHARGING) { + if (this.dave.bullets === this.dave.bulletsMax) { + this.dave.state = DaveState.STANDING; + this.resetReloadAnimation(); + } } this.dave.setView(); this.moveBullets(); @@ -391,7 +412,8 @@ class PlayLevel { if (e.altKey) { e.preventDefault(); } - if (this.dave.state === DaveState.STANDING) { + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.RECHARGING) { this.dave.state = DaveState.RUNNING; } if (this.dave.state !== DaveState.SHOOTING @@ -404,7 +426,8 @@ class PlayLevel { if (e.altKey) { e.preventDefault(); } - if (this.dave.state === DaveState.STANDING) { + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.RECHARGING) { this.dave.state = DaveState.RUNNING; } if (this.dave.state !== DaveState.SHOOTING @@ -414,7 +437,8 @@ class PlayLevel { } break; case 'ArrowUp': - if (this.dave.state === DaveState.STANDING) { + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.RECHARGING) { let foundDoor = false; this.gameView.doors.forEach((door) => { if (!door.opened @@ -429,13 +453,15 @@ class PlayLevel { } break; case 'ArrowDown': - if (this.dave.state === DaveState.STANDING) { + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.RECHARGING) { this.dave.shoot = DaveShoot.DOWN; } break; case 'Space': if (this.dave.state === DaveState.RUNNING - || this.dave.state === DaveState.STANDING) { + || this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.RECHARGING) { if (this.dave.shoot === DaveShoot.DOWN) { this.dave.state = DaveState.JUMPING_DOWN; } else { @@ -451,17 +477,11 @@ class PlayLevel { } if (this.dave.state === DaveState.STANDING || this.dave.state === DaveState.RUNNING - || this.dave.state === DaveState.RECHARGING) { + || this.dave.state === DaveState.RECHARGING + || this.dave.state === DaveState.SHOOTING + ) { this.dave.state = DaveState.SHOOTING; this.daveShoot(); - this.gameView.sounds[SoundType.SHOT].currentTime = 0; - this.gameView.sounds[SoundType.SHOT].play(); - setTimeout(() => { - this.dave.state = DaveState.STUCK; - setTimeout(() => { - this.dave.state = DaveState.STANDING; - }, 200); - }, 50); } break; case 'KeyG': @@ -650,47 +670,65 @@ class PlayLevel { } daveShoot(): void { - const fromX: number = this.dave.x + this.dave.w / 2; - const fromY: number = this.dave.y + this.dave.h / 2 - - this.dave.shootOffsetY; - const [dX, dY] = this.calcEndOfLineShoot(); - let closestWall: Rect | undefined; - this.gameView.walls.forEach((wall) => { - if (this.isLineCrossRect({ - x1: fromX, - y1: fromY, - x2: fromX + dX, - y2: fromY + dY, - }, wall)) { - if (!closestWall || this.isOneRectCloserAnother(wall, closestWall)) { - closestWall = wall; + if (this.dave.bullets > 0) { + this.dave.bullets -= 1; + this.gameView.showAmmo(); + this.gameView.sounds[SoundType.SHOT].currentTime = 0; + this.gameView.sounds[SoundType.SHOT].play(); + const fromX: number = this.dave.x + this.dave.w / 2; + const fromY: number = this.dave.y + this.dave.h / 2 + - this.dave.shootOffsetY; + const [dX, dY] = this.calcEndOfLineShoot(); + let closestWall: Rect | undefined; + this.gameView.walls.forEach((wall) => { + if (this.isLineCrossRect({ + x1: fromX, + y1: fromY, + x2: fromX + dX, + y2: fromY + dY, + }, wall)) { + if (!closestWall || this.isOneRectCloserAnother(wall, closestWall)) { + closestWall = wall; + } } - } - }); - let closestMonster: Monster | undefined; - this.gameView.monsters.forEach((monster) => { - if (this.isLineCrossRect({ - x1: fromX, - y1: fromY, - x2: fromX + dX, - y2: fromY + dY, - }, monster)) { - if (!closestMonster - || this.isOneRectCloserAnother(monster, closestMonster)) { - closestMonster = monster; + }); + let closestMonster: Monster | undefined; + this.gameView.monsters.forEach((monster) => { + if (this.isLineCrossRect({ + x1: fromX, + y1: fromY, + x2: fromX + dX, + y2: fromY + dY, + }, monster)) { + if (!closestMonster + || this.isOneRectCloserAnother(monster, closestMonster)) { + closestMonster = monster; + } + } + }); + if ((closestMonster && !closestWall) + || (closestMonster + && closestWall + && this.isOneRectCloserAnother(closestMonster, closestWall)) + ) { + closestMonster.getAttacked(); + if (closestMonster.health === 0) { + this.gameView.removeMonster(closestMonster); } } - }); - if ((closestMonster && !closestWall) - || (closestMonster - && closestWall - && this.isOneRectCloserAnother(closestMonster, closestWall)) - ) { - closestMonster.getAttacked(); - if (closestMonster.health === 0) { - this.gameView.removeMonster(closestMonster); - } + } else { + this.gameView.sounds[SoundType.EMPTY].currentTime = 0; + this.gameView.sounds[SoundType.EMPTY].play(); } + setTimeout(() => { + this.dave.state = DaveState.STUCK; + if (!this.shootTimer) { + this.shootTimer = window.setTimeout(() => { + this.dave.state = DaveState.STANDING; + this.shootTimer = undefined; + }, 200); + } + }, 50); } isOneRectCloserAnother(wall: Rect, monster: Rect): boolean { @@ -780,6 +818,7 @@ class PlayLevel { stopGame(): void { clearInterval(this.monsterAnimationTimer); cancelAnimationFrame(this.daveAnimationTimer); + this.resetReloadAnimation(); } restartLevel(): void { @@ -794,6 +833,36 @@ class PlayLevel { this.gameView.gameOver(); } } + + reloadStart(): void { + this.reloadStartTimer = window.setTimeout(() => { + this.reloadBullets(); + this.dave.state = DaveState.RECHARGING; + }, 500); + } + + reloadBullets(): void { + this.reloadAnimationTimer = window.setInterval(() => { + this.plusBullet(); + }, 700); + } + + plusBullet(): void { + this.dave.bullets += 1; + this.gameView.showAmmo(); + this.gameView.sounds[SoundType.RELOAD].play(); + } + + resetReloadAnimation(): void { + if (this.reloadAnimationTimer) { + clearInterval(this.reloadAnimationTimer); + this.reloadAnimationTimer = undefined; + } + if (this.reloadStartTimer) { + clearTimeout(this.reloadStartTimer); + this.reloadStartTimer = undefined; + } + } } export default PlayLevel; diff --git a/client/src/styles/level.css b/client/src/styles/level.css index c1809bf..f009675 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -65,7 +65,7 @@ body { .score { font-family: 'Perfect DOS VGA 437', sans-serif; position: absolute; - top: 10px; + top: 52px; left: 10px; color: #C62828; font-size: 18px; @@ -80,3 +80,48 @@ body { left: 251px; background: url("./../assets/levels/gameover.png") no-repeat no-repeat; } + +.ammo { + position: absolute; + top: 10px; + left: 10px; + width: 68px; + height: 32px; + background: url("./../assets/sprites/ammo.png") no-repeat no-repeat; +} + +.ammo0 { + background-position-y: 0; +} + +.ammo1 { + background-position-y: -32px; +} + +.ammo2 { + background-position-y: -64px; +} + +.ammo3 { + background-position-y: -96px; +} + +.ammo4 { + background-position-y: -128px; +} + +.ammo5 { + background-position-y: -160px; +} + +.ammo6 { + background-position-y: -192px; +} + +.ammo7 { + background-position-y: -224px; +} + +.ammo8 { + background-position-y: -256px; +} \ No newline at end of file diff --git a/client/src/styles/playerAnimation.scss b/client/src/styles/playerAnimation.scss index b7042cc..19b21ac 100644 --- a/client/src/styles/playerAnimation.scss +++ b/client/src/styles/playerAnimation.scss @@ -144,7 +144,7 @@ $bg-size: 5257px; &-reload { background: url("../assets/sprites/dave_sprites.png"); - animation: reload 0.5s ease-in-out infinite; + animation: reload 0.7s ease-in-out infinite; background-size: $bg-size; animation-timing-function: steps(1); } diff --git a/client/src/types/game.ts b/client/src/types/game.ts index 9216135..a40edfe 100644 --- a/client/src/types/game.ts +++ b/client/src/types/game.ts @@ -64,6 +64,8 @@ export enum SoundType { SHOT, LAND, BONUS1, + EMPTY, + RELOAD, } export type AllSound = { From 1f7efc73565bbe5a16befe76e73e3249fe7b4e46 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Mon, 13 Feb 2023 23:51:27 +0300 Subject: [PATCH 083/196] feat: add UI for zombie animation state --- client/src/types/interfaces/zombieAnimator.ts | 6 ++++++ 1 file changed, 6 insertions(+) create mode 100644 client/src/types/interfaces/zombieAnimator.ts diff --git a/client/src/types/interfaces/zombieAnimator.ts b/client/src/types/interfaces/zombieAnimator.ts new file mode 100644 index 0000000..c362ec7 --- /dev/null +++ b/client/src/types/interfaces/zombieAnimator.ts @@ -0,0 +1,6 @@ +import Direction from '../enums/directions'; + +export interface IZombieAnimator { + move(direction: Direction): void + attack(direction: Direction): void +} From f8ab29b2a0bf9cc3723b0ff8cd575fff47b3a286 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Mon, 13 Feb 2023 23:53:07 +0300 Subject: [PATCH 084/196] feat: add animation styles for zombies --- client/src/assets/sprites/zombie_sprite.png | Bin 0 -> 17052 bytes client/src/styles/zombieAnimation.scss | 40 ++++++++++ .../src/styles/zombieAnimationKeyframes.scss | 73 ++++++++++++++++++ 3 files changed, 113 insertions(+) create mode 100644 client/src/assets/sprites/zombie_sprite.png create mode 100644 client/src/styles/zombieAnimation.scss create mode 100644 client/src/styles/zombieAnimationKeyframes.scss diff --git a/client/src/assets/sprites/zombie_sprite.png b/client/src/assets/sprites/zombie_sprite.png new file mode 100644 index 0000000000000000000000000000000000000000..2c6ac406bcee2f638542e8ba023e7dc1cd73adc6 GIT binary patch literal 17052 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 literal 0 HcmV?d00001 diff --git a/client/src/styles/zombieAnimation.scss b/client/src/styles/zombieAnimation.scss new file mode 100644 index 0000000..b02b866 --- /dev/null +++ b/client/src/styles/zombieAnimation.scss @@ -0,0 +1,40 @@ +@import "zombieAnimationKeyframes"; + +.zombie { + &-animate { + background: url("../assets/sprites/zombie_sprite.png"); + animation-timing-function: steps(1); + + &-move-left { + background: url("../assets/sprites/zombie_sprite.png"); + animation: move-left-zombie 1s ease-in-out infinite; + animation-timing-function: steps(1); + } + + &-move-right { + background: url("../assets/sprites/zombie_sprite.png"); + animation: move-right-zombie 1s ease-in-out infinite; + animation-timing-function: steps(1); + } + + &-move-down { + background: url("../assets/sprites/zombie_sprite.png"); + animation: move-down-zombie 1s ease-in-out infinite; + animation-timing-function: steps(1); + } + + &-attack { + &-left { + background: url("../assets/sprites/zombie_sprite.png"); + animation: attack-left-zombie 1s ease-in-out infinite; + animation-timing-function: steps(1); + } + + &-right { + background: url("../assets/sprites/zombie_sprite.png"); + animation: attack-right-zombie 1s ease-in-out infinite; + animation-timing-function: steps(1); + } + } + } +} diff --git a/client/src/styles/zombieAnimationKeyframes.scss b/client/src/styles/zombieAnimationKeyframes.scss new file mode 100644 index 0000000..326d486 --- /dev/null +++ b/client/src/styles/zombieAnimationKeyframes.scss @@ -0,0 +1,73 @@ +@keyframes move-left-zombie { + 0% { + background-position: -630px 0; + } + + 25% { + background-position: -710px 0; + } + + 50% { + background-position: -797px 0; + } + + 75% { + background-position: -880px 0; + } +} + +@keyframes move-right-zombie { + 0% { + background-position: 0 0; + } + + 25% { + background-position: -87px 0; + } + + 50% { + background-position: -170px 0; + } + + 75% { + background-position: -258px 0; + } +} + +@keyframes move-down-zombie { + 0% { + background-position: -1260px 0; + } + + 50% { + background-position: -1356px 0; + } +} + +@keyframes attack-right-zombie { + 0% { + background-position: -1807px 0; + } + + 25% { + background-position: -1903px 0; + } + + 50% { + background-position: -1998px 0; + } +} + +@keyframes attack-left-zombie { + 0% { + background-position: -2438px 0; + } + + 25% { + background-position: -2534px 0; + } + + 50% { + background-position: -2630px 0; + } +} From b2da805fee1f065f0278e63a1ba0a5fc644eb5dd Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Mon, 13 Feb 2023 23:54:21 +0300 Subject: [PATCH 085/196] feat: add a controller to select the desire animation for zombies --- .../src/scripts/controllers/zombieAnimator.ts | 32 +++++++++++++++++++ 1 file changed, 32 insertions(+) create mode 100644 client/src/scripts/controllers/zombieAnimator.ts diff --git a/client/src/scripts/controllers/zombieAnimator.ts b/client/src/scripts/controllers/zombieAnimator.ts new file mode 100644 index 0000000..846b19c --- /dev/null +++ b/client/src/scripts/controllers/zombieAnimator.ts @@ -0,0 +1,32 @@ +import Direction from '../../types/enums/directions'; +import { IZombieAnimator } from '../../types/interfaces/zombieAnimator'; + +class ZombieAnimator implements IZombieAnimator { + constructor(private readonly zombieBlock: HTMLElement) { + + } + + move(direction: Direction): void { + const classes = this.zombieBlock.classList.toString() + .replace(/zombie-[^\s]+/g, '') + .trim(); + this.zombieBlock.removeAttribute('class'); + this.zombieBlock.setAttribute( + 'class', + `${classes} zombie-animate-move-${direction}`.trim(), + ); + } + + attack(direction: Direction): void { + const classes = this.zombieBlock.classList.toString() + .replace(/zombie-[^\s]+/g, '') + .trim(); + this.zombieBlock.removeAttribute('class'); + this.zombieBlock.setAttribute( + 'class', + `${classes} zombie-animate-attack-${direction}`.trim(), + ); + } +} + +export default ZombieAnimator; From abd976f555fba6b33b13298587635dd2c33a828c Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Mon, 13 Feb 2023 23:56:18 +0300 Subject: [PATCH 086/196] feat: add zombie animation styles --- client/src/styles/zombie.css | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/client/src/styles/zombie.css b/client/src/styles/zombie.css index 3ddc028..ff3b3b9 100644 --- a/client/src/styles/zombie.css +++ b/client/src/styles/zombie.css @@ -1,8 +1,10 @@ +@import "zombieAnimation"; + .zombie { position: absolute; top: 0; left: 0; - background-color: burlywood; + background-image: url("../assets/sprites/zombie_sprite.png"); z-index: 10; } @@ -14,6 +16,6 @@ position: absolute; top: 0; left: 0; - background-color:blueviolet; + background-color: blueviolet; z-index: 10; } From 6f31523cc0c1fd633c51cb1e3e11b5645c109fba Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Mon, 13 Feb 2023 23:56:37 +0300 Subject: [PATCH 087/196] feat: add zombie animation styles --- client/src/styles/main.scss | 2 ++ 1 file changed, 2 insertions(+) diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index 16a43f3..3715f24 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -1,4 +1,6 @@ @import "playerAnimation"; +@import "zombieAnimation"; +@import "croneAnimation"; * { margin: 0; From 27c57e93a8ae2606e824318967590cb88c6f6e2f Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Mon, 13 Feb 2023 23:58:49 +0300 Subject: [PATCH 088/196] feat: add crone animation styles --- client/src/assets/sprites/crone_sprite.png | Bin 0 -> 10216 bytes client/src/styles/crone.css | 4 +- client/src/styles/croneAnimation.scss | 34 ++++++++++ .../src/styles/croneAnimationKeyframes.scss | 63 ++++++++++++++++++ 4 files changed, 99 insertions(+), 2 deletions(-) create mode 100644 client/src/assets/sprites/crone_sprite.png create mode 100644 client/src/styles/croneAnimation.scss create mode 100644 client/src/styles/croneAnimationKeyframes.scss diff --git a/client/src/assets/sprites/crone_sprite.png b/client/src/assets/sprites/crone_sprite.png new file mode 100644 index 0000000000000000000000000000000000000000..29dba1028edc21cef858467f71cde660ece93a05 GIT binary patch literal 10216 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 EAG=x{b^rhX literal 0 HcmV?d00001 diff --git a/client/src/styles/crone.css b/client/src/styles/crone.css index 7445f1a..9b81aea 100644 --- a/client/src/styles/crone.css +++ b/client/src/styles/crone.css @@ -2,7 +2,7 @@ position: absolute; top: 0; left: 0; - background-color:cadetblue; + background-image: url("../assets/sprites/crone_sprite.png"); z-index: 10; } @@ -14,6 +14,6 @@ position: absolute; top: 0; left: 0; - background-color:blue; + background-color: blue; z-index: 10; } diff --git a/client/src/styles/croneAnimation.scss b/client/src/styles/croneAnimation.scss new file mode 100644 index 0000000..30a1e90 --- /dev/null +++ b/client/src/styles/croneAnimation.scss @@ -0,0 +1,34 @@ +@import "croneAnimationKeyframes"; + +.crone { + &-animate { + background: url("../assets/sprites/crone_sprite.png"); + animation-timing-function: steps(1); + + &-move-left { + background: url("../assets/sprites/crone_sprite.png"); + animation: move-left-crone 0.8s ease-in-out infinite; + animation-timing-function: steps(1); + } + + &-move-right { + background: url("../assets/sprites/crone_sprite.png"); + animation: move-right-crone 0.8s ease-in-out infinite; + animation-timing-function: steps(1); + } + + &-attack { + &-left { + background: url("../assets/sprites/crone_sprite.png"); + animation: attack-left-crone 0.8s ease-in-out infinite; + animation-timing-function: steps(1); + } + + &-right { + background: url("../assets/sprites/crone_sprite.png"); + animation: attack-right-crone 0.8s ease-in-out infinite; + animation-timing-function: steps(1); + } + } + } +} diff --git a/client/src/styles/croneAnimationKeyframes.scss b/client/src/styles/croneAnimationKeyframes.scss new file mode 100644 index 0000000..b63313a --- /dev/null +++ b/client/src/styles/croneAnimationKeyframes.scss @@ -0,0 +1,63 @@ +@keyframes move-left-crone { + 0% { + background-position: -331px 0; + } + + 25% { + background-position: -412px 0; + } + + 50% { + background-position: -497px 0; + } + + 75% { + background-position: -572px 0; + } +} + +@keyframes move-right-crone { + 0% { + background-position: 0 0; + } + + 25% { + background-position: -87px 0; + } + + 50% { + background-position: -170px 0; + } + + 75% { + background-position: -258px 0; + } +} + +@keyframes attack-right-crone { + 0% { + background-position: -653px 0; + } + + 25% { + background-position: -728px 0; + } + + 50% { + background-position: -799px 0; + } +} + +@keyframes attack-left-crone { + 0% { + background-position: -865px 0; + } + + 25% { + background-position: -934px 0; + } + + 50% { + background-position: -999px 0; + } +} From 1a0d076df11e93d8116c5405d15bb5ed8c54dcb6 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Tue, 14 Feb 2023 00:00:17 +0300 Subject: [PATCH 089/196] feat: add an interface for select the state of the animation for crone --- client/src/types/interfaces/croneAnimator.ts | 6 ++++++ 1 file changed, 6 insertions(+) create mode 100644 client/src/types/interfaces/croneAnimator.ts diff --git a/client/src/types/interfaces/croneAnimator.ts b/client/src/types/interfaces/croneAnimator.ts new file mode 100644 index 0000000..4f64a49 --- /dev/null +++ b/client/src/types/interfaces/croneAnimator.ts @@ -0,0 +1,6 @@ +import Direction from '../enums/directions'; + +export interface ICroneAnimator { + move(direction: Direction): void + attack(direction: Direction): void +} From 6795211457e135f8b14b5610e5fb46e378f4d26c Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Tue, 14 Feb 2023 00:01:11 +0300 Subject: [PATCH 090/196] feat: add a controller to select the state of the animation --- .../src/scripts/controllers/croneAnimator.ts | 32 +++++++++++++++++++ 1 file changed, 32 insertions(+) create mode 100644 client/src/scripts/controllers/croneAnimator.ts diff --git a/client/src/scripts/controllers/croneAnimator.ts b/client/src/scripts/controllers/croneAnimator.ts new file mode 100644 index 0000000..60a6ea1 --- /dev/null +++ b/client/src/scripts/controllers/croneAnimator.ts @@ -0,0 +1,32 @@ +import Direction from '../../types/enums/directions'; +import { ICroneAnimator } from '../../types/interfaces/croneAnimator'; + +class CroneAnimator implements ICroneAnimator { + constructor(private readonly croneBlock: HTMLElement) { + + } + + move(direction: Direction): void { + const classes = this.croneBlock.classList.toString() + .replace(/crone-[^\s]+/g, '') + .trim(); + this.croneBlock.removeAttribute('class'); + this.croneBlock.setAttribute( + 'class', + `${classes} crone-animate-move-${direction}`.trim(), + ); + } + + attack(direction: Direction): void { + const classes = this.croneBlock.classList.toString() + .replace(/crone-[^\s]+/g, '') + .trim(); + this.croneBlock.removeAttribute('class'); + this.croneBlock.setAttribute( + 'class', + `${classes} crone-animate-attack-${direction}`.trim(), + ); + } +} + +export default CroneAnimator; From 44a37ce237c5657573b43aec8a03fe7967607e44 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Tue, 14 Feb 2023 00:53:29 +0300 Subject: [PATCH 091/196] refactor: modify setListener from PlayLevel --- client/src/scripts/controllers/playLevel.ts | 365 +++++++++++--------- 1 file changed, 199 insertions(+), 166 deletions(-) diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index 9b6d914..0752e14 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -405,110 +405,135 @@ class PlayLevel { return false; } + tryRun(): void { + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.RECHARGING) { + this.dave.state = DaveState.RUNNING; + } + } + + tryMoveLeft(): void { + if (this.dave.state !== DaveState.SHOOTING + && this.dave.state !== DaveState.STUCK) { + this.dave.move = DaveMove.LEFT; + this.dave.look = DaveLook.LEFT; + } + } + + tryMoveRight(): void { + if (this.dave.state !== DaveState.SHOOTING + && this.dave.state !== DaveState.STUCK) { + this.dave.move = DaveMove.RIGHT; + this.dave.look = DaveLook.RIGHT; + } + } + + tryHandsUp(): void { + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.RECHARGING) { + let foundDoor = false; + this.gameView.doors.forEach((door) => { + if (!door.opened + && this.isRectCrossWithRect(door.area, this.dave)) { + this.gameView.openDoor(door); + foundDoor = true; + } + }); + if (!foundDoor) { + this.dave.shoot = DaveShoot.UP; + } + } + } + + tryHandsDown(): void { + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.RECHARGING) { + this.dave.shoot = DaveShoot.DOWN; + } + } + + tryJumpUpOrDown(): void { + if (this.dave.state === DaveState.RUNNING + || this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.RECHARGING) { + if (this.dave.shoot === DaveShoot.DOWN) { + this.dave.state = DaveState.JUMPING_DOWN; + } else { + this.dave.state = DaveState.JUMPING_UP; + this.gameView.sounds[SoundType.JUMP].play(); + } + this.dave.velocity = this.dave.jumpStartVelocity; + } + } + + tryHandsCenter(): void { + this.dave.shoot = DaveShoot.CENTER; + } + + tryStand(): void { + if (this.dave.state === DaveState.RUNNING) { + this.dave.state = DaveState.STANDING; + } + this.dave.move = DaveMove.NONE; + } + + preventAlt(e: KeyboardEvent): void { + if (e.altKey) { + e.preventDefault(); + } + } + + keyDownEvents(e: KeyboardEvent): void { + switch (e.code) { + case 'ArrowLeft': + this.preventAlt(e); + this.tryRun(); + this.tryMoveLeft(); + break; + case 'ArrowRight': + this.preventAlt(e); + this.tryRun(); + this.tryMoveRight(); + break; + case 'ArrowUp': + this.tryHandsUp(); + break; + case 'ArrowDown': + this.tryHandsDown(); + break; + case 'Space': + this.tryJumpUpOrDown(); + break; + case 'AltLeft': + this.preventAlt(e); + this.tryShoot(); + break; + case 'KeyG': + if (e.ctrlKey) { + e.preventDefault(); + this.gameView.godMode = !this.gameView.godMode; + } + break; + default: + break; + } + } + + keyUpEvents(e: KeyboardEvent): void { + if (e.code === 'ArrowRight' || e.code === 'ArrowLeft') { + this.tryStand(); + } + if (e.code === 'ArrowUp' || e.code === 'ArrowDown') { + this.tryHandsCenter(); + } + } + setListener(): void { window.addEventListener('keydown', (e: KeyboardEvent) => { - switch (e.code) { - case 'ArrowLeft': - if (e.altKey) { - e.preventDefault(); - } - if (this.dave.state === DaveState.STANDING - || this.dave.state === DaveState.RECHARGING) { - this.dave.state = DaveState.RUNNING; - } - if (this.dave.state !== DaveState.SHOOTING - && this.dave.state !== DaveState.STUCK) { - this.dave.move = DaveMove.LEFT; - this.dave.look = DaveLook.LEFT; - } - break; - case 'ArrowRight': - if (e.altKey) { - e.preventDefault(); - } - if (this.dave.state === DaveState.STANDING - || this.dave.state === DaveState.RECHARGING) { - this.dave.state = DaveState.RUNNING; - } - if (this.dave.state !== DaveState.SHOOTING - && this.dave.state !== DaveState.STUCK) { - this.dave.move = DaveMove.RIGHT; - this.dave.look = DaveLook.RIGHT; - } - break; - case 'ArrowUp': - if (this.dave.state === DaveState.STANDING - || this.dave.state === DaveState.RECHARGING) { - let foundDoor = false; - this.gameView.doors.forEach((door) => { - if (!door.opened - && this.isRectCrossWithRect(door.area, this.dave)) { - this.gameView.openDoor(door); - foundDoor = true; - } - }); - if (!foundDoor) { - this.dave.shoot = DaveShoot.UP; - } - } - break; - case 'ArrowDown': - if (this.dave.state === DaveState.STANDING - || this.dave.state === DaveState.RECHARGING) { - this.dave.shoot = DaveShoot.DOWN; - } - break; - case 'Space': - if (this.dave.state === DaveState.RUNNING - || this.dave.state === DaveState.STANDING - || this.dave.state === DaveState.RECHARGING) { - if (this.dave.shoot === DaveShoot.DOWN) { - this.dave.state = DaveState.JUMPING_DOWN; - } else { - this.dave.state = DaveState.JUMPING_UP; - this.gameView.sounds[SoundType.JUMP].play(); - } - this.dave.velocity = this.dave.jumpStartVelocity; - } - break; - case 'AltLeft': - if (e.altKey) { - e.preventDefault(); - } - if (this.dave.state === DaveState.STANDING - || this.dave.state === DaveState.RUNNING - || this.dave.state === DaveState.RECHARGING - || this.dave.state === DaveState.SHOOTING - ) { - this.dave.state = DaveState.SHOOTING; - this.daveShoot(); - } - break; - case 'KeyG': - if (e.ctrlKey) { - e.preventDefault(); - this.gameView.godMode = !this.gameView.godMode; - } - break; - default: - this.dave.setView(); - break; - } + this.keyDownEvents(e); }); window.addEventListener('keyup', (e: KeyboardEvent) => { - if (e.code === 'ArrowRight' || e.code === 'ArrowLeft') { - if (this.dave.state === DaveState.RUNNING) { - this.dave.state = DaveState.STANDING; - } - this.dave.move = DaveMove.NONE; - } - if (e.code === 'ArrowUp') { - this.dave.shoot = DaveShoot.CENTER; - } - if (e.code === 'ArrowDown') { - this.dave.shoot = DaveShoot.CENTER; - } - this.dave.setView(); + this.keyUpEvents(e); }); } @@ -669,88 +694,96 @@ class PlayLevel { return [dX, dY]; } - daveShoot(): void { - if (this.dave.bullets > 0) { - this.dave.bullets -= 1; - this.gameView.showAmmo(); - this.gameView.sounds[SoundType.SHOT].currentTime = 0; - this.gameView.sounds[SoundType.SHOT].play(); - const fromX: number = this.dave.x + this.dave.w / 2; - const fromY: number = this.dave.y + this.dave.h / 2 - - this.dave.shootOffsetY; - const [dX, dY] = this.calcEndOfLineShoot(); - let closestWall: Rect | undefined; - this.gameView.walls.forEach((wall) => { - if (this.isLineCrossRect({ - x1: fromX, - y1: fromY, - x2: fromX + dX, - y2: fromY + dY, - }, wall)) { - if (!closestWall || this.isOneRectCloserAnother(wall, closestWall)) { - closestWall = wall; + tryShoot(): void { + if (this.dave.state === DaveState.STANDING + || this.dave.state === DaveState.RUNNING + || this.dave.state === DaveState.RECHARGING + || this.dave.state === DaveState.SHOOTING + ) { + this.dave.state = DaveState.SHOOTING; + if (this.dave.bullets > 0) { + this.dave.bullets -= 1; + this.gameView.showAmmo(); + this.gameView.sounds[SoundType.SHOT].currentTime = 0; + this.gameView.sounds[SoundType.SHOT].play(); + const fromX: number = this.dave.x + this.dave.w / 2; + const fromY: number = this.dave.y + this.dave.h / 2 + - this.dave.shootOffsetY; + const [dX, dY] = this.calcEndOfLineShoot(); + let closestWall: Rect | undefined; + this.gameView.walls.forEach((wall) => { + if (this.isLineCrossRect({ + x1: fromX, + y1: fromY, + x2: fromX + dX, + y2: fromY + dY, + }, wall)) { + if (!closestWall + || this.isFirstRectCloserToDave(wall, closestWall)) { + closestWall = wall; + } } - } - }); - let closestMonster: Monster | undefined; - this.gameView.monsters.forEach((monster) => { - if (this.isLineCrossRect({ - x1: fromX, - y1: fromY, - x2: fromX + dX, - y2: fromY + dY, - }, monster)) { - if (!closestMonster - || this.isOneRectCloserAnother(monster, closestMonster)) { - closestMonster = monster; + }); + let closestMonster: Monster | undefined; + this.gameView.monsters.forEach((monster) => { + if (this.isLineCrossRect({ + x1: fromX, + y1: fromY, + x2: fromX + dX, + y2: fromY + dY, + }, monster)) { + if (!closestMonster + || this.isFirstRectCloserToDave(monster, closestMonster)) { + closestMonster = monster; + } + } + }); + if ((closestMonster && !closestWall) + || (closestMonster + && closestWall + && this.isFirstRectCloserToDave(closestMonster, closestWall)) + ) { + closestMonster.getAttacked(); + if (closestMonster.health === 0) { + this.gameView.removeMonster(closestMonster); } } - }); - if ((closestMonster && !closestWall) - || (closestMonster - && closestWall - && this.isOneRectCloserAnother(closestMonster, closestWall)) - ) { - closestMonster.getAttacked(); - if (closestMonster.health === 0) { - this.gameView.removeMonster(closestMonster); - } + } else { + this.gameView.sounds[SoundType.EMPTY].currentTime = 0; + this.gameView.sounds[SoundType.EMPTY].play(); } - } else { - this.gameView.sounds[SoundType.EMPTY].currentTime = 0; - this.gameView.sounds[SoundType.EMPTY].play(); + setTimeout(() => { + this.dave.state = DaveState.STUCK; + if (!this.shootTimer) { + this.shootTimer = window.setTimeout(() => { + this.dave.state = DaveState.STANDING; + this.shootTimer = undefined; + }, 200); + } + }, 50); } - setTimeout(() => { - this.dave.state = DaveState.STUCK; - if (!this.shootTimer) { - this.shootTimer = window.setTimeout(() => { - this.dave.state = DaveState.STANDING; - this.shootTimer = undefined; - }, 200); - } - }, 50); } - isOneRectCloserAnother(wall: Rect, monster: Rect): boolean { + isFirstRectCloserToDave(rect1: Rect, rect2: Rect): boolean { if (this.dave.look === DaveLook.RIGHT) { if (this.dave.shoot === DaveShoot.CENTER) { - return (wall.x + wall.w < monster.x); + return (rect1.x + rect1.w < rect2.x); } if (this.dave.shoot === DaveShoot.UP) { - return !!((wall.x + wall.w <= monster.x - || wall.y >= monster.y + monster.h)); + return !!((rect1.x + rect1.w <= rect2.x + || rect1.y >= rect2.y + rect2.h)); } if (this.dave.shoot === DaveShoot.DOWN) { - return !!((wall.x + wall.w <= monster.x - || wall.y + wall.h <= monster.y)); + return !!((rect1.x + rect1.w <= rect2.x + || rect1.y + rect1.h <= rect2.y)); } } else if (this.dave.look === DaveLook.LEFT) { if (this.dave.shoot === DaveShoot.CENTER) { - return (wall.x >= monster.x + monster.w); + return (rect1.x >= rect2.x + rect2.w); } if (this.dave.shoot === DaveShoot.UP) { - return !!((wall.x >= monster.x + monster.w - || wall.y >= monster.y + monster.h)); + return !!((rect1.x >= rect2.x + rect2.w + || rect1.y >= rect2.y + rect2.h)); } if (this.dave.shoot === DaveShoot.DOWN) { - return !!((wall.x >= monster.x + monster.w - || wall.y + wall.h <= monster.y)); + return !!((rect1.x >= rect2.x + rect2.w + || rect1.y + rect1.h <= rect2.y)); } } return false; From a1d133c2f61c96a3dc08aa9527dc652fdf63c70d Mon Sep 17 00:00:00 2001 From: HardManDev Date: Tue, 14 Feb 2023 18:56:01 +0300 Subject: [PATCH 092/196] feat: create Score model and schema --- server/package-lock.json | 31 ++++++++++++++++++++++++ server/package.json | 1 + server/src/models/scheme/score.schema.ts | 28 +++++++++++++++++++++ server/src/types/interfaces/score.ts | 8 ++++++ 4 files changed, 68 insertions(+) create mode 100644 server/src/models/scheme/score.schema.ts create mode 100644 server/src/types/interfaces/score.ts diff --git a/server/package-lock.json b/server/package-lock.json index 64af101..5c81100 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -16,6 +16,7 @@ "@nestjs/mongoose": "^9.2.1", "@nestjs/passport": "^9.0.3", "@nestjs/platform-express": "^9.0.0", + "@typegoose/typegoose": "^10.1.1", "bcrypt": "^5.1.0", "cookie-parser": "^1.4.6", "passport-jwt": "^4.0.1", @@ -3087,6 +3088,24 @@ "integrity": "sha512-yOlFc+7UtL/89t2ZhjPvvB/DeAr3r+Dq58IgzsFkOAvVC6NMJXmCGjbptdXdR9qsX7pKcTL+s87FtYREi2dEEQ==", "dev": true }, + "node_modules/@typegoose/typegoose": { + "version": "10.1.1", + "resolved": "https://registry.npmjs.org/@typegoose/typegoose/-/typegoose-10.1.1.tgz", + "integrity": "sha512-QzRzgFnsQ3/UTToUEVJ5ln4t/QzlznEat7bcn9tNt4U6QCytPVvTJnRe5SwrJllxakgz0yrnbKkTw9YeoiYXuQ==", + "dependencies": { + "lodash": "^4.17.20", + "loglevel": "^1.8.1", + "reflect-metadata": "^0.1.13", + "semver": "^7.3.8", + "tslib": "^2.5.0" + }, + "engines": { + "node": ">=14.17.0" + }, + "peerDependencies": { + "mongoose": "~6.9.0" + } + }, "node_modules/@types/babel__core": { "version": "7.20.0", "resolved": "https://registry.npmjs.org/@types/babel__core/-/babel__core-7.20.0.tgz", @@ -7570,6 +7589,18 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, + "node_modules/loglevel": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/loglevel/-/loglevel-1.8.1.tgz", + "integrity": "sha512-tCRIJM51SHjAayKwC+QAg8hT8vg6z7GSgLJKGvzuPb1Wc+hLzqtuVLxp6/HzSPOozuK+8ErAhy7U/sVzw8Dgfg==", + "engines": { + "node": ">= 0.6.0" + }, + "funding": { + "type": "tidelift", + "url": "https://tidelift.com/funding/github/npm/loglevel" + } + }, "node_modules/lru-cache": { "version": "5.1.1", "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", diff --git a/server/package.json b/server/package.json index 50f43d5..7a82521 100644 --- a/server/package.json +++ b/server/package.json @@ -27,6 +27,7 @@ "@nestjs/mongoose": "^9.2.1", "@nestjs/passport": "^9.0.3", "@nestjs/platform-express": "^9.0.0", + "@typegoose/typegoose": "^10.1.1", "bcrypt": "^5.1.0", "cookie-parser": "^1.4.6", "passport-jwt": "^4.0.1", diff --git a/server/src/models/scheme/score.schema.ts b/server/src/models/scheme/score.schema.ts new file mode 100644 index 0000000..70fdd34 --- /dev/null +++ b/server/src/models/scheme/score.schema.ts @@ -0,0 +1,28 @@ +import { Document } from 'mongoose'; +import { IScore } from '../../types/interfaces/score'; +import { Prop, SchemaFactory } from '@nestjs/mongoose'; +import { v4 as UUIDv4 } from 'uuid'; +import { Ref } from '@typegoose/typegoose'; +import { User } from './user.schema'; + +export class Score extends Document implements IScore { + @Prop({ + type: String, + isRequired: true, + default: UUIDv4, + }) + _id: string; + + @Prop({ + type: Number, + isRequired: true, + default: 0, + index: true, + }) + score: number; + + @Prop() + user: Ref; +} + +export const ScoreSchema = SchemaFactory.createForClass(Score); diff --git a/server/src/types/interfaces/score.ts b/server/src/types/interfaces/score.ts new file mode 100644 index 0000000..571c002 --- /dev/null +++ b/server/src/types/interfaces/score.ts @@ -0,0 +1,8 @@ +import { IUser } from './user'; +import { Ref } from '@typegoose/typegoose'; + +export interface IScore { + readonly _id: string; + readonly score: number; + readonly user: Ref; +} From fc754ee426dbdc5f8cc8dccdc935eb12b3447e47 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Tue, 14 Feb 2023 23:13:02 +0300 Subject: [PATCH 093/196] refactor: modify shoot, dave animation --- client/src/assets/sprites/dave_sprites.png | Bin 18663 -> 0 bytes .../src/assets/sprites/dave_sprites_vert.png | Bin 0 -> 17840 bytes client/src/scripts/components/dave.ts | 72 ++++------ client/src/scripts/components/monster.ts | 1 - client/src/scripts/controllers/playLevel.ts | 109 ++++++++------- client/src/styles/dave.css | 4 +- client/src/styles/playerAnimation.scss | 92 +++++-------- .../src/styles/playerAnimationKeyframes.scss | 127 ++++++------------ 8 files changed, 158 insertions(+), 247 deletions(-) delete mode 100644 client/src/assets/sprites/dave_sprites.png create mode 100644 client/src/assets/sprites/dave_sprites_vert.png diff --git a/client/src/assets/sprites/dave_sprites.png b/client/src/assets/sprites/dave_sprites.png deleted file mode 100644 index b8ae47971c273bafee1f4a13b1106549acc1d2fa..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 18663 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 K=d#Wzp$Py~c-Q&> diff --git a/client/src/assets/sprites/dave_sprites_vert.png b/client/src/assets/sprites/dave_sprites_vert.png new file mode 100644 index 0000000000000000000000000000000000000000..1f6e07489c722d17003e773283fba44f1a28c46a GIT binary patch literal 17840 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�Ge6e}-corTjWB7EAh>&w~%xJjYcNQqgk& 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 { + this.keyDownEvents(e); + }; + window.onkeyup = (e: KeyboardEvent): void => { + this.keyUpEvents(e); + }; + } + tryRun(): void { if (this.dave.state === DaveState.STANDING || this.dave.state === DaveState.RECHARGING) { @@ -528,15 +537,6 @@ class PlayLevel { } } - setListener(): void { - window.addEventListener('keydown', (e: KeyboardEvent) => { - this.keyDownEvents(e); - }); - window.addEventListener('keyup', (e: KeyboardEvent) => { - this.keyUpEvents(e); - }); - } - animateMonsters(): void { this.monsterAnimationTimer = window.setInterval(() => { for (let i = 0; i < this.gameView.monsters.length; i += 1) { @@ -550,6 +550,7 @@ class PlayLevel { moveMonster(monster: Monster): void { if (monster.moveTicks === monster.moveTicksMax) { + monster.sprite.innerHTML = `${monster.health}`; monster.moveTicks -= 1; let dX = 0; if (monster.moveDir === MonsterMove.RIGHT) { @@ -706,64 +707,64 @@ class PlayLevel { this.gameView.showAmmo(); this.gameView.sounds[SoundType.SHOT].currentTime = 0; this.gameView.sounds[SoundType.SHOT].play(); - const fromX: number = this.dave.x + this.dave.w / 2; - const fromY: number = this.dave.y + this.dave.h / 2 + const x: number = this.dave.x + this.dave.w / 2; + const y: number = this.dave.y + this.dave.h / 2 - this.dave.shootOffsetY; const [dX, dY] = this.calcEndOfLineShoot(); - let closestWall: Rect | undefined; - this.gameView.walls.forEach((wall) => { - if (this.isLineCrossRect({ - x1: fromX, - y1: fromY, - x2: fromX + dX, - y2: fromY + dY, - }, wall)) { - if (!closestWall - || this.isFirstRectCloserToDave(wall, closestWall)) { - closestWall = wall; - } - } - }); - let closestMonster: Monster | undefined; - this.gameView.monsters.forEach((monster) => { - if (this.isLineCrossRect({ - x1: fromX, - y1: fromY, - x2: fromX + dX, - y2: fromY + dY, - }, monster)) { - if (!closestMonster - || this.isFirstRectCloserToDave(monster, closestMonster)) { - closestMonster = monster; - } - } - }); + const shootLine = { + x1: x, y1: y, x2: x + dX, y2: y + dY, + }; + const closestWall: Rect | Monster | undefined = this.getClosestObj( + shootLine, + this.gameView.walls, + ); + const closestMonster: Rect | Monster | undefined = this.getClosestObj( + shootLine, + this.gameView.monsters, + ); if ((closestMonster && !closestWall) || (closestMonster && closestWall && this.isFirstRectCloserToDave(closestMonster, closestWall)) ) { - closestMonster.getAttacked(); - if (closestMonster.health === 0) { - this.gameView.removeMonster(closestMonster); + (closestMonster).getAttacked(); + if ((closestMonster).health === 0) { + this.gameView.removeMonster((closestMonster)); } } } else { this.gameView.sounds[SoundType.EMPTY].currentTime = 0; this.gameView.sounds[SoundType.EMPTY].play(); } - setTimeout(() => { - this.dave.state = DaveState.STUCK; - if (!this.shootTimer) { - this.shootTimer = window.setTimeout(() => { - this.dave.state = DaveState.STANDING; - this.shootTimer = undefined; - }, 200); - } - }, 50); + this.setDaveStuck(); } } + getClosestObj(shootLine: Line, rects: Rect[]): Rect | Monster | undefined { + let result: Rect | Monster | undefined; + rects.forEach((rect) => { + if (this.isLineCrossRect(shootLine, rect)) { + if (!result + || this.isFirstRectCloserToDave(rect, result)) { + result = rect; + } + } + }); + return result; + } + + setDaveStuck(): void { + setTimeout(() => { + this.dave.state = DaveState.STUCK; + if (!this.shootTimer) { + this.shootTimer = window.setTimeout(() => { + this.dave.state = DaveState.STANDING; + this.shootTimer = undefined; + }, 200); + } + }, 50); + } + isFirstRectCloserToDave(rect1: Rect, rect2: Rect): boolean { if (this.dave.look === DaveLook.RIGHT) { if (this.dave.shoot === DaveShoot.CENTER) { @@ -856,6 +857,7 @@ class PlayLevel { restartLevel(): void { if (this.gameView.lives > 0) { + this.resetListeners(); this.gameView.resetLevel(); this.gameView.loadLevelEntities(); this.dave = this.gameView.dave; @@ -867,6 +869,11 @@ class PlayLevel { } } + resetListeners(): void { + window.onkeydown = null; + window.onkeyup = null; + } + reloadStart(): void { this.reloadStartTimer = window.setTimeout(() => { this.reloadBullets(); diff --git a/client/src/styles/dave.css b/client/src/styles/dave.css index 45eb596..0521373 100644 --- a/client/src/styles/dave.css +++ b/client/src/styles/dave.css @@ -2,10 +2,10 @@ .player { position: absolute; - background-image: url("../assets/sprites/dave_sprites.png"); - background-size: 5257px; top: 0; left: 0; + width: 96px; + height: 96px; z-index: 100; } diff --git a/client/src/styles/playerAnimation.scss b/client/src/styles/playerAnimation.scss index 19b21ac..c4dcceb 100644 --- a/client/src/styles/playerAnimation.scss +++ b/client/src/styles/playerAnimation.scss @@ -4,148 +4,130 @@ $bg-size: 5257px; .players { &-animate { - background: url("../assets/sprites/dave_sprites.png"); - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + background-repeat: no-repeat; animation-timing-function: steps(1); &-move-left { - background: url("../assets/sprites/dave_sprites.png"); - animation: move-left 0.5s ease-in-out infinite; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + animation: move-left 0.4s ease-in-out infinite; animation-timing-function: steps(1); } &-move-right { - background: url("../assets/sprites/dave_sprites.png"); - animation: move-right 0.5s ease-in-out infinite; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + animation: move-right 0.4s ease-in-out infinite; animation-timing-function: steps(1); } &-jump { &-left { - background: url("../assets/sprites/dave_sprites.png"); - animation: jump-left 0.7s ease-in-out; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + animation: jump-left 0.3s ease-in-out; animation-timing-function: steps(1); } &-right { - background: url("../assets/sprites/dave_sprites.png"); - animation: jump-right 0.7s ease-in-out; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + animation: jump-right 0.3s ease-in-out; animation-timing-function: steps(1); } } &-fall { &-left { - background: url("../assets/sprites/dave_sprites.png"); - animation: fall-left 0.7s ease-in-out infinite; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + animation: fall-left 0.3s ease-in-out infinite; animation-timing-function: steps(1); } &-right { - background: url("../assets/sprites/dave_sprites.png"); - animation: fall-right 0.7s ease-in-out infinite; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + animation: fall-right 0.3s ease-in-out infinite; animation-timing-function: steps(1); } } &-look { &-left { - background-position: -583px 0; - width: 60px !important; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + background-position: 0 -768px; } &-right { + background: url("../assets/sprites/dave_sprites_vert.png"); background-position: 0 0; - background-size: $bg-size; } &-topRight { - background: url("../assets/sprites/dave_sprites.png") -2552px 0; - width: 73px !important; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + background-position: 0 -1536px; } &-topLeft { - background: url("../assets/sprites/dave_sprites.png") -3043px 0; - width: 73px !important; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + background-position: 0px -2112px; } &-downRight { - background: url("../assets/sprites/dave_sprites.png") -2696px 0; - width: 73px !important; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + background-position: 0 -1728px; } &-downLeft { - background: url("../assets/sprites/dave_sprites.png") -3179px 0; - width: 69px !important; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + background-position: 0 -2304px; } } &-shoot { &-left { - background: url("../assets/sprites/dave_sprites.png"); + background: url("../assets/sprites/dave_sprites_vert.png"); animation: shoot-left 0.5s ease-in-out infinite; - background-size: $bg-size; animation-timing-function: steps(1); } &-right { - background: url("../assets/sprites/dave_sprites.png"); + background: url("../assets/sprites/dave_sprites_vert.png"); animation: shoot-right 0.5s ease-in-out infinite; - background-size: $bg-size; animation-timing-function: steps(1); } &-topRight { - background: url("../assets/sprites/dave_sprites.png"); - animation: shoot-top-right 0.5s ease-in-out infinite; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + animation: shoot-top-right 0.5s ease-in-out; animation-timing-function: steps(1); } &-topLeft { - background: url("../assets/sprites/dave_sprites.png"); - animation: shoot-top-left 0.5s ease-in-out infinite; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + animation: shoot-top-left 0.5s ease-in-out; animation-timing-function: steps(1); } &-downRight { - background: url("../assets/sprites/dave_sprites.png"); - animation: shoot-down-right 0.5s ease-in-out infinite; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + animation: shoot-down-right 0.5s ease-in-out; animation-timing-function: steps(1); } &-downLeft { - background: url("../assets/sprites/dave_sprites.png"); - animation: shoot-down-left 0.5s ease-in-out infinite; - background-size: $bg-size; + background: url("../assets/sprites/dave_sprites_vert.png"); + animation: shoot-down-left 0.5s ease-in-out; animation-timing-function: steps(1); } } &-exit { - background: url("../assets/sprites/dave_sprites.png"); + background: url("../assets/sprites/dave_sprites_vert.png"); animation: exit 1s ease-in-out infinite; background-size: $bg-size; animation-timing-function: steps(1); } &-reload { - background: url("../assets/sprites/dave_sprites.png"); + background: url("../assets/sprites/dave_sprites_vert.png"); animation: reload 0.7s ease-in-out infinite; - background-size: $bg-size; animation-timing-function: steps(1); } } diff --git a/client/src/styles/playerAnimationKeyframes.scss b/client/src/styles/playerAnimationKeyframes.scss index e361e24..a2a400a 100644 --- a/client/src/styles/playerAnimationKeyframes.scss +++ b/client/src/styles/playerAnimationKeyframes.scss @@ -1,198 +1,147 @@ @keyframes move-left { 0% { - background-position: -644px 0; - width: 72px; + background-position: 0 -864px; } - 25% { - background-position: -718px 0; - width: 72px; + background-position: 0 -960px; } 50% { - background-position: -787px 0; - width: 72px; + background-position: 0 -1056px; } 75% { - background-position: -857px 0; - width: 72px; + background-position: 0 -1152px; } } @keyframes move-right { 0% { - background-position: -69px 0; - width: 72px; + background-position: 0 -96px; } 25% { - background-position: -146px 0; - width: 72px; + background-position: 0 -192px; } 50% { - background-position: -214px 0; - width: 72px; + background-position: 0 -288px; } 75% { - background-position: -284px 0; - width: 72px; + background-position: 0 -384px; } } @keyframes jump-left { - 0% { - background-position: -355px 0; - width: 72px; - } - 25% { - background-position: -432px 0; - width: 72px; + 0% { + background-position: 0 -1248px; } 50% { - background-position: -498px 0; - width: 72px; + background-position: 0 -1344px; } + } @keyframes jump-right { 0% { - background-position: -923px 0; - width: 72px; - } - - 25% { - background-position: -996px 0; - width: 72px; + background-position: 0 -480px; } 50% { - background-position: -1067px 0; - width: 72px; + background-position: 0 -576px; } } @keyframes fall-left { 0% { - background-position: -432px 0; - width: 78px; - } - - 50% { - background-position: -498px 0; - width: 78px; - } -} - -@keyframes fall-right { - 0% { - background-position: -996px 0; - width: 78px; + background-position: 0 -1344px; } 50% { - background-position: -1067px 0; - width: 78px; + background-position: 0 -1440px; } } @keyframes fall-right { 0% { - background-position: -996px 0; - width: 78px; + background-position: 0 -576px; } 50% { - background-position: -1067px 0; - width: 78px; + background-position: 0 -672px; } } @keyframes reload { 0% { - background-position: -1152px 0; - width: 78px; + background-position: 0 -2784px; } 50% { - background-position: -1220px 0; - width: 69px; + background-position: 0 -2688px; } } @keyframes shoot-right { 0% { - background-position: -2381px 0; - width: 82px; + background-position: 0 -1920px; } - 50% { - background-position: -2473px 0; - width: 82px; + 25% { + background-position: 0 -2016px; } } @keyframes shoot-top-right { 0% { - background-position: -2552px 0; - width: 75px; + background-position: 0 -1536px; } - 50% { - background-position: -2619px 0; - width: 75px; + 25% { + background-position: 0 -1632px; } } @keyframes shoot-down-right { 0% { - background-position: -2696px 0; - width: 75px; + background-position: 0 -1728px; } - 50% { - background-position: -2773px 0; - width: 70px; + 25% { + background-position: 0 -1824px; } } @keyframes shoot-left { 0% { - background-position: -2845px 0; - width: 78px; + background-position: 0 -2496px; } - 50% { - background-position: -2945px 0; - width: 78px; + 25% { + background-position: 0 -2592px; } } @keyframes shoot-top-left { 0% { - background-position: -3043px 0; - width: 75px; + background-position: 0 -2212px; } - 50% { - background-position: -3121px 0; - width: 56px; + 25% { + background-position: 0 -2208px; } } @keyframes shoot-down-left { 0% { - background-position: -3179px 0; - width: 69px; + background-position: 0 -2304px; } - 50% { - background-position: -3250px 0; - width: 70px; + 25% { + background-position: 0 -2400px; } } From 0831ecd622ddf7c002b635185aaa83b92da45f74 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Tue, 14 Feb 2023 23:27:11 +0300 Subject: [PATCH 094/196] refactor: scss styles --- client/src/styles/playerAnimation.scss | 2 +- client/src/styles/playerAnimationKeyframes.scss | 3 +-- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/client/src/styles/playerAnimation.scss b/client/src/styles/playerAnimation.scss index c4dcceb..fd07491 100644 --- a/client/src/styles/playerAnimation.scss +++ b/client/src/styles/playerAnimation.scss @@ -66,7 +66,7 @@ $bg-size: 5257px; &-topLeft { background: url("../assets/sprites/dave_sprites_vert.png"); - background-position: 0px -2112px; + background-position: 0 -2112px; } &-downRight { diff --git a/client/src/styles/playerAnimationKeyframes.scss b/client/src/styles/playerAnimationKeyframes.scss index a2a400a..586a614 100644 --- a/client/src/styles/playerAnimationKeyframes.scss +++ b/client/src/styles/playerAnimationKeyframes.scss @@ -2,6 +2,7 @@ 0% { background-position: 0 -864px; } + 25% { background-position: 0 -960px; } @@ -34,7 +35,6 @@ } @keyframes jump-left { - 0% { background-position: 0 -1248px; } @@ -42,7 +42,6 @@ 50% { background-position: 0 -1344px; } - } @keyframes jump-right { From 7328b8034d41b8c9dfc93097718f6df8b80b8637 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Wed, 15 Feb 2023 00:46:47 +0300 Subject: [PATCH 095/196] feat: add animation for enemy --- client/src/scripts/components/crone.ts | 24 +++++++++++++++++++-- client/src/scripts/components/zombie.ts | 20 +++++++++++++++++ client/src/scripts/controllers/playLevel.ts | 2 +- client/src/styles/crone.css | 2 +- client/src/styles/zombie.css | 6 +++--- 5 files changed, 47 insertions(+), 7 deletions(-) diff --git a/client/src/scripts/components/crone.ts b/client/src/scripts/components/crone.ts index 1e89477..25bf05d 100644 --- a/client/src/scripts/components/crone.ts +++ b/client/src/scripts/components/crone.ts @@ -1,9 +1,11 @@ /* eslint-disable class-methods-use-this */ import '@styles/crone'; +import Direction from '../../types/enums/directions'; import { LeftFeet, Offset, Rect } from '../../types/game'; import { Bullet, BulletMove, MonsterAttack, MonsterMove, MonsterState, } from '../../types/monster'; +import CroneAnimator from '../controllers/croneAnimator'; import Monster from './monster'; class Crone extends Monster { @@ -37,12 +39,14 @@ class Crone extends Monster { bulletOffsetY = 10; - bulletW = 20; + bulletW = 24; - bulletH = 10; + bulletH = 8; bonus = 100; + animation: CroneAnimator; + constructor(leftFeet: LeftFeet, levelArea: HTMLElement) { super(); this.sprite.classList.add('crone'); @@ -54,6 +58,22 @@ class Crone extends Monster { this.moveDir = Math.random() > 0.5 ? MonsterMove.LEFT : MonsterMove.RIGHT; this.setPosition(); this.levelArea = levelArea; + this.animation = new CroneAnimator(this.sprite); + } + + setView(): void { + const moveLook: Direction = this.moveDir === MonsterMove.LEFT + ? Direction.LEFT + : Direction.RIGHT; + const shootLook: Direction = this.attackDir === MonsterAttack.LEFT + ? Direction.LEFT + : Direction.RIGHT; + if (this.state === MonsterState.MOVING) { + this.animation.move(moveLook); + } + if (this.state === MonsterState.ATTACKING) { + this.animation.attack(shootLook); + } } attack(): void { diff --git a/client/src/scripts/components/zombie.ts b/client/src/scripts/components/zombie.ts index 4e24fdc..3caa049 100644 --- a/client/src/scripts/components/zombie.ts +++ b/client/src/scripts/components/zombie.ts @@ -1,8 +1,10 @@ import '@styles/zombie'; +import Direction from '../../types/enums/directions'; import { LeftFeet, Rect } from '../../types/game'; import { Bullet, MonsterAttack, MonsterMove, MonsterState, } from '../../types/monster'; +import ZombieAnimator from '../controllers/zombieAnimator'; import Monster from './monster'; class Zombie extends Monster { @@ -38,6 +40,8 @@ class Zombie extends Monster { bonus = 100; + animation: ZombieAnimator; + constructor(leftFeet: LeftFeet, levelArea: HTMLElement) { super(); this.sprite.classList.add('zombie'); @@ -49,6 +53,22 @@ class Zombie extends Monster { this.moveDir = Math.random() > 0.5 ? MonsterMove.LEFT : MonsterMove.RIGHT; this.setPosition(); this.levelArea = levelArea; + this.animation = new ZombieAnimator(this.sprite); + } + + setView(): void { + const centerLook: Direction = this.moveDir === MonsterMove.LEFT + ? Direction.LEFT + : Direction.RIGHT; + const shootLook: Direction = this.attackDir === MonsterAttack.LEFT + ? Direction.LEFT + : Direction.RIGHT; + if (this.state === MonsterState.MOVING) { + this.animation.move(centerLook); + } + if (this.state === MonsterState.ATTACKING) { + this.animation.attack(shootLook); + } } attack(): void { diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index 5c9f37a..db007b7 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -543,6 +543,7 @@ class PlayLevel { const monster = this.gameView.monsters[i]; if (monster.state === MonsterState.MOVING) { this.moveMonster(monster); + monster.setView(); } } }, 50); @@ -550,7 +551,6 @@ class PlayLevel { moveMonster(monster: Monster): void { if (monster.moveTicks === monster.moveTicksMax) { - monster.sprite.innerHTML = `${monster.health}`; monster.moveTicks -= 1; let dX = 0; if (monster.moveDir === MonsterMove.RIGHT) { diff --git a/client/src/styles/crone.css b/client/src/styles/crone.css index 9b81aea..ac40d15 100644 --- a/client/src/styles/crone.css +++ b/client/src/styles/crone.css @@ -14,6 +14,6 @@ position: absolute; top: 0; left: 0; - background-color: blue; + background-image: url("../assets/sprites/knife.png"); z-index: 10; } diff --git a/client/src/styles/zombie.css b/client/src/styles/zombie.css index ff3b3b9..eee7082 100644 --- a/client/src/styles/zombie.css +++ b/client/src/styles/zombie.css @@ -7,15 +7,15 @@ background-image: url("../assets/sprites/zombie_sprite.png"); z-index: 10; } - +/* .zombie.attacked { background-color: crimson; } - +*/ .zombie_bullet { position: absolute; top: 0; left: 0; - background-color: blueviolet; + /* background-color: blueviolet;*/ z-index: 10; } From cc5c94c598d5535294532341d0e7cbee35be078c Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Wed, 15 Feb 2023 17:17:53 +0300 Subject: [PATCH 096/196] feat: add meat explosion --- client/src/assets/sprites/meat.png | Bin 0 -> 2787 bytes client/src/scripts/components/game.ts | 49 ++++++- client/src/scripts/components/monster.ts | 1 + client/src/scripts/controllers/playLevel.ts | 148 +++++++++++++++++++- client/src/styles/monster.css | 27 ++++ client/src/types/game.ts | 6 + client/src/types/monster.ts | 13 +- 7 files changed, 238 insertions(+), 6 deletions(-) create mode 100644 client/src/assets/sprites/meat.png create mode 100644 client/src/styles/monster.css diff --git a/client/src/assets/sprites/meat.png b/client/src/assets/sprites/meat.png new file mode 100644 index 0000000000000000000000000000000000000000..e07a4c5085c75589a681287915346c4725c676b0 GIT binary patch literal 2787 zcmaJ?c{r478-MM|lF|v~Xc|Stm@yaz*=9IoG~#ZGKgYAgSJKv1P*y)Q~j_m zINNW&pq)89fXiiJ_4LBR!VqC-1e5KrhcYoSS;5fP*M&56IS~vlIb4^)QU8vB1345n zjm4!g8L$;ZvM)1~YYvAZ{W}FZ>jx}@^Q}x!!Suq(EIkwgxsuX%MFQdftJ3K|v^iWC z@Sk}9Cosn?f(7cifE;Ehn*v>&pZba`7S@IhlDSN_87RRK7(m@9IyDjw}TjQVFu26x_f;{6uHtjG-wPiEuu+@~Yw4cXf_*1-Z zw$z`;V)Rp6Jt!Exm5cq?MSnkn*t4?yL0f3^gZLl=Vmlk6_0bzy2~f8HL`OF~Pyzsp z>wG&@1XSc_0edw zfq{XcA=E)e7!1bP*cfU6Q&UqjGc$8@^WD35TUc0FT3T9JSy@|K+t}FPa5y|3Z)gwv|=H~A1?&0C#>FK#|-#%|| z@BRDtA2@Kp$H(X3!Gnhm9U_rPWHQ;;*Ox+}P^nZ91pWN{{Qdm{0s?3>T3}!xRJ!2c zU^<=7U@%xLR!B$)o6Y8MI9x6_G&J<^;lohthKGkoL_|bJMn*+N9XWC&Iy(C3(WA$X z9pmwMF)=a6j~_pA;>5|5Cu3t{4b!Y#KgoiXU?2Gdp0R4>D;+< z=g*%{PEJlqNl8sjO-oC=aN$CFdU{4iMrLMaR#q0D&%b!_;-yQMva_>ua&mHWbMx}@ zE?>TU<;s=({QRq{QczG(SXfw8RCN9N_2S~_w z^XJe1`s=T*uC5m^UUYYN_w@Ai_V&Jf`LeIC@71eU{r&x~U%!6y=FPysz~JEE(9qEE z@bJjU$mrPe7}DqLOvIZ~%ovi>dQ!zsyGxWXdzgMs)M0qNWvee{buE zQ*qvrH*w@m+$wu|;v7@_l zA3Xr)i|g^E2m=S<>?59N_-12+lo{(%t@zkL@yZB+2v91Hi%M>i7^2n4>Fik_W8%Fi zkUs^Oh>W%R*L@O!WyK?_!9~sN{TK~7d`bG5`dzT7^VikdV?SQz%@^YA{m8U z3Vxu<1&0eeNbM4_sRshYjmb@Xb1*WfODT$l3ZZ+L;8X7NMQ!=h2 z6{x0TiJjqIo?PewR7DvV4bCM=@ONlkm%4POGe7%`=63uCd)|b}F8MlwbSZEpGhcVZ z4l$vJ=uHEOlznT`z818Il0@(N4BTwn_LNpp79fYt(atk_itZFC&Kb!5id67!koI$$ zpLZAXLw*H{(Cc`2J55DPNJ(ZuulIl?qrbXuUK<$Fcn+=$9Q~u!y z%*k#hQdzQ)x?5mG;aT{q59X!DTPN{iEGD;{KoGT*QO2`Ie2!3lYZ5HfqV3@X&~!A= zIi=agdFVrr$XADPV|^lV0ptm6@+FD<;_MSO()qpe6~Mmg(F&;-utZn-#cmIbOQy_-`v+;*zs?F>iIwQ6j=!x0bay#)cU|bUdmNb$igNu4zNZ<+lva#}t zR^_y?1ijk!9E_-QMOT6&USj{&CqSiXgBod`2)t>r7>uOMqRr%F=Lpq>e32Z%q&qfb zuJN&)e{6xrb<}7>+r>>xuTSnh&58K}v}Nswb-~V9>%ZI;xPS>ctg4SVkY0IRp| zP*K%!hW>k<9$sj)gRuK!H|BAMaJX}1ATD?E{X5f%77reO=>~7EBY7@QaUxedMb{e? z`~0TpYDGlQoyzR=Y^mXhvh2xwN5wF#)iG@!q zgkm$-wlCBM+MO&A(K1iAs`ornpD(+y5**zvre90H r8Im+{Gg5EEe(KRK@22&aLC@+Dm6?ZEr}lQQJel@*CtRsD>G*#EUMseb literal 0 HcmV?d00001 diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 2a680de..8eef805 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -1,3 +1,4 @@ +/* eslint-disable class-methods-use-this */ import '@styles/level'; import jumpSound from '../../assets/sounds/jump.mp3'; import landSound from '../../assets/sounds/land.mp3'; @@ -8,12 +9,14 @@ import reloadSound from '../../assets/sounds/reload.mp3'; import { Rect, LevelEntity, LeftFeet, Door, DoorSize, - LootSize, Loot, SoundType, AllSound, + LootSize, Loot, SoundType, AllSound, Offset, ObjectState, } from '../../types/game'; import Player from './dave'; import Zombie from './zombie'; import { LEVEL1 } from '../../assets/levels/level1'; import Crone from './crone'; +import { Meat } from '../../types/monster'; +import Direction from '../../types/enums/directions'; export type Monster = Zombie | Crone; @@ -64,6 +67,12 @@ class GameView { ammoElement: HTMLElement; + meat: Meat[] = []; + + meatSizeX = 48; + + meatSizeY = 48; + constructor() { this.levelArea.classList.add('level-area'); this.levelArea.style.width = `${this.levelAreaW}px`; @@ -329,6 +338,44 @@ class GameView { } this.ammoElement.classList.add(`ammo${this.dave.bullets}`); } + + createMeatExplosion(monsterRect: Rect): void { + for (let i = 0; i <= 3; i += 1) { + const randDX = 2 + Math.round(Math.random() * 3); + const dXs: number[] = [randDX, randDX + 3, randDX, randDX - 3]; + const meatPart: Meat = { + area: { + x: monsterRect.x, + y: monsterRect.y, + w: this.meatSizeX, + h: this.meatSizeY, + }, + sprite: document.createElement('div'), + state: ObjectState.JUMPING_UP, + movedDir: (i > 1) ? Direction.LEFT : Direction.RIGHT, + velocity: 6, + dX: dXs[i], + }; + meatPart.sprite = document.createElement('div'); + meatPart.sprite.classList.add('meat'); + meatPart.sprite.style.width = `${meatPart.area.w}px`; + meatPart.sprite.style.height = `${meatPart.area.h}px`; + meatPart.sprite.style.transform = `translate(${meatPart.area.x}px, ${meatPart.area.y}px)`; + this.meat.push(meatPart); + this.levelArea.append(meatPart.sprite); + } + } + + moveMeatPart(meatPart: Meat, offset: Offset): void { + meatPart.area.x += offset[0]; + meatPart.area.y += offset[1]; + meatPart.sprite.style.transform = `translate(${meatPart.area.x}px, ${meatPart.area.y}px)`; + } + + removeMeatPart(meatPart: Meat): void { + this.meat.splice(this.meat.indexOf(meatPart), 1); + meatPart.sprite.remove(); + } } export default GameView; diff --git a/client/src/scripts/components/monster.ts b/client/src/scripts/components/monster.ts index 4a437d8..f6becfa 100644 --- a/client/src/scripts/components/monster.ts +++ b/client/src/scripts/components/monster.ts @@ -1,3 +1,4 @@ +import '@styles/monster'; import { MonsterAttack, MonsterMove, MonsterState } from '../../types/monster'; class Monster { diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index db007b7..cedc52f 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -1,6 +1,6 @@ /* eslint-disable class-methods-use-this */ import { - Line, Offset, Position, Rect, SoundType, + Line, ObjectState, Offset, Position, Rect, SoundType, } from '../../types/game'; import { DaveLook, DaveMove, DaveShoot, DaveState, @@ -9,9 +9,10 @@ import Player from '../components/dave'; import Zombie from '../components/zombie'; import GameView, { Monster } from '../components/game'; import { - BulletMove, MonsterAttack, MonsterMove, MonsterState, + BulletMove, Meat, MonsterAttack, MonsterMove, MonsterState, } from '../../types/monster'; import Crone from '../components/crone'; +import Direction from '../../types/enums/directions'; class PlayLevel { gameView: GameView; @@ -273,14 +274,15 @@ class PlayLevel { } } this.dave.setView(); - this.moveBullets(); + this.moveMonsterBullets(); + this.moveMeat(); this.checkLoot(); } }; tick(); } - moveBullets(): void { + moveMonsterBullets(): void { this.gameView.monsters.forEach((monster) => { if (monster instanceof Crone) { monster.bullet.forEach((bullet) => { @@ -313,6 +315,143 @@ class PlayLevel { }); } + moveMeat(): void { + this.gameView.meat.forEach((meatPart) => { + let dX = 0; + let dY = 0; + if (meatPart.state !== ObjectState.STANDING) { + if (meatPart.state === ObjectState.JUMPING_UP) { + [dX, dY] = this.getDiffMeatJumping(meatPart); + } else if (meatPart.state === ObjectState.FALLING) { + [dX, dY] = this.getDiffMeatFalling(meatPart); + } + this.gameView.moveMeatPart(meatPart, [dX, dY]); + } else if (!meatPart.animationTimer) { + meatPart.animationTimer = window.setTimeout(() => { + this.gameView.removeMeatPart(meatPart); + clearTimeout(meatPart.animationTimer); + }, 1000 + Math.round(Math.random() * 500)); + } + }); + } + + getDiffMeatJumping(obj: Meat): Offset { + let dX = 0; + let dY = 0; + dY = -obj.velocity * 2 - 2; + if (obj.movedDir === Direction.RIGHT) { + dX = obj.dX; + } else if (obj.movedDir === Direction.LEFT) { + dX = -obj.dX; + } + + obj.velocity -= 0.5; + const walls: Rect[] = this.isCrossWithWalls({ + x: obj.area.x + ((dX < 0) ? dX : 0), + y: obj.area.y + ((dY < 0) ? dY : 0), + w: obj.area.w + ((dX > 0) ? dX : 0), + h: obj.area.h + ((dY > 0) ? dY : 0), + }); + if (walls.length !== 0) { + let wallAbove: Rect | null = null; + let wallLeft: Rect | null = null; + let wallRight: Rect | null = null; + for (let i = 0; i < walls.length; i += 1) { + if (obj.area.x < walls[i].x + walls[i].w + && obj.area.x + obj.area.w > walls[i].x + && obj.area.y >= walls[i].y + walls[i].h) { + wallAbove = walls[i]; + } + if (dX > 0 && obj.area.x + dX + obj.area.w >= walls[i].x) { + wallRight = walls[i]; + } + if (dX < 0 && obj.area.x + dX <= walls[i].x + walls[i].w) { + wallLeft = walls[i]; + } + } + if (wallAbove) { + dY = wallAbove.y + wallAbove.h - obj.area.y; + obj.state = ObjectState.FALLING; + obj.velocity = 0; + if ((wallRight && dX > 0) || (wallLeft && dX < 0)) { + dX = 0; + } + } else { + dX = 0; + } + } + if (obj.velocity === 0) { + obj.state = ObjectState.FALLING; + } + return [dX, dY]; + } + + getDiffMeatFalling(obj: Meat): Offset { + let dX = 0; + let dY = 0; + dY = obj.velocity * 2 + 2; + if (obj.movedDir === Direction.RIGHT) { + dX = obj.dX; + } else if (obj.movedDir === Direction.LEFT) { + dX = -obj.dX; + } + obj.velocity += 0.5; + const walls: Rect[] = this.isCrossWithWalls({ + x: obj.area.x + ((dX < 0) ? dX : 0), + y: obj.area.y + ((dY < 0) ? dY : 0), + w: obj.area.w + ((dX > 0) ? dX : 0), + h: obj.area.h + ((dY > 0) ? dY : 0), + }); + const platforms: Rect[] = this.isCrossWithPlatforms( + { + x: obj.area.x + ((dX < 0) ? dX : 0), + y: obj.area.y + ((dY < 0) ? dY : 0), + w: obj.area.w + ((dX > 0) ? dX : 0), + h: obj.area.h + ((dY > 0) ? dY : 0), + }, + { + x: obj.area.x, + y: obj.area.w, + w: obj.area.y, + h: obj.area.h, + }, + ); + if (platforms.length) { + walls.push(...platforms); + } + + if (walls.length !== 0) { + let wallUnder: Rect | null = null; + let wallLeft: Rect | null = null; + let wallRight: Rect | null = null; + for (let i = 0; i < walls.length; i += 1) { + if (obj.area.x < walls[i].x + walls[i].w + && obj.area.x + obj.area.w > walls[i].x + && obj.area.y + obj.area.h <= walls[i].y) { + wallUnder = walls[i]; + } + if (dX > 0 && obj.area.x + dX + obj.area.w >= walls[i].x) { + wallRight = walls[i]; + } + if (dX < 0 && obj.area.x + dX <= walls[i].x + walls[i].w) { + wallLeft = walls[i]; + } + } + if (wallUnder) { + this.gameView.sounds[SoundType.LAND].play(); + dY = wallUnder.y - obj.area.h - obj.area.y; + obj.state = ObjectState.STANDING; + obj.velocity = 0; + if ((wallRight && dX > 0) || (wallLeft && dX < 0)) { + dX = 0; + } + } else { + dX = 0; + } + } + return [dX, dY]; + } + daveGoesDead(): void { this.dave.showDeathLayer(); this.dave.state = DaveState.DEAD; @@ -729,6 +868,7 @@ class PlayLevel { ) { (closestMonster).getAttacked(); if ((closestMonster).health === 0) { + this.gameView.createMeatExplosion(closestMonster); this.gameView.removeMonster((closestMonster)); } } diff --git a/client/src/styles/monster.css b/client/src/styles/monster.css new file mode 100644 index 0000000..67e37e6 --- /dev/null +++ b/client/src/styles/monster.css @@ -0,0 +1,27 @@ +.meat { + position: absolute; + top: 0; + left: 0; + z-index: 11; + background-image: url("../assets/sprites/meat.png"); + background-position: 0 -192px; + animation: meat 0.5s ease-in-out; + animation-timing-function: steps(1); +} + +@keyframes meat { + 0% { + background-position: 0 -48px; + } + + 50% { + background-position: 0 -96px; + } + + 100% { + background-position: 0 -192px; + } +} + + + diff --git a/client/src/types/game.ts b/client/src/types/game.ts index a40edfe..4044018 100644 --- a/client/src/types/game.ts +++ b/client/src/types/game.ts @@ -71,3 +71,9 @@ export enum SoundType { export type AllSound = { [key: string]: HTMLAudioElement; }; + +export enum ObjectState { + STANDING, + JUMPING_UP, + FALLING, +} diff --git a/client/src/types/monster.ts b/client/src/types/monster.ts index 2315fae..34c93d5 100644 --- a/client/src/types/monster.ts +++ b/client/src/types/monster.ts @@ -1,4 +1,5 @@ -import { Rect } from './game'; +import Direction from './enums/directions'; +import { ObjectState, Rect } from './game'; export enum MonsterState { STANDING, @@ -29,3 +30,13 @@ export enum BulletMove { LEFT, RIGHT, } + +export type Meat = { + area: Rect; + sprite: HTMLElement, + state: ObjectState, + movedDir: Direction; + velocity: number, + dX: number, + animationTimer?: number, +}; From a3dbcd2341ab30e6a08bc21f7dc367d99927a7d2 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 19:10:41 +0300 Subject: [PATCH 097/196] feat: create Score model and schema --- server/package-lock.json | 31 ------------------------ server/package.json | 1 - server/src/models/scheme/score.schema.ts | 21 ++++++++++------ server/src/models/scheme/user.schema.ts | 9 ++++++- server/src/types/interfaces/score.ts | 5 ++-- server/src/types/interfaces/user.ts | 2 ++ 6 files changed, 26 insertions(+), 43 deletions(-) diff --git a/server/package-lock.json b/server/package-lock.json index 5c81100..64af101 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -16,7 +16,6 @@ "@nestjs/mongoose": "^9.2.1", "@nestjs/passport": "^9.0.3", "@nestjs/platform-express": "^9.0.0", - "@typegoose/typegoose": "^10.1.1", "bcrypt": "^5.1.0", "cookie-parser": "^1.4.6", "passport-jwt": "^4.0.1", @@ -3088,24 +3087,6 @@ "integrity": "sha512-yOlFc+7UtL/89t2ZhjPvvB/DeAr3r+Dq58IgzsFkOAvVC6NMJXmCGjbptdXdR9qsX7pKcTL+s87FtYREi2dEEQ==", "dev": true }, - "node_modules/@typegoose/typegoose": { - "version": "10.1.1", - "resolved": "https://registry.npmjs.org/@typegoose/typegoose/-/typegoose-10.1.1.tgz", - "integrity": "sha512-QzRzgFnsQ3/UTToUEVJ5ln4t/QzlznEat7bcn9tNt4U6QCytPVvTJnRe5SwrJllxakgz0yrnbKkTw9YeoiYXuQ==", - "dependencies": { - "lodash": "^4.17.20", - "loglevel": "^1.8.1", - "reflect-metadata": "^0.1.13", - "semver": "^7.3.8", - "tslib": "^2.5.0" - }, - "engines": { - "node": ">=14.17.0" - }, - "peerDependencies": { - "mongoose": "~6.9.0" - } - }, "node_modules/@types/babel__core": { "version": "7.20.0", "resolved": "https://registry.npmjs.org/@types/babel__core/-/babel__core-7.20.0.tgz", @@ -7589,18 +7570,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/loglevel": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/loglevel/-/loglevel-1.8.1.tgz", - "integrity": "sha512-tCRIJM51SHjAayKwC+QAg8hT8vg6z7GSgLJKGvzuPb1Wc+hLzqtuVLxp6/HzSPOozuK+8ErAhy7U/sVzw8Dgfg==", - "engines": { - "node": ">= 0.6.0" - }, - "funding": { - "type": "tidelift", - "url": "https://tidelift.com/funding/github/npm/loglevel" - } - }, "node_modules/lru-cache": { "version": "5.1.1", "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", diff --git a/server/package.json b/server/package.json index 7a82521..50f43d5 100644 --- a/server/package.json +++ b/server/package.json @@ -27,7 +27,6 @@ "@nestjs/mongoose": "^9.2.1", "@nestjs/passport": "^9.0.3", "@nestjs/platform-express": "^9.0.0", - "@typegoose/typegoose": "^10.1.1", "bcrypt": "^5.1.0", "cookie-parser": "^1.4.6", "passport-jwt": "^4.0.1", diff --git a/server/src/models/scheme/score.schema.ts b/server/src/models/scheme/score.schema.ts index 70fdd34..40bf9b3 100644 --- a/server/src/models/scheme/score.schema.ts +++ b/server/src/models/scheme/score.schema.ts @@ -1,10 +1,9 @@ -import { Document } from 'mongoose'; +import { Document, Schema as MongooseSchema, Types } from 'mongoose'; import { IScore } from '../../types/interfaces/score'; -import { Prop, SchemaFactory } from '@nestjs/mongoose'; +import { Prop, Schema, SchemaFactory } from '@nestjs/mongoose'; import { v4 as UUIDv4 } from 'uuid'; -import { Ref } from '@typegoose/typegoose'; -import { User } from './user.schema'; +@Schema({ collection: 'scores' }) export class Score extends Document implements IScore { @Prop({ type: String, @@ -12,17 +11,25 @@ export class Score extends Document implements IScore { default: UUIDv4, }) _id: string; + @Prop({ + ref: 'User', + type: MongooseSchema.Types.ObjectId, + isRequired: true, + }) + user: Types.ObjectId; @Prop({ type: Number, isRequired: true, - default: 0, index: true, }) score: number; - @Prop() - user: Ref; + @Prop({ + type: Date, + default: Date.now, + }) + createdAt?: Date; } export const ScoreSchema = SchemaFactory.createForClass(Score); diff --git a/server/src/models/scheme/user.schema.ts b/server/src/models/scheme/user.schema.ts index 82df955..8837cee 100644 --- a/server/src/models/scheme/user.schema.ts +++ b/server/src/models/scheme/user.schema.ts @@ -1,4 +1,4 @@ -import { Document } from 'mongoose'; +import { Document, Schema as MongooseSchema, Types } from 'mongoose'; import { Prop, Schema, SchemaFactory } from '@nestjs/mongoose'; import { v4 as UUIDv4 } from 'uuid'; import { IUser } from '../../types/interfaces/user'; @@ -31,6 +31,13 @@ export class User extends Document implements IUser { }) authProvider: AuthProvider; + @Prop({ + ref: 'Score', + type: [MongooseSchema.Types.ObjectId], + isRequired: false, + }) + scores?: Array; + @Prop({ type: Date, default: Date.now, diff --git a/server/src/types/interfaces/score.ts b/server/src/types/interfaces/score.ts index 571c002..61bad2c 100644 --- a/server/src/types/interfaces/score.ts +++ b/server/src/types/interfaces/score.ts @@ -1,8 +1,7 @@ -import { IUser } from './user'; -import { Ref } from '@typegoose/typegoose'; +import { Types } from 'mongoose'; export interface IScore { readonly _id: string; readonly score: number; - readonly user: Ref; + readonly user: Types.ObjectId; } diff --git a/server/src/types/interfaces/user.ts b/server/src/types/interfaces/user.ts index 41dca2e..f514818 100644 --- a/server/src/types/interfaces/user.ts +++ b/server/src/types/interfaces/user.ts @@ -1,9 +1,11 @@ import { AuthProvider } from '../enums/authProviders'; +import { Types } from 'mongoose'; export interface IUser { readonly _id: string; readonly username: string; readonly password?: string; readonly authProvider: AuthProvider; + readonly scores?: Array; readonly createdAt?: Date; } From 06da324d2061107c5d7cc80b9f991e1524afd77e Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 21:59:19 +0300 Subject: [PATCH 098/196] feat: add user field in request protected JwtAuthGuard --- server/src/guards/jwtAuth.guard.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/src/guards/jwtAuth.guard.ts b/server/src/guards/jwtAuth.guard.ts index d9689fd..0c7af96 100644 --- a/server/src/guards/jwtAuth.guard.ts +++ b/server/src/guards/jwtAuth.guard.ts @@ -37,6 +37,6 @@ export class JwtAuthGuard extends PassportStrategy(JwtStrategy) { process.env.JWT_SECRET || 'super-secret-key', ) as UserJwtPayload; - await this.validate(payload); + req.user = await this.validate(payload); } } From b978088b859a2d7b461dce69c19e01c7caff3a45 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 22:01:26 +0300 Subject: [PATCH 099/196] refactor: remove unused scores filed from user schema and model --- server/src/models/scheme/user.schema.ts | 12 ++---------- server/src/types/interfaces/user.ts | 2 -- 2 files changed, 2 insertions(+), 12 deletions(-) diff --git a/server/src/models/scheme/user.schema.ts b/server/src/models/scheme/user.schema.ts index 8837cee..9f463ec 100644 --- a/server/src/models/scheme/user.schema.ts +++ b/server/src/models/scheme/user.schema.ts @@ -1,15 +1,14 @@ import { Document, Schema as MongooseSchema, Types } from 'mongoose'; import { Prop, Schema, SchemaFactory } from '@nestjs/mongoose'; -import { v4 as UUIDv4 } from 'uuid'; import { IUser } from '../../types/interfaces/user'; import { AuthProvider } from '../../types/enums/authProviders'; @Schema({ collection: 'users' }) export class User extends Document implements IUser { @Prop({ - type: String, + type: MongooseSchema.Types.ObjectId, isRequired: true, - default: UUIDv4, + default: Types.ObjectId, }) _id: string; @@ -31,13 +30,6 @@ export class User extends Document implements IUser { }) authProvider: AuthProvider; - @Prop({ - ref: 'Score', - type: [MongooseSchema.Types.ObjectId], - isRequired: false, - }) - scores?: Array; - @Prop({ type: Date, default: Date.now, diff --git a/server/src/types/interfaces/user.ts b/server/src/types/interfaces/user.ts index f514818..41dca2e 100644 --- a/server/src/types/interfaces/user.ts +++ b/server/src/types/interfaces/user.ts @@ -1,11 +1,9 @@ import { AuthProvider } from '../enums/authProviders'; -import { Types } from 'mongoose'; export interface IUser { readonly _id: string; readonly username: string; readonly password?: string; readonly authProvider: AuthProvider; - readonly scores?: Array; readonly createdAt?: Date; } From a01ed43706fb77bf5650e70fab1eb2dc255c1513 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 22:03:39 +0300 Subject: [PATCH 100/196] feat: score field set to index-able --- server/src/models/scheme/score.schema.ts | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/server/src/models/scheme/score.schema.ts b/server/src/models/scheme/score.schema.ts index 40bf9b3..76416a4 100644 --- a/server/src/models/scheme/score.schema.ts +++ b/server/src/models/scheme/score.schema.ts @@ -1,14 +1,13 @@ import { Document, Schema as MongooseSchema, Types } from 'mongoose'; import { IScore } from '../../types/interfaces/score'; import { Prop, Schema, SchemaFactory } from '@nestjs/mongoose'; -import { v4 as UUIDv4 } from 'uuid'; @Schema({ collection: 'scores' }) export class Score extends Document implements IScore { @Prop({ - type: String, + type: MongooseSchema.Types.ObjectId, isRequired: true, - default: UUIDv4, + default: Types.ObjectId, }) _id: string; @Prop({ @@ -21,6 +20,7 @@ export class Score extends Document implements IScore { @Prop({ type: Number, isRequired: true, + default: 0, index: true, }) score: number; @@ -33,3 +33,4 @@ export class Score extends Document implements IScore { } export const ScoreSchema = SchemaFactory.createForClass(Score); +ScoreSchema.index({ user: 1, score: 1 }, { unique: true }); From 0a6ef20cac6d0c43b0dcb82880e8d3a7f7dac00b Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 22:04:35 +0300 Subject: [PATCH 101/196] feat: create Score service --- server/src/modules/score/score.service.ts | 57 +++++++++++++++++++ server/src/types/authorizedRequest.ts | 6 ++ server/src/types/dto/score/createScoreDto.ts | 9 +++ server/src/types/dto/score/getScoreDto.ts | 7 +++ server/src/types/enums/sortFilters.ts | 4 ++ .../types/interfaces/collectionResponse.ts | 4 ++ 6 files changed, 87 insertions(+) create mode 100644 server/src/modules/score/score.service.ts create mode 100644 server/src/types/authorizedRequest.ts create mode 100644 server/src/types/dto/score/createScoreDto.ts create mode 100644 server/src/types/dto/score/getScoreDto.ts create mode 100644 server/src/types/enums/sortFilters.ts create mode 100644 server/src/types/interfaces/collectionResponse.ts diff --git a/server/src/modules/score/score.service.ts b/server/src/modules/score/score.service.ts new file mode 100644 index 0000000..aff314c --- /dev/null +++ b/server/src/modules/score/score.service.ts @@ -0,0 +1,57 @@ +import { ConflictException, Injectable } from '@nestjs/common'; +import { Model } from 'mongoose'; +import { Score } from '../../models/scheme/score.schema'; +import { + CreateScoreRequestDto, + CreateScoreResponseDto, +} from '../../types/dto/score/createScoreDto'; +import { InjectModel } from '@nestjs/mongoose'; +import { IUser } from '../../types/interfaces/user'; +import { IScore } from '../../types/interfaces/score'; +import { SortFilter } from '../../types/enums/sortFilters'; +import { User } from '../../models/scheme/user.schema'; +import { CollectionResponse } from '../../types/interfaces/collectionResponse'; + +@Injectable() +export class ScoreService { + constructor( + @InjectModel(Score.name) private readonly scoreModel: Model, + @InjectModel(User.name) private readonly userModel: Model, + ) {} + + async findAllByUser( + user: IUser, + sorter: SortFilter = SortFilter.DESCENDING, + page = 1, + limit = 100, + ): Promise> { + const result = await this.scoreModel + .find({ user: user._id }) + .sort({ score: sorter }) + .skip(limit * (page - 1)) + .limit(limit) + .exec(); + + return { + totalCount: await this.scoreModel.count(), + collection: result, + }; + } + + async create(score: CreateScoreRequestDto): Promise { + try { + const newScore = await this.scoreModel.create(score); + + await newScore.save(); + + return await newScore.populate({ + path: 'user', + select: '-password -createdAt', + }); + } catch (e) { + throw new ConflictException( + `Score '${score.score}' already exists for the user with id '${score.user._id}'`, + ); + } + } +} diff --git a/server/src/types/authorizedRequest.ts b/server/src/types/authorizedRequest.ts new file mode 100644 index 0000000..e4c39af --- /dev/null +++ b/server/src/types/authorizedRequest.ts @@ -0,0 +1,6 @@ +import { Request } from 'express'; +import { IUser } from './interfaces/user'; + +export type AuthorizedRequest = Request & { + user: IUser; +}; diff --git a/server/src/types/dto/score/createScoreDto.ts b/server/src/types/dto/score/createScoreDto.ts new file mode 100644 index 0000000..bff9709 --- /dev/null +++ b/server/src/types/dto/score/createScoreDto.ts @@ -0,0 +1,9 @@ +import { IScore } from '../../interfaces/score'; +import { IUser } from '../../interfaces/user'; + +export type CreateScoreRequestDto = Omit & { + user: IUser; +}; +export type CreateScoreResponseDto = Omit & { + user: Pick; +}; diff --git a/server/src/types/dto/score/getScoreDto.ts b/server/src/types/dto/score/getScoreDto.ts new file mode 100644 index 0000000..b3e5c73 --- /dev/null +++ b/server/src/types/dto/score/getScoreDto.ts @@ -0,0 +1,7 @@ +import { SortFilter } from '../../enums/sortFilters'; + +export type GetScoreRequestDto = { + page?: number; + limit?: number; + sortBy: SortFilter; +}; diff --git a/server/src/types/enums/sortFilters.ts b/server/src/types/enums/sortFilters.ts new file mode 100644 index 0000000..893bbb6 --- /dev/null +++ b/server/src/types/enums/sortFilters.ts @@ -0,0 +1,4 @@ +export enum SortFilter { + DESCENDING = -1, + ASCENDING = 1, +} diff --git a/server/src/types/interfaces/collectionResponse.ts b/server/src/types/interfaces/collectionResponse.ts new file mode 100644 index 0000000..d4f0acb --- /dev/null +++ b/server/src/types/interfaces/collectionResponse.ts @@ -0,0 +1,4 @@ +export interface CollectionResponse { + totalCount: number; + collection: Array; +} From d55110185ebf54a359e1cc6441b9b13faaad3f74 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 22:05:08 +0300 Subject: [PATCH 102/196] feat: create Score controller --- server/src/modules/score/score.controller.ts | 55 ++++++++++++++++++++ 1 file changed, 55 insertions(+) create mode 100644 server/src/modules/score/score.controller.ts diff --git a/server/src/modules/score/score.controller.ts b/server/src/modules/score/score.controller.ts new file mode 100644 index 0000000..b35638f --- /dev/null +++ b/server/src/modules/score/score.controller.ts @@ -0,0 +1,55 @@ +import { + Body, + Controller, + Get, + HttpStatus, + Post, + Query, + Req, + Res, + UseGuards, +} from '@nestjs/common'; +import { ScoreService } from './score.service'; +import { + CreateScoreRequestDto, + CreateScoreResponseDto, +} from '../../types/dto/score/createScoreDto'; +import { JwtAuthGuard } from '../../guards/jwtAuth.guard'; +import { AuthorizedRequest } from '../../types/authorizedRequest'; +import { GetScoreRequestDto } from '../../types/dto/score/getScoreDto'; +import { Response as ExpressResponse } from 'express'; + +@Controller('score') +export class ScoreController { + constructor(private readonly scoreService: ScoreService) {} + + @Get() + @UseGuards(JwtAuthGuard) + async get( + @Req() req: AuthorizedRequest, + @Query() query: GetScoreRequestDto, + @Res() res: ExpressResponse, + ): Promise { + const result = await this.scoreService.findAllByUser( + req.user, + query.sortBy, + query.page, + query.limit, + ); + + res.header('X-Total-Count', result.totalCount.toString()); + res.status(HttpStatus.OK).send([...result.collection]); + } + + @Post() + @UseGuards(JwtAuthGuard) + async create( + @Req() req: AuthorizedRequest, + @Body() score: Omit, + ): Promise { + return await this.scoreService.create({ + ...score, + user: req.user, + }); + } +} From fe5107707997a64fb3d92b5da692a025c827728c Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 22:05:19 +0300 Subject: [PATCH 103/196] feat: create Score module --- server/src/modules/app/app.module.ts | 2 ++ server/src/modules/score/score.module.ts | 19 +++++++++++++++++++ 2 files changed, 21 insertions(+) create mode 100644 server/src/modules/score/score.module.ts diff --git a/server/src/modules/app/app.module.ts b/server/src/modules/app/app.module.ts index 1eb5782..925c99f 100644 --- a/server/src/modules/app/app.module.ts +++ b/server/src/modules/app/app.module.ts @@ -9,6 +9,7 @@ import { AuthValidationMiddleware } from '../../middlewares/authValidation.middl import { AuthController } from '../auth/auth.controller'; import { UserService } from '../user/user.service'; import { User, UserSchema } from '../../models/scheme/user.schema'; +import { ScoreModule } from '../score/score.module'; @Module({ imports: [ @@ -26,6 +27,7 @@ import { User, UserSchema } from '../../models/scheme/user.schema'; MongooseModule.forFeature([{ name: User.name, schema: UserSchema }]), UserModule, AuthModule, + ScoreModule, ], controllers: [AppController], providers: [AppService, UserService], diff --git a/server/src/modules/score/score.module.ts b/server/src/modules/score/score.module.ts new file mode 100644 index 0000000..05e23ba --- /dev/null +++ b/server/src/modules/score/score.module.ts @@ -0,0 +1,19 @@ +import { Module } from '@nestjs/common'; +import { ScoreService } from './score.service'; +import { ScoreController } from './score.controller'; +import { MongooseModule } from '@nestjs/mongoose'; +import { User, UserSchema } from '../../models/scheme/user.schema'; +import { Score, ScoreSchema } from '../../models/scheme/score.schema'; +import { JwtService } from '@nestjs/jwt'; +import { ConfigService } from '@nestjs/config'; +import { UserService } from '../user/user.service'; + +@Module({ + imports: [ + MongooseModule.forFeature([{ name: Score.name, schema: ScoreSchema }]), + MongooseModule.forFeature([{ name: User.name, schema: UserSchema }]), + ], + providers: [ScoreService, JwtService, ConfigService, UserService], + controllers: [ScoreController], +}) +export class ScoreModule {} From 31a17a1df187d7f49199b70ab2e54f9879f5ce87 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 22:05:30 +0300 Subject: [PATCH 104/196] refactor: remove console.log --- server/src/modules/auth/strategies/jwtStrategy.ts | 3 --- 1 file changed, 3 deletions(-) diff --git a/server/src/modules/auth/strategies/jwtStrategy.ts b/server/src/modules/auth/strategies/jwtStrategy.ts index e7a1d81..add80f0 100644 --- a/server/src/modules/auth/strategies/jwtStrategy.ts +++ b/server/src/modules/auth/strategies/jwtStrategy.ts @@ -28,9 +28,6 @@ export class JwtStrategy extends PassportStrategy(Strategy) { throw new UnauthorizedException(); } - console.log(payload); - console.log(targetUser); - return targetUser; } } From 1d5b3b2ad19922910154f691e5c7040bf4f47ded Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 22:20:27 +0300 Subject: [PATCH 105/196] refactor: remove unused dependencies --- server/package-lock.json | 10 +--------- server/package.json | 4 +--- 2 files changed, 2 insertions(+), 12 deletions(-) diff --git a/server/package-lock.json b/server/package-lock.json index 64af101..ca7b01d 100644 --- a/server/package-lock.json +++ b/server/package-lock.json @@ -20,8 +20,7 @@ "cookie-parser": "^1.4.6", "passport-jwt": "^4.0.1", "reflect-metadata": "^0.1.13", - "rxjs": "^7.2.0", - "uuid": "^9.0.0" + "rxjs": "^7.2.0" }, "devDependencies": { "@nestjs/cli": "^9.0.0", @@ -34,7 +33,6 @@ "@types/node": "18.11.18", "@types/passport-jwt": "^3.0.8", "@types/supertest": "^2.0.11", - "@types/uuid": "^9.0.0", "@typescript-eslint/eslint-plugin": "^5.0.0", "@typescript-eslint/parser": "^5.0.0", "eslint": "^8.0.1", @@ -3383,12 +3381,6 @@ "@types/superagent": "*" } }, - "node_modules/@types/uuid": { - "version": "9.0.0", - "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-9.0.0.tgz", - "integrity": "sha512-kr90f+ERiQtKWMz5rP32ltJ/BtULDI5RVO0uavn1HQUOwjx0R1h0rnDYNL0CepF1zL5bSY6FISAfd9tOdDhU5Q==", - "dev": true - }, "node_modules/@types/webidl-conversions": { "version": "7.0.0", "resolved": "https://registry.npmjs.org/@types/webidl-conversions/-/webidl-conversions-7.0.0.tgz", diff --git a/server/package.json b/server/package.json index 50f43d5..0294cac 100644 --- a/server/package.json +++ b/server/package.json @@ -31,8 +31,7 @@ "cookie-parser": "^1.4.6", "passport-jwt": "^4.0.1", "reflect-metadata": "^0.1.13", - "rxjs": "^7.2.0", - "uuid": "^9.0.0" + "rxjs": "^7.2.0" }, "devDependencies": { "@nestjs/cli": "^9.0.0", @@ -45,7 +44,6 @@ "@types/node": "18.11.18", "@types/passport-jwt": "^3.0.8", "@types/supertest": "^2.0.11", - "@types/uuid": "^9.0.0", "@typescript-eslint/eslint-plugin": "^5.0.0", "@typescript-eslint/parser": "^5.0.0", "eslint": "^8.0.1", From 507111d024145dfdf56f49161e920315ace7cb66 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 22:22:02 +0300 Subject: [PATCH 106/196] refactor: remove unused methods in User service --- server/src/modules/user/user.service.ts | 66 +------------------------ 1 file changed, 1 insertion(+), 65 deletions(-) diff --git a/server/src/modules/user/user.service.ts b/server/src/modules/user/user.service.ts index fb284bb..dab0384 100644 --- a/server/src/modules/user/user.service.ts +++ b/server/src/modules/user/user.service.ts @@ -7,7 +7,6 @@ import { UserNotFoundError } from '../../errors/userNotFoundError'; import { UserAlreadyExists } from '../../errors/userAlreadyExists'; import { AuthProvider } from '../../types/enums/authProviders'; import { CreateUserRequestDto } from '../../types/dto/user/createUserDto'; -import { UpdateUserRequestDto } from '../../types/dto/user/updateUserDto'; @Injectable() export class UserService { @@ -25,23 +24,6 @@ export class UserService { return result; } - async findAll(page: number, limit: number): Promise { - const startIndex = (page - 1) * (limit <= 100 ? limit : 100); - return this.userModel.find({}).skip(startIndex).limit(limit).exec(); - } - - async findOne(id: IUser['_id']): Promise { - const result = await this.userModel.findOne({ _id: id }).exec(); - - if (!result) { - throw new UserNotFoundError({ - _id: id, - }); - } - - return result; - } - async findByUserNameAndAuthProvider( username: IUser['username'], authProvider: IUser['authProvider'], @@ -67,54 +49,8 @@ export class UserService { return createdUser.save(); } - async update( - id: IUser['_id'], - newUser: UpdateUserRequestDto, - ): Promise { - const targetUser = await this.userModel.findOne({ _id: id }).exec(); - - if (!targetUser) { - throw new UserNotFoundError({ - _id: id, - ...newUser, - }); - } - - await this.validateUser(newUser, true); - - await targetUser - .update( - { - _id: id, - ...newUser, - }, - { new: true }, - ) - .exec(); - await targetUser.save(); - - return { - _id: id, - ...newUser, - }; - } - - async delete(id: IUser['_id']): Promise { - const targetUser = await this.userModel.findOne({ _id: id }).exec(); - - if (!targetUser) { - throw new UserNotFoundError({ - _id: id, - }); - } - - await targetUser.remove(); - - return targetUser; - } - private async validateUser( - user: CreateUserRequestDto | UpdateUserRequestDto, + user: CreateUserRequestDto, skipDuplicateCheck = false, ): Promise { let duplicate = false; From f308626f24bd1f559762bad9f1670da1b487b054 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 22:22:24 +0300 Subject: [PATCH 107/196] refactor: remove unused controller and service in App module --- server/src/modules/app/app.module.ts | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/server/src/modules/app/app.module.ts b/server/src/modules/app/app.module.ts index 925c99f..7ae63bb 100644 --- a/server/src/modules/app/app.module.ts +++ b/server/src/modules/app/app.module.ts @@ -1,6 +1,4 @@ import { MiddlewareConsumer, Module } from '@nestjs/common'; -import { AppController } from './app.controller'; -import { AppService } from './app.service'; import { MongooseModule } from '@nestjs/mongoose'; import { ConfigModule } from '@nestjs/config'; import { UserModule } from '../user/user.module'; @@ -29,8 +27,7 @@ import { ScoreModule } from '../score/score.module'; AuthModule, ScoreModule, ], - controllers: [AppController], - providers: [AppService, UserService], + providers: [UserService], }) export class AppModule { configure(consumer: MiddlewareConsumer): void { From 7b1fd30adc491852a5a64b7a38c39140e7711d75 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 22:29:32 +0300 Subject: [PATCH 108/196] refactor: remove unused types --- server/src/modules/app/app.controller.ts | 14 -------------- server/src/modules/app/app.service.ts | 8 -------- server/src/types/dto/user/updateUserDto.ts | 3 --- 3 files changed, 25 deletions(-) delete mode 100644 server/src/modules/app/app.controller.ts delete mode 100644 server/src/modules/app/app.service.ts delete mode 100644 server/src/types/dto/user/updateUserDto.ts diff --git a/server/src/modules/app/app.controller.ts b/server/src/modules/app/app.controller.ts deleted file mode 100644 index d6c43da..0000000 --- a/server/src/modules/app/app.controller.ts +++ /dev/null @@ -1,14 +0,0 @@ -import { Controller, Get, UseGuards } from '@nestjs/common'; -import { AppService } from './app.service'; -import { JwtAuthGuard } from '../../guards/jwtAuth.guard'; - -@Controller() -export class AppController { - constructor(private readonly appService: AppService) {} - - @Get() - @UseGuards(JwtAuthGuard) - getHello(): string { - return this.appService.getHello(); - } -} diff --git a/server/src/modules/app/app.service.ts b/server/src/modules/app/app.service.ts deleted file mode 100644 index 927d7cc..0000000 --- a/server/src/modules/app/app.service.ts +++ /dev/null @@ -1,8 +0,0 @@ -import { Injectable } from '@nestjs/common'; - -@Injectable() -export class AppService { - getHello(): string { - return 'Hello World!'; - } -} diff --git a/server/src/types/dto/user/updateUserDto.ts b/server/src/types/dto/user/updateUserDto.ts deleted file mode 100644 index e0ee4d6..0000000 --- a/server/src/types/dto/user/updateUserDto.ts +++ /dev/null @@ -1,3 +0,0 @@ -import { CreateUserRequestDto } from './createUserDto'; - -export type UpdateUserRequestDto = CreateUserRequestDto; From 824ae2876a26c1c7a42d68b7e2914f2c00f98b22 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 23:24:22 +0300 Subject: [PATCH 109/196] feat: create middleware to limit the maximum value of the query parameter limit --- .../collectionLimitLimitation.middleware.ts | 17 +++++++++++++++++ server/src/modules/app/app.module.ts | 2 ++ 2 files changed, 19 insertions(+) create mode 100644 server/src/middlewares/collectionLimitLimitation.middleware.ts diff --git a/server/src/middlewares/collectionLimitLimitation.middleware.ts b/server/src/middlewares/collectionLimitLimitation.middleware.ts new file mode 100644 index 0000000..866df9c --- /dev/null +++ b/server/src/middlewares/collectionLimitLimitation.middleware.ts @@ -0,0 +1,17 @@ +import { Injectable, NestMiddleware } from '@nestjs/common'; +import { NextFunction, Request, Response } from 'express'; +import * as process from 'process'; + +@Injectable() +export class CollectionLimitLimitationMiddleware implements NestMiddleware { + use(req: Request, res: Response, next: NextFunction): void { + const max = process.env.MAX_COLLECTION_LIMIT || 100; + const limit = req.query.limit; + + if (limit && req.query.limit) { + req.query.limit = (Number(limit) <= max ? Number(limit) : max).toString(); + } + + next(); + } +} diff --git a/server/src/modules/app/app.module.ts b/server/src/modules/app/app.module.ts index 7ae63bb..846ffe5 100644 --- a/server/src/modules/app/app.module.ts +++ b/server/src/modules/app/app.module.ts @@ -8,6 +8,7 @@ import { AuthController } from '../auth/auth.controller'; import { UserService } from '../user/user.service'; import { User, UserSchema } from '../../models/scheme/user.schema'; import { ScoreModule } from '../score/score.module'; +import { CollectionLimitLimitationMiddleware } from '../../middlewares/collectionLimitLimitation.middleware'; @Module({ imports: [ @@ -31,6 +32,7 @@ import { ScoreModule } from '../score/score.module'; }) export class AppModule { configure(consumer: MiddlewareConsumer): void { + consumer.apply(CollectionLimitLimitationMiddleware).forRoutes('*'); consumer.apply(AuthValidationMiddleware).forRoutes(AuthController); } } From bf6999d49af0ab15fadf8315100084fd560b2967 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 23:26:38 +0300 Subject: [PATCH 110/196] refactor: move getScoreDto type into generic collectionDto --- server/src/modules/score/score.controller.ts | 4 ++-- server/src/types/dto/collectionDto.ts | 7 +++++++ server/src/types/dto/score/getScoreDto.ts | 7 ------- 3 files changed, 9 insertions(+), 9 deletions(-) create mode 100644 server/src/types/dto/collectionDto.ts delete mode 100644 server/src/types/dto/score/getScoreDto.ts diff --git a/server/src/modules/score/score.controller.ts b/server/src/modules/score/score.controller.ts index b35638f..0178ca3 100644 --- a/server/src/modules/score/score.controller.ts +++ b/server/src/modules/score/score.controller.ts @@ -16,8 +16,8 @@ import { } from '../../types/dto/score/createScoreDto'; import { JwtAuthGuard } from '../../guards/jwtAuth.guard'; import { AuthorizedRequest } from '../../types/authorizedRequest'; -import { GetScoreRequestDto } from '../../types/dto/score/getScoreDto'; import { Response as ExpressResponse } from 'express'; +import { CollectionRequestDto } from '../../types/dto/collectionDto'; @Controller('score') export class ScoreController { @@ -27,7 +27,7 @@ export class ScoreController { @UseGuards(JwtAuthGuard) async get( @Req() req: AuthorizedRequest, - @Query() query: GetScoreRequestDto, + @Query() query: CollectionRequestDto, @Res() res: ExpressResponse, ): Promise { const result = await this.scoreService.findAllByUser( diff --git a/server/src/types/dto/collectionDto.ts b/server/src/types/dto/collectionDto.ts new file mode 100644 index 0000000..4615dfa --- /dev/null +++ b/server/src/types/dto/collectionDto.ts @@ -0,0 +1,7 @@ +import { SortFilter } from '../enums/sortFilters'; + +export type CollectionRequestDto = { + page?: number; + limit?: number; + sortBy: SortFilter; +}; diff --git a/server/src/types/dto/score/getScoreDto.ts b/server/src/types/dto/score/getScoreDto.ts deleted file mode 100644 index b3e5c73..0000000 --- a/server/src/types/dto/score/getScoreDto.ts +++ /dev/null @@ -1,7 +0,0 @@ -import { SortFilter } from '../../enums/sortFilters'; - -export type GetScoreRequestDto = { - page?: number; - limit?: number; - sortBy: SortFilter; -}; From df0b312f1bc40772180f546a29d4f89a2f2520cc Mon Sep 17 00:00:00 2001 From: HardManDev Date: Thu, 16 Feb 2023 23:27:38 +0300 Subject: [PATCH 111/196] feat: create Leaderboard module with service and controller --- server/src/modules/app/app.module.ts | 2 ++ .../leaderboard/leaderboard.controller.ts | 24 +++++++++++++ .../modules/leaderboard/leaderboard.module.ts | 14 ++++++++ .../leaderboard/leaderboard.service.ts | 36 +++++++++++++++++++ 4 files changed, 76 insertions(+) create mode 100644 server/src/modules/leaderboard/leaderboard.controller.ts create mode 100644 server/src/modules/leaderboard/leaderboard.module.ts create mode 100644 server/src/modules/leaderboard/leaderboard.service.ts diff --git a/server/src/modules/app/app.module.ts b/server/src/modules/app/app.module.ts index 846ffe5..0511755 100644 --- a/server/src/modules/app/app.module.ts +++ b/server/src/modules/app/app.module.ts @@ -9,6 +9,7 @@ import { UserService } from '../user/user.service'; import { User, UserSchema } from '../../models/scheme/user.schema'; import { ScoreModule } from '../score/score.module'; import { CollectionLimitLimitationMiddleware } from '../../middlewares/collectionLimitLimitation.middleware'; +import { LeaderboardModule } from '../leaderboard/leaderboard.module'; @Module({ imports: [ @@ -27,6 +28,7 @@ import { CollectionLimitLimitationMiddleware } from '../../middlewares/collectio UserModule, AuthModule, ScoreModule, + LeaderboardModule, ], providers: [UserService], }) diff --git a/server/src/modules/leaderboard/leaderboard.controller.ts b/server/src/modules/leaderboard/leaderboard.controller.ts new file mode 100644 index 0000000..85fbdc9 --- /dev/null +++ b/server/src/modules/leaderboard/leaderboard.controller.ts @@ -0,0 +1,24 @@ +import { Controller, Get, HttpStatus, Query, Res } from '@nestjs/common'; +import { Response as ExpressResponse } from 'express'; +import { LeaderboardService } from './leaderboard.service'; +import { CollectionRequestDto } from '../../types/dto/collectionDto'; + +@Controller('leaderboard') +export class LeaderboardController { + constructor(private readonly leaderboardService: LeaderboardService) {} + + @Get() + async get( + @Query() query: CollectionRequestDto, + @Res() res: ExpressResponse, + ): Promise { + const result = await this.leaderboardService.findAll( + query.sortBy, + query.page, + query.limit, + ); + + res.header('X-Total-Count', result.totalCount.toString()); + res.status(HttpStatus.OK).send([...result.collection]); + } +} diff --git a/server/src/modules/leaderboard/leaderboard.module.ts b/server/src/modules/leaderboard/leaderboard.module.ts new file mode 100644 index 0000000..f9022b9 --- /dev/null +++ b/server/src/modules/leaderboard/leaderboard.module.ts @@ -0,0 +1,14 @@ +import { Module } from '@nestjs/common'; +import { LeaderboardService } from './leaderboard.service'; +import { LeaderboardController } from './leaderboard.controller'; +import { MongooseModule } from '@nestjs/mongoose'; +import { Score, ScoreSchema } from '../../models/scheme/score.schema'; + +@Module({ + imports: [ + MongooseModule.forFeature([{ name: Score.name, schema: ScoreSchema }]), + ], + providers: [LeaderboardService], + controllers: [LeaderboardController], +}) +export class LeaderboardModule {} diff --git a/server/src/modules/leaderboard/leaderboard.service.ts b/server/src/modules/leaderboard/leaderboard.service.ts new file mode 100644 index 0000000..4cb367e --- /dev/null +++ b/server/src/modules/leaderboard/leaderboard.service.ts @@ -0,0 +1,36 @@ +import { Injectable } from '@nestjs/common'; +import { InjectModel } from '@nestjs/mongoose'; +import { Score } from '../../models/scheme/score.schema'; +import { Model } from 'mongoose'; +import { CollectionResponse } from '../../types/interfaces/collectionResponse'; +import { IScore } from '../../types/interfaces/score'; +import { SortFilter } from '../../types/enums/sortFilters'; + +@Injectable() +export class LeaderboardService { + constructor( + @InjectModel(Score.name) private readonly scoreModel: Model, + ) {} + + async findAll( + sorter: SortFilter = SortFilter.DESCENDING, + page = 1, + limit = 100, + ): Promise> { + const result = await this.scoreModel + .find({}) + .sort({ score: sorter }) + .skip(limit * (page - 1)) + .limit(limit) + .populate({ + path: 'user', + select: '-password -createdAt', + }) + .exec(); + + return { + totalCount: await this.scoreModel.count(), + collection: result, + }; + } +} From 9c3fd125701f3a7da92d40114ef254ce3a02e350 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Mon, 20 Feb 2023 19:27:36 +0300 Subject: [PATCH 112/196] refactor: add geometry class, reduce length of methods --- client/src/scripts/components/game.ts | 2 +- client/src/scripts/controllers/geometry.ts | 124 ++++ client/src/scripts/controllers/playLevel.ts | 768 ++++++++------------ client/src/styles/crone.css | 38 +- client/src/styles/zombie.css | 42 +- client/src/types/game.ts | 18 + 6 files changed, 466 insertions(+), 526 deletions(-) create mode 100644 client/src/scripts/controllers/geometry.ts diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 8eef805..5054887 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -342,7 +342,7 @@ class GameView { createMeatExplosion(monsterRect: Rect): void { for (let i = 0; i <= 3; i += 1) { const randDX = 2 + Math.round(Math.random() * 3); - const dXs: number[] = [randDX, randDX + 3, randDX, randDX - 3]; + const dXs: number[] = [-randDX, -randDX - 3, randDX, randDX - 3]; const meatPart: Meat = { area: { x: monsterRect.x, diff --git a/client/src/scripts/controllers/geometry.ts b/client/src/scripts/controllers/geometry.ts new file mode 100644 index 0000000..7afcf21 --- /dev/null +++ b/client/src/scripts/controllers/geometry.ts @@ -0,0 +1,124 @@ +import { + Line, Movement, Offset, Rect, +} from '../../types/game'; + +class Geometry { + static getXOffset(move: Movement): Offset { + return [move.x.diff, 0]; + } + + static getXYOffset(move: Movement): Offset { + const v: number = move.y.velocity; + return [move.x.diff, v > 0 ? v * 2 + 2 : v * 2 - 2]; + } + + static getCrossWithPlatforms( + platforms: Rect[], + rectCommon: Rect, + rectStart: Rect, + ): Rect[] { + const crossPlatforms: Rect[] = []; + for (let i = 0; i < platforms.length; i += 1) { + if ( + rectCommon.x < platforms[i].x + + platforms[i].w + && rectCommon.x + rectCommon.w > platforms[i].x + && rectCommon.y < platforms[i].y + + platforms[i].h + && rectCommon.h + rectCommon.y > platforms[i].y + && rectStart.x < platforms[i].x + + platforms[i].w + && rectStart.x + rectStart.w > platforms[i].x + && rectStart.y + rectStart.h <= platforms[i].y + ) { + crossPlatforms.push(platforms[i]); + } + } + return crossPlatforms; + } + + static getCrossWithWalls(walls: Rect[], rectCommon: Rect): Rect[] { + const crossWalls: Rect[] = []; + for (let i = 0; i < walls.length; i += 1) { + if (Geometry.isRectCrossWithRect(rectCommon, walls[i])) { + crossWalls.push(walls[i]); + } + } + return crossWalls; + } + + static isLineCrossLine(line1: Line, line2: Line): boolean { + const x2x1: number = line1.x2 - line1.x1; + const x4x3: number = line2.x2 - line2.x1; + const y2y1: number = line1.y2 - line1.y1; + const y4y3: number = line2.y2 - line2.y1; + const x1x3: number = line1.x1 - line2.x1; + const y1y3: number = line1.y1 - line2.y1; + const d: number = (y4y3 * x2x1 - x4x3 * y2y1); + const uA: number = (x4x3 * y1y3 - y4y3 * x1x3) / d; + const uB: number = (x2x1 * y1y3 - y2y1 * x1x3) / d; + if (uA >= 0 && uA <= 1 && uB >= 0 && uB <= 1) { + return true; + } + return false; + } + + static isLineCrossRect(line: Line, rect: Rect): boolean { + const left: boolean = this.isLineCrossLine( + line, + { + x1: rect.x, + y1: rect.y, + x2: rect.x, + y2: rect.y + rect.h, + }, + ); + const right: boolean = this.isLineCrossLine( + line, + { + x1: rect.x + rect.w, + y1: rect.y, + x2: rect.x + rect.w, + y2: rect.y + rect.h, + }, + ); + const top: boolean = this.isLineCrossLine( + line, + { + x1: rect.x, + y1: rect.y, + x2: rect.x + rect.w, + y2: rect.y, + }, + ); + const bottom: boolean = this.isLineCrossLine( + line, + { + x1: rect.x, + y1: rect.y + rect.h, + x2: rect.x + rect.w, + y2: rect.y + rect.h, + }, + ); + return !!((left || right || top || bottom)); + } + + static isRectCrossWithRect(rect1: Rect, rect2: Rect): boolean { + return !!((rect1.x < rect2.x + rect2.w + && rect1.x + rect1.w > rect2.x + && rect1.y < rect2.y + rect2.h + && rect1.h + rect1.y > rect2.y + )); + } + + static getRectAfterOffset(rect: Rect, offset: Offset): Rect { + return { + x: rect.x + ((offset[0] < 0) ? offset[0] : 0), + y: rect.y + ((offset[1] < 0) ? offset[1] : 0), + w: rect.w + ((offset[0] > 0) ? offset[0] : 0), + h: rect.h + ((offset[1] > 0) ? offset[1] : 0), + }; + } +} + +export default Geometry; diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index cedc52f..008aea7 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -1,6 +1,7 @@ /* eslint-disable class-methods-use-this */ import { - Line, ObjectState, Offset, Position, Rect, SoundType, + Barrier, + Line, MoveAxis, Movement, ObjectState, Offset, Position, Rect, SoundType, } from '../../types/game'; import { DaveLook, DaveMove, DaveShoot, DaveState, @@ -12,7 +13,7 @@ import { BulletMove, Meat, MonsterAttack, MonsterMove, MonsterState, } from '../../types/monster'; import Crone from '../components/crone'; -import Direction from '../../types/enums/directions'; +import Geometry from './geometry'; class PlayLevel { gameView: GameView; @@ -41,165 +42,67 @@ class PlayLevel { this.animateMonsters(); } - getHorizontalDiffMovingLeftRight(): Offset { - let dX = 0; - if (this.dave.move === DaveMove.RIGHT) { - dX = this.dave.stepSize; - } else if (this.dave.move === DaveMove.LEFT) { - dX = -this.dave.stepSize; - } - if (this.isCrossWithWalls({ - x: this.dave.x + ((dX < 0) ? dX : 0), - y: this.dave.y, - w: this.dave.w + ((dX > 0) ? dX : 0), - h: this.dave.h, - }).length === 0) { - return [dX, 0]; + getXOffsetCorrected(offset: Offset): Offset { + if (Geometry.getCrossWithWalls( + this.gameView.walls, + Geometry.getRectAfterOffset(this.dave, offset), + ).length === 0) { + return offset; } return [0, 0]; } - getDiffFalling(): Offset { - let dX = 0; - let dY = 0; - dY = this.dave.velocity * 2 + 2; - if (this.dave.move === DaveMove.RIGHT) { - dX = this.dave.stepSize; - } else if (this.dave.move === DaveMove.LEFT) { - dX = -this.dave.stepSize; - } - this.dave.velocity += 0.5; - const walls: Rect[] = this.isCrossWithWalls({ - x: this.dave.x + ((dX < 0) ? dX : 0), - y: this.dave.y + ((dY < 0) ? dY : 0), - w: this.dave.w + ((dX > 0) ? dX : 0), - h: this.dave.h + ((dY > 0) ? dY : 0), - }); - const platforms: Rect[] = this.isCrossWithPlatforms( - { - x: this.dave.x + ((dX < 0) ? dX : 0), - y: this.dave.y + ((dY < 0) ? dY : 0), - w: this.dave.w + ((dX > 0) ? dX : 0), - h: this.dave.h + ((dY > 0) ? dY : 0), - }, - { - x: this.dave.x, - y: this.dave.w, - w: this.dave.y, - h: this.dave.h, - }, + getIntersectRectsWhenFalling(offset: Offset): Rect[] { + const walls: Rect[] = Geometry.getCrossWithWalls( + this.gameView.walls, + Geometry.getRectAfterOffset(this.dave, offset), + ); + const platforms: Rect[] = Geometry.getCrossWithPlatforms( + this.gameView.platforms, + Geometry.getRectAfterOffset(this.dave, offset), + this.dave, ); if (platforms.length) { walls.push(...platforms); } - - if (walls.length !== 0) { - let wallUnder: Rect | null = null; - let wallLeft: Rect | null = null; - let wallRight: Rect | null = null; - for (let i = 0; i < walls.length; i += 1) { - if (this.dave.x < walls[i].x + walls[i].w - && this.dave.x + this.dave.w > walls[i].x - && this.dave.y + this.dave.h <= walls[i].y) { - wallUnder = walls[i]; - } - if (dX > 0 && this.dave.x + dX + this.dave.w >= walls[i].x) { - wallRight = walls[i]; - } - if (dX < 0 && this.dave.x + dX <= walls[i].x + walls[i].w) { - wallLeft = walls[i]; - } - } - if (wallUnder) { - this.gameView.sounds[SoundType.LAND].play(); - dY = wallUnder.y - this.dave.h - this.dave.y; - this.dave.state = this.dave.move === DaveMove.NONE - ? DaveState.STANDING - : DaveState.RUNNING; - this.dave.velocity = 0; - if ((wallRight && dX > 0) || (wallLeft && dX < 0)) { - dX = 0; - } - } else { - dX = 0; - } - } - return [dX, dY]; + return walls; } - getDiffJumping(): Offset { - let dX = 0; - let dY = 0; - dY = -this.dave.velocity * 2 - 2; - if (this.dave.move === DaveMove.RIGHT) { - dX = this.dave.stepSize; - } else if (this.dave.move === DaveMove.LEFT) { - dX = -this.dave.stepSize; + getBarriers(rect: Rect, offset: Offset, move: Movement): Barrier { + const walls: Rect[] = Geometry.getCrossWithWalls( + this.gameView.walls, + Geometry.getRectAfterOffset(rect, offset), + ); + if (move.y.velocity > 0) { + const platforms: Rect[] = Geometry.getCrossWithPlatforms( + this.gameView.platforms, + Geometry.getRectAfterOffset(rect, offset), + rect, + ); + if (platforms.length) { + walls.push(...platforms); + } } - - this.dave.velocity -= 0.5; - const walls: Rect[] = this.isCrossWithWalls({ - x: this.dave.x + ((dX < 0) ? dX : 0), - y: this.dave.y + ((dY < 0) ? dY : 0), - w: this.dave.w + ((dX > 0) ? dX : 0), - h: this.dave.h + ((dY > 0) ? dY : 0), - }); - if (walls.length !== 0) { - let wallAbove: Rect | null = null; - let wallLeft: Rect | null = null; - let wallRight: Rect | null = null; - for (let i = 0; i < walls.length; i += 1) { - if (this.dave.x < walls[i].x + walls[i].w - && this.dave.x + this.dave.w > walls[i].x - && this.dave.y >= walls[i].y + walls[i].h) { - wallAbove = walls[i]; - } - if (dX > 0 && this.dave.x + dX + this.dave.w >= walls[i].x) { - wallRight = walls[i]; - } - if (dX < 0 && this.dave.x + dX <= walls[i].x + walls[i].w) { - wallLeft = walls[i]; - } + const barrier: Barrier = {}; + for (let i = 0; i < walls.length; i += 1) { + if (rect.x < walls[i].x + walls[i].w + && rect.x + rect.w > walls[i].x + && rect.y + rect.h <= walls[i].y) { + barrier.below = walls[i]; } - if (wallAbove) { - dY = wallAbove.y + wallAbove.h - this.dave.y; - this.dave.state = DaveState.FALLING; - this.dave.velocity = 0; - if ((wallRight && dX > 0) || (wallLeft && dX < 0)) { - dX = 0; - } - } else { - dX = 0; + if (rect.x < walls[i].x + walls[i].w + && rect.x + rect.w > walls[i].x + && rect.y >= walls[i].y + walls[i].h) { + barrier.above = walls[i]; + } + if (offset[0] > 0 && rect.x + offset[0] + rect.w >= walls[i].x) { + barrier.right = walls[i]; + } + if (offset[0] < 0 && rect.x + offset[0] <= walls[i].x + walls[i].w) { + barrier.left = walls[i]; } } - if (this.dave.velocity === 0) { - this.dave.state = DaveState.FALLING; - } - return [dX, dY]; - } - - getDiffStartJumpingDown(): Offset { - let dX = 0; - let dY = this.dave.velocity * 2 + 2; - if (this.dave.move === DaveMove.RIGHT) { - dX = this.dave.stepSize; - } else if (this.dave.move === DaveMove.LEFT) { - dX = -this.dave.stepSize; - } - this.dave.state = DaveState.STANDING; - this.dave.velocity += 0.5; - const walls: Rect[] = this.isCrossWithWalls({ - x: this.dave.x + ((dX < 0) ? dX : 0), - y: this.dave.y + ((dY < 0) ? dY : 0), - w: this.dave.w + ((dX > 0) ? dX : 0), - h: this.dave.h + ((dY > 0) ? dY : 0), - }); - if (walls.length === 0) { - this.dave.state = DaveState.FALLING; - } else { - dY = 0; - } - return [dX, dY]; + return barrier; } getDiffShooting(): Offset { @@ -209,12 +112,10 @@ class PlayLevel { } else if (this.dave.look === DaveLook.RIGHT) { dX = -this.dave.stepSize; } - if (this.isCrossWithWalls({ - x: this.dave.x + ((dX < 0) ? dX : 0), - y: this.dave.y, - w: this.dave.w + ((dX > 0) ? dX : 0), - h: this.dave.h, - }).length === 0) { + if (Geometry.getCrossWithWalls( + this.gameView.walls, + Geometry.getRectAfterOffset(this.dave, [dX, 0]), + ).length === 0) { return [dX, 0]; } return [0, 0]; @@ -233,20 +134,84 @@ class PlayLevel { if (this.dave.state !== DaveState.STANDING && this.dave.state !== DaveState.RECHARGING) { this.resetReloadAnimation(); + const emptyMove: MoveAxis = { diff: 0, accel: false, velocity: 0 }; + const move: Movement = { x: emptyMove, y: emptyMove }; + if (this.dave.move === DaveMove.RIGHT) { + move.x.diff = this.dave.stepSize; + } else if (this.dave.move === DaveMove.LEFT) { + move.x.diff = -this.dave.stepSize; + } let dX = 0; let dY = 0; if (this.dave.state === DaveState.RUNNING) { if (this.isDaveHasToFall()) { this.dave.state = DaveState.FALLING; } else { - [dX, dY] = this.getHorizontalDiffMovingLeftRight(); + [dX, dY] = this.getXOffsetCorrected(Geometry.getXOffset(move)); } } else if (this.dave.state === DaveState.FALLING) { - [dX, dY] = this.getDiffFalling(); + move.y.velocity = this.dave.velocity; + move.y.accel = true; + + [dX, dY] = Geometry.getXYOffset(move); + const barrier: Barrier = this.getBarriers( + this.dave, + [dX, dY], + move, + ); + if (barrier.below) { + this.gameView.sounds[SoundType.LAND].play(); + dY = barrier.below.y - this.dave.h - this.dave.y; + this.dave.state = this.dave.move === DaveMove.NONE + ? DaveState.STANDING + : DaveState.RUNNING; + this.dave.velocity = 0; + if ((barrier.right && dX > 0) || (barrier.left && dX < 0)) { + dX = 0; + } + } else if (barrier.left || barrier.right) { + dX = 0; + } + this.dave.velocity += 0.5; } else if (this.dave.state === DaveState.JUMPING_UP) { - [dX, dY] = this.getDiffJumping(); + move.y.velocity = -this.dave.velocity; + move.y.accel = true; + [dX, dY] = Geometry.getXYOffset(move); + this.dave.velocity -= 0.5; + const barrier: Barrier = this.getBarriers( + this.dave, + [dX, dY], + move, + ); + if (barrier.above) { + dY = barrier.above.y + barrier.above.h - this.dave.y; + this.dave.state = DaveState.FALLING; + this.dave.velocity = 0; + if ((barrier.right && dX > 0) || (barrier.left && dX < 0)) { + dX = 0; + } + } else if (barrier.left || barrier.right) { + dX = 0; + } + if (this.dave.velocity === 0) { + this.dave.state = DaveState.FALLING; + } } else if (this.dave.state === DaveState.JUMPING_DOWN) { - [dX, dY] = this.getDiffStartJumpingDown(); + move.y.velocity = this.dave.velocity; + move.y.accel = true; + [dX, dY] = Geometry.getXYOffset(move); + + this.dave.velocity += 0.5; + const walls: Rect[] = Geometry.getCrossWithWalls( + this.gameView.walls, + Geometry.getRectAfterOffset(this.dave, [dX, dY]), + ); + if (walls.length === 0) { + this.dave.state = DaveState.FALLING; + } else { + dY = 0; + this.dave.state = DaveState.STANDING; + } } else if (this.dave.state === DaveState.SHOOTING) { [dX, dY] = this.getDiffShooting(); } @@ -299,7 +264,10 @@ class PlayLevel { if (!this.gameView.godMode && this.checkAttackDave(fullRect)) { this.daveGoesDead(); } - if (this.isCrossWithWalls(fullRect).length === 0) { + if (Geometry.getCrossWithWalls( + this.gameView.walls, + fullRect, + ).length === 0) { (monster).moveBullet(bullet, [dX, dY]); } else { (monster).removeBullet(bullet); @@ -319,135 +287,68 @@ class PlayLevel { this.gameView.meat.forEach((meatPart) => { let dX = 0; let dY = 0; + const emptyMove: MoveAxis = { diff: 0, accel: false, velocity: 0 }; + const move: Movement = { x: emptyMove, y: emptyMove }; + move.x.diff = meatPart.dX; if (meatPart.state !== ObjectState.STANDING) { if (meatPart.state === ObjectState.JUMPING_UP) { - [dX, dY] = this.getDiffMeatJumping(meatPart); + move.y.velocity = -meatPart.velocity; + move.y.accel = true; + [dX, dY] = Geometry.getXYOffset(move); + meatPart.velocity -= 0.5; + const bar: Barrier = this.getBarriers(meatPart.area, [dX, dY], move); + [dX, dY] = this.getXYBArrier(meatPart.area, bar, [dX, dY]); + if (bar.above) { + meatPart.state = ObjectState.FALLING; + meatPart.velocity = 0; + } + if (meatPart.velocity === 0) { + meatPart.state = ObjectState.FALLING; + } } else if (meatPart.state === ObjectState.FALLING) { - [dX, dY] = this.getDiffMeatFalling(meatPart); + move.y.velocity = meatPart.velocity; + move.y.accel = true; + + [dX, dY] = Geometry.getXYOffset(move); + const bar: Barrier = this.getBarriers(meatPart.area, [dX, dY], move); + [dX, dY] = this.getXYBArrier(meatPart.area, bar, [dX, dY]); + if (bar.below) { + meatPart.state = ObjectState.STANDING; + meatPart.velocity = 0; + } + meatPart.velocity += 0.5; } this.gameView.moveMeatPart(meatPart, [dX, dY]); - } else if (!meatPart.animationTimer) { - meatPart.animationTimer = window.setTimeout(() => { - this.gameView.removeMeatPart(meatPart); - clearTimeout(meatPart.animationTimer); - }, 1000 + Math.round(Math.random() * 500)); + } else { + this.setMeatAnimation(meatPart); } }); } - getDiffMeatJumping(obj: Meat): Offset { - let dX = 0; - let dY = 0; - dY = -obj.velocity * 2 - 2; - if (obj.movedDir === Direction.RIGHT) { - dX = obj.dX; - } else if (obj.movedDir === Direction.LEFT) { - dX = -obj.dX; - } - - obj.velocity -= 0.5; - const walls: Rect[] = this.isCrossWithWalls({ - x: obj.area.x + ((dX < 0) ? dX : 0), - y: obj.area.y + ((dY < 0) ? dY : 0), - w: obj.area.w + ((dX > 0) ? dX : 0), - h: obj.area.h + ((dY > 0) ? dY : 0), - }); - if (walls.length !== 0) { - let wallAbove: Rect | null = null; - let wallLeft: Rect | null = null; - let wallRight: Rect | null = null; - for (let i = 0; i < walls.length; i += 1) { - if (obj.area.x < walls[i].x + walls[i].w - && obj.area.x + obj.area.w > walls[i].x - && obj.area.y >= walls[i].y + walls[i].h) { - wallAbove = walls[i]; - } - if (dX > 0 && obj.area.x + dX + obj.area.w >= walls[i].x) { - wallRight = walls[i]; - } - if (dX < 0 && obj.area.x + dX <= walls[i].x + walls[i].w) { - wallLeft = walls[i]; - } - } - if (wallAbove) { - dY = wallAbove.y + wallAbove.h - obj.area.y; - obj.state = ObjectState.FALLING; - obj.velocity = 0; - if ((wallRight && dX > 0) || (wallLeft && dX < 0)) { - dX = 0; - } - } else { - dX = 0; - } + setMeatAnimation(meatPart: Meat): void { + if (!meatPart.animationTimer) { + meatPart.animationTimer = window.setTimeout(() => { + this.gameView.removeMeatPart(meatPart); + clearTimeout(meatPart.animationTimer); + }, 1000 + Math.round(Math.random() * 500)); } - if (obj.velocity === 0) { - obj.state = ObjectState.FALLING; - } - return [dX, dY]; } - getDiffMeatFalling(obj: Meat): Offset { - let dX = 0; - let dY = 0; - dY = obj.velocity * 2 + 2; - if (obj.movedDir === Direction.RIGHT) { - dX = obj.dX; - } else if (obj.movedDir === Direction.LEFT) { - dX = -obj.dX; - } - obj.velocity += 0.5; - const walls: Rect[] = this.isCrossWithWalls({ - x: obj.area.x + ((dX < 0) ? dX : 0), - y: obj.area.y + ((dY < 0) ? dY : 0), - w: obj.area.w + ((dX > 0) ? dX : 0), - h: obj.area.h + ((dY > 0) ? dY : 0), - }); - const platforms: Rect[] = this.isCrossWithPlatforms( - { - x: obj.area.x + ((dX < 0) ? dX : 0), - y: obj.area.y + ((dY < 0) ? dY : 0), - w: obj.area.w + ((dX > 0) ? dX : 0), - h: obj.area.h + ((dY > 0) ? dY : 0), - }, - { - x: obj.area.x, - y: obj.area.w, - w: obj.area.y, - h: obj.area.h, - }, - ); - if (platforms.length) { - walls.push(...platforms); - } - - if (walls.length !== 0) { - let wallUnder: Rect | null = null; - let wallLeft: Rect | null = null; - let wallRight: Rect | null = null; - for (let i = 0; i < walls.length; i += 1) { - if (obj.area.x < walls[i].x + walls[i].w - && obj.area.x + obj.area.w > walls[i].x - && obj.area.y + obj.area.h <= walls[i].y) { - wallUnder = walls[i]; - } - if (dX > 0 && obj.area.x + dX + obj.area.w >= walls[i].x) { - wallRight = walls[i]; - } - if (dX < 0 && obj.area.x + dX <= walls[i].x + walls[i].w) { - wallLeft = walls[i]; - } + getXYBArrier(area: Rect, barrier: Barrier, offset: Offset): Offset { + let dX = offset[0]; + let dY = offset[1]; + if (barrier.above) { + dY = barrier.above.y + barrier.above.h - area.y; + if ((barrier.right && dX > 0) || (barrier.left && dX < 0)) { + dX = 0; } - if (wallUnder) { - this.gameView.sounds[SoundType.LAND].play(); - dY = wallUnder.y - obj.area.h - obj.area.y; - obj.state = ObjectState.STANDING; - obj.velocity = 0; - if ((wallRight && dX > 0) || (wallLeft && dX < 0)) { - dX = 0; - } - } else { + } else if (barrier.below) { + dY = barrier.below.y - area.h - area.y; + if ((barrier.right && dX > 0) || (barrier.left && dX < 0)) { dX = 0; } + } else if (barrier.left || barrier.right) { + dX = 0; } return [dX, dY]; } @@ -465,7 +366,7 @@ class PlayLevel { checkLoot(): void { this.gameView.loot.forEach((loot) => { - if (!loot.grabbed && this.isRectCrossWithRect(loot.area, this.dave)) { + if (!loot.grabbed && Geometry.isRectCrossWithRect(loot.area, this.dave)) { this.gameView.grabLoot(loot); this.gameView.sounds[SoundType.BONUS1].play(); } @@ -473,64 +374,23 @@ class PlayLevel { } checkAttackDave(bullet: Rect): boolean { - return !!this.isRectCrossWithRect(bullet, this.dave); - } - - isRectCrossWithRect(rect1: Rect, rect2: Rect): boolean { - return !!((rect1.x < rect2.x + rect2.w - && rect1.x + rect1.w > rect2.x - && rect1.y < rect2.y + rect2.h - && rect1.h + rect1.y > rect2.y - )); - } - - isCrossWithWalls(rectCommon: Rect): Rect[] { - const crossWalls: Rect[] = []; - for (let i = 0; i < this.gameView.walls.length; i += 1) { - if (this.isRectCrossWithRect(rectCommon, this.gameView.walls[i])) { - crossWalls.push(this.gameView.walls[i]); - } - } - return crossWalls; - } - - isCrossWithPlatforms(rectCommon: Rect, rectStart: Rect): Rect[] { - const crossPlatforms: Rect[] = []; - for (let i = 0; i < this.gameView.platforms.length; i += 1) { - if ( - rectCommon.x < this.gameView.platforms[i].x - + this.gameView.platforms[i].w - && rectCommon.x + rectCommon.w > this.gameView.platforms[i].x - && rectCommon.y < this.gameView.platforms[i].y - + this.gameView.platforms[i].h - && rectCommon.h + rectCommon.y > this.gameView.platforms[i].y - && rectStart.x < this.gameView.platforms[i].x - + this.gameView.platforms[i].w - && rectStart.x + rectStart.w > this.gameView.platforms[i].x - && rectStart.y + rectStart.h <= this.gameView.platforms[i].y - ) { - crossPlatforms.push(this.gameView.platforms[i]); - } - } - return crossPlatforms; + return !!Geometry.isRectCrossWithRect(bullet, this.dave); } isDaveHasToFall(): boolean { - const underWalls: Rect[] = this.isCrossWithWalls( - { - x: this.dave.x, - y: this.dave.y + this.dave.h, - w: this.dave.w, - h: 1, - }, + const daveRect: Rect = { + x: this.dave.x, + y: this.dave.y + this.dave.h, + w: this.dave.w, + h: 1, + }; + const underWalls: Rect[] = Geometry.getCrossWithWalls( + this.gameView.walls, + daveRect, ); - const underPlatforms: Rect[] = this.isCrossWithPlatforms( - { - x: this.dave.x, - y: this.dave.y + this.dave.h, - w: this.dave.w, - h: 1, - }, + const underPlatforms: Rect[] = Geometry.getCrossWithPlatforms( + this.gameView.platforms, + daveRect, { x: this.dave.x, y: this.dave.y, @@ -582,7 +442,7 @@ class PlayLevel { let foundDoor = false; this.gameView.doors.forEach((door) => { if (!door.opened - && this.isRectCrossWithRect(door.area, this.dave)) { + && Geometry.isRectCrossWithRect(door.area, this.dave)) { this.gameView.openDoor(door); foundDoor = true; } @@ -697,55 +557,24 @@ class PlayLevel { } else if (monster.moveDir === MonsterMove.LEFT) { dX = -monster.stepSize; } - if (this.isCrossWithWalls({ - x: monster.x + ((dX < 0) ? dX : 0), - y: monster.y, - w: monster.w + ((dX > 0) ? dX : 0), - h: monster.h, - }).length === 0) { + if (Geometry.getCrossWithWalls( + this.gameView.walls, + { + x: monster.x + ((dX < 0) ? dX : 0), + y: monster.y, + w: monster.w + ((dX > 0) ? dX : 0), + h: monster.h, + }, + ).length === 0) { const daveIsNear: Position = this.isDaveNearMonster(monster); const whereIsDave: Position = this.isDaveVisibleToMonster(monster); if (monster instanceof Crone) { - const shootOrNot: boolean = Math.random() > 0.90; - if (shootOrNot) { - if (whereIsDave === Position.LEFT) { - monster.state = MonsterState.ATTACKING; - monster.attackDir = MonsterAttack.LEFT; - (monster).attack(); - } else if (whereIsDave === Position.RIGHT) { - monster.state = MonsterState.ATTACKING; - monster.attackDir = MonsterAttack.RIGHT; - (monster).attack(); - } - } + this.croneAttack(monster, whereIsDave); } if (daveIsNear === Position.NONE) { - if ( - (whereIsDave === Position.LEFT - && monster.moveDir === MonsterMove.RIGHT) - || (whereIsDave === Position.RIGHT - && monster.moveDir === MonsterMove.LEFT) - ) { - if (monster.randomSteps > 0) { - monster.x += dX; - monster.randomSteps -= 1; - } else { - monster.swapMoving(); - monster.setRandomSteps(); - } - } else { - monster.x += dX; - } + this.monsterRandomMove(monster, whereIsDave, dX); } else if (monster instanceof Zombie) { - if (daveIsNear === Position.LEFT) { - monster.state = MonsterState.ATTACKING; - monster.attackDir = MonsterAttack.LEFT; - (monster).attack(); - } else if (daveIsNear === Position.RIGHT) { - monster.state = MonsterState.ATTACKING; - monster.attackDir = MonsterAttack.RIGHT; - (monster).attack(); - } + this.zombieAttack(monster, whereIsDave); } } else { monster.swapMoving(); @@ -758,6 +587,48 @@ class PlayLevel { } } + croneAttack(crone: Monster, davePos: Position): void { + const shootOrNot: boolean = Math.random() > 0.90; + if (shootOrNot) { + if (davePos === Position.LEFT) { + crone.attackDir = MonsterAttack.LEFT; + } else if (davePos === Position.RIGHT) { + crone.attackDir = MonsterAttack.RIGHT; + } + crone.state = MonsterState.ATTACKING; + (crone).attack(); + } + } + + zombieAttack(zombie: Monster, davePos: Position): void { + if (davePos === Position.LEFT) { + zombie.attackDir = MonsterAttack.LEFT; + } else if (davePos === Position.RIGHT) { + zombie.attackDir = MonsterAttack.RIGHT; + } + zombie.state = MonsterState.ATTACKING; + (zombie).attack(); + } + + monsterRandomMove(monster: Monster, davePos: Position, dX: number): void { + if ( + (davePos === Position.LEFT + && monster.moveDir === MonsterMove.RIGHT) + || (davePos === Position.RIGHT + && monster.moveDir === MonsterMove.LEFT) + ) { + if (monster.randomSteps > 0) { + monster.x += dX; + monster.randomSteps -= 1; + } else { + monster.swapMoving(); + monster.setRandomSteps(); + } + } else { + monster.x += dX; + } + } + isDaveVisibleToMonster(monster: Monster): Position { const diffX: number = this.dave.x - monster.x; const diffY: number = this.dave.y - monster.y; @@ -792,42 +663,24 @@ class PlayLevel { + this.gameView.levelAreaY + this.dave.h / 2; const toBottom: number = this.gameView.viewAreaH - toTop; if (this.dave.look === DaveLook.LEFT) { - dX = -toLeft; if (this.dave.shoot === DaveShoot.UP) { - if (-toLeft < -toTop) { - dX = -toTop; - dY = -toTop; - } else { - dY = -toLeft; - } + [dX, dY] = -toLeft < -toTop ? [-toTop, -toTop] : [-toLeft, -toLeft]; } else if (this.dave.shoot === DaveShoot.DOWN) { - if (toLeft > toBottom) { - dX = -toBottom; - dY = toBottom; - } else { - dY = toLeft; - } + [dX, dY] = toLeft > toBottom + ? [-toBottom, toBottom] + : [-toLeft, toLeft]; } else { - dY = 0; + [dX, dY] = [-toLeft, 0]; } } else if (this.dave.look === DaveLook.RIGHT) { - dX = toRight; if (this.dave.shoot === DaveShoot.UP) { - if (-toRight < -toTop) { - dX = toTop; - dY = -toTop; - } else { - dY = -toRight; - } + [dX, dY] = -toRight < -toTop ? [toTop, -toTop] : [toRight, -toRight]; } else if (this.dave.shoot === DaveShoot.DOWN) { - if (toRight > toBottom) { - dX = toBottom; - dY = toBottom; - } else { - dY = toRight; - } + [dX, dY] = toRight > toBottom + ? [toBottom, toBottom] + : [toRight, toRight]; } else { - dY = 0; + [dX, dY] = [toRight, 0]; } } @@ -846,32 +699,7 @@ class PlayLevel { this.gameView.showAmmo(); this.gameView.sounds[SoundType.SHOT].currentTime = 0; this.gameView.sounds[SoundType.SHOT].play(); - const x: number = this.dave.x + this.dave.w / 2; - const y: number = this.dave.y + this.dave.h / 2 - - this.dave.shootOffsetY; - const [dX, dY] = this.calcEndOfLineShoot(); - const shootLine = { - x1: x, y1: y, x2: x + dX, y2: y + dY, - }; - const closestWall: Rect | Monster | undefined = this.getClosestObj( - shootLine, - this.gameView.walls, - ); - const closestMonster: Rect | Monster | undefined = this.getClosestObj( - shootLine, - this.gameView.monsters, - ); - if ((closestMonster && !closestWall) - || (closestMonster - && closestWall - && this.isFirstRectCloserToDave(closestMonster, closestWall)) - ) { - (closestMonster).getAttacked(); - if ((closestMonster).health === 0) { - this.gameView.createMeatExplosion(closestMonster); - this.gameView.removeMonster((closestMonster)); - } - } + this.checkDaveShoot(); } else { this.gameView.sounds[SoundType.EMPTY].currentTime = 0; this.gameView.sounds[SoundType.EMPTY].play(); @@ -880,10 +708,39 @@ class PlayLevel { } } + checkDaveShoot(): void { + const x: number = this.dave.x + this.dave.w / 2; + const y: number = this.dave.y + this.dave.h / 2 + - this.dave.shootOffsetY; + const [dX, dY] = this.calcEndOfLineShoot(); + const shootLine = { + x1: x, y1: y, x2: x + dX, y2: y + dY, + }; + const closestWall: Rect | Monster | undefined = this.getClosestObj( + shootLine, + this.gameView.walls, + ); + const closestMonster: Rect | Monster | undefined = this.getClosestObj( + shootLine, + this.gameView.monsters, + ); + if ((closestMonster && !closestWall) + || (closestMonster + && closestWall + && this.isFirstRectCloserToDave(closestMonster, closestWall)) + ) { + (closestMonster).getAttacked(); + if ((closestMonster).health === 0) { + this.gameView.createMeatExplosion(closestMonster); + this.gameView.removeMonster((closestMonster)); + } + } + } + getClosestObj(shootLine: Line, rects: Rect[]): Rect | Monster | undefined { let result: Rect | Monster | undefined; rects.forEach((rect) => { - if (this.isLineCrossRect(shootLine, rect)) { + if (Geometry.isLineCrossRect(shootLine, rect)) { if (!result || this.isFirstRectCloserToDave(rect, result)) { result = rect; @@ -930,65 +787,6 @@ class PlayLevel { return false; } - isLineCrossLine(line1: Line, line2: Line): boolean { - const x2x1: number = line1.x2 - line1.x1; - const x4x3: number = line2.x2 - line2.x1; - const y2y1: number = line1.y2 - line1.y1; - const y4y3: number = line2.y2 - line2.y1; - const x1x3: number = line1.x1 - line2.x1; - const y1y3: number = line1.y1 - line2.y1; - const d: number = (y4y3 * x2x1 - x4x3 * y2y1); - const uA: number = (x4x3 * y1y3 - y4y3 * x1x3) / d; - const uB: number = (x2x1 * y1y3 - y2y1 * x1x3) / d; - if (uA >= 0 && uA <= 1 && uB >= 0 && uB <= 1) { - return true; - } - return false; - } - - isLineCrossRect(line: Line, rect: Rect): boolean { - const left: boolean = this.isLineCrossLine( - line, - { - x1: rect.x, - y1: rect.y, - x2: rect.x, - y2: rect.y + rect.h, - }, - ); - const right: boolean = this.isLineCrossLine( - line, - { - x1: rect.x + rect.w, - y1: rect.y, - x2: rect.x + rect.w, - y2: rect.y + rect.h, - }, - ); - const top: boolean = this.isLineCrossLine( - line, - { - x1: rect.x, - y1: rect.y, - x2: rect.x + rect.w, - y2: rect.y, - }, - ); - const bottom: boolean = this.isLineCrossLine( - line, - { - x1: rect.x, - y1: rect.y + rect.h, - x2: rect.x + rect.w, - y2: rect.y + rect.h, - }, - ); - if (left || right || top || bottom) { - return true; - } - return false; - } - stopGame(): void { clearInterval(this.monsterAnimationTimer); cancelAnimationFrame(this.daveAnimationTimer); diff --git a/client/src/styles/crone.css b/client/src/styles/crone.css index ac40d15..e8ecf59 100644 --- a/client/src/styles/crone.css +++ b/client/src/styles/crone.css @@ -1,19 +1,19 @@ -.crone { - position: absolute; - top: 0; - left: 0; - background-image: url("../assets/sprites/crone_sprite.png"); - z-index: 10; -} - -.crone.attacked { - background-color: green; -} - -.crone_bullet { - position: absolute; - top: 0; - left: 0; - background-image: url("../assets/sprites/knife.png"); - z-index: 10; -} +.crone { + position: absolute; + top: 0; + left: 0; + background-image: url("../assets/sprites/crone_sprite.png"); + z-index: 10; +} + +.crone.attacked { + filter: brightness(2); +} + +.crone_bullet { + position: absolute; + top: 0; + left: 0; + background-image: url("../assets/sprites/knife.png"); + z-index: 10; +} diff --git a/client/src/styles/zombie.css b/client/src/styles/zombie.css index eee7082..5b27f40 100644 --- a/client/src/styles/zombie.css +++ b/client/src/styles/zombie.css @@ -1,21 +1,21 @@ -@import "zombieAnimation"; - -.zombie { - position: absolute; - top: 0; - left: 0; - background-image: url("../assets/sprites/zombie_sprite.png"); - z-index: 10; -} -/* -.zombie.attacked { - background-color: crimson; -} -*/ -.zombie_bullet { - position: absolute; - top: 0; - left: 0; - /* background-color: blueviolet;*/ - z-index: 10; -} +@import "zombieAnimation"; + +.zombie { + position: absolute; + top: 0; + left: 0; + background-image: url("../assets/sprites/zombie_sprite.png"); + z-index: 10; +} + +.zombie.attacked { + filter: brightness(2); +} + +.zombie_bullet { + position: absolute; + top: 0; + left: 0; + /* background-color: blueviolet;*/ + z-index: 10; +} diff --git a/client/src/types/game.ts b/client/src/types/game.ts index 4044018..b8f12c7 100644 --- a/client/src/types/game.ts +++ b/client/src/types/game.ts @@ -77,3 +77,21 @@ export enum ObjectState { JUMPING_UP, FALLING, } + +export type Movement = { + x: MoveAxis, + y: MoveAxis, +}; + +export type MoveAxis = { + diff: number, + accel: boolean, + velocity: number, +}; + +export type Barrier = { + above?: Rect, + right?: Rect, + below?: Rect, + left?: Rect, +}; From 431f0819dc22b3df7a9707f1529aa50452151e71 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Fri, 24 Feb 2023 21:08:35 +0300 Subject: [PATCH 113/196] feat: made an animation for pickups --- client/src/assets/sprites/100.png | Bin 0 -> 1049 bytes client/src/assets/sprites/200.png | Bin 0 -> 1091 bytes client/src/assets/sprites/400.png | Bin 0 -> 1051 bytes client/src/assets/sprites/bonus1.png | Bin 0 -> 1208 bytes client/src/assets/sprites/bonus2.png | Bin 0 -> 1218 bytes client/src/assets/sprites/bonus4.png | Bin 0 -> 1222 bytes client/src/styles/level.css | 49 +++++++++++++++++++++------ client/src/styles/lootKeyframes.scss | 39 +++++++++++++++++++++ 8 files changed, 77 insertions(+), 11 deletions(-) create mode 100644 client/src/assets/sprites/100.png create mode 100644 client/src/assets/sprites/200.png create mode 100644 client/src/assets/sprites/400.png create mode 100644 client/src/assets/sprites/bonus1.png create mode 100644 client/src/assets/sprites/bonus2.png create mode 100644 client/src/assets/sprites/bonus4.png create mode 100644 client/src/styles/lootKeyframes.scss diff --git a/client/src/assets/sprites/100.png b/client/src/assets/sprites/100.png new file mode 100644 index 0000000000000000000000000000000000000000..20753274b992c7fc491ad7515edd6b5fcede5284 GIT binary patch literal 1049 zcmaJ=U1-x#6pl>U9Bw{|C=)Ijf}+h&vu0~pH@c>Em8I0SuO&|6sf)64L#k~poD6CL#y0-Jd8j{>|58wBlbM86!RyuXA zqy2b0MNu8eVL3xq&i~q4$iMLA;2K$u;dmZr(IhUZ4y2+wnt&i_s#7onRekQ_ChVuE z7TU<=ab6jbG-NWWk6}F1CTxo8AM|Whn}!%nz$wFu&_7?jp@E@C=+ThEDRvANjp2C* zX6I8mZGKt{>-69N==UTdU_z_{&z!Mb$&1icU5VJfo25Y&f~O<&Zc=$A4PwZFAjAj( zjpKPBiVWWq5=H(j2y%Ro<;W`r_#P=FO2J-GduS5P(I=&hoT$Yjy9iyx*p^tfR4Oqg zfkDm`%ZI~ZUn3X{5JbS8v#{y~EVsL^AVXJk3>zEB0=}X;fo5@pCYkP*VA>5?%dH&~ zIWX2!ZI)*^zoa@)QT`7#%?8@V8Mv44KZV`goDJCwbkVG%k;YAS`=M+p=0FuACx_5X z{S?zhgppfBHi%_KaB9@BbX0OrSMiD>B`p`LmIjk@geD4%Vd#<|^E}@h3rB~20c4 z1)bmNiwY8*uNTGcaiDw&BoZ0O=Iw(MW)>$WBu&uiA8cH4yQ+Q@vg3}a(TR5 z9w3fNrDE(qe}q^Ea3+-{+X}VwvNKB@YEq8oyw5-GU1(q64#hsc+j%s0rwwKw+Qd|Whbu2O@M_`h`q3LVsq~YtDR44Z{Jp%gG=BMElopcPslxr$*E`>e>nkho*M4=X mUTAsi)0x)q*EZL;u8%G3qXHQagTit*2}UL3Df#(OVetF|93B-hC9@7fiPd8yNN9I^9fE>921=J;Nhm^s5~M>Cl|db(E?uH1gt{24*qhbW4sDN_dGG!BzVG+F_xsI_ zp6>R_ikb?FqADXDVvNi#`#n%XzC$0&ACu`A4h`ZyG=h_o38^*(4MPyoq)`}yl9Ims z68b5sgjVB&cre<<%SdxdHpZFK48o=;e@n`cRD{2H` zLhYC|Vc%qTT%H`0eG1*u4E!mc2xt&XAf=7#7M~L6oGwq+c9@|-4uZ!7ddJjYv*3G!c!#UVS-ox>3FW4P4$!01ed`t}Q<{~?RPGD^C z43kVIoyi6#GDjKK=kwVbZnuLV99CM#Qp%xQb$JC5TC%AcSVcOp6{TS`fd!g4-8q70 z?8)lZ?lqAMV^WgAuuhkKq&zSh{XbOG_RtoN!F|8~6t?1N12Qpap$Stag&V1}QyF~F zgc3$(9HH_2E%qc3MpgnDAlS!&(*vrmprlow!$+fhM7OY{%P=AeG*NJ>s=|BNrclu9 z4z>lj5X*+dCa>5K2sCkxUayDqdO~@wh~xNw9;_PJs~uH6cnK{AWbRIflKY$6Th zj?Alty|fk7+vO^Sy#xw!8DfU93;S20^C8kb_HwUn$!4$dp-#HpByBxCcmF;4C8~S6 z;-Rgr2|*BQYiqOFOWABQ32$$2&%9fEOIBq#*4;<8WKcDoC1Db}77^RxsrB!7IuA{Q zgW}@JjjKu#yEwIa_)}uNR6TnlxIWWZ6|Ml&RmHEm#3{Y#NdM1YWvy%d)%D+!OQox9 zdga2`g(J_-saun&EpRbxTx2??6P@#_8GB5MMB+TCNMPn2S3hcvH$=8 literal 0 HcmV?d00001 diff --git a/client/src/assets/sprites/400.png b/client/src/assets/sprites/400.png new file mode 100644 index 0000000000000000000000000000000000000000..44bfa274c07f5c65bb732d134962f7409fdc17dd GIT binary patch literal 1051 zcmaJ=&ubGw6kd(BwY7?ZiY4H5i=fc#k2KkurD;gA8yo4Cm;{=Wbh|rkmUeg6-HAzq zr{cjMcu`Ofg8l>AUfP2mJa|zAD_BsZAb1igcoV^tIGZNXgK^p2dGq+b@4Ywg&5g{| z`TpL4UW%gn(-Tsbtep4t_{e`|>%baWPGY%$b7&5iRR>aW9nC_JHr08Ug{r=E`86D) zC?9R)3%H<6iW)K*)x$6q(yjES%B03!#2V)hH2$&G7pkgjsu2_lE4PBAgo|~mX1A-T#^lnlGB?FSkfgsF` z1T>E4fgmt^C@cv4FbHydkmblL1o)5`7R2BvXg)NF=IC=`R!TKvkzJH7Vr+{nTP~NG z@(6>Rd6thvBA!Mt7$As%yJTUt60qE%mVyLb%`t3jAPabk>MSbZC`~fmEy1+gvX*`46cI*l5!oP_6Tq2i!_raNJ=?%5ikP-stXdjOOHrCAFovOvLU2@yghQ!#LXdf0 zmJ+-q#ko;FCCfrs;Lf$U64FX0v~Y{7x4B`iBi9=R(@)8m=#u_c@K;6sZ{yFwR;`z#_Z=3O6YOts4-OAgY4L^N|PwE$M zB~ILV<@5Dz%z*gvd+NxZ)!Mz%cJ~AMTKMIgXKTm59<2Tt+}YauQ?2}h;nDd}lqX8AXHb5Otl literal 0 HcmV?d00001 diff --git a/client/src/assets/sprites/bonus1.png b/client/src/assets/sprites/bonus1.png new file mode 100644 index 0000000000000000000000000000000000000000..97589ea54beac036a527895baf37611c5195a495 GIT binary patch literal 1208 zcmaJ=TWs4@7&c8S+R%c=MNm|sgR4mlHL;zG+gQ!IBu=-mIaEoYeF4q2Pg^UskFie| zr$}fmh%spoE7Q1X50gL)?Sg1{VYFf6T5*{ss%a0EiV6>mNtG(l9tMjPj@u^iKsd5} z{&UXvegEbBK01`%+u?oGOHouuYM+=PGfUostse57%-j_xQzuT2;4B)$1=)gBOhuy* zq;z>4W}vJVU-%aGQAyb@9Af!(0r5r}{eu?!r2(y#?5N^j~4#CEqC8f-#v zK1y!|H6jgx1hOCq`-47(NC@*npciZpns~F+F(D%k zZu=suC_RC(DKJc-Q1BOmeq@a^TqF{4H39)2LHO*Vfn~>M*xfY+5!#BSnOH*xa24fI zG=-xyiF7Lk-K@(R_I8;_!5Bw28P3nTDb;|I^#4#@ucK|8f&aw&pTc&oXhJ3fZ8T*m zh$SgpoagOpwU(;E7?)P*K6&wTYJ`A!XQDHWZi=qclNse|8>!|Ez&)%S#Mjis5d?|NVi+0 zt-m-sbDsPXj}0BjB`cLmHJ@MZ>Z(+p|C*w@Tw`}NnIPuehFG%nO`ZDtM{PmXOG4o>V5dc=V)N#*lTw`EzdN0dpzs& zpU&+4pmUE|iX8c@U1|TWyxIcZ4YoH2wW*%$#o5JjH+5e8hFZSw)H4^G4&7;ekp8}D zIdS#Uk-6(2xw86X^Ham`|9;rJv4 zq}24xJX@vryZ0+8WTx0Eg`4^s_!c;)W@LI)6{QAO`Gq7`WhYyvDB0U7*i={n4aiL` zNmQuF&B-gas<2f8n`;GRgM{^!6u?SKvTcwn`GuBNuFf>#!Gt)CP zF*P$Y)KM@pFf`IP03tJ8LlY}gGbUo-h6WQb!1OB;3-k^33_xCjDfIQluQWFouDZA+C>7yetOgf{R2HP_ z2c;J0mlh=hBQ8xDWL1Hcb5UwyNq$jCetr%t6azByOY(~|@(UE4gUu8)!ZY(y^2>`g z!Rmc|tvvIJOA_;vQ$1a5m4GJbWoD*WIlG#=nOeG7I69fR7#g~|SUMRSSy(!nIJr4F zn>jj~!}Pl3Czs}?=9R$orXciM;?xUD3b_S9n_W_iGRsm^+=}vZ6~JD$%Eav!Go0o@ z^`_uv@OxB0}&x!%FgnEEah-+|g zFvC_5$j<)H@aIo(@c&h-R{i<&M@B{l$Yofy3aIe^|NpvYQr-Yryd^s8jK>HKHRf@e&fi3URj|7|DJO(qxv=2i3G@II&%xvh(p~Hfp_1iHPb?ptJoB)nd?ky~;#z)XMw4t^h8r1g9{rGP*c`K1xN33yu}9xe z?YGconzp}YcH=r(1|L;}M*EB2{K*;9GrvyqYzWiOWb|s=bDH<|W$!lTs?|m84Cfa& zY;z4-?7*de)s|t!sU5-!=M`IAuXr!t<*hnF@@=&Qr_bIJ*}Y!`6Bue2?c-ef_HP8x O*9@MnelF{r5}E*9*{i$& literal 0 HcmV?d00001 diff --git a/client/src/assets/sprites/bonus4.png b/client/src/assets/sprites/bonus4.png new file mode 100644 index 0000000000000000000000000000000000000000..41d035861cd0a55b8419ec07df3628b33d1c27cb GIT binary patch literal 1222 zcmaJ=U1%It6ux1_NRyO;QfP^II}N1~cV}idJIxN+{OxR-ZL-_#&bEm@gidzuX2;3Q zozC32KY5821Ru1}hDQ9sLMbF^DL%MVXr)mDY0-x~ScUqsDx#?dA&T^2b-kPJrarh{ zX6BxI_`dI)d(N3R;<2M`yY}w_0JKGhr3BqM`ksEuMZeRDra`*xBjIr(<21=CHUa}G zo07lkooQA zZ3b#;kQwtwxu_LF8Ev>=Be@VurV4s0pfY{EuqP){0Rs^Q=8S365pzLiTUVrZ)y*<+ z8$$FT^C+qDXdH&HjiBG-bEi0-hl1eYyZnN{zW}`)?`1jq2yVVh^b4Z*2&^rJMzhtl zn2?5QvFIttWC*cDmd$3fo~+M2w zIe5lS(Z;0@Rzq20$VLjmb`s<1dKKdtOt6!|77WP(JUphED$Y8c+xTcyjF=8l%oK`9 zL53=LG))zUIIl0@?K(0rNK4I!rNCgQdq^0N1iuvahd6JYE8*0PflN~8s*kzd4Y}1( zFf1BbLbmn_Qip78!0juGTH{>&4fSeVwQ(*&LoQ2`VXKY(SEK7LIz3f$XKd+VXYi3p zr`@Jwy>bEmPJf95@zG>hmgRD}w<62MVzHv@VJ`7E8MRtrhQ zWO}SEaO`-~7Ips_kp_~v`@dcs+5I_emD)aZ)Zxy z&ON2ICVlhJ+_nD2wOM@mYp@DRN87<) zfBpFDo={r6r2laW;&(q-{CF|G>FeWGfBrEH{lVtZoBQ94T>f-x(=~Il_~pac!WU!u z);Fc*4t;py{H>1s(z(8u^xc>4jEwaEy|fWJckk9b_~f01Q%!eA&M$PZf1Q{pv~b{J W;{6{!JmX!X6#$WNOu9aJ`s_d6j;PiE literal 0 HcmV?d00001 diff --git a/client/src/styles/level.css b/client/src/styles/level.css index f009675..33c1fb5 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -1,9 +1,10 @@ -@import url('https://fonts.cdnfonts.com/css/perfect-dos-vga-437'); +@import "https://fonts.cdnfonts.com/css/perfect-dos-vga-437"; +@import "lootKeyframes"; body { overflow: hidden; height: 100vw; - background-color: #cccccc; + background-color: #ccc; } #container { @@ -13,7 +14,7 @@ body { .view-area { position: relative; - background-color: #ffffff; + background-color: #fff; opacity: 1; overflow: hidden; margin: 100px auto; @@ -43,33 +44,59 @@ body { z-index: 1; } -.loot { +.loot1 { position: absolute; width: 40px; height: 32px; z-index: 2; + background: url("./../assets/sprites/100.png") no-repeat no-repeat; + animation: bonus 2.5s ease-in-out infinite; +} + +.loot2 { + position: absolute; + width: 40px; + height: 32px; + z-index: 2; + background: url("./../assets/sprites/200.png") no-repeat no-repeat; + animation: bonus 2.5s ease-in-out infinite; +} + +.loot3 { + position: absolute; + width: 40px; + height: 32px; + z-index: 2; + background: url("./../assets/sprites/400.png") no-repeat no-repeat; + animation: bonus 2.5s ease-in-out infinite; } .loot100 { - background: url("./../assets/levels/loot1.png") no-repeat no-repeat; + background: url("./../assets/sprites/bonus1.png") no-repeat no-repeat; + animation: loot100 0.5s ease-in-out infinite; + animation-timing-function: steps(1); } .loot200 { - background: url("./../assets/levels/loot2.png") no-repeat no-repeat; + background: url("./../assets/sprites/bonus2.png") no-repeat no-repeat; + animation: loot200 0.5s ease-in-out infinite; + animation-timing-function: steps(1); } .loot400 { - background: url("./../assets/levels/loot4.png") no-repeat no-repeat; + background: url("./../assets/sprites/bonus4.png") no-repeat no-repeat; + animation: loot400 0.5s ease-in-out infinite; + animation-timing-function: steps(1); } .score { - font-family: 'Perfect DOS VGA 437', sans-serif; + font-family: "Perfect DOS VGA 437", sans-serif; position: absolute; top: 52px; left: 10px; - color: #C62828; + color: #c62828; font-size: 18px; - background-color: rgb(250, 250, 250, 70%); + background-color: rgb(250 250 250 / 70%); } .game-over { @@ -124,4 +151,4 @@ body { .ammo8 { background-position-y: -256px; -} \ No newline at end of file +} diff --git a/client/src/styles/lootKeyframes.scss b/client/src/styles/lootKeyframes.scss new file mode 100644 index 0000000..9be4b7d --- /dev/null +++ b/client/src/styles/lootKeyframes.scss @@ -0,0 +1,39 @@ +@keyframes loot100 { + 0% { + background-position: 0 -10px; + } + + 25% { + background-position: 0 -58px; + } +} + +@keyframes loot200 { + 0% { + background-position: 0 -10px; + } + + 25% { + background-position: 0 -58px; + } +} + +@keyframes loot400 { + 0% { + background-position: 0 -10px; + } + + 25% { + background-position: 0 -58px; + } +} + +@keyframes bonus { + 0% { + transform: translateY(0); + } + + 100% { + transform: translateY(-100px); + } +} From a19b77fcaec25f49e7d53a90b1e459fbd894d2f1 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sat, 25 Feb 2023 00:37:53 +0300 Subject: [PATCH 114/196] feat: add interface for death animation --- client/src/types/enums/death.ts | 6 ++++++ client/src/types/interfaces/deathAnimator.ts | 5 +++++ 2 files changed, 11 insertions(+) create mode 100644 client/src/types/enums/death.ts create mode 100644 client/src/types/interfaces/deathAnimator.ts diff --git a/client/src/types/enums/death.ts b/client/src/types/enums/death.ts new file mode 100644 index 0000000..bb0c745 --- /dev/null +++ b/client/src/types/enums/death.ts @@ -0,0 +1,6 @@ +enum Death { + ZOMBIE = 'zombie', + CRONE = 'crone', +} + +export default Death; diff --git a/client/src/types/interfaces/deathAnimator.ts b/client/src/types/interfaces/deathAnimator.ts new file mode 100644 index 0000000..11b317c --- /dev/null +++ b/client/src/types/interfaces/deathAnimator.ts @@ -0,0 +1,5 @@ +import Death from '../enums/death'; + +export interface IDeathAnimator { + death(death: Death): void +} From a18e30a2d1f33155ac2ef7abc0cb8abe92e6531d Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sat, 25 Feb 2023 00:40:26 +0300 Subject: [PATCH 115/196] feat: add styles and animation for death --- client/src/assets/sprites/death_sprite.png | Bin 0 -> 9788 bytes client/src/styles/deathAnimation.scss | 34 +++++++++++++++ .../src/styles/deathAnimationKeyframes.scss | 39 ++++++++++++++++++ client/src/styles/main.scss | 1 + 4 files changed, 74 insertions(+) create mode 100644 client/src/assets/sprites/death_sprite.png create mode 100644 client/src/styles/deathAnimation.scss create mode 100644 client/src/styles/deathAnimationKeyframes.scss diff --git a/client/src/assets/sprites/death_sprite.png b/client/src/assets/sprites/death_sprite.png new file mode 100644 index 0000000000000000000000000000000000000000..4f149d78a842684f72d3eee2bc0124bc5bf3bd8d GIT binary patch literal 9788 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 bK*PeVMf&^In1sLYQuMX&X;s~R{Nn!rgoK;X literal 0 HcmV?d00001 diff --git a/client/src/styles/deathAnimation.scss b/client/src/styles/deathAnimation.scss new file mode 100644 index 0000000..9ef3527 --- /dev/null +++ b/client/src/styles/deathAnimation.scss @@ -0,0 +1,34 @@ +@import "deathAnimationKeyframes"; + +.death { + &-animate { + background: url("../assets/sprites/death_sprite.png"); + animation-timing-function: steps(1); + + &-zombie { + position: absolute; + top: -20px; + left: -40px; + width: 144px; + height: 144px; + z-index: 101; + display: none; + background: url("../assets/sprites/death_sprite.png"); + animation: death-zombie 1s ease-in-out infinite; + animation-timing-function: steps(1); + } + + &-crone { + position: absolute; + top: -20px; + left: -40px; + width: 144px; + height: 144px; + z-index: 101; + display: none; + background: url("../assets/sprites/death_sprite.png"); + animation: death-crone 1s ease-in-out infinite; + animation-timing-function: steps(1); + } + } +} diff --git a/client/src/styles/deathAnimationKeyframes.scss b/client/src/styles/deathAnimationKeyframes.scss new file mode 100644 index 0000000..5eeaf4c --- /dev/null +++ b/client/src/styles/deathAnimationKeyframes.scss @@ -0,0 +1,39 @@ +@keyframes death-zombie { + 0% { + background-position: 0 0; + } + + 25% { + background-position: -194px 0; + } + + 50% { + background-position: -387px 0; + } + + 75% { + background-position: -581px 0; + } + + 100% { + background-position: -775px 0; + } +} + +@keyframes death-crone { + 0% { + background-position: -969px 0; + } + + 25% { + background-position: -1163px 0; + } + + 50% { + background-position: -1357px 0; + } + + 75% { + background-position: -1551px 0; + } +} diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index 3715f24..aec2eb6 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -1,4 +1,5 @@ @import "playerAnimation"; +@import "deathAnimation"; @import "zombieAnimation"; @import "croneAnimation"; From 833edc9794793811b05dbe660dea458b7df74941 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sat, 25 Feb 2023 00:41:52 +0300 Subject: [PATCH 116/196] feat: add a controller to control the death animation --- .../src/scripts/controllers/deathAnimator.ts | 21 +++++++++++++++++++ 1 file changed, 21 insertions(+) create mode 100644 client/src/scripts/controllers/deathAnimator.ts diff --git a/client/src/scripts/controllers/deathAnimator.ts b/client/src/scripts/controllers/deathAnimator.ts new file mode 100644 index 0000000..6b2d6d8 --- /dev/null +++ b/client/src/scripts/controllers/deathAnimator.ts @@ -0,0 +1,21 @@ +import { IDeathAnimator } from '../../types/interfaces/deathAnimator'; +import Death from '../../types/enums/death'; + +class DeathAnimator implements IDeathAnimator { + constructor(private readonly deathBlock: HTMLElement) { + + } + + death(death: Death): void { + const classes = this.deathBlock.classList.toString() + .replace(/death-[^\s]+/g, '') + .trim(); + this.deathBlock.removeAttribute('class'); + this.deathBlock.setAttribute( + 'class', + `${classes} death-animate-${death}`.trim(), + ); + } +} + +export default DeathAnimator; From a93ab6c1f45046b339749deb9358794900228fab Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sat, 25 Feb 2023 20:14:43 +0300 Subject: [PATCH 117/196] feature: apply death animation --- client/src/scripts/components/dave.ts | 9 +++++++-- client/src/scripts/controllers/playLevel.ts | 13 +++++++------ client/src/styles/dave.css | 12 +----------- 3 files changed, 15 insertions(+), 19 deletions(-) diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index 4e81d8d..de7eff4 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -7,6 +7,8 @@ import { } from '../../types/dave'; import PlayAnimator from '../controllers/playAnimator'; import Direction from '../../types/enums/directions'; +import DeathAnimator from '../controllers/deathAnimator'; +import Death from '../../types/enums/death'; class Player { x = 0; @@ -37,6 +39,8 @@ class Player { animation: PlayAnimator; + deathAnimation: DeathAnimator; + deathLayer: HTMLElement; bullets = 8; @@ -50,7 +54,7 @@ class Player { this.setPosition(); this.animation = new PlayAnimator(this.sprite); this.deathLayer = document.createElement('div'); - this.deathLayer.classList.add('death-layer'); + this.deathAnimation = new DeathAnimator(this.deathLayer); this.sprite.append(this.deathLayer); } @@ -141,7 +145,8 @@ class Player { this.sprite.style.transform = `translate(${this.x}px, ${this.y}px)`; } - showDeathLayer(): void { + showDeathLayer(death: Death): void { + this.deathAnimation.death(death); this.deathLayer.style.display = 'block'; } } diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index 008aea7..812b045 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -14,6 +14,7 @@ import { } from '../../types/monster'; import Crone from '../components/crone'; import Geometry from './geometry'; +import Death from '../../types/enums/death'; class PlayLevel { gameView: GameView; @@ -262,7 +263,7 @@ class PlayLevel { h: bullet.area.h, }; if (!this.gameView.godMode && this.checkAttackDave(fullRect)) { - this.daveGoesDead(); + this.daveGoesDead(Death.CRONE); } if (Geometry.getCrossWithWalls( this.gameView.walls, @@ -278,7 +279,7 @@ class PlayLevel { && !this.gameView.godMode && monster.bullet && this.checkAttackDave(monster.bullet.area)) { - this.daveGoesDead(); + this.daveGoesDead(Death.ZOMBIE); } }); } @@ -353,15 +354,15 @@ class PlayLevel { return [dX, dY]; } - daveGoesDead(): void { - this.dave.showDeathLayer(); + daveGoesDead(death: Death): void { + this.dave.showDeathLayer(death); this.dave.state = DaveState.DEAD; this.gameView.lives -= 1; this.stopGame(); this.gameView.updateScoreOnScreen(); setTimeout(() => { this.restartLevel(); - }, 3000); + }, 1000); } checkLoot(): void { @@ -588,7 +589,7 @@ class PlayLevel { } croneAttack(crone: Monster, davePos: Position): void { - const shootOrNot: boolean = Math.random() > 0.90; + const shootOrNot: boolean = Math.random() > 0.95; if (shootOrNot) { if (davePos === Position.LEFT) { crone.attackDir = MonsterAttack.LEFT; diff --git a/client/src/styles/dave.css b/client/src/styles/dave.css index 0521373..ab73059 100644 --- a/client/src/styles/dave.css +++ b/client/src/styles/dave.css @@ -3,19 +3,9 @@ .player { position: absolute; top: 0; - left: 0; + left: -12px; width: 96px; height: 96px; z-index: 100; } -.death-layer { - position: absolute; - top: -20px; - left: -40px; - width: 144px; - height: 144px; - z-index: 101; - background-color: crimson; - display: none; -} From 2eb832419a3f4698d039d090dcc9b903c5b37a26 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Sat, 25 Feb 2023 20:16:19 +0300 Subject: [PATCH 118/196] fix: crone empty shots --- client/src/scripts/controllers/playLevel.ts | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index 812b045..0f2db7f 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -595,6 +595,10 @@ class PlayLevel { crone.attackDir = MonsterAttack.LEFT; } else if (davePos === Position.RIGHT) { crone.attackDir = MonsterAttack.RIGHT; + } else { + crone.attackDir = Math.random() > 0.5 + ? MonsterAttack.RIGHT + : MonsterAttack.LEFT; } crone.state = MonsterState.ATTACKING; (crone).attack(); From b306a7c543cf6b70104874623e1fc6221a73a5a5 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sat, 25 Feb 2023 21:57:14 +0300 Subject: [PATCH 119/196] fix: fix zombie attack animation --- client/src/assets/sprites/zombie_sprite.png | Bin 17052 -> 17163 bytes client/src/styles/zombieAnimation.scss | 10 +++--- .../src/styles/zombieAnimationKeyframes.scss | 30 +++++++++++------- 3 files changed, 24 insertions(+), 16 deletions(-) diff --git a/client/src/assets/sprites/zombie_sprite.png b/client/src/assets/sprites/zombie_sprite.png index 2c6ac406bcee2f638542e8ba023e7dc1cd73adc6..32b6fad13a111d151acdd63b74055be7b355c861 100644 GIT binary patch delta 14560 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 Date: Sun, 26 Feb 2023 00:29:12 +0300 Subject: [PATCH 120/196] feat: create API interaction interfaces --- client/src/types/apiResponseError.ts | 6 ++++++ client/src/types/enums/httpMethods.ts | 8 ++++++++ client/src/types/interfaces/api/apiController.ts | 8 ++++++++ client/src/types/interfaces/api/apiRequest.ts | 15 +++++++++++++++ client/src/types/interfaces/api/apiResponse.ts | 3 +++ 5 files changed, 40 insertions(+) create mode 100644 client/src/types/apiResponseError.ts create mode 100644 client/src/types/enums/httpMethods.ts create mode 100644 client/src/types/interfaces/api/apiController.ts create mode 100644 client/src/types/interfaces/api/apiRequest.ts create mode 100644 client/src/types/interfaces/api/apiResponse.ts diff --git a/client/src/types/apiResponseError.ts b/client/src/types/apiResponseError.ts new file mode 100644 index 0000000..335c10d --- /dev/null +++ b/client/src/types/apiResponseError.ts @@ -0,0 +1,6 @@ +export type APIResponseError = Error | { + statusCode: number, + message: string, + error: string + [key: string]: string | number | boolean | object | undefined | null +}; diff --git a/client/src/types/enums/httpMethods.ts b/client/src/types/enums/httpMethods.ts new file mode 100644 index 0000000..b28cdf3 --- /dev/null +++ b/client/src/types/enums/httpMethods.ts @@ -0,0 +1,8 @@ +enum HTTPMethod { + GET = 'GET', + POST = 'POST', + PUT = 'PUT', + DELETE = 'DELETE', +} + +export default HTTPMethod; diff --git a/client/src/types/interfaces/api/apiController.ts b/client/src/types/interfaces/api/apiController.ts new file mode 100644 index 0000000..dc26430 --- /dev/null +++ b/client/src/types/interfaces/api/apiController.ts @@ -0,0 +1,8 @@ +import { APIRequest } from './apiRequest'; +import { APIResponse } from './apiResponse'; + +export interface IAPIController { + fetch( + request: APIRequest + ): Promise +} diff --git a/client/src/types/interfaces/api/apiRequest.ts b/client/src/types/interfaces/api/apiRequest.ts new file mode 100644 index 0000000..eabe85a --- /dev/null +++ b/client/src/types/interfaces/api/apiRequest.ts @@ -0,0 +1,15 @@ +import HTTPMethod from '../../enums/httpMethods'; +import { APIResponse } from './apiResponse'; + +export interface APIRequest { + method: HTTPMethod + endpoint: string + headers?: Headers + queryParams?: { + [key: string]: string + } + body?: { + [key: string]: string | number | boolean | object | null | undefined + } + response: new () => TResponse +} diff --git a/client/src/types/interfaces/api/apiResponse.ts b/client/src/types/interfaces/api/apiResponse.ts new file mode 100644 index 0000000..77018cf --- /dev/null +++ b/client/src/types/interfaces/api/apiResponse.ts @@ -0,0 +1,3 @@ +export interface APIResponse { + map(rawResponse: Response): Promise +} From f5c208e3f728a2a9cd77ec61e13f3bc0280ea568 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 00:29:59 +0300 Subject: [PATCH 121/196] refactor: remove unused .gitkeep files --- client/src/scripts/components/.gitkeep | 0 client/src/scripts/controllers/.gitkeep | 0 2 files changed, 0 insertions(+), 0 deletions(-) delete mode 100644 client/src/scripts/components/.gitkeep delete mode 100644 client/src/scripts/controllers/.gitkeep diff --git a/client/src/scripts/components/.gitkeep b/client/src/scripts/components/.gitkeep deleted file mode 100644 index e69de29..0000000 diff --git a/client/src/scripts/controllers/.gitkeep b/client/src/scripts/controllers/.gitkeep deleted file mode 100644 index e69de29..0000000 From 391fe0314ca5ade2b3c262f27c7f3cef5a567b31 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 00:30:36 +0300 Subject: [PATCH 122/196] feat: create API controller implementation --- .../src/scripts/controllers/apiController.ts | 51 +++++++++++++++++++ 1 file changed, 51 insertions(+) create mode 100644 client/src/scripts/controllers/apiController.ts diff --git a/client/src/scripts/controllers/apiController.ts b/client/src/scripts/controllers/apiController.ts new file mode 100644 index 0000000..c51fd28 --- /dev/null +++ b/client/src/scripts/controllers/apiController.ts @@ -0,0 +1,51 @@ +import { IAPIController } from '../../types/interfaces/api/apiController'; +import { APIRequest } from '../../types/interfaces/api/apiRequest'; +import { APIResponse } from '../../types/interfaces/api/apiResponse'; + +class APIController implements IAPIController { + constructor( + private readonly baseURL: string = 'http://localhost:3000', + ) { + } + + fetch( + request: APIRequest, + ): Promise { + return new Promise((resolve, reject) => { + const url = new URL(request.endpoint, this.baseURL); + const headers = new Headers(request.headers); + + if (request.queryParams) { + Object.entries(request.queryParams) + .forEach(([key, value]) => { + url.searchParams.append(key, value.toString()); + }); + } + + headers.append('Content-Type', 'application/json'); + headers.append('Access-Control-Allow-Origin', '*'); + + fetch(url.href, { + method: request.method, + headers, + body: request.body ? JSON.stringify(request.body) : undefined, + credentials: 'include', + }) + .then(async (rawResponse) => { + if (!rawResponse.ok) { + const body = await rawResponse.json(); + reject(body); + } + + // eslint-disable-next-line new-cap + const response = new request.response(); + await response.map(rawResponse); + resolve(response); + }) + .catch((err) => reject(err)); + }); + } +} + +const api = new APIController(process.env.API_URL); +export default api; From 8e09865c1387a7c32d48fb018537283c35b32d28 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 00:30:54 +0300 Subject: [PATCH 123/196] feat: create base API request --- .../scripts/api/requests/baseAPIRequest.ts | 20 +++++++++++++++++++ 1 file changed, 20 insertions(+) create mode 100644 client/src/scripts/api/requests/baseAPIRequest.ts diff --git a/client/src/scripts/api/requests/baseAPIRequest.ts b/client/src/scripts/api/requests/baseAPIRequest.ts new file mode 100644 index 0000000..ba03fb0 --- /dev/null +++ b/client/src/scripts/api/requests/baseAPIRequest.ts @@ -0,0 +1,20 @@ +import { APIRequest } from '../../../types/interfaces/api/apiRequest'; +import HTTPMethod from '../../../types/enums/httpMethods'; +import { APIResponse } from '../../../types/interfaces/api/apiResponse'; + +export default abstract class BaseAPIRequest +implements APIRequest { + protected constructor( + readonly method: HTTPMethod, + readonly endpoint: string, + readonly response: new () => TResponse, + readonly headers?: Headers, + readonly queryParams?: { + [key: string]: string + }, + readonly body?: { + [key: string]: string | number | boolean | object | null | undefined + }, + ) { + } +} From 2ff82449ce14a6f7b518f2b8852d23642a64c390 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 00:31:33 +0300 Subject: [PATCH 124/196] feat: create auth user local request model --- .../api/requests/auth/authUserLocalRequest.ts | 26 +++++++++++++++++ .../responses/auth/authUserLocalResponse.ts | 28 +++++++++++++++++++ 2 files changed, 54 insertions(+) create mode 100644 client/src/scripts/api/requests/auth/authUserLocalRequest.ts create mode 100644 client/src/scripts/api/responses/auth/authUserLocalResponse.ts diff --git a/client/src/scripts/api/requests/auth/authUserLocalRequest.ts b/client/src/scripts/api/requests/auth/authUserLocalRequest.ts new file mode 100644 index 0000000..218ea8a --- /dev/null +++ b/client/src/scripts/api/requests/auth/authUserLocalRequest.ts @@ -0,0 +1,26 @@ +import BaseAPIRequest from '../baseAPIRequest'; +import HTTPMethod from '../../../../types/enums/httpMethods'; +import AuthUserLocalResponse from '../../responses/auth/authUserLocalResponse'; + +export default class AuthUserLocalRequest + extends BaseAPIRequest { + constructor( + username: string, + password: string, + action: 'login' | 'register', + ) { + super( + HTTPMethod.POST, + `/auth/${action}`, + AuthUserLocalResponse, + new Headers(), + { + provider: 'local', + }, + { + username, + password, + }, + ); + } +} diff --git a/client/src/scripts/api/responses/auth/authUserLocalResponse.ts b/client/src/scripts/api/responses/auth/authUserLocalResponse.ts new file mode 100644 index 0000000..2d2ff8a --- /dev/null +++ b/client/src/scripts/api/responses/auth/authUserLocalResponse.ts @@ -0,0 +1,28 @@ +import { APIResponse } from '../../../../types/interfaces/api/apiResponse'; +import MappingFailedError from '../../../errors/mappingFailedError'; + +export default class AuthUserLocalResponse implements APIResponse { + id?: string; + + username?: string; + + authProvider?: string; + + accessToken?: string; + + async map(rawResponse: Response): Promise { + try { + const res = await rawResponse.json(); + + // eslint-disable-next-line no-underscore-dangle + this.id = res._id; + this.username = res.username; + this.authProvider = res.authProvider; + this.accessToken = res.accessToken; + + return this; + } catch (e: unknown) { + throw new MappingFailedError(Response, AuthUserLocalResponse); + } + } +} From cc0a356b9607478e347365410ecccfc5ad40afc7 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 00:32:07 +0300 Subject: [PATCH 125/196] feat: create request model for create score --- .../api/requests/score/createScoreRequest.ts | 19 ++++++++++ .../responses/score/createScoreResponse.ts | 37 +++++++++++++++++++ 2 files changed, 56 insertions(+) create mode 100644 client/src/scripts/api/requests/score/createScoreRequest.ts create mode 100644 client/src/scripts/api/responses/score/createScoreResponse.ts diff --git a/client/src/scripts/api/requests/score/createScoreRequest.ts b/client/src/scripts/api/requests/score/createScoreRequest.ts new file mode 100644 index 0000000..6851685 --- /dev/null +++ b/client/src/scripts/api/requests/score/createScoreRequest.ts @@ -0,0 +1,19 @@ +import BaseAPIRequest from '../baseAPIRequest'; +import CreateScoreResponse from '../../responses/score/createScoreResponse'; +import HTTPMethod from '../../../../types/enums/httpMethods'; + +export default class CreateScoreRequest + extends BaseAPIRequest { + constructor(score: number) { + super( + HTTPMethod.POST, + '/score', + CreateScoreResponse, + new Headers(), + {}, + { + score, + }, + ); + } +} diff --git a/client/src/scripts/api/responses/score/createScoreResponse.ts b/client/src/scripts/api/responses/score/createScoreResponse.ts new file mode 100644 index 0000000..9a24111 --- /dev/null +++ b/client/src/scripts/api/responses/score/createScoreResponse.ts @@ -0,0 +1,37 @@ +import { APIResponse } from '../../../../types/interfaces/api/apiResponse'; +import MappingFailedError from '../../../errors/mappingFailedError'; + +export default class CreateScoreResponse implements APIResponse { + id?: string; + + score?: number; + + createdAt?: Date; + + user?: { + id?: string + username?: string + authProvider?: string + }; + + async map(rawResponse: Response): Promise { + try { + const json = await rawResponse.json(); + + // eslint-disable-next-line no-underscore-dangle + this.id = json._id; + this.score = json.score; + this.createdAt = new Date(Date.parse(json.createdAt)); + this.user = { + // eslint-disable-next-line no-underscore-dangle + id: json.user._id, + username: json.user.username, + authProvider: json.user.authProvider, + }; + + return this; + } catch (e: unknown) { + throw new MappingFailedError(Response, CreateScoreResponse); + } + } +} From a5404992cfbef71a631d2726b47684bec2a1b087 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 00:32:16 +0300 Subject: [PATCH 126/196] feat: create request model for get score --- .../api/requests/score/getScoreRequest.ts | 19 ++++++++++ .../api/responses/score/getScoreResponse.ts | 37 +++++++++++++++++++ 2 files changed, 56 insertions(+) create mode 100644 client/src/scripts/api/requests/score/getScoreRequest.ts create mode 100644 client/src/scripts/api/responses/score/getScoreResponse.ts diff --git a/client/src/scripts/api/requests/score/getScoreRequest.ts b/client/src/scripts/api/requests/score/getScoreRequest.ts new file mode 100644 index 0000000..be422bb --- /dev/null +++ b/client/src/scripts/api/requests/score/getScoreRequest.ts @@ -0,0 +1,19 @@ +import BaseAPIRequest from '../baseAPIRequest'; +import GetScoreResponse from '../../responses/score/getScoreResponse'; +import HTTPMethod from '../../../../types/enums/httpMethods'; + +export default class GetScoreRequest extends BaseAPIRequest { + constructor(page = 1, limit = 100, sortBy: 'asc' | 'desc' = 'desc') { + super( + HTTPMethod.GET, + '/score', + GetScoreResponse, + new Headers(), + { + page: page.toString(), + limit: limit.toString(), + sortBy, + }, + ); + } +} diff --git a/client/src/scripts/api/responses/score/getScoreResponse.ts b/client/src/scripts/api/responses/score/getScoreResponse.ts new file mode 100644 index 0000000..efdf903 --- /dev/null +++ b/client/src/scripts/api/responses/score/getScoreResponse.ts @@ -0,0 +1,37 @@ +import { APIResponse } from '../../../../types/interfaces/api/apiResponse'; +import MappingFailedError from '../../../errors/mappingFailedError'; + +export default class GetScoreResponse implements APIResponse { + totalCount?: number; + + scores: Array<{ + id?: string + user?: string + score?: number + createdAt?: Date + }> = []; + + async map(rawResponse: Response): Promise { + try { + const json = await rawResponse.json(); + + this.totalCount = Number(rawResponse.headers.get('X-Total-Count')); + + if (Array.isArray(json)) { + json.forEach((score) => { + this.scores.push({ + // eslint-disable-next-line no-underscore-dangle + id: score._id, + user: score.user, + score: score.score, + createdAt: new Date(Date.parse(score.createdAt)), + }); + }); + } + + return this; + } catch (e: unknown) { + throw new MappingFailedError(Response, GetScoreResponse); + } + } +} From ddfc0f37c07d24446ca95d79d203682b911691c2 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 00:32:28 +0300 Subject: [PATCH 127/196] feat: create request model for get leaderboard --- .../leaderboard/getLeaderboardRequest.ts | 21 +++++++++ .../leaderboard/getLeaderboardResponse.ts | 46 +++++++++++++++++++ 2 files changed, 67 insertions(+) create mode 100644 client/src/scripts/api/requests/leaderboard/getLeaderboardRequest.ts create mode 100644 client/src/scripts/api/responses/leaderboard/getLeaderboardResponse.ts diff --git a/client/src/scripts/api/requests/leaderboard/getLeaderboardRequest.ts b/client/src/scripts/api/requests/leaderboard/getLeaderboardRequest.ts new file mode 100644 index 0000000..71d1d38 --- /dev/null +++ b/client/src/scripts/api/requests/leaderboard/getLeaderboardRequest.ts @@ -0,0 +1,21 @@ +import BaseAPIRequest from '../baseAPIRequest'; +import GetLeaderboardResponse + from '../../responses/leaderboard/getLeaderboardResponse'; +import HTTPMethod from '../../../../types/enums/httpMethods'; + +export default class GetLeaderboardRequest + extends BaseAPIRequest { + constructor(page = 1, limit = 100, sortBy: 'asc' | 'desc' = 'desc') { + super( + HTTPMethod.GET, + '/leaderboard', + GetLeaderboardResponse, + new Headers(), + { + page: page.toString(), + limit: limit.toString(), + sortBy, + }, + ); + } +} diff --git a/client/src/scripts/api/responses/leaderboard/getLeaderboardResponse.ts b/client/src/scripts/api/responses/leaderboard/getLeaderboardResponse.ts new file mode 100644 index 0000000..bf8a502 --- /dev/null +++ b/client/src/scripts/api/responses/leaderboard/getLeaderboardResponse.ts @@ -0,0 +1,46 @@ +import { APIResponse } from '../../../../types/interfaces/api/apiResponse'; +import MappingFailedError from '../../../errors/mappingFailedError'; + +export default class GetLeaderboardResponse implements APIResponse { + totalCount?: number; + + scores: Array<{ + id?: string + score?: number + createdAt?: Date + user?: { + id?: string + username?: string + authProvider?: string + } + }> = []; + + async map(rawResponse: Response): Promise { + try { + const json = await rawResponse.json(); + + this.totalCount = Number(rawResponse.headers.get('X-Total-Count')); + + if (Array.isArray(json)) { + json.forEach((score) => { + this.scores.push({ + // eslint-disable-next-line no-underscore-dangle + id: score._id, + score: score.score, + createdAt: new Date(Date.parse(score.createdAt)), + user: { + // eslint-disable-next-line no-underscore-dangle + id: score.user._id, + username: score.user.username, + authProvider: score.user.authProvider, + }, + }); + }); + } + + return this; + } catch (e: unknown) { + throw new MappingFailedError(Response, GetLeaderboardResponse); + } + } +} From 84d1edbf4a0089e0e90a2e72fa6dcc23cae79ebe Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 00:32:52 +0300 Subject: [PATCH 128/196] feat: create MappingFailedError --- client/src/scripts/errors/mappingFailedError.ts | 6 ++++++ 1 file changed, 6 insertions(+) create mode 100644 client/src/scripts/errors/mappingFailedError.ts diff --git a/client/src/scripts/errors/mappingFailedError.ts b/client/src/scripts/errors/mappingFailedError.ts new file mode 100644 index 0000000..134b5b6 --- /dev/null +++ b/client/src/scripts/errors/mappingFailedError.ts @@ -0,0 +1,6 @@ +export default class MappingFailedError extends Error { + constructor(srcName: new () => unknown, targetName: new () => unknown) { + super(`'${srcName.prototype.constructor.name}' failed to map` + + `'${targetName.prototype.constructor.name}'`); + } +} From a225c462232d08a33a2f92e2de781b6ea33b2144 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 00:55:06 +0300 Subject: [PATCH 129/196] fix: fix CORS --- server/src/main.ts | 5 ++++- .../src/modules/leaderboard/leaderboard.controller.ts | 10 +++++++++- server/src/modules/score/score.controller.ts | 2 ++ 3 files changed, 15 insertions(+), 2 deletions(-) diff --git a/server/src/main.ts b/server/src/main.ts index 5f1c2e2..ed36290 100644 --- a/server/src/main.ts +++ b/server/src/main.ts @@ -6,7 +6,10 @@ async function bootstrap(): Promise { const app = await NestFactory.create(AppModule); app.use(cookieParser()); - app.enableCors(); + app.enableCors({ + origin: ['http://localhost:8080', '*'], + credentials: true, + }); await app.listen(process.env.PORT || 3000); } diff --git a/server/src/modules/leaderboard/leaderboard.controller.ts b/server/src/modules/leaderboard/leaderboard.controller.ts index 85fbdc9..405e384 100644 --- a/server/src/modules/leaderboard/leaderboard.controller.ts +++ b/server/src/modules/leaderboard/leaderboard.controller.ts @@ -1,4 +1,11 @@ -import { Controller, Get, HttpStatus, Query, Res } from '@nestjs/common'; +import { + Controller, + Get, + Header, + HttpStatus, + Query, + Res, +} from '@nestjs/common'; import { Response as ExpressResponse } from 'express'; import { LeaderboardService } from './leaderboard.service'; import { CollectionRequestDto } from '../../types/dto/collectionDto'; @@ -8,6 +15,7 @@ export class LeaderboardController { constructor(private readonly leaderboardService: LeaderboardService) {} @Get() + @Header('Access-Control-Expose-Headers', 'X-Total-Count') async get( @Query() query: CollectionRequestDto, @Res() res: ExpressResponse, diff --git a/server/src/modules/score/score.controller.ts b/server/src/modules/score/score.controller.ts index 0178ca3..e53087a 100644 --- a/server/src/modules/score/score.controller.ts +++ b/server/src/modules/score/score.controller.ts @@ -8,6 +8,7 @@ import { Req, Res, UseGuards, + Header, } from '@nestjs/common'; import { ScoreService } from './score.service'; import { @@ -24,6 +25,7 @@ export class ScoreController { constructor(private readonly scoreService: ScoreService) {} @Get() + @Header('Access-Control-Expose-Headers', 'X-Total-Count') @UseGuards(JwtAuthGuard) async get( @Req() req: AuthorizedRequest, From 525c03264144f710f86a79b4bece86171da5c101 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 01:00:44 +0300 Subject: [PATCH 130/196] fix: fix X-Total-Count header for get score by user --- server/src/modules/score/score.service.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/src/modules/score/score.service.ts b/server/src/modules/score/score.service.ts index aff314c..6e912c4 100644 --- a/server/src/modules/score/score.service.ts +++ b/server/src/modules/score/score.service.ts @@ -33,7 +33,7 @@ export class ScoreService { .exec(); return { - totalCount: await this.scoreModel.count(), + totalCount: await this.scoreModel.find({ user: user._id }).count(), collection: result, }; } From 3697030827d3bb03fac982122238918f333d8678 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sun, 26 Feb 2023 02:06:15 +0300 Subject: [PATCH 131/196] feat: create an animation of gunpowder during the main character's shot --- .../sprites/dave_sprites_vert_shoot.png | Bin 0 -> 26816 bytes client/src/styles/playerAnimation.scss | 16 ++++----- .../src/styles/playerAnimationKeyframes.scss | 32 +++++++++++------- 3 files changed, 28 insertions(+), 20 deletions(-) create mode 100644 client/src/assets/sprites/dave_sprites_vert_shoot.png diff --git a/client/src/assets/sprites/dave_sprites_vert_shoot.png b/client/src/assets/sprites/dave_sprites_vert_shoot.png new file mode 100644 index 0000000000000000000000000000000000000000..9c2b650321ed5af4e40d072cea90c9ce2e22b973 GIT binary patch literal 26816 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 Date: Sun, 26 Feb 2023 02:06:15 +0300 Subject: [PATCH 132/196] feat: create an animation of gunpowder during the main character's shot --- .../sprites/dave_sprites_vert_shoot.png | Bin 0 -> 26816 bytes client/src/styles/playerAnimation.scss | 14 ++++---- .../src/styles/playerAnimationKeyframes.scss | 32 +++++++++++------- 3 files changed, 27 insertions(+), 19 deletions(-) create mode 100644 client/src/assets/sprites/dave_sprites_vert_shoot.png diff --git a/client/src/assets/sprites/dave_sprites_vert_shoot.png b/client/src/assets/sprites/dave_sprites_vert_shoot.png new file mode 100644 index 0000000000000000000000000000000000000000..9c2b650321ed5af4e40d072cea90c9ce2e22b973 GIT binary patch literal 26816 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 Date: Sun, 26 Feb 2023 02:19:19 +0300 Subject: [PATCH 133/196] refactor: change the file to match stylelint --- client/src/styles/playerAnimation.scss | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/client/src/styles/playerAnimation.scss b/client/src/styles/playerAnimation.scss index fd07491..eb084e5 100644 --- a/client/src/styles/playerAnimation.scss +++ b/client/src/styles/playerAnimation.scss @@ -82,37 +82,37 @@ $bg-size: 5257px; &-shoot { &-left { - background: url("../assets/sprites/dave_sprites_vert.png"); + background: url("../assets/sprites/dave_sprites_vert_shoot.png"); animation: shoot-left 0.5s ease-in-out infinite; animation-timing-function: steps(1); } &-right { - background: url("../assets/sprites/dave_sprites_vert.png"); + background: url("../assets/sprites/dave_sprites_vert_shoot.png"); animation: shoot-right 0.5s ease-in-out infinite; animation-timing-function: steps(1); } &-topRight { - background: url("../assets/sprites/dave_sprites_vert.png"); + background: url("../assets/sprites/dave_sprites_vert_shoot.png"); animation: shoot-top-right 0.5s ease-in-out; animation-timing-function: steps(1); } &-topLeft { - background: url("../assets/sprites/dave_sprites_vert.png"); + background: url("../assets/sprites/dave_sprites_vert_shoot.png"); animation: shoot-top-left 0.5s ease-in-out; animation-timing-function: steps(1); } &-downRight { - background: url("../assets/sprites/dave_sprites_vert.png"); + background: url("../assets/sprites/dave_sprites_vert_shoot.png"); animation: shoot-down-right 0.5s ease-in-out; animation-timing-function: steps(1); } &-downLeft { - background: url("../assets/sprites/dave_sprites_vert.png"); + background: url("../assets/sprites/dave_sprites_vert_shoot.png"); animation: shoot-down-left 0.5s ease-in-out; animation-timing-function: steps(1); } From 82d54289ad29fc803f3f383552f019bae2d59919 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sun, 26 Feb 2023 10:35:01 +0300 Subject: [PATCH 134/196] feat: apply animation for pickup and made a random loot behind the doors --- client/src/scripts/components/game.ts | 14 +++++++++++--- client/src/styles/level.css | 12 ++++++++++++ 2 files changed, 23 insertions(+), 3 deletions(-) diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 5054887..98111f7 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -173,6 +173,9 @@ class GameView { loadDoors(entityType: LevelEntity): void { LEVEL1.split('\n').forEach((line, indx) => { const arrLine = line.split(' '); + const randomValues = [100, 200, 400]; + const randomIndex = Math.floor(Math.random() * randomValues.length); + const randomValue = randomValues[randomIndex]; for (let i = 0; i < arrLine.length; i += 1) { if (arrLine[i] === entityType) { const loot = { @@ -184,7 +187,7 @@ class GameView { }, sprite: document.createElement('div'), grabbed: false, - bonus: parseInt(entityType, 10) * 100, + bonus: parseInt(entityType, 10) * randomValue, }; const door: Door = { area: { @@ -245,7 +248,13 @@ class GameView { door.sprite.style.height = `${door.area.h}px`; door.sprite.style.left = `${door.area.x}px`; door.sprite.style.top = `${door.area.y}px`; - door.loot.sprite.classList.add('loot'); + if (door.loot.bonus === 100) { + door.loot.sprite.classList.add('loot1'); + } else if (door.loot.bonus === 200) { + door.loot.sprite.classList.add('loot2'); + } else if (door.loot.bonus === 400) { + door.loot.sprite.classList.add('loot3'); + } door.loot.sprite.classList.add(`loot${door.loot.bonus}`); door.loot.sprite.style.width = `${door.loot.area.w}px`; door.loot.sprite.style.height = `${door.loot.area.h}px`; @@ -266,7 +275,6 @@ class GameView { this.score += loot.bonus; this.updateScoreOnScreen(); loot.sprite.classList.remove(`loot${loot.bonus}`); - loot.sprite.innerHTML = `${loot.bonus}`; setTimeout(() => { loot.sprite.remove(); this.loot.splice(this.loot.indexOf(loot), 1); diff --git a/client/src/styles/level.css b/client/src/styles/level.css index 33c1fb5..b14b1dc 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -72,18 +72,30 @@ body { } .loot100 { + position: absolute; + width: 40px; + height: 32px; + z-index: 2; background: url("./../assets/sprites/bonus1.png") no-repeat no-repeat; animation: loot100 0.5s ease-in-out infinite; animation-timing-function: steps(1); } .loot200 { + position: absolute; + width: 40px; + height: 32px; + z-index: 2; background: url("./../assets/sprites/bonus2.png") no-repeat no-repeat; animation: loot200 0.5s ease-in-out infinite; animation-timing-function: steps(1); } .loot400 { + position: absolute; + width: 40px; + height: 32px; + z-index: 2; background: url("./../assets/sprites/bonus4.png") no-repeat no-repeat; animation: loot400 0.5s ease-in-out infinite; animation-timing-function: steps(1); From f05a8aaeb21ff09d492cdb30f9048a940cd4f3e2 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Sun, 26 Feb 2023 12:21:23 +0300 Subject: [PATCH 135/196] fix: fix crone attack animation --- client/src/assets/sprites/crone_sprite.png | Bin 10216 -> 10331 bytes client/src/styles/croneAnimation.scss | 4 +-- .../src/styles/croneAnimationKeyframes.scss | 24 +++++++++++++----- 3 files changed, 20 insertions(+), 8 deletions(-) diff --git a/client/src/assets/sprites/crone_sprite.png b/client/src/assets/sprites/crone_sprite.png index 29dba1028edc21cef858467f71cde660ece93a05..f94c338152ca0793aac2c33c8c91c158f78902bd 100644 GIT binary patch delta 7671 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 diff --git a/client/src/styles/croneAnimation.scss b/client/src/styles/croneAnimation.scss index 30a1e90..4b616b3 100644 --- a/client/src/styles/croneAnimation.scss +++ b/client/src/styles/croneAnimation.scss @@ -20,13 +20,13 @@ &-attack { &-left { background: url("../assets/sprites/crone_sprite.png"); - animation: attack-left-crone 0.8s ease-in-out infinite; + animation: attack-left-crone 0.4s ease-in-out infinite; animation-timing-function: steps(1); } &-right { background: url("../assets/sprites/crone_sprite.png"); - animation: attack-right-crone 0.8s ease-in-out infinite; + animation: attack-right-crone 0.4s ease-in-out infinite; animation-timing-function: steps(1); } } diff --git a/client/src/styles/croneAnimationKeyframes.scss b/client/src/styles/croneAnimationKeyframes.scss index b63313a..c52d688 100644 --- a/client/src/styles/croneAnimationKeyframes.scss +++ b/client/src/styles/croneAnimationKeyframes.scss @@ -36,28 +36,40 @@ @keyframes attack-right-crone { 0% { - background-position: -653px 0; + background-position: -659px 0; + width: 90px; + left: -12px; } 25% { - background-position: -728px 0; + background-position: -759px 0; + width: 90px; + left: -12px; } 50% { - background-position: -799px 0; + background-position: -868px 0; + width: 90px; + left: 4px; } } @keyframes attack-left-crone { 0% { - background-position: -865px 0; + background-position: -965px 0; + width: 90px; + left: -12px; } 25% { - background-position: -934px 0; + background-position: -1073px 0; + width: 90px; + left: -12px; } 50% { - background-position: -999px 0; + background-position: -1160px 0; + width: 90px; + left: -28px; } } From 12635f544e8b44f177548858afba1b05c4ae2645 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 17:31:17 +0300 Subject: [PATCH 136/196] feat: create polyfill for document.createElement --- client/src/scripts/utils/createElement.ts | 42 +++++++++++++++++++++++ 1 file changed, 42 insertions(+) create mode 100644 client/src/scripts/utils/createElement.ts diff --git a/client/src/scripts/utils/createElement.ts b/client/src/scripts/utils/createElement.ts new file mode 100644 index 0000000..259cc1c --- /dev/null +++ b/client/src/scripts/utils/createElement.ts @@ -0,0 +1,42 @@ +function createElement( + tagName: K, + props: { + [key: string]: string + | number + | boolean + | object + | EventListenerOrEventListenerObject + } = {}, + children: Array = [], +): HTMLElementTagNameMap[K] { + const domElement = document.createElement(tagName); + + Object.entries(props) + .forEach(([key, value]) => { + if (value instanceof Function) { + const type = key.startsWith('on') + ? key.split('on')[1] + : key; + + domElement.addEventListener(type.toLowerCase(), value); + return; + } + + if (typeof value === 'boolean') { + if (value) { + domElement.setAttribute(key, ''); + } + return; + } + + domElement.setAttribute(key, value.toString()); + }); + + children.forEach((child) => { + domElement.appendChild(child); + }); + + return domElement; +} + +export default createElement; From 5a2d0a1ec8fb67a6fb05d8ba74496bc642a416c7 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 17:32:37 +0300 Subject: [PATCH 137/196] feat: create user auth form --- client/src/scripts/components/UserAuthForm.ts | 126 ++++++++++++++++++ .../src/styles/components/userAuthForm.scss | 79 +++++++++++ 2 files changed, 205 insertions(+) create mode 100644 client/src/scripts/components/UserAuthForm.ts create mode 100644 client/src/styles/components/userAuthForm.scss diff --git a/client/src/scripts/components/UserAuthForm.ts b/client/src/scripts/components/UserAuthForm.ts new file mode 100644 index 0000000..4da27e4 --- /dev/null +++ b/client/src/scripts/components/UserAuthForm.ts @@ -0,0 +1,126 @@ +import createElement from '../utils/createElement'; +import api from '../controllers/apiController'; +import AuthUserLocalRequest from '../api/requests/auth/authUserLocalRequest'; +import { APIResponseError } from '../../types/apiResponseError'; + +export default function UserAuthForm(): Element { + const errorLabel = createElement('label', { + class: 'auth-form__label auth-form__error-label', + }); + const usernameInput = createElement('input', { + class: 'auth-form__input auth-form__username-input', + type: 'text', + placeholder: 'Enter awesome username...', + }); + const passwordInput = createElement('input', { + class: 'auth-form__input auth-form__password-input', + type: 'password', + placeholder: 'Enter strong password', + }); + const passwordConfirmInput = createElement('input', { + class: 'auth-form__input auth-form__password-confirm-input', + type: 'password', + placeholder: 'Repeat password', + }); + + const closeForm = (): void => { + errorLabel.textContent = ''; + usernameInput.value = ''; + passwordInput.value = ''; + passwordConfirmInput.value = ''; + + document.querySelector('.auth-form')?.classList + .remove('active', 'login', 'register'); + }; + + const loginButton = createElement('button', { + class: 'auth-form__button auth-form__login-button', + onClick: async () => { + await api.fetch( + new AuthUserLocalRequest( + usernameInput.value.trim(), + passwordInput.value.trim(), + 'login', + ), + ) + .then((res) => { + if (res.accessToken) { + closeForm(); + } + }) + .catch((err: APIResponseError) => { + if (err.message) { + errorLabel.textContent = err.message; + } + }); + }, + }, [document.createTextNode('Login')]); + + const registerButton = createElement('button', { + class: 'auth-form__button auth-form__register-button', + onClick: async () => { + if (passwordInput.value.trim() !== passwordConfirmInput.value.trim()) { + errorLabel.textContent = 'Password mismatch!'; + return; + } + + await api.fetch( + new AuthUserLocalRequest( + usernameInput.value.trim(), + passwordInput.value.trim(), + 'register', + ), + ) + .then((res) => { + if (res.accessToken) { + closeForm(); + } + }) + .catch((err: APIResponseError) => { + if (err.message) { + errorLabel.textContent = err.message; + } + }); + }, + }, [document.createTextNode('Register')]); + + return createElement('div', { + class: 'auth-form', + onClick: closeForm, + }, [ + createElement('div', { + class: 'auth-form__container', + onClick: (e: PointerEvent) => { + e.stopPropagation(); + }, + }, [ + createElement('div', { + class: 'auth-form__username', + }, [ + createElement('label', { + class: 'auth-form__label auth-form__username-label', + }, [document.createTextNode('Username:')]), + usernameInput, + ]), + createElement('div', { + class: 'auth-form__password', + }, [ + createElement('label', { + class: 'auth-form__label auth-form__password-label', + }, [document.createTextNode('Password:')]), + passwordInput, + ]), + createElement('div', { + class: 'auth-form__password-confirm', + }, [ + createElement('label', { + class: 'auth-form__label auth-form__password-confirm-label', + }, [document.createTextNode('Confirm password:')]), + passwordConfirmInput, + ]), + errorLabel, + loginButton, + registerButton, + ]), + ]); +} diff --git a/client/src/styles/components/userAuthForm.scss b/client/src/styles/components/userAuthForm.scss new file mode 100644 index 0000000..90ea72e --- /dev/null +++ b/client/src/styles/components/userAuthForm.scss @@ -0,0 +1,79 @@ +.auth-form { + display: none; + align-items: center; + justify-content: center; + width: 100%; + height: 100%; + background: transparentize(#000, 0.5); + backdrop-filter: blur(8px); + position: absolute; + left: 0; + top: 0; + + &.active { + display: flex; + } + + &__container { + display: flex; + align-items: center; + justify-content: center; + flex-direction: column; + gap: 16px; + padding: 32px; + background: transparentize(#555, 0.75); + backdrop-filter: blur(16px); + border-radius: 8px; + } + + &__label { + display: flex; + margin-bottom: 4px; + color: #fff; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 16pt; + } + + &__input { + display: flex; + width: 300px; + + &::placeholder { + font-family: "Perfect DOS VGA 437", sans-serif; + } + } + + &__button { + display: none; + width: 300px; + } + + &__error-label { + display: flex; + align-items: center; + justify-content: center; + text-align: center; + color: red; + max-width: 300px; + } + + &.login { + .auth-form__login-button { + display: flex; + } + + .auth-form__password-confirm-label { + display: none; + } + + .auth-form__password-confirm-input { + display: none; + } + } + + &.register { + .auth-form__register-button { + display: flex; + } + } +} From 1c59f38b24de76662748ee4d3830e05edac08529 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 17:33:16 +0300 Subject: [PATCH 138/196] feat: create base inputs and buttons styles --- client/src/styles/components/ui/buttons.scss | 19 +++++++++++++++++++ client/src/styles/components/ui/inputs.scss | 14 ++++++++++++++ client/src/styles/main.scss | 5 +++++ 3 files changed, 38 insertions(+) create mode 100644 client/src/styles/components/ui/buttons.scss create mode 100644 client/src/styles/components/ui/inputs.scss diff --git a/client/src/styles/components/ui/buttons.scss b/client/src/styles/components/ui/buttons.scss new file mode 100644 index 0000000..12c08ec --- /dev/null +++ b/client/src/styles/components/ui/buttons.scss @@ -0,0 +1,19 @@ +button { + display: flex; + align-items: center; + justify-content: center; + padding: 8px; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 22pt; + outline: none; + border: none; + border-radius: 5px; + cursor: pointer; + transition: all 0.3s ease-in-out; + + &:hover { + background: #000; + color: #fff; + transition: all 0.3s ease-in-out; + } +} diff --git a/client/src/styles/components/ui/inputs.scss b/client/src/styles/components/ui/inputs.scss new file mode 100644 index 0000000..4e7ab9f --- /dev/null +++ b/client/src/styles/components/ui/inputs.scss @@ -0,0 +1,14 @@ +input { + display: flex; + align-items: center; + padding: 8px; + outline: none; + border: none; + border-radius: 5px; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 16pt; + + &[type="password"] { + font-family: sans-serif; + } +} diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index aec2eb6..109b907 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -1,7 +1,12 @@ +@import "https://fonts.cdnfonts.com/css/perfect-dos-vga-437"; @import "playerAnimation"; @import "deathAnimation"; @import "zombieAnimation"; @import "croneAnimation"; +@import "components/header"; +@import "components/userAuthForm"; +@import "components/ui/inputs"; +@import "components/ui/buttons"; * { margin: 0; From 022f5d30fb1e4c5c99a3cfddc09d782569ee3335 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 17:33:45 +0300 Subject: [PATCH 139/196] feat: create header component --- client/src/scripts/components/Header.ts | 33 ++++++++++++++++++++++++ client/src/styles/components/header.scss | 19 ++++++++++++++ 2 files changed, 52 insertions(+) create mode 100644 client/src/scripts/components/Header.ts create mode 100644 client/src/styles/components/header.scss diff --git a/client/src/scripts/components/Header.ts b/client/src/scripts/components/Header.ts new file mode 100644 index 0000000..1ad8664 --- /dev/null +++ b/client/src/scripts/components/Header.ts @@ -0,0 +1,33 @@ +import createElement from '../utils/createElement'; + +export default function Header(): Element { + const logoImage = createElement('img', { + class: 'header__logo', + }); + const loginButton = createElement('button', { + class: 'header__auth-button login__button', + onClick: () => { + document.querySelector('.auth-form')?.classList + .add('active', 'login'); + }, + }, [document.createTextNode('Login')]); + const registerButton = createElement('button', { + class: 'header__auth-button register__button', + onClick: () => { + document.querySelector('.auth-form')?.classList + .add('active', 'register'); + }, + }, [document.createTextNode('Register')]); + + return createElement('header', { + class: 'app__header header', + }, [ + logoImage, + createElement('div', { + class: 'header__auth login', + }, [ + loginButton, + registerButton, + ]), + ]); +} diff --git a/client/src/styles/components/header.scss b/client/src/styles/components/header.scss new file mode 100644 index 0000000..3f99fc9 --- /dev/null +++ b/client/src/styles/components/header.scss @@ -0,0 +1,19 @@ +.header { + display: flex; + flex-direction: row; + justify-content: space-between; + align-items: center; + width: 100%; + height: 64px; + padding-inline: 16px; + + &__auth { + display: flex; + flex-direction: row; + gap: 8px; + } + + &__auth-button { + font-size: 18pt; + } +} From d6126ef4e684e5d9174005f5732c576c3193d115 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 17:34:04 +0300 Subject: [PATCH 140/196] feat: create app component --- client/src/index.ts | 4 ++++ client/src/scripts/components/App.ts | 16 ++++++++++++++++ client/src/scripts/components/game.ts | 2 +- client/src/styles/level.css | 1 - 4 files changed, 21 insertions(+), 2 deletions(-) create mode 100644 client/src/scripts/components/App.ts diff --git a/client/src/index.ts b/client/src/index.ts index 249dc76..95f1325 100644 --- a/client/src/index.ts +++ b/client/src/index.ts @@ -1,5 +1,9 @@ import '@styles/main'; import PlayLevel from './scripts/controllers/playLevel'; +import App from './scripts/components/App'; const playLevel = new PlayLevel(); + +document.body.appendChild(App(playLevel)); + playLevel.startGame(); diff --git a/client/src/scripts/components/App.ts b/client/src/scripts/components/App.ts new file mode 100644 index 0000000..4ec456c --- /dev/null +++ b/client/src/scripts/components/App.ts @@ -0,0 +1,16 @@ +import createElement from '../utils/createElement'; +import Header from './Header'; +import PlayLevel from '../controllers/playLevel'; +import UserAuthForm from './UserAuthForm'; + +export default function App(playerLevel: PlayLevel): Element { + return createElement('div', { + class: 'app', + }, [ + Header(), + createElement('div', { + class: 'app__container', + }, [playerLevel.gameView.viewArea]), + UserAuthForm(), + ]); +} diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 5054887..3bb343f 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -85,7 +85,7 @@ class GameView { this.ammoElement = document.createElement('div'); this.ammoElement.classList.add('ammo'); this.viewArea.append(this.levelArea, this.scoreElement, this.ammoElement); - document.querySelector('body')?.append(this.viewArea); + // document.querySelector('body')?.append(this.viewArea); this.sounds[SoundType.JUMP] = new Audio(jumpSound); this.sounds[SoundType.LAND] = new Audio(landSound); this.sounds[SoundType.SHOT] = new Audio(shotSound); diff --git a/client/src/styles/level.css b/client/src/styles/level.css index 33c1fb5..a151afe 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -1,4 +1,3 @@ -@import "https://fonts.cdnfonts.com/css/perfect-dos-vga-437"; @import "lootKeyframes"; body { From a73fdd426c0505f627de4ede2e4c97afe09bd4af Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 18:37:41 +0300 Subject: [PATCH 141/196] feat: create user controller --- server/src/modules/auth/auth.controller.ts | 4 ++-- server/src/modules/user/user.controller.ts | 15 +++++++++++++++ server/src/modules/user/user.module.ts | 5 ++++- server/src/modules/user/user.service.ts | 13 +++++++++++++ server/src/types/dto/user/getUserDto.ts | 6 ++++++ 5 files changed, 40 insertions(+), 3 deletions(-) create mode 100644 server/src/modules/user/user.controller.ts create mode 100644 server/src/types/dto/user/getUserDto.ts diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index a6c82d0..c928491 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -39,7 +39,7 @@ export class AuthController { ); res.cookie('auth_token', registeredUser.accessToken, { - httpOnly: true, + httpOnly: false, }); res.status(HttpStatus.OK).send(registeredUser); @@ -74,7 +74,7 @@ export class AuthController { ); res.cookie('auth_token', registeredUser.accessToken, { - httpOnly: true, + httpOnly: false, }); res.status(HttpStatus.OK).send(registeredUser); diff --git a/server/src/modules/user/user.controller.ts b/server/src/modules/user/user.controller.ts new file mode 100644 index 0000000..a35c412 --- /dev/null +++ b/server/src/modules/user/user.controller.ts @@ -0,0 +1,15 @@ +import { Controller, Get, Req, UseGuards } from '@nestjs/common'; +import { JwtAuthGuard } from '../../guards/jwtAuth.guard'; +import { AuthorizedRequest } from '../../types/authorizedRequest'; +import { UserInfoDto } from '../../types/dto/user/getUserDto'; +import { UserService } from './user.service'; + +@Controller('user') +export class UserController { + constructor(private readonly userService: UserService) {} + @Get() + @UseGuards(JwtAuthGuard) + async get(@Req() req: AuthorizedRequest): Promise { + return await this.userService.findOmitPassword(req.user); + } +} diff --git a/server/src/modules/user/user.module.ts b/server/src/modules/user/user.module.ts index e254c15..2d36ca9 100644 --- a/server/src/modules/user/user.module.ts +++ b/server/src/modules/user/user.module.ts @@ -2,11 +2,14 @@ import { Module } from '@nestjs/common'; import { UserService } from './user.service'; import { MongooseModule } from '@nestjs/mongoose'; import { User, UserSchema } from '../../models/scheme/user.schema'; +import { UserController } from './user.controller'; +import { ConfigService } from '@nestjs/config'; @Module({ imports: [ MongooseModule.forFeature([{ name: User.name, schema: UserSchema }]), ], - providers: [UserService], + providers: [UserService, ConfigService], + controllers: [UserController], }) export class UserModule {} diff --git a/server/src/modules/user/user.service.ts b/server/src/modules/user/user.service.ts index dab0384..9b6de3c 100644 --- a/server/src/modules/user/user.service.ts +++ b/server/src/modules/user/user.service.ts @@ -24,6 +24,19 @@ export class UserService { return result; } + async findOmitPassword(filter: object): Promise> { + const result = await this.userModel + .findOne(filter) + .select('-password') + .exec(); + + if (!result) { + throw new UserNotFoundError(filter); + } + + return result; + } + async findByUserNameAndAuthProvider( username: IUser['username'], authProvider: IUser['authProvider'], diff --git a/server/src/types/dto/user/getUserDto.ts b/server/src/types/dto/user/getUserDto.ts new file mode 100644 index 0000000..7552b7c --- /dev/null +++ b/server/src/types/dto/user/getUserDto.ts @@ -0,0 +1,6 @@ +import { IUser } from '../../interfaces/user'; + +export type UserInfoDto = Pick< + IUser, + '_id' | 'username' | 'authProvider' | 'createdAt' +>; From f2bb05701822d108cfd18febf95dce6379cbae2f Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 18:47:42 +0300 Subject: [PATCH 142/196] feat: create get user info API request --- .../api/requests/user/getUserInfoRequest.ts | 14 ++++++++++ .../api/responses/user/getUserInfoResponse.ts | 28 +++++++++++++++++++ 2 files changed, 42 insertions(+) create mode 100644 client/src/scripts/api/requests/user/getUserInfoRequest.ts create mode 100644 client/src/scripts/api/responses/user/getUserInfoResponse.ts diff --git a/client/src/scripts/api/requests/user/getUserInfoRequest.ts b/client/src/scripts/api/requests/user/getUserInfoRequest.ts new file mode 100644 index 0000000..a38dd45 --- /dev/null +++ b/client/src/scripts/api/requests/user/getUserInfoRequest.ts @@ -0,0 +1,14 @@ +import BaseAPIRequest from '../baseAPIRequest'; +import GetUserInfoResponse from '../../responses/user/getUserInfoResponse'; +import HTTPMethod from '../../../../types/enums/httpMethods'; + +export default class GetUserInfoRequest + extends BaseAPIRequest { + constructor() { + super( + HTTPMethod.GET, + '/user', + GetUserInfoResponse, + ); + } +} diff --git a/client/src/scripts/api/responses/user/getUserInfoResponse.ts b/client/src/scripts/api/responses/user/getUserInfoResponse.ts new file mode 100644 index 0000000..06ecc52 --- /dev/null +++ b/client/src/scripts/api/responses/user/getUserInfoResponse.ts @@ -0,0 +1,28 @@ +import { APIResponse } from '../../../../types/interfaces/api/apiResponse'; +import MappingFailedError from '../../../errors/mappingFailedError'; + +export default class GetUserInfoResponse implements APIResponse { + id?: string; + + username?: string; + + authProvider?: string; + + createdAt?: Date; + + async map(rawResponse: Response): Promise { + try { + const json = await rawResponse.json(); + + // eslint-disable-next-line no-underscore-dangle + this.id = json._id; + this.username = json.username; + this.authProvider = json.authProvider; + this.createdAt = new Date(Date.parse(json.createdAt)); + + return this; + } catch (e: unknown) { + throw new MappingFailedError(Response, GetUserInfoResponse); + } + } +} From 461822c310e9ad72c226eb01223338afd3f8adb5 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 23:19:19 +0300 Subject: [PATCH 143/196] feat: create utils for get and delete cookies --- client/src/scripts/utils/deleteCookie.ts | 3 +++ client/src/scripts/utils/getCookie.ts | 9 +++++++++ 2 files changed, 12 insertions(+) create mode 100644 client/src/scripts/utils/deleteCookie.ts create mode 100644 client/src/scripts/utils/getCookie.ts diff --git a/client/src/scripts/utils/deleteCookie.ts b/client/src/scripts/utils/deleteCookie.ts new file mode 100644 index 0000000..e52f7d0 --- /dev/null +++ b/client/src/scripts/utils/deleteCookie.ts @@ -0,0 +1,3 @@ +export default function deleteCookie(name: string): void { + document.cookie = `${name}=;expires=${Date.now()};path=/;`; +} diff --git a/client/src/scripts/utils/getCookie.ts b/client/src/scripts/utils/getCookie.ts new file mode 100644 index 0000000..ad91a2b --- /dev/null +++ b/client/src/scripts/utils/getCookie.ts @@ -0,0 +1,9 @@ +export default function getCookie(name: string): string | undefined { + const value = `; ${document.cookie}`; + const parts = value.split(`; ${name}=`); + if (parts.length === 2) { + return parts.pop()?.split(';').shift(); + } + + return undefined; +} From 138d268e463620efea6d7685932d28bcc58ba768 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 23:19:54 +0300 Subject: [PATCH 144/196] feat: create util for generate color from user id --- .../src/scripts/utils/generateColorFromUserId.ts | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) create mode 100644 client/src/scripts/utils/generateColorFromUserId.ts diff --git a/client/src/scripts/utils/generateColorFromUserId.ts b/client/src/scripts/utils/generateColorFromUserId.ts new file mode 100644 index 0000000..3eb9fc3 --- /dev/null +++ b/client/src/scripts/utils/generateColorFromUserId.ts @@ -0,0 +1,16 @@ +export default function generateColorFromUserId(userId: string): string { + let hash = 0; + + userId.split('') + .forEach((e) => { + hash = (hash * 33) + e.charCodeAt(0); + }); + + hash += userId.length; + + const r = Math.floor(((hash * 17) % 200) / 2) + 75; + const g = Math.floor(((hash * 19) % 200) / 2) + 75; + const b = Math.floor(((hash * 23) % 200) / 2) + 75; + + return `rgb(${r}, ${g}, ${b})`; +} From 68414cac4648f1d0adcdae67e8e54495b82cd51c Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 23:20:19 +0300 Subject: [PATCH 145/196] feat: add exit.svg --- client/src/assets/.gitkeep | 0 client/src/assets/icons/exit.svg | 2 ++ 2 files changed, 2 insertions(+) delete mode 100644 client/src/assets/.gitkeep create mode 100644 client/src/assets/icons/exit.svg diff --git a/client/src/assets/.gitkeep b/client/src/assets/.gitkeep deleted file mode 100644 index e69de29..0000000 diff --git a/client/src/assets/icons/exit.svg b/client/src/assets/icons/exit.svg new file mode 100644 index 0000000..c346c88 --- /dev/null +++ b/client/src/assets/icons/exit.svg @@ -0,0 +1,2 @@ + + From 74eac5e984d057e42579a6e74282253849653eab Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 23:20:45 +0300 Subject: [PATCH 146/196] feat: create auth controller --- .../src/scripts/controllers/authController.ts | 109 ++++++++++++++++++ 1 file changed, 109 insertions(+) create mode 100644 client/src/scripts/controllers/authController.ts diff --git a/client/src/scripts/controllers/authController.ts b/client/src/scripts/controllers/authController.ts new file mode 100644 index 0000000..19fa623 --- /dev/null +++ b/client/src/scripts/controllers/authController.ts @@ -0,0 +1,109 @@ +import { EventEmitter } from 'events'; +import api from './apiController'; +import AuthUserLocalRequest from '../api/requests/auth/authUserLocalRequest'; +import GetUserInfoRequest from '../api/requests/user/getUserInfoRequest'; +import deleteCookie from '../utils/deleteCookie'; + +class AuthController extends EventEmitter { + async loginUserLocal(username?: string, password?: string): Promise { + if (!username || !password) { + await api.fetch( + new GetUserInfoRequest(), + ) + .then((res) => this.emit('loginSuccess', res)) + .catch(() => {}); + return; + } + + if (username && (username.trim() === '' || username.length < 3)) { + this.emit( + 'loginFailed', + new Error('Username must be more than 3 characters!'), + ); + return; + } + + if (password && (password.trim() === '' || password.length < 8)) { + this.emit( + 'loginFailed', + new Error('Password must be more than 8 characters!'), + ); + return; + } + + await api.fetch( + new AuthUserLocalRequest( + username.trim(), + password.trim(), + 'login', + ), + ) + .then((res) => this.emit('loginSuccess', res)) + .catch((err) => this.emit('loginFailed', err)); + } + + async registerUserLocal( + username: string, + password: string, + confirmPassword: string, + ): Promise { + if (username.trim() === '' || username.length < 3) { + this.emit( + 'registerFailed', + new Error('Username must be more than 3 characters!'), + ); + return; + } + + if (username.length > 12) { + this.emit( + 'registerFailed', + new Error('The username must be no more than 12 characters!'), + ); + return; + } + + if (password.trim() === '' || password.length < 8) { + this.emit( + 'registerFailed', + new Error('Password must be more than 8 characters!'), + ); + return; + } + + if (confirmPassword.trim() === '') { + this.emit( + 'registerFailed', + new Error('Please confirm your password!'), + ); + return; + } + + if (confirmPassword.trim() !== password.trim()) { + this.emit( + 'registerFailed', + new Error('Password mismatch!'), + ); + return; + } + + await api.fetch( + new AuthUserLocalRequest( + username.trim(), + password.trim(), + 'register', + ), + ) + .then((res) => this.emit('registerSuccess', res)) + .catch((err) => this.emit('registerFailed', err)); + } + + userLogout(): void { + deleteCookie('auth_token'); + + this.emit('userLogout'); + } +} + +const authController = new AuthController(); +export default authController; From 84b522f885edb87d9c2e24c0ff766827ea8ad005 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 26 Feb 2023 23:23:40 +0300 Subject: [PATCH 147/196] feat: create user profile component --- client/src/scripts/components/Header.ts | 22 +---- client/src/scripts/components/UserAuthForm.ts | 63 ++++-------- client/src/scripts/components/UserProfile.ts | 95 +++++++++++++++++++ client/src/styles/components/header.scss | 10 -- client/src/styles/components/ui/buttons.scss | 3 +- .../src/styles/components/userAuthForm.scss | 4 +- client/src/styles/components/userProfile.scss | 85 +++++++++++++++++ client/src/styles/level.css | 1 - client/src/styles/main.scss | 5 + 9 files changed, 211 insertions(+), 77 deletions(-) create mode 100644 client/src/scripts/components/UserProfile.ts create mode 100644 client/src/styles/components/userProfile.scss diff --git a/client/src/scripts/components/Header.ts b/client/src/scripts/components/Header.ts index 1ad8664..5bc8fb8 100644 --- a/client/src/scripts/components/Header.ts +++ b/client/src/scripts/components/Header.ts @@ -1,33 +1,15 @@ import createElement from '../utils/createElement'; +import UserProfile from './UserProfile'; export default function Header(): Element { const logoImage = createElement('img', { class: 'header__logo', }); - const loginButton = createElement('button', { - class: 'header__auth-button login__button', - onClick: () => { - document.querySelector('.auth-form')?.classList - .add('active', 'login'); - }, - }, [document.createTextNode('Login')]); - const registerButton = createElement('button', { - class: 'header__auth-button register__button', - onClick: () => { - document.querySelector('.auth-form')?.classList - .add('active', 'register'); - }, - }, [document.createTextNode('Register')]); return createElement('header', { class: 'app__header header', }, [ logoImage, - createElement('div', { - class: 'header__auth login', - }, [ - loginButton, - registerButton, - ]), + UserProfile(), ]); } diff --git a/client/src/scripts/components/UserAuthForm.ts b/client/src/scripts/components/UserAuthForm.ts index 4da27e4..4dab2ed 100644 --- a/client/src/scripts/components/UserAuthForm.ts +++ b/client/src/scripts/components/UserAuthForm.ts @@ -1,7 +1,5 @@ import createElement from '../utils/createElement'; -import api from '../controllers/apiController'; -import AuthUserLocalRequest from '../api/requests/auth/authUserLocalRequest'; -import { APIResponseError } from '../../types/apiResponseError'; +import authController from '../controllers/authController'; export default function UserAuthForm(): Element { const errorLabel = createElement('label', { @@ -36,54 +34,33 @@ export default function UserAuthForm(): Element { const loginButton = createElement('button', { class: 'auth-form__button auth-form__login-button', onClick: async () => { - await api.fetch( - new AuthUserLocalRequest( - usernameInput.value.trim(), - passwordInput.value.trim(), - 'login', - ), - ) - .then((res) => { - if (res.accessToken) { - closeForm(); - } - }) - .catch((err: APIResponseError) => { - if (err.message) { - errorLabel.textContent = err.message; - } - }); + await authController.loginUserLocal( + usernameInput.value.trim() || ' ', + passwordInput.value.trim() || ' ', + ); }, }, [document.createTextNode('Login')]); - const registerButton = createElement('button', { class: 'auth-form__button auth-form__register-button', onClick: async () => { - if (passwordInput.value.trim() !== passwordConfirmInput.value.trim()) { - errorLabel.textContent = 'Password mismatch!'; - return; - } - - await api.fetch( - new AuthUserLocalRequest( - usernameInput.value.trim(), - passwordInput.value.trim(), - 'register', - ), - ) - .then((res) => { - if (res.accessToken) { - closeForm(); - } - }) - .catch((err: APIResponseError) => { - if (err.message) { - errorLabel.textContent = err.message; - } - }); + await authController.registerUserLocal( + usernameInput.value.trim(), + passwordInput.value.trim(), + passwordConfirmInput.value.trim(), + ); }, }, [document.createTextNode('Register')]); + authController.on('loginFailed', (err: { message: string }) => { + errorLabel.textContent = err.message; + }); + authController.on('registerFailed', (err: { message: string }) => { + errorLabel.textContent = err.message; + }); + + authController.on('loginSuccess', closeForm); + authController.on('registerSuccess', closeForm); + return createElement('div', { class: 'auth-form', onClick: closeForm, diff --git a/client/src/scripts/components/UserProfile.ts b/client/src/scripts/components/UserProfile.ts new file mode 100644 index 0000000..5101637 --- /dev/null +++ b/client/src/scripts/components/UserProfile.ts @@ -0,0 +1,95 @@ +import createElement from '../utils/createElement'; +import GetUserInfoResponse from '../api/responses/user/getUserInfoResponse'; +import authController from '../controllers/authController'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import exitIcon from '../../assets/icons/exit.svg'; +import generateColorFromUserId from '../utils/generateColorFromUserId'; + +let isFirstRender = true; + +export default function UserProfile(): Element { + if (isFirstRender) { + isFirstRender = false; + authController.loginUserLocal() + .then(() => {}) + .catch(() => {}); + } + + const loginButton = createElement('button', { + class: 'header__auth-button login__button', + onClick: () => { + document.querySelector('.auth-form')?.classList + .add('active', 'login'); + }, + }, [document.createTextNode('Login')]); + const registerButton = createElement('button', { + class: 'header__auth-button register__button', + onClick: () => { + document.querySelector('.auth-form')?.classList + .add('active', 'register'); + }, + }, [document.createTextNode('Register')]); + const userAvatarImage = createElement('span', { + class: 'user-profile__avatar-image', + }); + const userAvatar = createElement('div', { + class: 'user-profile__avatar', + }, [ + userAvatarImage, + ]); + const userId = createElement('span', { + class: 'user-profile__id', + }); + const username = createElement('span', { + class: 'user-profile__username', + }); + const authButtons = createElement('div', { + class: 'user-profile__auth-buttons active', + }, [ + loginButton, + registerButton, + ]); + const userInfo = createElement('div', { + class: 'user-profile__user', + }, [ + userAvatar, + createElement('div', { + class: 'user-profile__user-info', + }, [ + userId, + username, + ]), + createElement('img', { + class: 'user-profile__exit-button', + src: exitIcon, + onClick: () => { + authController.userLogout(); + }, + }), + ]); + + const onUserAuth = (user: GetUserInfoResponse): void => { + authButtons.classList.remove('active'); + userInfo.classList.add('active'); + + userAvatarImage.textContent = (`${user.username}`)[0].toString(); + userAvatar.style.backgroundColor = generateColorFromUserId(user.id || ''); + userId.textContent = `${user.id}`; + username.textContent = `${user.username}`; + }; + + authController.on('loginSuccess', onUserAuth); + authController.on('registerSuccess', onUserAuth); + authController.on('userLogout', () => { + userInfo.classList.remove('active'); + authButtons.classList.add('active'); + }); + + return createElement('div', { + class: 'header__user-profile user-profile', + }, [ + userInfo, + authButtons, + ]); +} diff --git a/client/src/styles/components/header.scss b/client/src/styles/components/header.scss index 3f99fc9..154b8c4 100644 --- a/client/src/styles/components/header.scss +++ b/client/src/styles/components/header.scss @@ -6,14 +6,4 @@ width: 100%; height: 64px; padding-inline: 16px; - - &__auth { - display: flex; - flex-direction: row; - gap: 8px; - } - - &__auth-button { - font-size: 18pt; - } } diff --git a/client/src/styles/components/ui/buttons.scss b/client/src/styles/components/ui/buttons.scss index 12c08ec..7504a6f 100644 --- a/client/src/styles/components/ui/buttons.scss +++ b/client/src/styles/components/ui/buttons.scss @@ -4,6 +4,7 @@ button { justify-content: center; padding: 8px; font-family: "Perfect DOS VGA 437", sans-serif; + color: #a6896d; font-size: 22pt; outline: none; border: none; @@ -12,7 +13,7 @@ button { transition: all 0.3s ease-in-out; &:hover { - background: #000; + background: #a6896d; color: #fff; transition: all 0.3s ease-in-out; } diff --git a/client/src/styles/components/userAuthForm.scss b/client/src/styles/components/userAuthForm.scss index 90ea72e..35d46de 100644 --- a/client/src/styles/components/userAuthForm.scss +++ b/client/src/styles/components/userAuthForm.scss @@ -19,9 +19,9 @@ align-items: center; justify-content: center; flex-direction: column; - gap: 16px; + gap: 8px; padding: 32px; - background: transparentize(#555, 0.75); + background: transparentize(#a6896d, 0.75); backdrop-filter: blur(16px); border-radius: 8px; } diff --git a/client/src/styles/components/userProfile.scss b/client/src/styles/components/userProfile.scss new file mode 100644 index 0000000..9d17b0c --- /dev/null +++ b/client/src/styles/components/userProfile.scss @@ -0,0 +1,85 @@ +.user-profile { + display: flex; + flex-direction: row; + + &__user { + display: none; + flex-direction: row; + align-items: center; + padding: 16px 8px 8px; + background: #bbada0; + border-radius: 0 0 5px 5px; + + &-info { + display: flex; + flex-direction: column; + margin-left: 16px; + } + + &.active { + display: flex; + } + } + + &__exit-button { + display: flex; + align-items: center; + justify-content: center; + width: 48px; + height: 48px; + margin-left: 16px; + outline: none; + border: none; + background: transparent; + cursor: pointer; + filter: invert(90%) sepia(2%) saturate(2712%) hue-rotate(322deg) brightness(110%) contrast(87%); + + &:hover { + filter: invert(19%) sepia(89%) saturate(3290%) hue-rotate(337deg) brightness(85%) contrast(103%); + } + } + + &__id { + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 10pt; + color: #eee4da; + text-transform: uppercase; + } + + &__username { + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 32pt; + color: #fff; + } + + &__auth-buttons { + display: none; + flex-direction: row; + gap: 8px; + + &.active { + display: flex; + } + } + + &__avatar { + display: flex; + align-items: center; + justify-content: center; + width: 64px; + height: 64px; + border-radius: 100%; + + &-image { + display: flex; + align-items: center; + justify-content: center; + margin-top: 5px; + margin-left: 7px; + text-transform: uppercase; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 32pt; + color: #fff; + } + } +} diff --git a/client/src/styles/level.css b/client/src/styles/level.css index 43b0ed9..4543795 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -3,7 +3,6 @@ body { overflow: hidden; height: 100vw; - background-color: #ccc; } #container { diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index 109b907..a73945e 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -4,6 +4,7 @@ @import "zombieAnimation"; @import "croneAnimation"; @import "components/header"; +@import "components/userProfile"; @import "components/userAuthForm"; @import "components/ui/inputs"; @import "components/ui/buttons"; @@ -13,3 +14,7 @@ padding: 0; box-sizing: border-box; } + +body { + background-color: #faf8ef; +} From d9d873a4675da0c5079a7a114a81c5c686de0482 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Mon, 27 Feb 2023 01:27:44 +0300 Subject: [PATCH 148/196] fix: change speed zombie animation --- client/src/styles/zombieAnimation.scss | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/client/src/styles/zombieAnimation.scss b/client/src/styles/zombieAnimation.scss index f78383d..b02b866 100644 --- a/client/src/styles/zombieAnimation.scss +++ b/client/src/styles/zombieAnimation.scss @@ -7,32 +7,32 @@ &-move-left { background: url("../assets/sprites/zombie_sprite.png"); - animation: move-left-zombie 0.7s ease-in-out infinite; + animation: move-left-zombie 1s ease-in-out infinite; animation-timing-function: steps(1); } &-move-right { background: url("../assets/sprites/zombie_sprite.png"); - animation: move-right-zombie 0.7s ease-in-out infinite; + animation: move-right-zombie 1s ease-in-out infinite; animation-timing-function: steps(1); } &-move-down { background: url("../assets/sprites/zombie_sprite.png"); - animation: move-down-zombie 0.7s ease-in-out infinite; + animation: move-down-zombie 1s ease-in-out infinite; animation-timing-function: steps(1); } &-attack { &-left { background: url("../assets/sprites/zombie_sprite.png"); - animation: attack-left-zombie 0.7s ease-in-out infinite; + animation: attack-left-zombie 1s ease-in-out infinite; animation-timing-function: steps(1); } &-right { background: url("../assets/sprites/zombie_sprite.png"); - animation: attack-right-zombie 0.8s ease-in-out infinite; + animation: attack-right-zombie 1s ease-in-out infinite; animation-timing-function: steps(1); } } From a15a9ce261b7f47cf6d80b0f26805dece6a5a650 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Mon, 27 Feb 2023 02:12:52 +0300 Subject: [PATCH 149/196] fix: fix generate loot --- client/src/scripts/components/game.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 1331c46..642da49 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -187,7 +187,7 @@ class GameView { }, sprite: document.createElement('div'), grabbed: false, - bonus: parseInt(entityType, 10) * randomValue, + bonus: randomValue, }; const door: Door = { area: { @@ -328,6 +328,7 @@ class GameView { this.platforms = []; this.monsters = []; this.levelArea.innerHTML = ''; + this.doors = []; } updateScoreOnScreen(): void { From 53b733aea7a417c422d8170d227b4e2fdeea3327 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 02:16:04 +0300 Subject: [PATCH 150/196] feat: create leaderboard component --- client/src/scripts/components/App.ts | 9 +- client/src/scripts/components/Leaderboard.ts | 84 +++++++++++++++++++ client/src/scripts/components/ScoreCard.ts | 43 ++++++++++ .../controllers/leaderboardController.ts | 17 ++++ client/src/styles/components/leaderboard.scss | 64 ++++++++++++++ client/src/styles/components/scoreCard.scss | 71 ++++++++++++++++ client/src/styles/level.css | 1 - client/src/styles/main.scss | 11 +++ client/src/types/userScore.ts | 10 +++ 9 files changed, 308 insertions(+), 2 deletions(-) create mode 100644 client/src/scripts/components/Leaderboard.ts create mode 100644 client/src/scripts/components/ScoreCard.ts create mode 100644 client/src/scripts/controllers/leaderboardController.ts create mode 100644 client/src/styles/components/leaderboard.scss create mode 100644 client/src/styles/components/scoreCard.scss create mode 100644 client/src/types/userScore.ts diff --git a/client/src/scripts/components/App.ts b/client/src/scripts/components/App.ts index 4ec456c..6557deb 100644 --- a/client/src/scripts/components/App.ts +++ b/client/src/scripts/components/App.ts @@ -2,6 +2,7 @@ import createElement from '../utils/createElement'; import Header from './Header'; import PlayLevel from '../controllers/playLevel'; import UserAuthForm from './UserAuthForm'; +import Leaderboard from './Leaderboard'; export default function App(playerLevel: PlayLevel): Element { return createElement('div', { @@ -10,7 +11,13 @@ export default function App(playerLevel: PlayLevel): Element { Header(), createElement('div', { class: 'app__container', - }, [playerLevel.gameView.viewArea]), + }, [ + Leaderboard(), + playerLevel.gameView.viewArea, + createElement('div', { + style: 'display: flex; width: 485px', + }), + ]), UserAuthForm(), ]); } diff --git a/client/src/scripts/components/Leaderboard.ts b/client/src/scripts/components/Leaderboard.ts new file mode 100644 index 0000000..fc114e3 --- /dev/null +++ b/client/src/scripts/components/Leaderboard.ts @@ -0,0 +1,84 @@ +import createElement from '../utils/createElement'; +import ScoreCard from './ScoreCard'; +import leaderboardController from '../controllers/leaderboardController'; +import GetLeaderboardResponse + from '../api/responses/leaderboard/getLeaderboardResponse'; + +export default function Leaderboard(): Element { + let page = 1; + const limit = 7; + + const fetchItems = (): void => { + leaderboardController.fetchLeaderboard(page, limit) + .then(() => {}) + .catch(() => {}); + }; + + fetchItems(); + + setInterval(() => fetchItems(), 60 * 1000); + + const currentPage = createElement('div', { + class: 'leaderboard__current-page', + }, [document.createTextNode(page.toString())]); + const prevPageButton = createElement('button', { + class: 'leaderboard__page-button leaderboard__prev-page-button', + onClick: () => { + page -= 1; + fetchItems(); + }, + }, [document.createTextNode('<')]); + const nextPageButton = createElement('button', { + class: 'leaderboard__page-button leaderboard__next-page-button', + onClick: () => { + page += 1; + fetchItems(); + }, + }, [document.createTextNode('>')]); + const pagination = createElement('div', { + class: 'leaderboard__pagination', + }, [ + prevPageButton, + currentPage, + nextPageButton, + ]); + let scoreList = createElement('div', { + class: 'leaderboard__list', + }, [ + document.createTextNode('So far it\'s empty :('), + ]); + + leaderboardController.on('success', (res: GetLeaderboardResponse) => { + const startIndex = (page - 1) * limit; + const newScoreList = createElement('div', { + class: 'leaderboard__list', + }, [ + ...res.scores + .map((score, i) => ScoreCard(i + 1 + startIndex, score)), + ]); + + scoreList.replaceWith(newScoreList); + scoreList = newScoreList; + + if (Math.ceil((res.totalCount || 0) / limit) > 1) { + pagination.classList.add('active'); + } else { + pagination.classList.remove('active'); + } + + prevPageButton.disabled = page === 1; + nextPageButton.disabled = page === Math.ceil((res.totalCount || 0) / limit) + || page + 1 > 99 / limit; + currentPage.textContent = page.toString(); + }); + + return createElement('div', { + class: 'leaderboard', + }, [ + createElement('h2', { + class: 'leaderboard__title', + }, [document.createTextNode('Leaderboard')]), + scoreList, + pagination, + ]); +} diff --git a/client/src/scripts/components/ScoreCard.ts b/client/src/scripts/components/ScoreCard.ts new file mode 100644 index 0000000..3086dfc --- /dev/null +++ b/client/src/scripts/components/ScoreCard.ts @@ -0,0 +1,43 @@ +import { UserScore } from '../../types/userScore'; +import createElement from '../utils/createElement'; +import generateColorFromUserId from '../utils/generateColorFromUserId'; + +export default function ScoreCard( + index: number, + scoreData: UserScore, +): Element { + return createElement('div', { + class: 'score-card', + }, [ + createElement('div', { + class: 'score-card__main', + }, [ + createElement('span', { + class: 'score-card__index', + }, [document.createTextNode(index.toString())]), + createElement('div', { + class: 'score-card__user-avatar', + style: `background-color: ${generateColorFromUserId(scoreData.user?.id || '')}`, + }, [ + createElement('span', { + class: 'score-card__user-avatar-image', + }, [document.createTextNode(`${scoreData.user?.username}`[0])]), + ]), + createElement('div', { + class: 'score-card__score-info', + }, [ + createElement('span', { + class: 'score-card__datetime', + }, [document.createTextNode( + `${scoreData.createdAt?.toLocaleDateString()} | ${scoreData.createdAt?.toLocaleTimeString()}`, + )]), + createElement('span', { + class: 'score-card__username', + }, [document.createTextNode(`${scoreData.user?.username}`)]), + ]), + ]), + createElement('span', { + class: 'score-card__score', + }, [document.createTextNode(`${scoreData.score}`)]), + ]); +} diff --git a/client/src/scripts/controllers/leaderboardController.ts b/client/src/scripts/controllers/leaderboardController.ts new file mode 100644 index 0000000..cbc1b13 --- /dev/null +++ b/client/src/scripts/controllers/leaderboardController.ts @@ -0,0 +1,17 @@ +import { EventEmitter } from 'events'; +import api from './apiController'; +import GetLeaderboardRequest + from '../api/requests/leaderboard/getLeaderboardRequest'; + +class LeaderboardController extends EventEmitter { + async fetchLeaderboard(page = 1, limit = 100, sortBy: 'asc' | 'desc' = 'desc'): Promise { + await api.fetch( + new GetLeaderboardRequest(page, limit, sortBy), + ) + .then((res) => this.emit('success', res)) + .catch(() => {}); + } +} + +const leaderboardController = new LeaderboardController(); +export default leaderboardController; diff --git a/client/src/styles/components/leaderboard.scss b/client/src/styles/components/leaderboard.scss new file mode 100644 index 0000000..6910a0c --- /dev/null +++ b/client/src/styles/components/leaderboard.scss @@ -0,0 +1,64 @@ +.leaderboard { + display: flex; + align-items: center; + flex-direction: column; + width: 485px; + height: 630px; + padding: 8px; + gap: 8px; + border-radius: 8px; + + &__title { + display: flex; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 32pt; + color: #776e65; + } + + &__list { + display: flex; + align-items: center; + flex-direction: column; + gap: 8px; + height: 496px; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 24pt; + color: #776e65; + overflow-y: auto; + } + + &__pagination { + display: none; + align-items: center; + justify-content: center; + flex-direction: row; + width: 100%; + gap: 16px; + font-size: 32pt; + + &.active { + display: flex; + } + } + + &__page-button { + display: flex; + align-items: center; + justify-content: center; + width: 128px; + height: 48px; + font-size: 32pt; + + &:disabled { + opacity: 0; + } + } + + &__current-page { + display: flex; + margin-inline: 16px; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 32pt; + color: #776e65; + } +} diff --git a/client/src/styles/components/scoreCard.scss b/client/src/styles/components/scoreCard.scss new file mode 100644 index 0000000..edc1da4 --- /dev/null +++ b/client/src/styles/components/scoreCard.scss @@ -0,0 +1,71 @@ +.score-card { + display: flex; + align-items: center; + width: 100%; + height: 64px; + padding: 4px; + background: #a6896d; + border-radius: 5px; + + &__main { + display: flex; + align-items: center; + width: 100%; + } + + &__user-avatar { + display: flex; + align-items: center; + justify-content: center; + width: 48px; + height: 48px; + border-radius: 100%; + + &-image { + margin-top: 2px; + margin-left: 4px; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 24pt; + font-weight: 600; + color: #fff; + text-transform: uppercase; + } + } + + &__index { + display: flex; + justify-content: flex-end; + margin-inline: 8px; + min-width: 48px; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 32pt; + color: #fff; + } + + &__score-info { + display: flex; + flex-direction: column; + margin-inline: 16px; + } + + &__datetime { + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 10pt; + color: #eee4da; + text-transform: uppercase; + } + + &__username { + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 24pt; + color: #fff; + } + + &__score { + min-width: 105px; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 28pt; + text-align: right; + color: #fff; + } +} diff --git a/client/src/styles/level.css b/client/src/styles/level.css index 4543795..fa80940 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -15,7 +15,6 @@ body { background-color: #fff; opacity: 1; overflow: hidden; - margin: 100px auto; } .player-area { diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index a73945e..6ce69b4 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -6,6 +6,8 @@ @import "components/header"; @import "components/userProfile"; @import "components/userAuthForm"; +@import "components/leaderboard"; +@import "components/scoreCard"; @import "components/ui/inputs"; @import "components/ui/buttons"; @@ -18,3 +20,12 @@ body { background-color: #faf8ef; } + +.app { + &__container { + display: flex; + justify-content: space-between; + flex-direction: row; + padding-block: 22px; + } +} diff --git a/client/src/types/userScore.ts b/client/src/types/userScore.ts new file mode 100644 index 0000000..12a77fb --- /dev/null +++ b/client/src/types/userScore.ts @@ -0,0 +1,10 @@ +export type UserScore = { + id?: string + score?: number + createdAt?: Date + user?: { + id?: string + username?: string + authProvider?: string + } +}; From ddccf88a82caac87b2ee04939daa056c9e5af835 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 02:36:11 +0300 Subject: [PATCH 151/196] fix: fix fetch leaderboard timeout --- client/src/scripts/components/Leaderboard.ts | 4 ++++ client/src/scripts/controllers/leaderboardController.ts | 2 ++ 2 files changed, 6 insertions(+) diff --git a/client/src/scripts/components/Leaderboard.ts b/client/src/scripts/components/Leaderboard.ts index fc114e3..181f6f4 100644 --- a/client/src/scripts/components/Leaderboard.ts +++ b/client/src/scripts/components/Leaderboard.ts @@ -48,6 +48,10 @@ export default function Leaderboard(): Element { document.createTextNode('So far it\'s empty :('), ]); + leaderboardController.on('fetching', () => { + prevPageButton.disabled = true; + nextPageButton.disabled = true; + }); leaderboardController.on('success', (res: GetLeaderboardResponse) => { const startIndex = (page - 1) * limit; const newScoreList = createElement('div', { diff --git a/client/src/scripts/controllers/leaderboardController.ts b/client/src/scripts/controllers/leaderboardController.ts index cbc1b13..a16144d 100644 --- a/client/src/scripts/controllers/leaderboardController.ts +++ b/client/src/scripts/controllers/leaderboardController.ts @@ -5,6 +5,8 @@ import GetLeaderboardRequest class LeaderboardController extends EventEmitter { async fetchLeaderboard(page = 1, limit = 100, sortBy: 'asc' | 'desc' = 'desc'): Promise { + this.emit('fetching'); + await api.fetch( new GetLeaderboardRequest(page, limit, sortBy), ) From 0d60322e68456cdf8a421d2c9e60f68b9dcc4252 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 03:37:32 +0300 Subject: [PATCH 152/196] feat: create base results component --- client/src/scripts/components/App.ts | 5 +- .../src/scripts/components/BestResultCard.ts | 24 ++++++++ client/src/scripts/components/BestResults.ts | 61 +++++++++++++++++++ .../controllers/leaderboardController.ts | 15 +++++ client/src/scripts/models/.gitkeep | 0 .../src/styles/components/bestResultCard.scss | 40 ++++++++++++ client/src/styles/components/bestResults.scss | 29 +++++++++ client/src/styles/main.scss | 2 + client/src/types/userScore.ts | 7 +++ 9 files changed, 180 insertions(+), 3 deletions(-) create mode 100644 client/src/scripts/components/BestResultCard.ts create mode 100644 client/src/scripts/components/BestResults.ts delete mode 100644 client/src/scripts/models/.gitkeep create mode 100644 client/src/styles/components/bestResultCard.scss create mode 100644 client/src/styles/components/bestResults.scss diff --git a/client/src/scripts/components/App.ts b/client/src/scripts/components/App.ts index 6557deb..37eabcb 100644 --- a/client/src/scripts/components/App.ts +++ b/client/src/scripts/components/App.ts @@ -3,6 +3,7 @@ import Header from './Header'; import PlayLevel from '../controllers/playLevel'; import UserAuthForm from './UserAuthForm'; import Leaderboard from './Leaderboard'; +import BestResults from './BestResults'; export default function App(playerLevel: PlayLevel): Element { return createElement('div', { @@ -14,9 +15,7 @@ export default function App(playerLevel: PlayLevel): Element { }, [ Leaderboard(), playerLevel.gameView.viewArea, - createElement('div', { - style: 'display: flex; width: 485px', - }), + BestResults(), ]), UserAuthForm(), ]); diff --git a/client/src/scripts/components/BestResultCard.ts b/client/src/scripts/components/BestResultCard.ts new file mode 100644 index 0000000..a4f97ba --- /dev/null +++ b/client/src/scripts/components/BestResultCard.ts @@ -0,0 +1,24 @@ +import { Score } from '../../types/userScore'; +import createElement from '../utils/createElement'; + +export default function BestResultCard(index: number, score: Score): Element { + return createElement('div', { + class: 'best-score', + }, [ + createElement('div', { + class: 'best-score__index', + }, [document.createTextNode(`${index}`)]), + createElement('div', { + class: 'best-score__info', + }, [ + createElement('span', { + class: 'best-score__datetime', + }, [document.createTextNode( + `${score.createdAt?.toLocaleDateString()} | ${score.createdAt?.toLocaleTimeString()}`, + )]), + createElement('span', { + class: 'best-score__score', + }, [document.createTextNode(`${score.score}`)]), + ]), + ]); +} diff --git a/client/src/scripts/components/BestResults.ts b/client/src/scripts/components/BestResults.ts new file mode 100644 index 0000000..51eed46 --- /dev/null +++ b/client/src/scripts/components/BestResults.ts @@ -0,0 +1,61 @@ +import createElement from '../utils/createElement'; +import BestResultCard from './BestResultCard'; +import leaderboardController from '../controllers/leaderboardController'; +import authController from '../controllers/authController'; +import GetScoreResponse from '../api/responses/score/getScoreResponse'; + +export default function BestResults(): Element { + const placeholder = document.createTextNode( + 'Authorize to save and see the best results!', + ); + let list = createElement('div', { + class: 'best-results__list', + }, [ + placeholder, + ]); + + authController.on('loginSuccess', () => { + leaderboardController.fetchUserBestResults(1, 10) + .then(() => { + placeholder.textContent = 'You haven\'t set a record yet!'; + }) + .catch(() => {}); + }); + authController.on('registerSuccess', () => { + leaderboardController.fetchUserBestResults(1, 10) + .then(() => { + placeholder.textContent = 'You haven\'t set a record yet!'; + }) + .catch(() => {}); + }); + authController.on('userLogout', () => { + list.replaceChildren(placeholder); + + placeholder.textContent = 'Authorize to save and see the best results!'; + }); + leaderboardController.on('successUserBestResult', (res: GetScoreResponse) => { + if (res.scores.length < 1) { + placeholder.textContent = 'You haven\'t set a record yet!'; + return; + } + + const newList = createElement('div', { + class: 'best-results__list', + }, [ + ...res.scores + .map((score, i) => BestResultCard(i + 1, score)), + ]); + + list.replaceWith(newList); + list = newList; + }); + + return createElement('div', { + class: 'best-results', + }, [ + createElement('h2', { + class: 'best-results__title', + }, [document.createTextNode('Best results')]), + list, + ]); +} diff --git a/client/src/scripts/controllers/leaderboardController.ts b/client/src/scripts/controllers/leaderboardController.ts index a16144d..d42506a 100644 --- a/client/src/scripts/controllers/leaderboardController.ts +++ b/client/src/scripts/controllers/leaderboardController.ts @@ -2,6 +2,7 @@ import { EventEmitter } from 'events'; import api from './apiController'; import GetLeaderboardRequest from '../api/requests/leaderboard/getLeaderboardRequest'; +import GetScoreRequest from '../api/requests/score/getScoreRequest'; class LeaderboardController extends EventEmitter { async fetchLeaderboard(page = 1, limit = 100, sortBy: 'asc' | 'desc' = 'desc'): Promise { @@ -13,6 +14,20 @@ class LeaderboardController extends EventEmitter { .then((res) => this.emit('success', res)) .catch(() => {}); } + + async fetchUserBestResults( + page = 1, + limit = 100, + sortBy: 'asc' | 'desc' = 'desc', + ): Promise { + this.emit('fetchingUserBestResult'); + + await api.fetch( + new GetScoreRequest(page, limit, sortBy), + ) + .then((res) => this.emit('successUserBestResult', res)) + .catch(() => {}); + } } const leaderboardController = new LeaderboardController(); diff --git a/client/src/scripts/models/.gitkeep b/client/src/scripts/models/.gitkeep deleted file mode 100644 index e69de29..0000000 diff --git a/client/src/styles/components/bestResultCard.scss b/client/src/styles/components/bestResultCard.scss new file mode 100644 index 0000000..53e0c89 --- /dev/null +++ b/client/src/styles/components/bestResultCard.scss @@ -0,0 +1,40 @@ +.best-score { + display: flex; + align-items: center; + width: 100%; + height: 64px; + padding: 4px; + background: #a6896d; + border-radius: 5px; + + &__index { + display: flex; + justify-content: flex-end; + margin-inline: 8px; + min-width: 48px; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 20pt; + color: #fff; + } + + &__info { + display: flex; + flex-direction: column; + margin-inline: 16px; + } + + &__datetime { + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 10pt; + color: #eee4da; + text-transform: uppercase; + } + + &__score { + min-width: 105px; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 20pt; + text-align: right; + color: #fff; + } +} diff --git a/client/src/styles/components/bestResults.scss b/client/src/styles/components/bestResults.scss new file mode 100644 index 0000000..7b33512 --- /dev/null +++ b/client/src/styles/components/bestResults.scss @@ -0,0 +1,29 @@ +.best-results { + display: flex; + align-items: center; + flex-direction: column; + width: 485px; + height: 630px; + padding: 8px; + gap: 8px; + border-radius: 8px; + + &__title { + display: flex; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 32pt; + color: #776e65; + } + + &__list { + display: flex; + align-items: center; + flex-direction: column; + gap: 8px; + text-align: center; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 24pt; + color: #776e65; + overflow-y: auto; + } +} diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index 6ce69b4..3e3696b 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -7,6 +7,8 @@ @import "components/userProfile"; @import "components/userAuthForm"; @import "components/leaderboard"; +@import "components/bestResultCard"; +@import "components/bestResults"; @import "components/scoreCard"; @import "components/ui/inputs"; @import "components/ui/buttons"; diff --git a/client/src/types/userScore.ts b/client/src/types/userScore.ts index 12a77fb..5114787 100644 --- a/client/src/types/userScore.ts +++ b/client/src/types/userScore.ts @@ -8,3 +8,10 @@ export type UserScore = { authProvider?: string } }; + +export type Score = { + id?: string + score?: number + createdAt?: Date + user?: string +}; From 00d2ed3444019a6a71f2fc9a690e3f1d39f2eaf3 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Mon, 27 Feb 2023 03:47:48 +0300 Subject: [PATCH 153/196] feat: made new loot sprites --- client/src/assets/sprites/1600.png | Bin 0 -> 2976 bytes client/src/assets/sprites/800.png | Bin 0 -> 2942 bytes client/src/assets/sprites/bonus16.png | Bin 0 -> 3345 bytes client/src/assets/sprites/bonus8.png | Bin 0 -> 3322 bytes 4 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 client/src/assets/sprites/1600.png create mode 100644 client/src/assets/sprites/800.png create mode 100644 client/src/assets/sprites/bonus16.png create mode 100644 client/src/assets/sprites/bonus8.png diff --git a/client/src/assets/sprites/1600.png b/client/src/assets/sprites/1600.png new file mode 100644 index 0000000000000000000000000000000000000000..deb58f1d1fdf3acd2d43c367d50806ba249f9825 GIT binary patch literal 2976 zcmV;R3t#k!P)StO&>uS)ve<0AYj>5AR{$W90N^4L=L-RlQUJ&DC0@ZjPh;=*jPLSYvv5M~MFBAl0-BNIsH z15C~g000{K(ZT*WKal6<?_01!^k@7iDG<<3=fuAC~28EsPoqkpK{9G%|Vj005J}`Hw&=0RYXHq~ibpyyzHQsFW8>#s~laM4*8xut5h5 z!4#~(4xGUqyucR%VFpA%3?#rj5JCpzfE)^;7?wd9RKPme1hudO8lVxH;SjXJF*pt9 z;1XPc>u?taU>Kgl7`%oF1VP9M6Ja4bh!J9r*dopd7nzO(B4J20l7OTj>4+3jBE`sZ zqynizYLQ(?Bl0bB6giDtK>Co|$RIL`{EECsF_eL_Q3KQhbwIhO9~z3rpmWi5G!I>X zmZEFX8nhlgfVQHi(M#xcbO3#dj$?q)F%D*o*1Pf{>6$SWH+$s3q(pv=X`qR|$iJF~TPzlc-O$C3+J1 z#CT#lv5;6stS0Uu9wDA3UMCI{Uz12A4#|?_P6{CkNG+sOq(0IRX`DyT~9-sA|ffUF>wk++Z!kWZ5P$;0Hg6gtI-;!FvmBvPc55=u2?Kjj3apE5$3psG>L zsh-pbs)#zDT1jo7c2F-(3)vyY4>O^>2$gY-Gd%Qm(Z8e zYv>2*=jns=cMJ`N4THx>VkjAF8G9M07`GWOnM|ey)0dgZR4~^v8<}UA514ONSSt1^ zd=-((5|uiYR+WC0=c-gyb5%dpd8!Lkt5pxHURHgkMpd&=fR^vEcAI*_=wwAG2sV%zY%w@v@XU~7=xdm1xY6*0;iwVIXu6TaXrs|dqbIl~ z?uTdNHFy_3W~^@g_pF#!K2~{F^;XxcN!DEJEbDF7 zS8PxlSDOr*I-AS3sI8l=#CDr)-xT5$k15hA^;2%zG3@;83hbKf2JJcaVfH2VZT8O{ z%p4LO);n}Nd~$Sk%yw*Wyz8XlG{dRHsl(}4XB%gsbDi@w7p6;)%MzD%mlsoQr;4X; zpL)xc%+^yMd)ZNTI#eJ*$O)i@o$z8)e??LqN_gLa_%;TM>o2SC_ zkmoO6c3xRt`@J4dvz#WL)-Y|z+r(Soy~}%GIzByR`p)SCKE^%*pL(B%zNWq+-#xw~ ze%5}Oeh2)X`#bu}{g3#+;d$~F@lFL`0l@*~0lk45fwKc^10MvL1f>Tx1&sx}1}_Xg z6+#RN4Ot&@lW)Km@*DYMGu&q^n$Z=?2%QyL8~QNJCQKgI5srq>2;UHXZ>IT7>CCnW zh~P(Th`1kV8JQRPeH1AwGO8}>QM6NZadh`A)~w`N`)9q5@sFvDxjWlxwsLl7tZHmh zY-8-3xPZ8-xPf?w_(k!T5_A(J3GIpG#Ms0=iQ{tu=WLoYoaCBRmULsT<=mpV7v|~C z%bs^USv6UZd^m-e5|^?+<%1wXP%juy<)>~<9TW0|n}ttBzM_qyQL(qUN<5P0omQ3h zINdvaL;7fjPeygdGYL;pD|wL_lDQ-EO;$wK-mK5raoH_7l$?~Dqf!lNmb5F^Ft;eT zPi8AClMUo~=55LwlZVRpxOiFd;3B_8yA~shQx|tGF!j;$toK>JuS&gYLDkTP@C~gS@r~shUu{a>bfJ1` z^^VQ7&C1OKHDNXFTgC{M|V%fo{xK_dk6MK@9S!GZ*1JJzrV5xZBjOk z9!NTH<(q(S+MDf~ceQX@Dh|Ry<-sT4rhI$jQ0Sq~!`#Eo-%($2E^vo}is5J@NVEf|KK?WT&2;PCq@=ncR8z zO#GQ^T~S@VXG71PKNocFOt)Y6$@AXlk6rM*aP%VgV%sIRORYVwJx6|U{ozQjTW{-S z_si{9Jg#)~P3t?+@6&(!YQWWV*Z9{iU7vZq@5byKw{9lg9JnRA_4s!7?H6|n?o8ZW zdXIRo{Jz@#>IeD{>VLHUv1Pz*;P_y`V9&!@5AO~Mho1hF|I>%z(nrik)gwkDjgOrl z9~%uCz4Bzvli{bbrxVZ0epdf^>vOB;-~HnIOV3#R*zgPai_gEVd8zYq@2jb=I>#f& zAH2?aJ@KaetnphhVLN|`$B#eX$vk3hnxcR0u&!ox?6ss&zyI6t#OKjO1=Q!8=NbA?!e!@1A^WG zdI8!h3B-u4?w`)kDjTy~jz#2E%Xj$s4p^e}4$uqG7$3VG2GOy#+9i$#y#w?DrfnbT z5|}?4^bXJq&`^%Jbf9;DUVw&y%?N*XX3e>%Iv#iU)ebnzr+0u}fGjTczrug1KMmf| WGHzB5VFw8S0000StO&>uS)ve<0AYj>5AR{$W90N^4L=L-RlQUJ&DC0@ZjPh;=*jPLSYvv5M~MFBAl0-BNIsH z15C~g000{K(ZT*WKal6<?_01!^k@7iDG<<3=fuAC~28EsPoqkpK{9G%|Vj005J}`Hw&=0RYXHq~ibpyyzHQsFW8>#s~laM4*8xut5h5 z!4#~(4xGUqyucR%VFpA%3?#rj5JCpzfE)^;7?wd9RKPme1hudO8lVxH;SjXJF*pt9 z;1XPc>u?taU>Kgl7`%oF1VP9M6Ja4bh!J9r*dopd7nzO(B4J20l7OTj>4+3jBE`sZ zqynizYLQ(?Bl0bB6giDtK>Co|$RIL`{EECsF_eL_Q3KQhbwIhO9~z3rpmWi5G!I>X zmZEFX8nhlgfVQHi(M#xcbO3#dj$?q)F%D*o*1Pf{>6$SWH+$s3q(pv=X`qR|$iJF~TPzlc-O$C3+J1 z#CT#lv5;6stS0Uu9wDA3UMCI{Uz12A4#|?_P6{CkNG+sOq(0IRX`DyT~9-sA|ffUF>wk++Z!kWZ5P$;0Hg6gtI-;!FvmBvPc55=u2?Kjj3apE5$3psG>L zsh-pbs)#zDT1jo7c2F-(3)vyY4>O^>2$gY-Gd%Qm(Z8e zYv>2*=jns=cMJ`N4THx>VkjAF8G9M07`GWOnM|ey)0dgZR4~^v8<}UA514ONSSt1^ zd=-((5|uiYR+WC0=c-gyb5%dpd8!Lkt5pxHURHgkMpd&=fR^vEcAI*_=wwAG2sV%zY%w@v@XU~7=xdm1xY6*0;iwVIXu6TaXrs|dqbIl~ z?uTdNHFy_3W~^@g_pF#!K2~{F^;XxcN!DEJEbDF7 zS8PxlSDOr*I-AS3sI8l=#CDr)-xT5$k15hA^;2%zG3@;83hbKf2JJcaVfH2VZT8O{ z%p4LO);n}Nd~$Sk%yw*Wyz8XlG{dRHsl(}4XB%gsbDi@w7p6;)%MzD%mlsoQr;4X; zpL)xc%+^yMd)ZNTI#eJ*$O)i@o$z8)e??LqN_gLa_%;TM>o2SC_ zkmoO6c3xRt`@J4dvz#WL)-Y|z+r(Soy~}%GIzByR`p)SCKE^%*pL(B%zNWq+-#xw~ ze%5}Oeh2)X`#bu}{g3#+;d$~F@lFL`0l@*~0lk45fwKc^10MvL1f>Tx1&sx}1}_Xg z6+#RN4Ot&@lW)Km@*DYMGu&q^n$Z=?2%QyL8~QNJCQKgI5srq>2;UHXZ>IT7>CCnW zh~P(Th`1kV8JQRPeH1AwGO8}>QM6NZadh`A)~w`N`)9q5@sFvDxjWlxwsLl7tZHmh zY-8-3xPZ8-xPf?w_(k!T5_A(J3GIpG#Ms0=iQ{tu=WLoYoaCBRmULsT<=mpV7v|~C z%bs^USv6UZd^m-e5|^?+<%1wXP%juy<)>~<9TW0|n}ttBzM_qyQL(qUN<5P0omQ3h zINdvaL;7fjPeygdGYL;pD|wL_lDQ-EO;$wK-mK5raoH_7l$?~Dqf!lNmb5F^Ft;eT zPi8AClMUo~=55LwlZVRpxOiFd;3B_8yA~shQx|tGF!j;$toK>JuS&gYLDkTP@C~gS@r~shUu{a>bfJ1` z^^VQ7&C1OKHDNXFTgC{M|V%fo{xK_dk6MK@9S!GZ*1JJzrV5xZBjOk z9!NTH<(q(S+MDf~ceQX@Dh|Ry<-sT4rhI$jQ0Sq~!`#Eo-%($2E^vo}is5J@NVEf|KK?WT&2;PCq@=ncR8z zO#GQ^T~S@VXG71PKNocFOt)Y6$@AXlk6rM*aP%VgV%sIRORYVwJx6|U{ozQjTW{-S z_si{9Jg#)~P3t?+@6&(!YQWWV*Z9{iU7vZq@5byKw{9lg9JnRA_4s!7?H6|n?o8ZW zdXIRo{Jz@#>IeD{>VLHUv1Pz*;P_y`V9&!@5AO~Mho1hF|I>%z(nrik)gwkDjgOrl z9~%uCz4Bzvli{bbrxVZ0epdf^>vOB;-~HnIOV3#R*zgPai_gEVd8zYq@2jb=I>#f& zAH2?aJ@Kaet3Xp;68*be@J@!OI;( zNkn4!7NlxviI;&FaRJ^y>JjCU zp8&i8vxQe6Ziyv1GD)J%!Yb?WG_CCS0!ssJWH>E oPXOLPR||!kA8k+I6M#2x0aC4Fs~U7l5C8xG07*qoM6N<$g5yMs-T(jq literal 0 HcmV?d00001 diff --git a/client/src/assets/sprites/bonus16.png b/client/src/assets/sprites/bonus16.png new file mode 100644 index 0000000000000000000000000000000000000000..a2e6fb88c10ea941c31038de879b839bbca55713 GIT binary patch literal 3345 zcmV+s4es)ZP)StO&>uS)ve<0AYj>5AR{$W90N^4L=L-RlQUJ&DC0@ZjPh;=*jPLSYvv5M~MFBAl0-BNIsH z15C~g000{K(ZT*WKal6<?_01!^k@7iDG<<3=fuAC~28EsPoqkpK{9G%|Vj005J}`Hw&=0RYXHq~ibpyyzHQsFW8>#s~laM4*8xut5h5 z!4#~(4xGUqyucR%VFpA%3?#rj5JCpzfE)^;7?wd9RKPme1hudO8lVxH;SjXJF*pt9 z;1XPc>u?taU>Kgl7`%oF1VP9M6Ja4bh!J9r*dopd7nzO(B4J20l7OTj>4+3jBE`sZ zqynizYLQ(?Bl0bB6giDtK>Co|$RIL`{EECsF_eL_Q3KQhbwIhO9~z3rpmWi5G!I>X zmZEFX8nhlgfVQHi(M#xcbO3#dj$?q)F%D*o*1Pf{>6$SWH+$s3q(pv=X`qR|$iJF~TPzlc-O$C3+J1 z#CT#lv5;6stS0Uu9wDA3UMCI{Uz12A4#|?_P6{CkNG+sOq(0IRX`DyT~9-sA|ffUF>wk++Z!kWZ5P$;0Hg6gtI-;!FvmBvPc55=u2?Kjj3apE5$3psG>L zsh-pbs)#zDT1jo7c2F-(3)vyY4>O^>2$gY-Gd%Qm(Z8e zYv>2*=jns=cMJ`N4THx>VkjAF8G9M07`GWOnM|ey)0dgZR4~^v8<}UA514ONSSt1^ zd=-((5|uiYR+WC0=c-gyb5%dpd8!Lkt5pxHURHgkMpd&=fR^vEcAI*_=wwAG2sV%zY%w@v@XU~7=xdm1xY6*0;iwVIXu6TaXrs|dqbIl~ z?uTdNHFy_3W~^@g_pF#!K2~{F^;XxcN!DEJEbDF7 zS8PxlSDOr*I-AS3sI8l=#CDr)-xT5$k15hA^;2%zG3@;83hbKf2JJcaVfH2VZT8O{ z%p4LO);n}Nd~$Sk%yw*Wyz8XlG{dRHsl(}4XB%gsbDi@w7p6;)%MzD%mlsoQr;4X; zpL)xc%+^yMd)ZNTI#eJ*$O)i@o$z8)e??LqN_gLa_%;TM>o2SC_ zkmoO6c3xRt`@J4dvz#WL)-Y|z+r(Soy~}%GIzByR`p)SCKE^%*pL(B%zNWq+-#xw~ ze%5}Oeh2)X`#bu}{g3#+;d$~F@lFL`0l@*~0lk45fwKc^10MvL1f>Tx1&sx}1}_Xg z6+#RN4Ot&@lW)Km@*DYMGu&q^n$Z=?2%QyL8~QNJCQKgI5srq>2;UHXZ>IT7>CCnW zh~P(Th`1kV8JQRPeH1AwGO8}>QM6NZadh`A)~w`N`)9q5@sFvDxjWlxwsLl7tZHmh zY-8-3xPZ8-xPf?w_(k!T5_A(J3GIpG#Ms0=iQ{tu=WLoYoaCBRmULsT<=mpV7v|~C z%bs^USv6UZd^m-e5|^?+<%1wXP%juy<)>~<9TW0|n}ttBzM_qyQL(qUN<5P0omQ3h zINdvaL;7fjPeygdGYL;pD|wL_lDQ-EO;$wK-mK5raoH_7l$?~Dqf!lNmb5F^Ft;eT zPi8AClMUo~=55LwlZVRpxOiFd;3B_8yA~shQx|tGF!j;$toK>JuS&gYLDkTP@C~gS@r~shUu{a>bfJ1` z^^VQ7&C1OKHDNXFTgC{M|V%fo{xK_dk6MK@9S!GZ*1JJzrV5xZBjOk z9!NTH<(q(S+MDf~ceQX@Dh|Ry<-sT4rhI$jQ0Sq~!`#Eo-%($2E^vo}is5J@NVEf|KK?WT&2;PCq@=ncR8z zO#GQ^T~S@VXG71PKNocFOt)Y6$@AXlk6rM*aP%VgV%sIRORYVwJx6|U{ozQjTW{-S z_si{9Jg#)~P3t?+@6&(!YQWWV*Z9{iU7vZq@5byKw{9lg9JnRA_4s!7?H6|n?o8ZW zdXIRo{Jz@#>IeD{>VLHUv1Pz*;P_y`V9&!@5AO~Mho1hF|I>%z(nrik)gwkDjgOrl z9~%uCz4Bzvli{bbrxVZ0epdf^>vOB;-~HnIOV3#R*zgPai_gEVd8zYq@2jb=I>#f& zAH2?aJ@Kaetj4`W2(mOyeKq{ftGVlHJxW2-Ku!Qw`o@U)$VY;*q-gj3{3G@z_fYz9R z)~NPEbJ#jY!13g#jVrXRX@Xyb!^_<|d7X{k0eS(dy-=9ZRxBqNPn>^!PVTFb-T`_6 zr+Xna&`8vKq!*xffL_4poI6Tr)-E&*!~a3&9BTI$A>{G!7ZIv5nSQ*^kS-~uNH=;1 z=mq!~c7vSH>i9eYKOIR0bPR@3^b{6&) z^bXJqD8HS~qgcvM?*P33ZAPXg>%fLEo>flt4$uoIRYKZQDF(d*^a9>V>XA>T_6hV3 z&H<~OzK7G9iSJ0rxp*v#C(B_3s!ZPo-)Jtk-JI%2+NU8pNmZ=kC%jtP4Z%1JxtNkD5|s4I%U$YwNOxkq{h zdI#tQNMB@Kgcmu`J3uesG-kywqgFimz_*ySIX>sGMbFSXU;StO&>uS)ve<0AYj>5AR{$W90N^4L=L-RlQUJ&DC0@ZjPh;=*jPLSYvv5M~MFBAl0-BNIsH z15C~g000{K(ZT*WKal6<?_01!^k@7iDG<<3=fuAC~28EsPoqkpK{9G%|Vj005J}`Hw&=0RYXHq~ibpyyzHQsFW8>#s~laM4*8xut5h5 z!4#~(4xGUqyucR%VFpA%3?#rj5JCpzfE)^;7?wd9RKPme1hudO8lVxH;SjXJF*pt9 z;1XPc>u?taU>Kgl7`%oF1VP9M6Ja4bh!J9r*dopd7nzO(B4J20l7OTj>4+3jBE`sZ zqynizYLQ(?Bl0bB6giDtK>Co|$RIL`{EECsF_eL_Q3KQhbwIhO9~z3rpmWi5G!I>X zmZEFX8nhlgfVQHi(M#xcbO3#dj$?q)F%D*o*1Pf{>6$SWH+$s3q(pv=X`qR|$iJF~TPzlc-O$C3+J1 z#CT#lv5;6stS0Uu9wDA3UMCI{Uz12A4#|?_P6{CkNG+sOq(0IRX`DyT~9-sA|ffUF>wk++Z!kWZ5P$;0Hg6gtI-;!FvmBvPc55=u2?Kjj3apE5$3psG>L zsh-pbs)#zDT1jo7c2F-(3)vyY4>O^>2$gY-Gd%Qm(Z8e zYv>2*=jns=cMJ`N4THx>VkjAF8G9M07`GWOnM|ey)0dgZR4~^v8<}UA514ONSSt1^ zd=-((5|uiYR+WC0=c-gyb5%dpd8!Lkt5pxHURHgkMpd&=fR^vEcAI*_=wwAG2sV%zY%w@v@XU~7=xdm1xY6*0;iwVIXu6TaXrs|dqbIl~ z?uTdNHFy_3W~^@g_pF#!K2~{F^;XxcN!DEJEbDF7 zS8PxlSDOr*I-AS3sI8l=#CDr)-xT5$k15hA^;2%zG3@;83hbKf2JJcaVfH2VZT8O{ z%p4LO);n}Nd~$Sk%yw*Wyz8XlG{dRHsl(}4XB%gsbDi@w7p6;)%MzD%mlsoQr;4X; zpL)xc%+^yMd)ZNTI#eJ*$O)i@o$z8)e??LqN_gLa_%;TM>o2SC_ zkmoO6c3xRt`@J4dvz#WL)-Y|z+r(Soy~}%GIzByR`p)SCKE^%*pL(B%zNWq+-#xw~ ze%5}Oeh2)X`#bu}{g3#+;d$~F@lFL`0l@*~0lk45fwKc^10MvL1f>Tx1&sx}1}_Xg z6+#RN4Ot&@lW)Km@*DYMGu&q^n$Z=?2%QyL8~QNJCQKgI5srq>2;UHXZ>IT7>CCnW zh~P(Th`1kV8JQRPeH1AwGO8}>QM6NZadh`A)~w`N`)9q5@sFvDxjWlxwsLl7tZHmh zY-8-3xPZ8-xPf?w_(k!T5_A(J3GIpG#Ms0=iQ{tu=WLoYoaCBRmULsT<=mpV7v|~C z%bs^USv6UZd^m-e5|^?+<%1wXP%juy<)>~<9TW0|n}ttBzM_qyQL(qUN<5P0omQ3h zINdvaL;7fjPeygdGYL;pD|wL_lDQ-EO;$wK-mK5raoH_7l$?~Dqf!lNmb5F^Ft;eT zPi8AClMUo~=55LwlZVRpxOiFd;3B_8yA~shQx|tGF!j;$toK>JuS&gYLDkTP@C~gS@r~shUu{a>bfJ1` z^^VQ7&C1OKHDNXFTgC{M|V%fo{xK_dk6MK@9S!GZ*1JJzrV5xZBjOk z9!NTH<(q(S+MDf~ceQX@Dh|Ry<-sT4rhI$jQ0Sq~!`#Eo-%($2E^vo}is5J@NVEf|KK?WT&2;PCq@=ncR8z zO#GQ^T~S@VXG71PKNocFOt)Y6$@AXlk6rM*aP%VgV%sIRORYVwJx6|U{ozQjTW{-S z_si{9Jg#)~P3t?+@6&(!YQWWV*Z9{iU7vZq@5byKw{9lg9JnRA_4s!7?H6|n?o8ZW zdXIRo{Jz@#>IeD{>VLHUv1Pz*;P_y`V9&!@5AO~Mho1hF|I>%z(nrik)gwkDjgOrl z9~%uCz4Bzvli{bbrxVZ0epdf^>vOB;-~HnIOV3#R*zgPai_gEVd8zYq@2jb=I>#f& zAH2?aJ@Kaet}hK!astjNc}~lIv&y;7-3KgYH4{ai3p}1~3fp1kM&Jg=KGA``WK#jFNYhTJiH< zcm?1IJh2cfx3xCx*Q@963++@i26zSF2~6@VvjRSVsgvXZce_s=)%62L0}PvA;M$>LIjCS^Ii0`LT8{8BGj$aGUb z4V)>I%=F*L=lW;I2Co1-0cT{AQM6jfYM`^wG6jhCR}&HSB?m^DM;f!s@~v{E=g2*h6<@ z)1Wvn)B`mq)$j_y6R Date: Mon, 27 Feb 2023 03:48:30 +0300 Subject: [PATCH 154/196] feat: apply animation for new loot --- client/src/scripts/components/game.ts | 6 ++++- client/src/styles/level.css | 39 +++++++++++++++++++++++++++ client/src/styles/lootKeyframes.scss | 20 ++++++++++++++ 3 files changed, 64 insertions(+), 1 deletion(-) diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index 642da49..e18c628 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -173,7 +173,7 @@ class GameView { loadDoors(entityType: LevelEntity): void { LEVEL1.split('\n').forEach((line, indx) => { const arrLine = line.split(' '); - const randomValues = [100, 200, 400]; + const randomValues = [100, 200, 400, 800, 1600]; const randomIndex = Math.floor(Math.random() * randomValues.length); const randomValue = randomValues[randomIndex]; for (let i = 0; i < arrLine.length; i += 1) { @@ -254,6 +254,10 @@ class GameView { door.loot.sprite.classList.add('loot2'); } else if (door.loot.bonus === 400) { door.loot.sprite.classList.add('loot3'); + } else if (door.loot.bonus === 800) { + door.loot.sprite.classList.add('loot4'); + } else if (door.loot.bonus === 1600) { + door.loot.sprite.classList.add('loot5'); } door.loot.sprite.classList.add(`loot${door.loot.bonus}`); door.loot.sprite.style.width = `${door.loot.area.w}px`; diff --git a/client/src/styles/level.css b/client/src/styles/level.css index fa80940..764fc94 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -68,6 +68,24 @@ body { animation: bonus 2.5s ease-in-out infinite; } +.loot4 { + position: absolute; + width: 40px; + height: 32px; + z-index: 2; + background: url("./../assets/sprites/800.png") no-repeat no-repeat; + animation: bonus 2.5s ease-in-out infinite; +} + +.loot5 { + position: absolute; + width: 44px !important; + height: 32px; + z-index: 2; + background: url("./../assets/sprites/1600.png") no-repeat no-repeat; + animation: bonus 2.5s ease-in-out infinite; +} + .loot100 { position: absolute; width: 40px; @@ -98,6 +116,27 @@ body { animation-timing-function: steps(1); } +.loot800 { + position: absolute; + width: 40px; + height: 32px; + z-index: 2; + background: url("./../assets/sprites/bonus8.png") no-repeat no-repeat; + animation: loot800 0.5s ease-in-out infinite; + animation-timing-function: steps(1); +} + +.loot1600 { + position: absolute; + width: 40px; + height: 32px; + left: -5px; + z-index: 2; + background: url("./../assets/sprites/bonus16.png") no-repeat no-repeat; + animation: loot1600 0.5s ease-in-out infinite; + animation-timing-function: steps(1); +} + .score { font-family: "Perfect DOS VGA 437", sans-serif; position: absolute; diff --git a/client/src/styles/lootKeyframes.scss b/client/src/styles/lootKeyframes.scss index 9be4b7d..0701087 100644 --- a/client/src/styles/lootKeyframes.scss +++ b/client/src/styles/lootKeyframes.scss @@ -28,6 +28,26 @@ } } +@keyframes loot800 { + 0% { + background-position: 0 -5px; + } + + 25% { + background-position: 0 -50px; + } +} + +@keyframes loot1600 { + 0% { + background-position: 0 -5px; + } + + 25% { + background-position: 0 -47px; + } +} + @keyframes bonus { 0% { transform: translateY(0); From 25b8ca10d13df12d58c41c54933bdeaa771341d5 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 04:24:17 +0300 Subject: [PATCH 155/196] fix: results panels size --- client/src/scripts/components/BestResults.ts | 29 ++++++++++++-- client/src/scripts/components/Leaderboard.ts | 29 ++++++++++++-- client/src/styles/components/bestResults.scss | 29 +++++++++++++- client/src/styles/components/leaderboard.scss | 40 ++++++++++++++++++- client/src/styles/main.scss | 3 +- 5 files changed, 119 insertions(+), 11 deletions(-) diff --git a/client/src/scripts/components/BestResults.ts b/client/src/scripts/components/BestResults.ts index 51eed46..025f292 100644 --- a/client/src/scripts/components/BestResults.ts +++ b/client/src/scripts/components/BestResults.ts @@ -51,11 +51,32 @@ export default function BestResults(): Element { }); return createElement('div', { - class: 'best-results', + class: 'best-results hide', }, [ - createElement('h2', { - class: 'best-results__title', - }, [document.createTextNode('Best results')]), + createElement('div', { + class: 'leaderboard__header', + }, [ + createElement('h2', { + class: 'best-results__title', + }, [ + document.createTextNode('Best results'), + ]), + createElement('button', { + class: 'best-results__hide-button', + onClick: () => { + const hideButton = document.querySelector('.best-results__hide-button'); + const targetElement = document.querySelector('.best-results'); + + if (targetElement) { + targetElement.classList.toggle('hide'); + } + + if (hideButton && targetElement) { + hideButton.textContent = targetElement.classList.contains('hide') ? '<<' : '>>'; + } + }, + }, [document.createTextNode('<<')]), + ]), list, ]); } diff --git a/client/src/scripts/components/Leaderboard.ts b/client/src/scripts/components/Leaderboard.ts index 181f6f4..88467c6 100644 --- a/client/src/scripts/components/Leaderboard.ts +++ b/client/src/scripts/components/Leaderboard.ts @@ -77,11 +77,32 @@ export default function Leaderboard(): Element { }); return createElement('div', { - class: 'leaderboard', + class: 'leaderboard hide', }, [ - createElement('h2', { - class: 'leaderboard__title', - }, [document.createTextNode('Leaderboard')]), + createElement('div', { + class: 'leaderboard__header', + }, [ + createElement('button', { + class: 'leaderboard__hide-button', + onClick: () => { + const hideButton = document.querySelector('.leaderboard__hide-button'); + const targetElement = document.querySelector('.leaderboard'); + + if (targetElement) { + targetElement.classList.toggle('hide'); + } + + if (hideButton && targetElement) { + hideButton.textContent = targetElement.classList.contains('hide') ? '>>' : '<<'; + } + }, + }, [document.createTextNode('>>')]), + createElement('h2', { + class: 'leaderboard__title', + }, [ + document.createTextNode('Leaderboard'), + ]), + ]), scoreList, pagination, ]); diff --git a/client/src/styles/components/bestResults.scss b/client/src/styles/components/bestResults.scss index 7b33512..4dd7339 100644 --- a/client/src/styles/components/bestResults.scss +++ b/client/src/styles/components/bestResults.scss @@ -6,7 +6,16 @@ height: 630px; padding: 8px; gap: 8px; - border-radius: 8px; + background: transparentize(#bbada0, 0.5); + backdrop-filter: blur(16px); + position: absolute; + right: 0; + + &__hide-button { + margin-top: -4px; + margin-inline: 8px; + font-size: 14pt; + } &__title { display: flex; @@ -26,4 +35,22 @@ color: #776e65; overflow-y: auto; } + + &.hide { + width: 48px; + cursor: pointer; + + .best-results__title { + display: flex; + position: absolute; + width: 300px; + right: -260%; + top: 45%; + transform: rotate(90deg); + } + + .best-results__list { + display: none; + } + } } diff --git a/client/src/styles/components/leaderboard.scss b/client/src/styles/components/leaderboard.scss index 6910a0c..001ebfc 100644 --- a/client/src/styles/components/leaderboard.scss +++ b/client/src/styles/components/leaderboard.scss @@ -6,7 +6,24 @@ height: 630px; padding: 8px; gap: 8px; - border-radius: 8px; + background: transparentize(#bbada0, 0.5); + backdrop-filter: blur(16px); + position: absolute; + left: 0; + z-index: 99999; + + &__header { + display: flex; + align-items: center; + justify-content: center; + flex-direction: row; + } + + &__hide-button { + margin-top: -4px; + margin-inline: 8px; + font-size: 14pt; + } &__title { display: flex; @@ -61,4 +78,25 @@ font-size: 32pt; color: #776e65; } + + &.hide { + width: 48px; + cursor: pointer; + + .leaderboard__title { + display: block; + position: absolute; + left: -230%; + top: 45%; + transform: rotate(90deg); + } + + .leaderboard__list { + display: none; + } + + .leaderboard__pagination { + display: none; + } + } } diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index 3e3696b..ad01ea2 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -26,8 +26,9 @@ body { .app { &__container { display: flex; - justify-content: space-between; + justify-content: center; flex-direction: row; padding-block: 22px; + position: relative; } } From d199cabc4227347870290b358d8109415fa53e5b Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 04:59:50 +0300 Subject: [PATCH 156/196] fix: fix z-indexes --- client/src/styles/components/bestResults.scss | 1 + client/src/styles/components/leaderboard.scss | 2 +- client/src/styles/components/userAuthForm.scss | 1 + 3 files changed, 3 insertions(+), 1 deletion(-) diff --git a/client/src/styles/components/bestResults.scss b/client/src/styles/components/bestResults.scss index 4dd7339..3c6e513 100644 --- a/client/src/styles/components/bestResults.scss +++ b/client/src/styles/components/bestResults.scss @@ -10,6 +10,7 @@ backdrop-filter: blur(16px); position: absolute; right: 0; + z-index: 999; &__hide-button { margin-top: -4px; diff --git a/client/src/styles/components/leaderboard.scss b/client/src/styles/components/leaderboard.scss index 001ebfc..5df7420 100644 --- a/client/src/styles/components/leaderboard.scss +++ b/client/src/styles/components/leaderboard.scss @@ -10,7 +10,7 @@ backdrop-filter: blur(16px); position: absolute; left: 0; - z-index: 99999; + z-index: 999; &__header { display: flex; diff --git a/client/src/styles/components/userAuthForm.scss b/client/src/styles/components/userAuthForm.scss index 35d46de..7d6297f 100644 --- a/client/src/styles/components/userAuthForm.scss +++ b/client/src/styles/components/userAuthForm.scss @@ -9,6 +9,7 @@ position: absolute; left: 0; top: 0; + z-index: 99999; &.active { display: flex; From af528a9e6475ddaa6cedc52f18c0fe6d4385318e Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 05:01:33 +0300 Subject: [PATCH 157/196] feat: add create score logic when dave goes dead --- client/src/scripts/components/BestResults.ts | 15 ++++++--------- client/src/scripts/components/Leaderboard.ts | 1 + .../scripts/controllers/leaderboardController.ts | 9 +++++++++ client/src/scripts/controllers/playLevel.ts | 5 ++++- 4 files changed, 20 insertions(+), 10 deletions(-) diff --git a/client/src/scripts/components/BestResults.ts b/client/src/scripts/components/BestResults.ts index 025f292..5b6fdab 100644 --- a/client/src/scripts/components/BestResults.ts +++ b/client/src/scripts/components/BestResults.ts @@ -14,20 +14,16 @@ export default function BestResults(): Element { placeholder, ]); - authController.on('loginSuccess', () => { + const fetchUserBestResult = (): void => { leaderboardController.fetchUserBestResults(1, 10) .then(() => { placeholder.textContent = 'You haven\'t set a record yet!'; }) .catch(() => {}); - }); - authController.on('registerSuccess', () => { - leaderboardController.fetchUserBestResults(1, 10) - .then(() => { - placeholder.textContent = 'You haven\'t set a record yet!'; - }) - .catch(() => {}); - }); + }; + + authController.on('loginSuccess', fetchUserBestResult); + authController.on('registerSuccess', fetchUserBestResult); authController.on('userLogout', () => { list.replaceChildren(placeholder); @@ -49,6 +45,7 @@ export default function BestResults(): Element { list.replaceWith(newList); list = newList; }); + leaderboardController.on('scoreCreated', fetchUserBestResult); return createElement('div', { class: 'best-results hide', diff --git a/client/src/scripts/components/Leaderboard.ts b/client/src/scripts/components/Leaderboard.ts index 88467c6..1e8a1a1 100644 --- a/client/src/scripts/components/Leaderboard.ts +++ b/client/src/scripts/components/Leaderboard.ts @@ -75,6 +75,7 @@ export default function Leaderboard(): Element { || page + 1 > 99 / limit; currentPage.textContent = page.toString(); }); + leaderboardController.on('scoreCreated', fetchItems); return createElement('div', { class: 'leaderboard hide', diff --git a/client/src/scripts/controllers/leaderboardController.ts b/client/src/scripts/controllers/leaderboardController.ts index d42506a..09bc7af 100644 --- a/client/src/scripts/controllers/leaderboardController.ts +++ b/client/src/scripts/controllers/leaderboardController.ts @@ -3,6 +3,7 @@ import api from './apiController'; import GetLeaderboardRequest from '../api/requests/leaderboard/getLeaderboardRequest'; import GetScoreRequest from '../api/requests/score/getScoreRequest'; +import CreateScoreRequest from '../api/requests/score/createScoreRequest'; class LeaderboardController extends EventEmitter { async fetchLeaderboard(page = 1, limit = 100, sortBy: 'asc' | 'desc' = 'desc'): Promise { @@ -28,6 +29,14 @@ class LeaderboardController extends EventEmitter { .then((res) => this.emit('successUserBestResult', res)) .catch(() => {}); } + + async createScore(score: number): Promise { + await api.fetch( + new CreateScoreRequest(score), + ) + .then((res) => this.emit('scoreCreated', res)) + .catch(() => {}); + } } const leaderboardController = new LeaderboardController(); diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index 0f2db7f..a1919a7 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -15,6 +15,8 @@ import { import Crone from '../components/crone'; import Geometry from './geometry'; import Death from '../../types/enums/death'; +import leaderboardController from './leaderboardController'; +import authController from './authController'; class PlayLevel { gameView: GameView; @@ -360,7 +362,8 @@ class PlayLevel { this.gameView.lives -= 1; this.stopGame(); this.gameView.updateScoreOnScreen(); - setTimeout(() => { + setTimeout(async () => { + await leaderboardController.createScore(this.gameView.score); this.restartLevel(); }, 1000); } From aa77bc931bcbc489597d2d74dc04334a0897b4e9 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 05:15:29 +0300 Subject: [PATCH 158/196] hotfix: fix CORS --- server/src/main.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/src/main.ts b/server/src/main.ts index ed36290..be54f29 100644 --- a/server/src/main.ts +++ b/server/src/main.ts @@ -7,7 +7,7 @@ async function bootstrap(): Promise { app.use(cookieParser()); app.enableCors({ - origin: ['http://localhost:8080', '*'], + origin: ['http://localhost:8080', '*', (process.env.FRONT_END_URL || '*')], credentials: true, }); From e87f4da1cab5c9a7e17a520321cfb28ed8fb455e Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 05:20:51 +0300 Subject: [PATCH 159/196] hotfix: fix CORS --- server/src/main.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/server/src/main.ts b/server/src/main.ts index be54f29..c7074d7 100644 --- a/server/src/main.ts +++ b/server/src/main.ts @@ -5,9 +5,10 @@ import * as cookieParser from 'cookie-parser'; async function bootstrap(): Promise { const app = await NestFactory.create(AppModule); + console.log(`CORS: ${process.env.FRONT_END_URL || 'http://localhost:8080'}`) app.use(cookieParser()); app.enableCors({ - origin: ['http://localhost:8080', '*', (process.env.FRONT_END_URL || '*')], + origin: [(process.env.FRONT_END_URL || 'http://localhost:8080')], credentials: true, }); From e8ec16c5447670a248c44d7dffa11d045c2c30cc Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 05:35:51 +0300 Subject: [PATCH 160/196] fix: fix cookies policy --- server/src/modules/auth/auth.controller.ts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index c928491..e9259c2 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -40,6 +40,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { httpOnly: false, + secure: true, }); res.status(HttpStatus.OK).send(registeredUser); @@ -75,6 +76,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { httpOnly: false, + secure: true, }); res.status(HttpStatus.OK).send(registeredUser); From d79db8089db0e462b8104a912905e83a83962630 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 05:35:51 +0300 Subject: [PATCH 161/196] hotfix: fix cookies policy --- server/src/modules/auth/auth.controller.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index c928491..a6c82d0 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -39,7 +39,7 @@ export class AuthController { ); res.cookie('auth_token', registeredUser.accessToken, { - httpOnly: false, + httpOnly: true, }); res.status(HttpStatus.OK).send(registeredUser); @@ -74,7 +74,7 @@ export class AuthController { ); res.cookie('auth_token', registeredUser.accessToken, { - httpOnly: false, + httpOnly: true, }); res.status(HttpStatus.OK).send(registeredUser); From 1886e4b9faaa8d7a7ce2e0169d8757c92dbde529 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 05:55:00 +0300 Subject: [PATCH 162/196] hotfix: fix cookies policy --- server/src/modules/auth/auth.controller.ts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index a6c82d0..24ed77c 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -40,6 +40,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { httpOnly: true, + sameSite: true, }); res.status(HttpStatus.OK).send(registeredUser); @@ -75,6 +76,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { httpOnly: true, + sameSite: true, }); res.status(HttpStatus.OK).send(registeredUser); From 8af7c17fdc08f461c80907b516f66b661ee3c0fb Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 05:55:00 +0300 Subject: [PATCH 163/196] hotfix: fix cookies policy --- server/src/modules/auth/auth.controller.ts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index a6c82d0..c0558e5 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -40,6 +40,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { httpOnly: true, + sameSite: false, }); res.status(HttpStatus.OK).send(registeredUser); @@ -75,6 +76,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { httpOnly: true, + sameSite: false, }); res.status(HttpStatus.OK).send(registeredUser); From 12f83a9850655d0cffa64a2fac62707ea13ccf99 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 05:58:45 +0300 Subject: [PATCH 164/196] hotfix: fix cookies policy --- server/src/modules/auth/auth.controller.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index 24ed77c..c0558e5 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -40,7 +40,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { httpOnly: true, - sameSite: true, + sameSite: false, }); res.status(HttpStatus.OK).send(registeredUser); @@ -76,7 +76,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { httpOnly: true, - sameSite: true, + sameSite: false, }); res.status(HttpStatus.OK).send(registeredUser); From d7646dc015f70e062561f8a098767b1f414d1349 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 06:01:01 +0300 Subject: [PATCH 165/196] hotfix: fix cookies policy --- server/src/modules/auth/auth.controller.ts | 10 ++-------- 1 file changed, 2 insertions(+), 8 deletions(-) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index c0558e5..77c707e 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -38,10 +38,7 @@ export class AuthController { AuthProvider.LOCAL, ); - res.cookie('auth_token', registeredUser.accessToken, { - httpOnly: true, - sameSite: false, - }); + res.cookie('auth_token', registeredUser.accessToken); res.status(HttpStatus.OK).send(registeredUser); return registeredUser; @@ -74,10 +71,7 @@ export class AuthController { AuthProvider.LOCAL, ); - res.cookie('auth_token', registeredUser.accessToken, { - httpOnly: true, - sameSite: false, - }); + res.cookie('auth_token', registeredUser.accessToken); res.status(HttpStatus.OK).send(registeredUser); return registeredUser; From 6304b128920da6e5eb3a5b2c6621b9e1a770a3c0 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 07:08:15 +0300 Subject: [PATCH 166/196] hotfix: fix cookies policy --- server/src/main.ts | 4 ++-- server/src/modules/auth/auth.controller.ts | 8 ++++++-- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/server/src/main.ts b/server/src/main.ts index c7074d7..afc3877 100644 --- a/server/src/main.ts +++ b/server/src/main.ts @@ -5,10 +5,10 @@ import * as cookieParser from 'cookie-parser'; async function bootstrap(): Promise { const app = await NestFactory.create(AppModule); - console.log(`CORS: ${process.env.FRONT_END_URL || 'http://localhost:8080'}`) + console.log(`CORS: ${process.env.FRONT_END_URL || 'http://localhost:8080'}`); app.use(cookieParser()); app.enableCors({ - origin: [(process.env.FRONT_END_URL || 'http://localhost:8080')], + origin: [process.env.FRONT_END_URL || 'http://localhost:8080'], credentials: true, }); diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index 77c707e..01ba035 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -38,7 +38,9 @@ export class AuthController { AuthProvider.LOCAL, ); - res.cookie('auth_token', registeredUser.accessToken); + res.cookie('auth_token', registeredUser.accessToken, { + sameSite: 'none', + }); res.status(HttpStatus.OK).send(registeredUser); return registeredUser; @@ -71,7 +73,9 @@ export class AuthController { AuthProvider.LOCAL, ); - res.cookie('auth_token', registeredUser.accessToken); + res.cookie('auth_token', registeredUser.accessToken, { + sameSite: 'none', + }); res.status(HttpStatus.OK).send(registeredUser); return registeredUser; From 9d367d533ea549dd36fe0ac6d9a793467239b163 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 07:12:58 +0300 Subject: [PATCH 167/196] hotfix: fix cookies policy --- server/src/modules/auth/auth.controller.ts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index 01ba035..4449915 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -40,6 +40,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { sameSite: 'none', + secure: true, }); res.status(HttpStatus.OK).send(registeredUser); @@ -75,6 +76,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { sameSite: 'none', + secure: true, }); res.status(HttpStatus.OK).send(registeredUser); From fb579f66cd1ef2206c3b7e0654c6e6ec261ab394 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 07:25:46 +0300 Subject: [PATCH 168/196] hotfix: fix cookies policy --- client/src/scripts/controllers/apiController.ts | 1 - server/src/main.ts | 3 +-- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/client/src/scripts/controllers/apiController.ts b/client/src/scripts/controllers/apiController.ts index c51fd28..e147169 100644 --- a/client/src/scripts/controllers/apiController.ts +++ b/client/src/scripts/controllers/apiController.ts @@ -23,7 +23,6 @@ class APIController implements IAPIController { } headers.append('Content-Type', 'application/json'); - headers.append('Access-Control-Allow-Origin', '*'); fetch(url.href, { method: request.method, diff --git a/server/src/main.ts b/server/src/main.ts index afc3877..bd1a6fb 100644 --- a/server/src/main.ts +++ b/server/src/main.ts @@ -5,10 +5,9 @@ import * as cookieParser from 'cookie-parser'; async function bootstrap(): Promise { const app = await NestFactory.create(AppModule); - console.log(`CORS: ${process.env.FRONT_END_URL || 'http://localhost:8080'}`); app.use(cookieParser()); app.enableCors({ - origin: [process.env.FRONT_END_URL || 'http://localhost:8080'], + origin: true, credentials: true, }); From 9eafb1af6146dbf7e160fccd6877c27d95813a1e Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 07:53:09 +0300 Subject: [PATCH 169/196] hotfix: fix cookies policy --- client/src/scripts/controllers/authController.ts | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) diff --git a/client/src/scripts/controllers/authController.ts b/client/src/scripts/controllers/authController.ts index 19fa623..2ffed70 100644 --- a/client/src/scripts/controllers/authController.ts +++ b/client/src/scripts/controllers/authController.ts @@ -10,7 +10,9 @@ class AuthController extends EventEmitter { await api.fetch( new GetUserInfoRequest(), ) - .then((res) => this.emit('loginSuccess', res)) + .then((res) => { + this.emit('loginSuccess', res); + }) .catch(() => {}); return; } @@ -38,7 +40,11 @@ class AuthController extends EventEmitter { 'login', ), ) - .then((res) => this.emit('loginSuccess', res)) + .then((res) => { + this.emit('loginSuccess', res); + + document.cookie = `auth_token=${res.accessToken}; expires=Fri, 31 Dec 9999 23:59:59 GMT; path=/`; + }) .catch((err) => this.emit('loginFailed', err)); } @@ -94,7 +100,11 @@ class AuthController extends EventEmitter { 'register', ), ) - .then((res) => this.emit('registerSuccess', res)) + .then((res) => { + this.emit('registerSuccess', res); + + document.cookie = `auth_token=${res.accessToken}; expires=Fri, 31 Dec 9999 23:59:59 GMT; path=/`; + }) .catch((err) => this.emit('registerFailed', err)); } From a5051d68b434dea87ceaa607504f4141abfaf690 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 09:47:11 +0300 Subject: [PATCH 170/196] hotfix: fix cookies policy --- client/src/scripts/controllers/authController.ts | 12 ++---------- 1 file changed, 2 insertions(+), 10 deletions(-) diff --git a/client/src/scripts/controllers/authController.ts b/client/src/scripts/controllers/authController.ts index 2ffed70..66eb7b1 100644 --- a/client/src/scripts/controllers/authController.ts +++ b/client/src/scripts/controllers/authController.ts @@ -40,11 +40,7 @@ class AuthController extends EventEmitter { 'login', ), ) - .then((res) => { - this.emit('loginSuccess', res); - - document.cookie = `auth_token=${res.accessToken}; expires=Fri, 31 Dec 9999 23:59:59 GMT; path=/`; - }) + .then((res) => this.emit('loginSuccess', res)) .catch((err) => this.emit('loginFailed', err)); } @@ -100,11 +96,7 @@ class AuthController extends EventEmitter { 'register', ), ) - .then((res) => { - this.emit('registerSuccess', res); - - document.cookie = `auth_token=${res.accessToken}; expires=Fri, 31 Dec 9999 23:59:59 GMT; path=/`; - }) + .then((res) => this.emit('registerSuccess', res)) .catch((err) => this.emit('registerFailed', err)); } From c55836b4dcd9df87a5c8c804aed50a8a21280a5c Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Mon, 27 Feb 2023 18:40:39 +0300 Subject: [PATCH 171/196] feat: add open exit door and game over --- client/src/assets/levels/level1.ts | 4 +- client/src/assets/levels/leveldoor.png | Bin 0 -> 1119 bytes .../src/assets/sprites/dave_sprites_vert.png | Bin 17840 -> 19114 bytes client/src/scripts/components/dave.ts | 2 + client/src/scripts/components/game.ts | 41 +++++++++++++++++- client/src/scripts/controllers/geometry.ts | 8 ++++ client/src/scripts/controllers/playLevel.ts | 26 ++++++++++- client/src/styles/level.css | 8 ++++ client/src/styles/playerAnimation.scss | 4 +- .../src/styles/playerAnimationKeyframes.scss | 12 ++--- client/src/types/dave.ts | 1 + client/src/types/game.ts | 7 +++ 12 files changed, 97 insertions(+), 16 deletions(-) create mode 100644 client/src/assets/levels/leveldoor.png diff --git a/client/src/assets/levels/level1.ts b/client/src/assets/levels/level1.ts index bd88585..7e388fc 100644 --- a/client/src/assets/levels/level1.ts +++ b/client/src/assets/levels/level1.ts @@ -1,9 +1,9 @@ export const LEVEL1 = `0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W W 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W 0 Z 0 0 W 0 0 W +0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W Z E 0 0 W 0 0 W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P P P P 0 0 0 W -0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 2 0 C 0 0 0 0 W 0 W 0 0 0 0 0 0 0 Z 0 0 0 0 0 Z 0 0 0 0 0 P P P P 0 C 0 W +0 0 0 0 0 0 0 4 0 0 0 0 0 0 0 0 0 0 P W 0 0 0 2 0 C 0 0 0 0 W 0 W 0 0 0 0 0 0 0 Z 0 0 0 0 0 Z 0 0 0 0 0 P P P P 0 C 0 W 0 0 0 0 0 0 P P P P 0 0 0 0 0 0 0 0 P W P P P W W W W W W W W 0 W W W W W W W W W W W W W W W W W W W W W W W W W W W W 0 0 0 0 P 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 P W P P P 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 W diff --git a/client/src/assets/levels/leveldoor.png b/client/src/assets/levels/leveldoor.png new file mode 100644 index 0000000000000000000000000000000000000000..2362650a10399e69ff895e37a7ada3846be70f75 GIT binary patch literal 1119 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

5HaBS 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 diff --git a/client/src/scripts/components/dave.ts b/client/src/scripts/components/dave.ts index de7eff4..6ea26a8 100644 --- a/client/src/scripts/components/dave.ts +++ b/client/src/scripts/components/dave.ts @@ -93,6 +93,8 @@ class Player { } } else if (this.state === DaveState.RECHARGING) { this.animation.reload(); + } else if (this.state === DaveState.EXITING) { + this.animation.exit(); } else { this.animation.look(centerLook); } diff --git a/client/src/scripts/components/game.ts b/client/src/scripts/components/game.ts index e18c628..0ae29ae 100644 --- a/client/src/scripts/components/game.ts +++ b/client/src/scripts/components/game.ts @@ -9,7 +9,7 @@ import reloadSound from '../../assets/sounds/reload.mp3'; import { Rect, LevelEntity, LeftFeet, Door, DoorSize, - LootSize, Loot, SoundType, AllSound, Offset, ObjectState, + LootSize, Loot, SoundType, AllSound, Offset, ObjectState, ExitDoor, } from '../../types/game'; import Player from './dave'; import Zombie from './zombie'; @@ -51,6 +51,8 @@ class GameView { doors: Door[] = []; + exitDoor: ExitDoor; + dave: Player; loot: Loot[] = []; @@ -85,7 +87,6 @@ class GameView { this.ammoElement = document.createElement('div'); this.ammoElement.classList.add('ammo'); this.viewArea.append(this.levelArea, this.scoreElement, this.ammoElement); - // document.querySelector('body')?.append(this.viewArea); this.sounds[SoundType.JUMP] = new Audio(jumpSound); this.sounds[SoundType.LAND] = new Audio(landSound); this.sounds[SoundType.SHOT] = new Audio(shotSound); @@ -109,6 +110,7 @@ class GameView { this.loadDoors(LevelEntity.DOOR1); this.loadDoors(LevelEntity.DOOR2); this.loadDoors(LevelEntity.DOOR4); + this.loadExitDoor(LevelEntity.EXIT_DOOR); this.dave = new Player(this.loadCharacters(LevelEntity.DAVE)[0]); this.insertPlayer(); this.showAmmo(); @@ -207,6 +209,28 @@ class GameView { this.showClosedDoors(); } + loadExitDoor(entityType: LevelEntity): void { + LEVEL1.split('\n').forEach((line, indx) => { + const arrLine = line.split(' '); + for (let i = 0; i < arrLine.length; i += 1) { + if (arrLine[i] === entityType) { + const exitDoor: ExitDoor = { + area: { + x: i * this.tileSize, + y: (indx + 1) * this.tileSize - DoorSize.H, + w: DoorSize.W, + h: DoorSize.H, + }, + sprite: document.createElement('div'), + opened: false, + }; + this.exitDoor = exitDoor; + } + } + }); + this.showExitDoor(); + } + showWalls(): void { this.walls.forEach((item) => { const elem: HTMLElement = document.createElement('div'); @@ -267,6 +291,14 @@ class GameView { }); } + showExitDoor(): void { + this.exitDoor.sprite.classList.add('exit-door'); + this.exitDoor.sprite.style.width = `${this.exitDoor.area.w}px`; + this.exitDoor.sprite.style.height = `${this.exitDoor.area.h}px`; + this.exitDoor.sprite.style.left = `${this.exitDoor.area.x}px`; + this.exitDoor.sprite.style.top = `${this.exitDoor.area.y}px`; + } + openDoor(door: Door): void { door.opened = true; this.levelArea.append(door.sprite); @@ -274,6 +306,11 @@ class GameView { this.loot.push(door.loot); } + openExitDoor(door: ExitDoor): void { + door.opened = true; + this.levelArea.append(door.sprite); + } + grabLoot(loot: Loot): void { loot.grabbed = true; this.score += loot.bonus; diff --git a/client/src/scripts/controllers/geometry.ts b/client/src/scripts/controllers/geometry.ts index 7afcf21..73dffb6 100644 --- a/client/src/scripts/controllers/geometry.ts +++ b/client/src/scripts/controllers/geometry.ts @@ -119,6 +119,14 @@ class Geometry { h: rect.h + ((offset[1] > 0) ? offset[1] : 0), }; } + + static isRectInsideRect(rect1: Rect, rect2: Rect): boolean { + return !!((rect1.x <= rect2.x + && rect1.x + rect1.w >= rect2.x + rect2.w + && rect1.y <= rect2.y + && rect1.h + rect1.y >= rect2.y + rect2.h + )); + } } export default Geometry; diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index a1919a7..8a607d7 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -451,6 +451,28 @@ class PlayLevel { foundDoor = true; } }); + if (Geometry.isRectCrossWithRect( + this.gameView.exitDoor.area, + this.dave, + ) + ) { + if (this.gameView.exitDoor.opened) { + if (Geometry.isRectInsideRect( + this.gameView.exitDoor.area, + this.dave, + ) + ) { + this.dave.state = DaveState.EXITING; + setTimeout(() => { + this.stopGame(); + this.gameView.gameOver(); + }, 2000); + } + } else { + this.gameView.openExitDoor(this.gameView.exitDoor); + } + foundDoor = true; + } if (!foundDoor) { this.dave.shoot = DaveShoot.UP; } @@ -592,7 +614,7 @@ class PlayLevel { } croneAttack(crone: Monster, davePos: Position): void { - const shootOrNot: boolean = Math.random() > 0.95; + const shootOrNot: boolean = Math.random() > 0.96; if (shootOrNot) { if (davePos === Position.LEFT) { crone.attackDir = MonsterAttack.LEFT; @@ -824,7 +846,7 @@ class PlayLevel { this.reloadStartTimer = window.setTimeout(() => { this.reloadBullets(); this.dave.state = DaveState.RECHARGING; - }, 500); + }, 200); } reloadBullets(): void { diff --git a/client/src/styles/level.css b/client/src/styles/level.css index 764fc94..227a67b 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -41,6 +41,14 @@ body { z-index: 1; } +.exit-door { + position: absolute; + width: 96px; + height: 144px; + background: url("./../assets/levels/leveldoor.png") no-repeat no-repeat; + z-index: 1; +} + .loot1 { position: absolute; width: 40px; diff --git a/client/src/styles/playerAnimation.scss b/client/src/styles/playerAnimation.scss index eb084e5..84d89cb 100644 --- a/client/src/styles/playerAnimation.scss +++ b/client/src/styles/playerAnimation.scss @@ -120,8 +120,8 @@ $bg-size: 5257px; &-exit { background: url("../assets/sprites/dave_sprites_vert.png"); - animation: exit 1s ease-in-out infinite; - background-size: $bg-size; + animation: exit 2s ease-in-out; + background-position: 0 -3168px; animation-timing-function: steps(1); } diff --git a/client/src/styles/playerAnimationKeyframes.scss b/client/src/styles/playerAnimationKeyframes.scss index b236165..8825358 100644 --- a/client/src/styles/playerAnimationKeyframes.scss +++ b/client/src/styles/playerAnimationKeyframes.scss @@ -154,22 +154,18 @@ @keyframes exit { 0% { - background-position: -3323px 0; - width: 78px; + background-position: 0 -2880px; } 25% { - background-position: -3400px 0; - width: 78px; + background-position: 0 -2976px; } 50% { - background-position: -3470px 0; - width: 78px; + background-position: 0 -3072px; } 75% { - background-position: -3545px 0; - width: 63px; + background-position: 0 -3168px; } } diff --git a/client/src/types/dave.ts b/client/src/types/dave.ts index 3dff843..28986f4 100644 --- a/client/src/types/dave.ts +++ b/client/src/types/dave.ts @@ -8,6 +8,7 @@ export enum DaveState { RECHARGING, STUCK, DEAD, + EXITING, } export enum DaveMove { diff --git a/client/src/types/game.ts b/client/src/types/game.ts index b8f12c7..1929dbb 100644 --- a/client/src/types/game.ts +++ b/client/src/types/game.ts @@ -19,6 +19,7 @@ export enum LevelEntity { DOOR1 = '1', DOOR2 = '2', DOOR4 = '4', + EXIT_DOOR = 'E', } export type Offset = [number, number]; @@ -42,6 +43,12 @@ export type Door = { opened: boolean; }; +export type ExitDoor = { + area: Rect; + sprite: HTMLElement; + opened: boolean; +}; + export type Loot = { area: Rect; sprite: HTMLElement; From f1fdc3ade943352d37f5fee2fbac35e47ca02432 Mon Sep 17 00:00:00 2001 From: jukfloyd Date: Mon, 27 Feb 2023 19:05:51 +0300 Subject: [PATCH 172/196] feat: add saving score on game over --- client/src/scripts/controllers/playLevel.ts | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/client/src/scripts/controllers/playLevel.ts b/client/src/scripts/controllers/playLevel.ts index 8a607d7..d494dc0 100644 --- a/client/src/scripts/controllers/playLevel.ts +++ b/client/src/scripts/controllers/playLevel.ts @@ -362,8 +362,7 @@ class PlayLevel { this.gameView.lives -= 1; this.stopGame(); this.gameView.updateScoreOnScreen(); - setTimeout(async () => { - await leaderboardController.createScore(this.gameView.score); + setTimeout(() => { this.restartLevel(); }, 1000); } @@ -465,7 +464,7 @@ class PlayLevel { this.dave.state = DaveState.EXITING; setTimeout(() => { this.stopGame(); - this.gameView.gameOver(); + this.gameOver(); }, 2000); } } else { @@ -833,10 +832,17 @@ class PlayLevel { this.setListener(); this.animateMonsters(); } else { - this.gameView.gameOver(); + this.gameOver(); } } + gameOver(): void { + this.gameView.gameOver(); + setTimeout(async () => { + await leaderboardController.createScore(this.gameView.score); + }, 0); + } + resetListeners(): void { window.onkeydown = null; window.onkeyup = null; From 8ce2ab2345b6af6cca2106b701606d99f19190fd Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 19:24:49 +0300 Subject: [PATCH 173/196] feat: create footer component --- client/src/assets/icons/rss-logo.svg | 16 +++ client/src/scripts/components/App.ts | 2 + client/src/scripts/components/Footer.ts | 125 +++++++++++++++++++++++ client/src/styles/components/footer.scss | 81 +++++++++++++++ client/src/styles/components/header.scss | 4 + client/src/styles/main.scss | 10 +- 6 files changed, 237 insertions(+), 1 deletion(-) create mode 100644 client/src/assets/icons/rss-logo.svg create mode 100644 client/src/scripts/components/Footer.ts create mode 100644 client/src/styles/components/footer.scss diff --git a/client/src/assets/icons/rss-logo.svg b/client/src/assets/icons/rss-logo.svg new file mode 100644 index 0000000..295dfd9 --- /dev/null +++ b/client/src/assets/icons/rss-logo.svg @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + diff --git a/client/src/scripts/components/App.ts b/client/src/scripts/components/App.ts index 37eabcb..3d3b2f2 100644 --- a/client/src/scripts/components/App.ts +++ b/client/src/scripts/components/App.ts @@ -4,6 +4,7 @@ import PlayLevel from '../controllers/playLevel'; import UserAuthForm from './UserAuthForm'; import Leaderboard from './Leaderboard'; import BestResults from './BestResults'; +import Footer from './Footer'; export default function App(playerLevel: PlayLevel): Element { return createElement('div', { @@ -17,6 +18,7 @@ export default function App(playerLevel: PlayLevel): Element { playerLevel.gameView.viewArea, BestResults(), ]), + Footer(), UserAuthForm(), ]); } diff --git a/client/src/scripts/components/Footer.ts b/client/src/scripts/components/Footer.ts new file mode 100644 index 0000000..80d4b19 --- /dev/null +++ b/client/src/scripts/components/Footer.ts @@ -0,0 +1,125 @@ +import createElement from '../utils/createElement'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import rssLogoImage from '../../assets/icons/rss-logo.svg'; + +export default function Footer(): Element { + return createElement('footer', { + class: 'app__footer footer', + }, [ + createElement('div', { + class: 'footer__copyright', + }, [ + createElement('span', { + class: 'footer__copyright-vendor', + }, [document.createTextNode( + 'All rights belong to their respective owners.', + )]), + createElement('span', { + class: 'footer__copyright-license', + }, [document.createTextNode( + 'This is a non-commercial project distributed under the MIT license.', + )]), + createElement('span', { + class: 'footer__copyright-self', + }, [document.createTextNode( + 'Copyright (c) 2023 HardManDev, VasaSkor, Alexey Zhuchkov. All right reserved.', + )]), + + ]), + createElement('div', { + class: 'footer__authors', + }, [ + createElement('a', { + class: 'footer__author-card-link', + href: 'https://github.com/HardManDev/', + }, [ + createElement('div', { + class: 'footer__author-card', + }, [ + createElement('img', { + class: 'footer__author-card-avatar', + src: 'https://avatars.githubusercontent.com/u/98614868?s=40&v=4', + }), + createElement('div', { + class: 'footer__author-card-container', + }, [ + createElement('span', { + class: 'footer__author-card-role', + }, [ + document.createTextNode('Team-lead'), + ]), + createElement('span', { + class: 'footer__author-card-username', + }, [ + document.createTextNode('HardManDev'), + ]), + ]), + ]), + ]), + createElement('a', { + class: 'footer__author-card-link', + href: 'https://github.com/jukfloyd/', + }, [ + createElement('div', { + class: 'footer__author-card', + }, [ + createElement('img', { + class: 'footer__author-card-avatar', + src: 'https://avatars.githubusercontent.com/u/109034212?s=40&v=4', + }), + createElement('div', { + class: 'footer__author-card-container', + }, [ + createElement('span', { + class: 'footer__author-card-role', + }, [ + document.createTextNode('Gameplay'), + ]), + createElement('span', { + class: 'footer__author-card-username', + }, [ + document.createTextNode('jukfloyd'), + ]), + ]), + ]), + ]), + createElement('a', { + class: 'footer__author-card-link', + href: 'https://github.com/vasaskor', + }, [ + createElement('div', { + class: 'footer__author-card', + }, [ + createElement('img', { + class: 'footer__author-card-avatar', + src: 'https://avatars.githubusercontent.com/u/106305964?s=40&v=4', + }), + createElement('div', { + class: 'footer__author-card-container', + }, [ + createElement('span', { + class: 'footer__author-card-role', + }, [ + document.createTextNode('Styling'), + ]), + createElement('span', { + class: 'footer__author-card-username', + }, [ + document.createTextNode('VasaSkor'), + ]), + ]), + ]), + ]), + ]), + createElement('a', { + class: 'footer__logo', + href: 'https://rs.school/js/', + }, [ + createElement('img', { + class: 'footer__logo-image', + src: rssLogoImage, + }), + ]), + ]); +} diff --git a/client/src/styles/components/footer.scss b/client/src/styles/components/footer.scss new file mode 100644 index 0000000..77775c5 --- /dev/null +++ b/client/src/styles/components/footer.scss @@ -0,0 +1,81 @@ +.footer { + display: flex; + width: 100%; + align-items: center; + justify-content: space-between; + background: transparentize(#bbada0, 0.15); + backdrop-filter: blur(16px); + position: absolute; + padding-inline: 16px; + padding-block: 8px; + left: 0; + bottom: 0; + z-index: 9999; + + &__copyright { + display: flex; + justify-content: center; + flex-direction: column; + font-family: "Perfect DOS VGA 437", sans-serif; + font-size: 12pt; + gap: 2px; + letter-spacing: -1px; + color: #eee4da; + } + + &__authors { + display: flex; + flex-direction: row; + gap: 8px; + } + + &__author-card { + display: flex; + align-items: center; + justify-content: center; + flex-direction: row; + gap: 8px; + padding: 5px 8px 5px 5px; + border-radius: 3px; + background: #bbada0; + cursor: pointer; + transition: background-color 0.3s ease-in-out; + + &:hover { + background: #887b72; + transition: background-color 0.3s ease-in-out; + } + + &-link { + display: flex; + } + + &-avatar { + border-radius: 100%; + } + + &-role { + color: #eee4da; + } + + &-username { + font-size: 14pt; + color: #fff; + margin-left: 2px; + } + + &-container { + display: flex; + justify-content: center; + flex-direction: column; + + & > span { + font-family: "Perfect DOS VGA 437", sans-serif; + } + } + } + + &__logo { + filter: invert(99%) sepia(0%) saturate(202%) hue-rotate(349deg) brightness(117%) contrast(100%); + } +} diff --git a/client/src/styles/components/header.scss b/client/src/styles/components/header.scss index 154b8c4..638ebca 100644 --- a/client/src/styles/components/header.scss +++ b/client/src/styles/components/header.scss @@ -6,4 +6,8 @@ width: 100%; height: 64px; padding-inline: 16px; + position: absolute; + left: 0; + top: 0; + z-index: 999; } diff --git a/client/src/styles/main.scss b/client/src/styles/main.scss index ad01ea2..421f569 100644 --- a/client/src/styles/main.scss +++ b/client/src/styles/main.scss @@ -10,6 +10,7 @@ @import "components/bestResultCard"; @import "components/bestResults"; @import "components/scoreCard"; +@import "components/footer"; @import "components/ui/inputs"; @import "components/ui/buttons"; @@ -17,18 +18,25 @@ margin: 0; padding: 0; box-sizing: border-box; + text-decoration: none; } body { background-color: #faf8ef; + width: 100%; + height: 100%; } .app { + height: 100vh; + position: relative; + &__container { display: flex; + align-items: center; justify-content: center; + height: 100%; flex-direction: row; - padding-block: 22px; position: relative; } } From 178a065369a88ece317d6a293af8b6033e11c776 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 19:49:02 +0300 Subject: [PATCH 174/196] feat: add file-loader --- client/package-lock.json | 204 ++++++++++++++++++--------------------- client/package.json | 3 + 2 files changed, 96 insertions(+), 111 deletions(-) diff --git a/client/package-lock.json b/client/package-lock.json index 69c86fb..1a0acf4 100644 --- a/client/package-lock.json +++ b/client/package-lock.json @@ -8,6 +8,9 @@ "name": "rs-clone-client", "version": "0.0.1", "license": "MIT", + "dependencies": { + "file-loader": "^6.2.0" + }, "devDependencies": { "@babel/preset-env": "^7.20.2", "@babel/preset-typescript": "^7.18.6", @@ -1824,7 +1827,6 @@ "version": "3.1.0", "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.0.tgz", "integrity": "sha512-F2msla3tad+Mfht5cJq7LSXcdudKTWCVYUgw6pLFOOHSTtZlj6SWNYAp+AhuqLmWdBO2X5hPrLcu8cVP8fy28w==", - "dev": true, "engines": { "node": ">=6.0.0" } @@ -1833,7 +1835,6 @@ "version": "1.1.2", "resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.1.2.tgz", "integrity": "sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==", - "dev": true, "engines": { "node": ">=6.0.0" } @@ -1842,7 +1843,6 @@ "version": "0.3.2", "resolved": "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.2.tgz", "integrity": "sha512-m7O9o2uR8k2ObDysZYzdfhb08VuEml5oWGiosa1VdaPZ/A6QyPkAJuwN0Q1lhULOf6B7MtQmHENS743hWtCrgw==", - "dev": true, "dependencies": { "@jridgewell/gen-mapping": "^0.3.0", "@jridgewell/trace-mapping": "^0.3.9" @@ -1852,7 +1852,6 @@ "version": "0.3.2", "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.2.tgz", "integrity": "sha512-mh65xKQAzI6iBcFzwv28KVWSmCkdRBWoOh+bYQGW3+6OZvbbN3TqMGo5hqYxQniRcH9F2VZIoJCm4pa3BPDK/A==", - "dev": true, "dependencies": { "@jridgewell/set-array": "^1.0.1", "@jridgewell/sourcemap-codec": "^1.4.10", @@ -1865,14 +1864,12 @@ "node_modules/@jridgewell/sourcemap-codec": { "version": "1.4.14", "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.14.tgz", - "integrity": "sha512-XPSJHWmi394fuUuzDnGz1wiKqWfo1yXecHQMRf2l6hztTO+nPru658AyDngaBe7isIxEkRsPR3FZh+s7iVa4Uw==", - "dev": true + "integrity": "sha512-XPSJHWmi394fuUuzDnGz1wiKqWfo1yXecHQMRf2l6hztTO+nPru658AyDngaBe7isIxEkRsPR3FZh+s7iVa4Uw==" }, "node_modules/@jridgewell/trace-mapping": { "version": "0.3.17", "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.17.tgz", "integrity": "sha512-MCNzAp77qzKca9+W/+I0+sEpaUnZoeasnghNeVc41VZCEKaCH73Vq3BZZ/SzWIgrqE4H4ceI+p+b6C0mHf9T4g==", - "dev": true, "dependencies": { "@jridgewell/resolve-uri": "3.1.0", "@jridgewell/sourcemap-codec": "1.4.14" @@ -1961,7 +1958,6 @@ "version": "8.21.0", "resolved": "https://registry.npmjs.org/@types/eslint/-/eslint-8.21.0.tgz", "integrity": "sha512-35EhHNOXgxnUgh4XCJsGhE7zdlDhYDN/aMG6UbkByCFFNgQ7b3U+uVoqBpicFydR8JEfgdjCF7SJ7MiJfzuiTA==", - "dev": true, "dependencies": { "@types/estree": "*", "@types/json-schema": "*" @@ -1971,7 +1967,6 @@ "version": "3.7.4", "resolved": "https://registry.npmjs.org/@types/eslint-scope/-/eslint-scope-3.7.4.tgz", "integrity": "sha512-9K4zoImiZc3HlIp6AVUDE4CWYx22a+lhSZMYNpbjW04+YF0KWj4pJXnEMjdnFTiQibFFmElcsasJXDbdI/EPhA==", - "dev": true, "dependencies": { "@types/eslint": "*", "@types/estree": "*" @@ -1980,8 +1975,7 @@ "node_modules/@types/estree": { "version": "0.0.51", "resolved": "https://registry.npmjs.org/@types/estree/-/estree-0.0.51.tgz", - "integrity": "sha512-CuPgU6f3eT/XgKKPqKd/gLZV1Xmvf1a2R5POBOGQa6uv82xpls89HU5zKeVoyR8XzHd1RGNOlQlvUe3CFkjWNQ==", - "dev": true + "integrity": "sha512-CuPgU6f3eT/XgKKPqKd/gLZV1Xmvf1a2R5POBOGQa6uv82xpls89HU5zKeVoyR8XzHd1RGNOlQlvUe3CFkjWNQ==" }, "node_modules/@types/express": { "version": "4.17.17", @@ -2034,8 +2028,7 @@ "node_modules/@types/json-schema": { "version": "7.0.11", "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.11.tgz", - "integrity": "sha512-wOuvG1SN4Us4rez+tylwwwCV1psiNVOkJeM3AUWUNWg/jDQY2+HE/444y5gc+jBmRqASOm2Oeh5c1axHobwRKQ==", - "dev": true + "integrity": "sha512-wOuvG1SN4Us4rez+tylwwwCV1psiNVOkJeM3AUWUNWg/jDQY2+HE/444y5gc+jBmRqASOm2Oeh5c1axHobwRKQ==" }, "node_modules/@types/json5": { "version": "0.0.29", @@ -2065,8 +2058,7 @@ "node_modules/@types/node": { "version": "18.11.18", "resolved": "https://registry.npmjs.org/@types/node/-/node-18.11.18.tgz", - "integrity": "sha512-DHQpWGjyQKSHj3ebjFI/wRKcqQcdR+MoFBygntYOZytCqNfkd2ZC4ARDJ2DQqhjH5p85Nnd3jhUJIXrszFX/JA==", - "dev": true + "integrity": "sha512-DHQpWGjyQKSHj3ebjFI/wRKcqQcdR+MoFBygntYOZytCqNfkd2ZC4ARDJ2DQqhjH5p85Nnd3jhUJIXrszFX/JA==" }, "node_modules/@types/normalize-package-data": { "version": "2.4.1", @@ -2461,7 +2453,6 @@ "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/ast/-/ast-1.11.1.tgz", "integrity": "sha512-ukBh14qFLjxTQNTXocdyksN5QdM28S1CxHt2rdskFyL+xFV7VremuBLVbmCePj+URalXBENx/9Lm7lnhihtCSw==", - "dev": true, "dependencies": { "@webassemblyjs/helper-numbers": "1.11.1", "@webassemblyjs/helper-wasm-bytecode": "1.11.1" @@ -2470,26 +2461,22 @@ "node_modules/@webassemblyjs/floating-point-hex-parser": { "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/floating-point-hex-parser/-/floating-point-hex-parser-1.11.1.tgz", - "integrity": "sha512-iGRfyc5Bq+NnNuX8b5hwBrRjzf0ocrJPI6GWFodBFzmFnyvrQ83SHKhmilCU/8Jv67i4GJZBMhEzltxzcNagtQ==", - "dev": true + "integrity": "sha512-iGRfyc5Bq+NnNuX8b5hwBrRjzf0ocrJPI6GWFodBFzmFnyvrQ83SHKhmilCU/8Jv67i4GJZBMhEzltxzcNagtQ==" }, "node_modules/@webassemblyjs/helper-api-error": { "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-api-error/-/helper-api-error-1.11.1.tgz", - "integrity": "sha512-RlhS8CBCXfRUR/cwo2ho9bkheSXG0+NwooXcc3PAILALf2QLdFyj7KGsKRbVc95hZnhnERon4kW/D3SZpp6Tcg==", - "dev": true + "integrity": "sha512-RlhS8CBCXfRUR/cwo2ho9bkheSXG0+NwooXcc3PAILALf2QLdFyj7KGsKRbVc95hZnhnERon4kW/D3SZpp6Tcg==" }, "node_modules/@webassemblyjs/helper-buffer": { "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-buffer/-/helper-buffer-1.11.1.tgz", - "integrity": "sha512-gwikF65aDNeeXa8JxXa2BAk+REjSyhrNC9ZwdT0f8jc4dQQeDQ7G4m0f2QCLPJiMTTO6wfDmRmj/pW0PsUvIcA==", - "dev": true + "integrity": "sha512-gwikF65aDNeeXa8JxXa2BAk+REjSyhrNC9ZwdT0f8jc4dQQeDQ7G4m0f2QCLPJiMTTO6wfDmRmj/pW0PsUvIcA==" }, "node_modules/@webassemblyjs/helper-numbers": { "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-numbers/-/helper-numbers-1.11.1.tgz", "integrity": "sha512-vDkbxiB8zfnPdNK9Rajcey5C0w+QJugEglN0of+kmO8l7lDb77AnlKYQF7aarZuCrv+l0UvqL+68gSDr3k9LPQ==", - "dev": true, "dependencies": { "@webassemblyjs/floating-point-hex-parser": "1.11.1", "@webassemblyjs/helper-api-error": "1.11.1", @@ -2499,14 +2486,12 @@ "node_modules/@webassemblyjs/helper-wasm-bytecode": { "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-bytecode/-/helper-wasm-bytecode-1.11.1.tgz", - "integrity": "sha512-PvpoOGiJwXeTrSf/qfudJhwlvDQxFgelbMqtq52WWiXC6Xgg1IREdngmPN3bs4RoO83PnL/nFrxucXj1+BX62Q==", - "dev": true + "integrity": "sha512-PvpoOGiJwXeTrSf/qfudJhwlvDQxFgelbMqtq52WWiXC6Xgg1IREdngmPN3bs4RoO83PnL/nFrxucXj1+BX62Q==" }, "node_modules/@webassemblyjs/helper-wasm-section": { "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/helper-wasm-section/-/helper-wasm-section-1.11.1.tgz", "integrity": "sha512-10P9No29rYX1j7F3EVPX3JvGPQPae+AomuSTPiF9eBQeChHI6iqjMIwR9JmOJXwpnn/oVGDk7I5IlskuMwU/pg==", - "dev": true, "dependencies": { "@webassemblyjs/ast": "1.11.1", "@webassemblyjs/helper-buffer": "1.11.1", @@ -2518,7 +2503,6 @@ "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/ieee754/-/ieee754-1.11.1.tgz", "integrity": "sha512-hJ87QIPtAMKbFq6CGTkZYJivEwZDbQUgYd3qKSadTNOhVY7p+gfP6Sr0lLRVTaG1JjFj+r3YchoqRYxNH3M0GQ==", - "dev": true, "dependencies": { "@xtuc/ieee754": "^1.2.0" } @@ -2527,7 +2511,6 @@ "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/leb128/-/leb128-1.11.1.tgz", "integrity": "sha512-BJ2P0hNZ0u+Th1YZXJpzW6miwqQUGcIHT1G/sf72gLVD9DZ5AdYTqPNbHZh6K1M5VmKvFXwGSWZADz+qBWxeRw==", - "dev": true, "dependencies": { "@xtuc/long": "4.2.2" } @@ -2535,14 +2518,12 @@ "node_modules/@webassemblyjs/utf8": { "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/utf8/-/utf8-1.11.1.tgz", - "integrity": "sha512-9kqcxAEdMhiwQkHpkNiorZzqpGrodQQ2IGrHHxCy+Ozng0ofyMA0lTqiLkVs1uzTRejX+/O0EOT7KxqVPuXosQ==", - "dev": true + "integrity": "sha512-9kqcxAEdMhiwQkHpkNiorZzqpGrodQQ2IGrHHxCy+Ozng0ofyMA0lTqiLkVs1uzTRejX+/O0EOT7KxqVPuXosQ==" }, "node_modules/@webassemblyjs/wasm-edit": { "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-edit/-/wasm-edit-1.11.1.tgz", "integrity": "sha512-g+RsupUC1aTHfR8CDgnsVRVZFJqdkFHpsHMfJuWQzWU3tvnLC07UqHICfP+4XyL2tnr1amvl1Sdp06TnYCmVkA==", - "dev": true, "dependencies": { "@webassemblyjs/ast": "1.11.1", "@webassemblyjs/helper-buffer": "1.11.1", @@ -2558,7 +2539,6 @@ "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-gen/-/wasm-gen-1.11.1.tgz", "integrity": "sha512-F7QqKXwwNlMmsulj6+O7r4mmtAlCWfO/0HdgOxSklZfQcDu0TpLiD1mRt/zF25Bk59FIjEuGAIyn5ei4yMfLhA==", - "dev": true, "dependencies": { "@webassemblyjs/ast": "1.11.1", "@webassemblyjs/helper-wasm-bytecode": "1.11.1", @@ -2571,7 +2551,6 @@ "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-opt/-/wasm-opt-1.11.1.tgz", "integrity": "sha512-VqnkNqnZlU5EB64pp1l7hdm3hmQw7Vgqa0KF/KCNO9sIpI6Fk6brDEiX+iCOYrvMuBWDws0NkTOxYEb85XQHHw==", - "dev": true, "dependencies": { "@webassemblyjs/ast": "1.11.1", "@webassemblyjs/helper-buffer": "1.11.1", @@ -2583,7 +2562,6 @@ "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/wasm-parser/-/wasm-parser-1.11.1.tgz", "integrity": "sha512-rrBujw+dJu32gYB7/Lup6UhdkPx9S9SnobZzRVL7VcBH9Bt9bCBLEuX/YXOOtBsOZ4NQrRykKhffRWHvigQvOA==", - "dev": true, "dependencies": { "@webassemblyjs/ast": "1.11.1", "@webassemblyjs/helper-api-error": "1.11.1", @@ -2597,7 +2575,6 @@ "version": "1.11.1", "resolved": "https://registry.npmjs.org/@webassemblyjs/wast-printer/-/wast-printer-1.11.1.tgz", "integrity": "sha512-IQboUWM4eKzWW+N/jij2sRatKMh99QEelo3Eb2q0qXkvPRISAj8Qxtmw5itwqK+TTkBuUIE45AxYPToqPtL5gg==", - "dev": true, "dependencies": { "@webassemblyjs/ast": "1.11.1", "@xtuc/long": "4.2.2" @@ -2650,14 +2627,12 @@ "node_modules/@xtuc/ieee754": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/@xtuc/ieee754/-/ieee754-1.2.0.tgz", - "integrity": "sha512-DX8nKgqcGwsc0eJSqYt5lwP4DH5FlHnmuWWBRy7X0NcaGR0ZtuyeESgMwTYVEtxmsNGY+qit4QYT/MIYTOTPeA==", - "dev": true + "integrity": "sha512-DX8nKgqcGwsc0eJSqYt5lwP4DH5FlHnmuWWBRy7X0NcaGR0ZtuyeESgMwTYVEtxmsNGY+qit4QYT/MIYTOTPeA==" }, "node_modules/@xtuc/long": { "version": "4.2.2", "resolved": "https://registry.npmjs.org/@xtuc/long/-/long-4.2.2.tgz", - "integrity": "sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ==", - "dev": true + "integrity": "sha512-NuHqBY1PB/D8xU6s/thBgOAiAP7HOYDQ32+BFZILJ8ivkUkAHQnWfn6WhL79Owj1qmUnoN/YPhktdIoucipkAQ==" }, "node_modules/accepts": { "version": "1.3.8", @@ -2676,7 +2651,6 @@ "version": "8.8.2", "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.8.2.tgz", "integrity": "sha512-xjIYgE8HBrkpd/sJqOGNspf8uHG+NOHGOw6a/Urj8taM2EXfdNAH2oFcPeIFfsv3+kz/mJrS5VuMqbNLjCa2vw==", - "dev": true, "bin": { "acorn": "bin/acorn" }, @@ -2688,7 +2662,6 @@ "version": "1.8.0", "resolved": "https://registry.npmjs.org/acorn-import-assertions/-/acorn-import-assertions-1.8.0.tgz", "integrity": "sha512-m7VZ3jwz4eK6A4Vtt8Ew1/mNbP24u0FhdyfA7fSvnJR6LMdfOYnmuIrrJAgrYfYJ10F/otaHTtrtrtmHdMNzEw==", - "dev": true, "peerDependencies": { "acorn": "^8" } @@ -3019,7 +2992,6 @@ "version": "5.2.2", "resolved": "https://registry.npmjs.org/big.js/-/big.js-5.2.2.tgz", "integrity": "sha512-vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ==", - "dev": true, "engines": { "node": "*" } @@ -3125,7 +3097,6 @@ "version": "4.21.5", "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.21.5.tgz", "integrity": "sha512-tUkiguQGW7S3IhB7N+c2MV/HZPSCPAAiYBZXLsBhFB/PCy6ZKKsZrmBayHV9fdGV/ARIfJ14NkxKzRDjvp7L6w==", - "dev": true, "funding": [ { "type": "opencollective", @@ -3152,8 +3123,7 @@ "node_modules/buffer-from": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", - "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==", - "dev": true + "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==" }, "node_modules/bytes": { "version": "3.0.0", @@ -3226,7 +3196,6 @@ "version": "1.0.30001450", "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001450.tgz", "integrity": "sha512-qMBmvmQmFXaSxexkjjfMvD5rnDL0+m+dUMZKoDYsGG8iZN29RuYh9eRoMvKsT6uMAWlyUUGDEQGJJYjzCIO9ew==", - "dev": true, "funding": [ { "type": "opencollective", @@ -3283,7 +3252,6 @@ "version": "1.0.3", "resolved": "https://registry.npmjs.org/chrome-trace-event/-/chrome-trace-event-1.0.3.tgz", "integrity": "sha512-p3KULyQg4S7NIHixdwbGX+nFHkoBiA4YQmyWtjb8XngSKV124nJmRysgAeujbUVb15vh+RvFUfCPqU7rXk+hZg==", - "dev": true, "engines": { "node": ">=6.0" } @@ -3905,8 +3873,7 @@ "node_modules/electron-to-chromium": { "version": "1.4.286", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.4.286.tgz", - "integrity": "sha512-Vp3CVhmYpgf4iXNKAucoQUDcCrBQX3XLBtwgFqP9BUXuucgvAV9zWp1kYU7LL9j4++s9O+12cb3wMtN4SJy6UQ==", - "dev": true + "integrity": "sha512-Vp3CVhmYpgf4iXNKAucoQUDcCrBQX3XLBtwgFqP9BUXuucgvAV9zWp1kYU7LL9j4++s9O+12cb3wMtN4SJy6UQ==" }, "node_modules/emoji-regex": { "version": "8.0.0", @@ -3918,7 +3885,6 @@ "version": "3.0.0", "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-3.0.0.tgz", "integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==", - "dev": true, "engines": { "node": ">= 4" } @@ -3936,7 +3902,6 @@ "version": "5.12.0", "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.12.0.tgz", "integrity": "sha512-QHTXI/sZQmko1cbDoNAa3mJ5qhWUUNAq3vR0/YiD379fWQrcfuoX1+HW2S0MTt7XmoPLapdaDKUtelUSPic7hQ==", - "dev": true, "dependencies": { "graceful-fs": "^4.2.4", "tapable": "^2.2.0" @@ -4025,8 +3990,7 @@ "node_modules/es-module-lexer": { "version": "0.9.3", "resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-0.9.3.tgz", - "integrity": "sha512-1HQ2M2sPtxwnvOvT1ZClHyQDiggdNjURWpY2we6aMKCQiUVxTmVs2UYPLIrD84sS+kMdUwfBSylbJPwNnBrnHQ==", - "dev": true + "integrity": "sha512-1HQ2M2sPtxwnvOvT1ZClHyQDiggdNjURWpY2we6aMKCQiUVxTmVs2UYPLIrD84sS+kMdUwfBSylbJPwNnBrnHQ==" }, "node_modules/es-set-tostringtag": { "version": "2.0.1", @@ -4073,7 +4037,6 @@ "version": "3.1.1", "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", "integrity": "sha512-k0er2gUkLf8O0zKJiAhmkTnJlTvINGv7ygDNPbeIsX/TJjGJZHuh9B2UxbsaEkmlEo9MfhrSzmhIlhRlI2GXnw==", - "dev": true, "engines": { "node": ">=6" } @@ -4290,7 +4253,6 @@ "version": "5.1.1", "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", "integrity": "sha512-2NxwbF/hZ0KpepYN0cNbo+FN6XoK7GaHlQhgx/hIZl6Va0bF45RQOOwhLIy8lQDbuCiadSLCBnH2CFYquit5bw==", - "dev": true, "dependencies": { "esrecurse": "^4.3.0", "estraverse": "^4.1.1" @@ -4600,7 +4562,6 @@ "version": "4.3.0", "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.3.0.tgz", "integrity": "sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==", - "dev": true, "dependencies": { "estraverse": "^5.2.0" }, @@ -4612,7 +4573,6 @@ "version": "5.3.0", "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-5.3.0.tgz", "integrity": "sha512-MMdARuVEQziNTeJD8DgMqmhwR11BRQ/cBP+pLtYdSTnf3MIO8fFeiINEbX36ZdNlfU/7A9f3gUw49B3oQsvwBA==", - "dev": true, "engines": { "node": ">=4.0" } @@ -4621,7 +4581,6 @@ "version": "4.3.0", "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.3.0.tgz", "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==", - "dev": true, "engines": { "node": ">=4.0" } @@ -4654,7 +4613,6 @@ "version": "3.3.0", "resolved": "https://registry.npmjs.org/events/-/events-3.3.0.tgz", "integrity": "sha512-mQw+2fkQbALzQ7V0MY0IqdnXNOeTtP4r0lN9z7AAawCXgqea7bDii20AYrIBrFd/Hx0M2Ocz6S111CaFkUcb0Q==", - "dev": true, "engines": { "node": ">=0.8.x" } @@ -4748,8 +4706,7 @@ "node_modules/fast-deep-equal": { "version": "3.1.3", "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", - "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", - "dev": true + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==" }, "node_modules/fast-glob": { "version": "3.2.12", @@ -4770,8 +4727,7 @@ "node_modules/fast-json-stable-stringify": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", - "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", - "dev": true + "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==" }, "node_modules/fast-levenshtein": { "version": "2.0.6", @@ -4821,6 +4777,70 @@ "node": "^10.12.0 || >=12.0.0" } }, + "node_modules/file-loader": { + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/file-loader/-/file-loader-6.2.0.tgz", + "integrity": "sha512-qo3glqyTa61Ytg4u73GultjHGjdRyig3tG6lPtyX/jOEJvHif9uB0/OCI2Kif6ctF3caQTW2G5gym21oAsI4pw==", + "dependencies": { + "loader-utils": "^2.0.0", + "schema-utils": "^3.0.0" + }, + "engines": { + "node": ">= 10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + }, + "peerDependencies": { + "webpack": "^4.0.0 || ^5.0.0" + } + }, + "node_modules/file-loader/node_modules/ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dependencies": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/epoberezkin" + } + }, + "node_modules/file-loader/node_modules/ajv-keywords": { + "version": "3.5.2", + "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", + "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", + "peerDependencies": { + "ajv": "^6.9.1" + } + }, + "node_modules/file-loader/node_modules/json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==" + }, + "node_modules/file-loader/node_modules/schema-utils": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.1.1.tgz", + "integrity": "sha512-Y5PQxS4ITlC+EahLuXaY86TXfR7Dc5lw294alXOq86JAHCihAIZfqv8nNCWvaEJvaC51uN9hbLGeV0cFBdH+Fw==", + "dependencies": { + "@types/json-schema": "^7.0.8", + "ajv": "^6.12.5", + "ajv-keywords": "^3.5.2" + }, + "engines": { + "node": ">= 10.13.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/webpack" + } + }, "node_modules/fill-range": { "version": "7.0.1", "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-7.0.1.tgz", @@ -5136,8 +5156,7 @@ "node_modules/glob-to-regexp": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/glob-to-regexp/-/glob-to-regexp-0.4.1.tgz", - "integrity": "sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==", - "dev": true + "integrity": "sha512-lkX1HJXwyMcprw/5YUZc2s7DrpAiHB21/V+E1rHUrVNokkvB6bqMzT0VfV6/86ZNabt1k14YOIaT7nDvOX3Iiw==" }, "node_modules/global-modules": { "version": "2.0.0", @@ -5247,8 +5266,7 @@ "node_modules/graceful-fs": { "version": "4.2.10", "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.10.tgz", - "integrity": "sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==", - "dev": true + "integrity": "sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==" }, "node_modules/grapheme-splitter": { "version": "1.0.4", @@ -6119,7 +6137,6 @@ "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", - "dev": true, "dependencies": { "@types/node": "*", "merge-stream": "^2.0.0", @@ -6133,7 +6150,6 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", - "dev": true, "engines": { "node": ">=8" } @@ -6142,7 +6158,6 @@ "version": "8.1.1", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", - "dev": true, "dependencies": { "has-flag": "^4.0.0" }, @@ -6196,8 +6211,7 @@ "node_modules/json-parse-even-better-errors": { "version": "2.3.1", "resolved": "https://registry.npmjs.org/json-parse-even-better-errors/-/json-parse-even-better-errors-2.3.1.tgz", - "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==", - "dev": true + "integrity": "sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==" }, "node_modules/json-schema-traverse": { "version": "1.0.0", @@ -6215,7 +6229,6 @@ "version": "2.2.3", "resolved": "https://registry.npmjs.org/json5/-/json5-2.2.3.tgz", "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==", - "dev": true, "bin": { "json5": "lib/cli.js" }, @@ -6270,7 +6283,6 @@ "version": "4.3.0", "resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.3.0.tgz", "integrity": "sha512-3R/1M+yS3j5ou80Me59j7F9IMs4PXs3VqRrm0TU3AbKPxlmpoY1TNscJV/oGJXo8qCatFGTfDbY6W6ipGOYXfg==", - "dev": true, "engines": { "node": ">=6.11.5" } @@ -6279,7 +6291,6 @@ "version": "2.0.4", "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-2.0.4.tgz", "integrity": "sha512-xXqpXoINfFhgua9xiqD8fPFHgkoq1mmmpE92WlDbm9rNRd/EbRb+Gqf908T2DMfuHjjJlksiK2RbHVOdD/MqSw==", - "dev": true, "dependencies": { "big.js": "^5.2.2", "emojis-list": "^3.0.0", @@ -6448,8 +6459,7 @@ "node_modules/merge-stream": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", - "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==", - "dev": true + "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==" }, "node_modules/merge2": { "version": "1.4.1", @@ -6498,7 +6508,6 @@ "version": "1.52.0", "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", - "dev": true, "engines": { "node": ">= 0.6" } @@ -6507,7 +6516,6 @@ "version": "2.1.35", "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", - "dev": true, "dependencies": { "mime-db": "1.52.0" }, @@ -6658,8 +6666,7 @@ "node_modules/neo-async": { "version": "2.6.2", "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.2.tgz", - "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==", - "dev": true + "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==" }, "node_modules/no-case": { "version": "3.0.4", @@ -6683,8 +6690,7 @@ "node_modules/node-releases": { "version": "2.0.9", "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.9.tgz", - "integrity": "sha512-2xfmOrRkGogbTK9R6Leda0DGiXeY3p2NJpy4+gNCffdUvV6mdEJnaDEic1i3Ec2djAo8jWYoJMR5PB0MSMpxUA==", - "dev": true + "integrity": "sha512-2xfmOrRkGogbTK9R6Leda0DGiXeY3p2NJpy4+gNCffdUvV6mdEJnaDEic1i3Ec2djAo8jWYoJMR5PB0MSMpxUA==" }, "node_modules/normalize-package-data": { "version": "3.0.3", @@ -7112,8 +7118,7 @@ "node_modules/picocolors": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/picocolors/-/picocolors-1.0.0.tgz", - "integrity": "sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==", - "dev": true + "integrity": "sha512-1fygroTLlHu66zi26VoTDv8yRgm0Fccecssto+MhsZ0D/DGW2sm8E8AjW7NU5VVTRt5GxbeZ5qBuJr+HyLYkjQ==" }, "node_modules/picomatch": { "version": "2.3.1", @@ -7427,7 +7432,6 @@ "version": "2.3.0", "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.0.tgz", "integrity": "sha512-rRV+zQD8tVFys26lAGR9WUuS4iUAngJScM+ZRSKtvl5tKeZ2t5bvdNFdNHBW9FWR4guGHlgmsZ1G7BSm2wTbuA==", - "dev": true, "engines": { "node": ">=6" } @@ -7480,7 +7484,6 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", "integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==", - "dev": true, "dependencies": { "safe-buffer": "^5.1.0" } @@ -7894,7 +7897,6 @@ "version": "5.2.1", "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", - "dev": true, "funding": [ { "type": "github", @@ -8080,7 +8082,6 @@ "version": "6.0.1", "resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-6.0.1.tgz", "integrity": "sha512-owoXEFjWRllis8/M1Q+Cw5k8ZH40e3zhp/ovX+Xr/vi1qj6QesbyXXViFbpNvWvPNAD62SutwEXavefrLJWj7w==", - "dev": true, "dependencies": { "randombytes": "^2.1.0" } @@ -8311,7 +8312,6 @@ "version": "0.6.1", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", - "dev": true, "engines": { "node": ">=0.10.0" } @@ -8329,7 +8329,6 @@ "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==", - "dev": true, "dependencies": { "buffer-from": "^1.0.0", "source-map": "^0.6.0" @@ -8787,7 +8786,6 @@ "version": "2.2.1", "resolved": "https://registry.npmjs.org/tapable/-/tapable-2.2.1.tgz", "integrity": "sha512-GNzQvQTOIP6RyTfE2Qxb8ZVlNmw0n88vp1szwWRimP02mnTsx3Wtn5qRdqY9w2XduFNUgvOwhNnQsjwCp+kqaQ==", - "dev": true, "engines": { "node": ">=6" } @@ -8796,7 +8794,6 @@ "version": "5.16.3", "resolved": "https://registry.npmjs.org/terser/-/terser-5.16.3.tgz", "integrity": "sha512-v8wWLaS/xt3nE9dgKEWhNUFP6q4kngO5B8eYFUuebsu7Dw/UNAnpUod6UHo04jSSkv8TzKHjZDSd7EXdDQAl8Q==", - "dev": true, "dependencies": { "@jridgewell/source-map": "^0.3.2", "acorn": "^8.5.0", @@ -8814,7 +8811,6 @@ "version": "5.3.6", "resolved": "https://registry.npmjs.org/terser-webpack-plugin/-/terser-webpack-plugin-5.3.6.tgz", "integrity": "sha512-kfLFk+PoLUQIbLmB1+PZDMRSZS99Mp+/MHqDNmMA6tOItzRt+Npe3E+fsMs5mfcM0wCtrrdU387UnV+vnSffXQ==", - "dev": true, "dependencies": { "@jridgewell/trace-mapping": "^0.3.14", "jest-worker": "^27.4.5", @@ -8848,7 +8844,6 @@ "version": "6.12.6", "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "dev": true, "dependencies": { "fast-deep-equal": "^3.1.1", "fast-json-stable-stringify": "^2.0.0", @@ -8864,7 +8859,6 @@ "version": "3.5.2", "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "dev": true, "peerDependencies": { "ajv": "^6.9.1" } @@ -8872,14 +8866,12 @@ "node_modules/terser-webpack-plugin/node_modules/json-schema-traverse": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "dev": true + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==" }, "node_modules/terser-webpack-plugin/node_modules/schema-utils": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.1.1.tgz", "integrity": "sha512-Y5PQxS4ITlC+EahLuXaY86TXfR7Dc5lw294alXOq86JAHCihAIZfqv8nNCWvaEJvaC51uN9hbLGeV0cFBdH+Fw==", - "dev": true, "dependencies": { "@types/json-schema": "^7.0.8", "ajv": "^6.12.5", @@ -8896,8 +8888,7 @@ "node_modules/terser/node_modules/commander": { "version": "2.20.3", "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", - "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==", - "dev": true + "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==" }, "node_modules/text-table": { "version": "0.2.0", @@ -9135,7 +9126,6 @@ "version": "1.0.10", "resolved": "https://registry.npmjs.org/update-browserslist-db/-/update-browserslist-db-1.0.10.tgz", "integrity": "sha512-OztqDenkfFkbSG+tRxBeAnCVPckDBcvibKd35yDONx6OU8N7sqgwc7rCbkJ/WcYtVRZ4ba68d6byhC21GFh7sQ==", - "dev": true, "funding": [ { "type": "opencollective", @@ -9161,7 +9151,6 @@ "version": "4.4.1", "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", - "dev": true, "dependencies": { "punycode": "^2.1.0" } @@ -9301,7 +9290,6 @@ "version": "2.4.0", "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.4.0.tgz", "integrity": "sha512-Lcvm7MGST/4fup+ifyKi2hjyIAwcdI4HRgtvTpIUxBRhB+RFtUh8XtDOxUfctVCnhVi+QQj49i91OyvzkJl6cg==", - "dev": true, "dependencies": { "glob-to-regexp": "^0.4.1", "graceful-fs": "^4.1.2" @@ -9323,7 +9311,6 @@ "version": "5.75.0", "resolved": "https://registry.npmjs.org/webpack/-/webpack-5.75.0.tgz", "integrity": "sha512-piaIaoVJlqMsPtX/+3KTTO6jfvrSYgauFVdt8cr9LTHKmcq/AMd4mhzsiP7ZF/PGRNPGA8336jldh9l2Kt2ogQ==", - "dev": true, "dependencies": { "@types/eslint-scope": "^3.7.3", "@types/estree": "^0.0.51", @@ -9530,7 +9517,6 @@ "version": "3.2.3", "resolved": "https://registry.npmjs.org/webpack-sources/-/webpack-sources-3.2.3.tgz", "integrity": "sha512-/DyMEOrDgLKKIG0fmvtz+4dUX/3Ghozwgm6iPp8KRhvn+eQf9+Q7GWxVNMk3+uCPWfdXYC4ExGBckIXdFEfH1w==", - "dev": true, "engines": { "node": ">=10.13.0" } @@ -9539,7 +9525,6 @@ "version": "6.12.6", "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", - "dev": true, "dependencies": { "fast-deep-equal": "^3.1.1", "fast-json-stable-stringify": "^2.0.0", @@ -9555,7 +9540,6 @@ "version": "3.5.2", "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz", "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", - "dev": true, "peerDependencies": { "ajv": "^6.9.1" } @@ -9563,14 +9547,12 @@ "node_modules/webpack/node_modules/json-schema-traverse": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "dev": true + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==" }, "node_modules/webpack/node_modules/schema-utils": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.1.1.tgz", "integrity": "sha512-Y5PQxS4ITlC+EahLuXaY86TXfR7Dc5lw294alXOq86JAHCihAIZfqv8nNCWvaEJvaC51uN9hbLGeV0cFBdH+Fw==", - "dev": true, "dependencies": { "@types/json-schema": "^7.0.8", "ajv": "^6.12.5", diff --git a/client/package.json b/client/package.json index 1cda9ce..4a7f79b 100644 --- a/client/package.json +++ b/client/package.json @@ -43,5 +43,8 @@ "webpack": "^5.75.0", "webpack-cli": "^5.0.1", "webpack-dev-server": "^4.11.1" + }, + "dependencies": { + "file-loader": "^6.2.0" } } From 3a868ce0ddc5ee94f409d2db29260ca6f86686a3 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 19:49:23 +0300 Subject: [PATCH 175/196] feat: add logo --- client/src/assets/logo.png | Bin 0 -> 25059 bytes client/src/scripts/components/Header.ts | 13 ++++++++----- 2 files changed, 8 insertions(+), 5 deletions(-) create mode 100644 client/src/assets/logo.png diff --git a/client/src/assets/logo.png b/client/src/assets/logo.png new file mode 100644 index 0000000000000000000000000000000000000000..2160a2ad3cfd3b041e29c3670073578d1a54e5d1 GIT binary patch literal 25059 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 literal 0 HcmV?d00001 diff --git a/client/src/scripts/components/Header.ts b/client/src/scripts/components/Header.ts index 5bc8fb8..ffbb482 100644 --- a/client/src/scripts/components/Header.ts +++ b/client/src/scripts/components/Header.ts @@ -1,15 +1,18 @@ import createElement from '../utils/createElement'; import UserProfile from './UserProfile'; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore +import logoImage from '../../assets/logo.png'; export default function Header(): Element { - const logoImage = createElement('img', { - class: 'header__logo', - }); - return createElement('header', { class: 'app__header header', }, [ - logoImage, + createElement('img', { + class: 'header__logo', + src: logoImage, + style: 'margin-top: -5px; width: 464px;', + }), UserProfile(), ]); } From 1d901a037f70ca12e6859358c24a15cfec73b67a Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 20:06:35 +0300 Subject: [PATCH 176/196] hotfix: fix remove cookie logic --- client/src/scripts/utils/deleteCookie.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/src/scripts/utils/deleteCookie.ts b/client/src/scripts/utils/deleteCookie.ts index e52f7d0..1754be1 100644 --- a/client/src/scripts/utils/deleteCookie.ts +++ b/client/src/scripts/utils/deleteCookie.ts @@ -1,3 +1,3 @@ export default function deleteCookie(name: string): void { - document.cookie = `${name}=;expires=${Date.now()};path=/;`; + document.cookie = `${name}=;expires=${Date.now()}; Path=/; Secure; SameSite=None;`; } From d6461e4340ca029e364a93659e5f12883fe6ced4 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 20:22:36 +0300 Subject: [PATCH 177/196] hotfix: fix remove cookie logic --- client/src/scripts/utils/deleteCookie.ts | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/client/src/scripts/utils/deleteCookie.ts b/client/src/scripts/utils/deleteCookie.ts index 1754be1..fa9315c 100644 --- a/client/src/scripts/utils/deleteCookie.ts +++ b/client/src/scripts/utils/deleteCookie.ts @@ -1,3 +1,7 @@ export default function deleteCookie(name: string): void { - document.cookie = `${name}=;expires=${Date.now()}; Path=/; Secure; SameSite=None;`; + const originRegex = /^(?:(?:[a-z]+:)?\/\/)?(?:[^@/]+@)?([^:/]+)/i; + const origin = (process.env.API_URL || 'http://localhost:3000') + .match(originRegex); + + document.cookie = `${name}=;domain=${origin ? origin[1] : 'localhost'};expires=${Date.now()}; Path=/; Secure; SameSite=None;`; } From c36598cec5120b2f686209d464807ddc7bcf07c4 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 20:25:49 +0300 Subject: [PATCH 178/196] hotfix: fix remove cookie logic --- client/src/scripts/utils/deleteCookie.ts | 1 + 1 file changed, 1 insertion(+) diff --git a/client/src/scripts/utils/deleteCookie.ts b/client/src/scripts/utils/deleteCookie.ts index fa9315c..4e4e857 100644 --- a/client/src/scripts/utils/deleteCookie.ts +++ b/client/src/scripts/utils/deleteCookie.ts @@ -3,5 +3,6 @@ export default function deleteCookie(name: string): void { const origin = (process.env.API_URL || 'http://localhost:3000') .match(originRegex); + console.log(origin ? origin[1] : 'localhost'); document.cookie = `${name}=;domain=${origin ? origin[1] : 'localhost'};expires=${Date.now()}; Path=/; Secure; SameSite=None;`; } From 7d96374191628f4c457d819033e48a1baad65391 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 20:44:40 +0300 Subject: [PATCH 179/196] hotfix: fix remove cookie logic --- client/src/scripts/utils/deleteCookie.ts | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/client/src/scripts/utils/deleteCookie.ts b/client/src/scripts/utils/deleteCookie.ts index 4e4e857..6740d6b 100644 --- a/client/src/scripts/utils/deleteCookie.ts +++ b/client/src/scripts/utils/deleteCookie.ts @@ -3,6 +3,5 @@ export default function deleteCookie(name: string): void { const origin = (process.env.API_URL || 'http://localhost:3000') .match(originRegex); - console.log(origin ? origin[1] : 'localhost'); - document.cookie = `${name}=;domain=${origin ? origin[1] : 'localhost'};expires=${Date.now()}; Path=/; Secure; SameSite=None;`; + document.cookie = `${name}=;domain=${origin ? origin[1] : 'localhost'};expires=Thu, 01 Jan 1970 00:00:00 GMT;Path=/;Secure;SameSite=None;`; } From e5e589e0a7c443ca5ba5d30fe8dcce4b3b3d286c Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 20:52:06 +0300 Subject: [PATCH 180/196] hotfix: fix remove cookie logic --- client/src/scripts/utils/deleteCookie.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/client/src/scripts/utils/deleteCookie.ts b/client/src/scripts/utils/deleteCookie.ts index 6740d6b..c3507c1 100644 --- a/client/src/scripts/utils/deleteCookie.ts +++ b/client/src/scripts/utils/deleteCookie.ts @@ -3,5 +3,6 @@ export default function deleteCookie(name: string): void { const origin = (process.env.API_URL || 'http://localhost:3000') .match(originRegex); - document.cookie = `${name}=;domain=${origin ? origin[1] : 'localhost'};expires=Thu, 01 Jan 1970 00:00:00 GMT;Path=/;Secure;SameSite=None;`; + // document.cookie = `${name}=;domain=${origin ? origin[1] : 'localhost'};expires=Thu, 01 Jan 1970 00:00:00 GMT;Path=/;Secure;SameSite=None;`; + document.cookie = 'auth_token=; expires=Thu, 01 Jan 1970 00:00:00 UTC;domain=hardmandev-rs-clone.up.railway.app;Path=/;Secure;SameSite=None;'; } From 5fc6bbbf50b36080a2ff1d79575550fe1b672e0c Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 20:55:43 +0300 Subject: [PATCH 181/196] hotfix: fix remove cookie logic --- client/src/scripts/utils/deleteCookie.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/src/scripts/utils/deleteCookie.ts b/client/src/scripts/utils/deleteCookie.ts index c3507c1..8e1f940 100644 --- a/client/src/scripts/utils/deleteCookie.ts +++ b/client/src/scripts/utils/deleteCookie.ts @@ -4,5 +4,5 @@ export default function deleteCookie(name: string): void { .match(originRegex); // document.cookie = `${name}=;domain=${origin ? origin[1] : 'localhost'};expires=Thu, 01 Jan 1970 00:00:00 GMT;Path=/;Secure;SameSite=None;`; - document.cookie = 'auth_token=; expires=Thu, 01 Jan 1970 00:00:00 UTC;domain=hardmandev-rs-clone.up.railway.app;Path=/;Secure;SameSite=None;'; + document.cookie = 'auth_token= ;domain=hardmandev-rs-clone.up.railway.app;Path=/;Secure;SameSite=None;'; } From 7e4bab5101728fcf75cba7332ceac004f046b58f Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 20:57:56 +0300 Subject: [PATCH 182/196] hotfix: fix remove cookie logic --- client/src/scripts/utils/deleteCookie.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/src/scripts/utils/deleteCookie.ts b/client/src/scripts/utils/deleteCookie.ts index 8e1f940..d3f476e 100644 --- a/client/src/scripts/utils/deleteCookie.ts +++ b/client/src/scripts/utils/deleteCookie.ts @@ -4,5 +4,5 @@ export default function deleteCookie(name: string): void { .match(originRegex); // document.cookie = `${name}=;domain=${origin ? origin[1] : 'localhost'};expires=Thu, 01 Jan 1970 00:00:00 GMT;Path=/;Secure;SameSite=None;`; - document.cookie = 'auth_token= ;domain=hardmandev-rs-clone.up.railway.app;Path=/;Secure;SameSite=None;'; + document.cookie = 'auth_token= ;expires=Fri, 05 Jun 2020 12:00:00 UTC;domain=hardmandev-rs-clone.up.railway.app;Path=/;Secure;SameSite=None;'; } From 0b31999cbb8735f4a046f3010fc333faf95b6243 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 21:00:54 +0300 Subject: [PATCH 183/196] hotfix: fix remove cookie logic --- client/src/scripts/utils/deleteCookie.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/src/scripts/utils/deleteCookie.ts b/client/src/scripts/utils/deleteCookie.ts index d3f476e..a5a2e9e 100644 --- a/client/src/scripts/utils/deleteCookie.ts +++ b/client/src/scripts/utils/deleteCookie.ts @@ -4,5 +4,5 @@ export default function deleteCookie(name: string): void { .match(originRegex); // document.cookie = `${name}=;domain=${origin ? origin[1] : 'localhost'};expires=Thu, 01 Jan 1970 00:00:00 GMT;Path=/;Secure;SameSite=None;`; - document.cookie = 'auth_token= ;expires=Fri, 05 Jun 2020 12:00:00 UTC;domain=hardmandev-rs-clone.up.railway.app;Path=/;Secure;SameSite=None;'; + document.cookie = 'auth_token= ;expires=Fri, 05 Jun 2024 12:00:00 UTC;domain=hardmandev-rs-clone.up.railway.app;Path=/;Secure;SameSite=None;'; } From 0256f1dc5f6f29f699ddb06382241928c722b3e0 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Mon, 27 Feb 2023 21:01:00 +0300 Subject: [PATCH 184/196] feat: url-loader change limit --- client/webpack.config.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/webpack.config.js b/client/webpack.config.js index 52562e1..2ffbebf 100644 --- a/client/webpack.config.js +++ b/client/webpack.config.js @@ -132,7 +132,7 @@ module.exports = async (env, argv) => { { loader: 'url-loader', options: { - limit: 16000, + limit: 32000, name: '[path][name].[ext]', }, }, From fd1310621d5a32e6d8db1e9155355bdd74d166a9 Mon Sep 17 00:00:00 2001 From: VasaSkor <106305964+VasaSkor@users.noreply.github.com> Date: Mon, 27 Feb 2023 21:02:25 +0300 Subject: [PATCH 185/196] feat: add control screen and sound start game --- client/src/assets/levels/controls_img.png | Bin 0 -> 12638 bytes client/src/scripts/components/game.ts | 25 +++++++++++++++++++++- client/src/styles/level.css | 14 ++++++++++++ client/src/types/game.ts | 1 + 4 files changed, 39 insertions(+), 1 deletion(-) create mode 100644 client/src/assets/levels/controls_img.png diff --git a/client/src/assets/levels/controls_img.png b/client/src/assets/levels/controls_img.png new file mode 100644 index 0000000000000000000000000000000000000000..fcae970ee422e71bfc09c75900ce50809c5b96af GIT binary patch literal 12638 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 { + if (this.playIntroSound) { + this.sounds[SoundType.START].play(); + } + this.toggleControls(); + this.playIntroSound = false; + }; } loadLevelEntities(): void { @@ -389,6 +404,14 @@ class GameView { this.ammoElement.classList.add(`ammo${this.dave.bullets}`); } + toggleControls(): void { + if (this.controlsScreen.style.display === 'none') { + this.controlsScreen.style.display = 'block'; + } else { + this.controlsScreen.style.display = 'none'; + } + } + createMeatExplosion(monsterRect: Rect): void { for (let i = 0; i <= 3; i += 1) { const randDX = 2 + Math.round(Math.random() * 3); diff --git a/client/src/styles/level.css b/client/src/styles/level.css index 227a67b..b198016 100644 --- a/client/src/styles/level.css +++ b/client/src/styles/level.css @@ -164,6 +164,20 @@ body { background: url("./../assets/levels/gameover.png") no-repeat no-repeat; } +.controls { + position: absolute; + top: 50px; + left: 100px; + width: 760px; + height: 500px; + font-size: 32px; + background-image: url("./../assets/levels/controls_img.png"); + padding: 30px; + line-height: 60px; + display: block; + z-index: 1; +} + .ammo { position: absolute; top: 10px; diff --git a/client/src/types/game.ts b/client/src/types/game.ts index 1929dbb..0203b7c 100644 --- a/client/src/types/game.ts +++ b/client/src/types/game.ts @@ -73,6 +73,7 @@ export enum SoundType { BONUS1, EMPTY, RELOAD, + START, } export type AllSound = { From 8e7e269590fa3e18759c8b5aada87ffd50b6fa72 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 21:04:01 +0300 Subject: [PATCH 186/196] hotfix: fix remove cookie logic --- server/src/modules/auth/auth.controller.ts | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index 4449915..8040895 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -74,10 +74,7 @@ export class AuthController { AuthProvider.LOCAL, ); - res.cookie('auth_token', registeredUser.accessToken, { - sameSite: 'none', - secure: true, - }); + res.cookie('auth_token', registeredUser.accessToken; res.status(HttpStatus.OK).send(registeredUser); return registeredUser; From 87047b86ff5a43865af0b98966a7c19d8245f49a Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 21:06:23 +0300 Subject: [PATCH 187/196] hotfix: fix remove cookie logic --- server/src/modules/auth/auth.controller.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index 8040895..0384f37 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -74,7 +74,7 @@ export class AuthController { AuthProvider.LOCAL, ); - res.cookie('auth_token', registeredUser.accessToken; + res.cookie('auth_token', registeredUser.accessToken); res.status(HttpStatus.OK).send(registeredUser); return registeredUser; From 14fa84bbaa1e4f34fe3547c2155eec729891ae33 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 21:09:29 +0300 Subject: [PATCH 188/196] hotfix: fix remove cookie logic --- server/src/modules/auth/auth.controller.ts | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index 0384f37..4449915 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -74,7 +74,10 @@ export class AuthController { AuthProvider.LOCAL, ); - res.cookie('auth_token', registeredUser.accessToken); + res.cookie('auth_token', registeredUser.accessToken, { + sameSite: 'none', + secure: true, + }); res.status(HttpStatus.OK).send(registeredUser); return registeredUser; From 44f02ac8d5f860781fd97915bc44449ff2f1ec7e Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 21:13:43 +0300 Subject: [PATCH 189/196] hotfix: fix remove cookie logic --- client/src/scripts/utils/deleteCookie.ts | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/client/src/scripts/utils/deleteCookie.ts b/client/src/scripts/utils/deleteCookie.ts index a5a2e9e..6740d6b 100644 --- a/client/src/scripts/utils/deleteCookie.ts +++ b/client/src/scripts/utils/deleteCookie.ts @@ -3,6 +3,5 @@ export default function deleteCookie(name: string): void { const origin = (process.env.API_URL || 'http://localhost:3000') .match(originRegex); - // document.cookie = `${name}=;domain=${origin ? origin[1] : 'localhost'};expires=Thu, 01 Jan 1970 00:00:00 GMT;Path=/;Secure;SameSite=None;`; - document.cookie = 'auth_token= ;expires=Fri, 05 Jun 2024 12:00:00 UTC;domain=hardmandev-rs-clone.up.railway.app;Path=/;Secure;SameSite=None;'; + document.cookie = `${name}=;domain=${origin ? origin[1] : 'localhost'};expires=Thu, 01 Jan 1970 00:00:00 GMT;Path=/;Secure;SameSite=None;`; } From c6f90b2f989fd055f7318d7971087527ef883878 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 23:39:15 +0300 Subject: [PATCH 190/196] hotfix: fix cookies policy --- client/src/scripts/utils/deleteCookie.ts | 2 +- server/src/modules/auth/auth.controller.ts | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/client/src/scripts/utils/deleteCookie.ts b/client/src/scripts/utils/deleteCookie.ts index 6740d6b..1272b0b 100644 --- a/client/src/scripts/utils/deleteCookie.ts +++ b/client/src/scripts/utils/deleteCookie.ts @@ -1,6 +1,6 @@ export default function deleteCookie(name: string): void { const originRegex = /^(?:(?:[a-z]+:)?\/\/)?(?:[^@/]+@)?([^:/]+)/i; - const origin = (process.env.API_URL || 'http://localhost:3000') + const origin = (process.env.DOMAIN || 'http://localhost:8080') .match(originRegex); document.cookie = `${name}=;domain=${origin ? origin[1] : 'localhost'};expires=Thu, 01 Jan 1970 00:00:00 GMT;Path=/;Secure;SameSite=None;`; diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index 4449915..9d0959b 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -41,6 +41,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { sameSite: 'none', secure: true, + domain: process.env.DOMAIN || 'localhost', }); res.status(HttpStatus.OK).send(registeredUser); @@ -77,6 +78,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { sameSite: 'none', secure: true, + domain: process.env.DOMAIN || 'localhost', }); res.status(HttpStatus.OK).send(registeredUser); From d1721c2937ace307d7e5ea4f3a2d2c81922969a2 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Mon, 27 Feb 2023 23:59:57 +0300 Subject: [PATCH 191/196] hotfix: fix cookies policy --- client/netlify.toml | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 client/netlify.toml diff --git a/client/netlify.toml b/client/netlify.toml new file mode 100644 index 0000000..3f0afa7 --- /dev/null +++ b/client/netlify.toml @@ -0,0 +1,5 @@ +[[headers]] + # Define which paths this specific [[headers]] block will cover. + for = "/*" + [headers.values] + Access-Control-Allow-Origin = "*" \ No newline at end of file From 1b4f324b6678457f88a8299b066becd072d82236 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Tue, 28 Feb 2023 00:08:11 +0300 Subject: [PATCH 192/196] hotfix: fix cookies policy --- server/src/modules/auth/auth.controller.ts | 2 -- 1 file changed, 2 deletions(-) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index 9d0959b..4449915 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -41,7 +41,6 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { sameSite: 'none', secure: true, - domain: process.env.DOMAIN || 'localhost', }); res.status(HttpStatus.OK).send(registeredUser); @@ -78,7 +77,6 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { sameSite: 'none', secure: true, - domain: process.env.DOMAIN || 'localhost', }); res.status(HttpStatus.OK).send(registeredUser); From 5eb082afa8d80facfa89ecfda0301935467aafa4 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Tue, 28 Feb 2023 00:17:56 +0300 Subject: [PATCH 193/196] hotfix: fix cookies policy --- server/src/modules/auth/auth.controller.ts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/server/src/modules/auth/auth.controller.ts b/server/src/modules/auth/auth.controller.ts index 4449915..a83a41d 100644 --- a/server/src/modules/auth/auth.controller.ts +++ b/server/src/modules/auth/auth.controller.ts @@ -41,6 +41,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { sameSite: 'none', secure: true, + domain: process.env.DOMAIN, }); res.status(HttpStatus.OK).send(registeredUser); @@ -77,6 +78,7 @@ export class AuthController { res.cookie('auth_token', registeredUser.accessToken, { sameSite: 'none', secure: true, + domain: process.env.DOMAIN, }); res.status(HttpStatus.OK).send(registeredUser); From 538ac119739309cac6380e012ae826d2840a6bd1 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Tue, 28 Feb 2023 00:34:10 +0300 Subject: [PATCH 194/196] hotfix: update README.md --- README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/README.md b/README.md index f6a1026..33fe589 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,6 @@ # RS Clone [![LICENSE](https://img.shields.io/badge/License-MIT-yellow.svg?style=flat-square)](https://opensource.org/licenses/MIT) +[![CodeFactor](https://www.codefactor.io/repository/github/hardmandev/rs-clone/badge)](https://www.codefactor.io/repository/github/hardmandev/rs-clone) [![Linters checks](https://github.com/HardManDev/rs-clone/actions/workflows/linterChecks.yml/badge.svg)](https://github.com/HardManDev/rs-clone/actions/workflows/linterChecks.yml) [![Netlify Status](https://api.netlify.com/api/v1/badges/94ea65cd-5857-4022-a8f4-923b64062608/deploy-status?style=flat-square)](https://app.netlify.com/sites/hardmandev-rs-clone/deploys) From fcc904ca6acc2519952f145118e50c8c30ec4e4e Mon Sep 17 00:00:00 2001 From: HardManDev Date: Tue, 28 Feb 2023 00:36:05 +0300 Subject: [PATCH 195/196] hotfix: update README.md --- README.md | 1 - 1 file changed, 1 deletion(-) diff --git a/README.md b/README.md index 33fe589..f6a1026 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,5 @@ # RS Clone [![LICENSE](https://img.shields.io/badge/License-MIT-yellow.svg?style=flat-square)](https://opensource.org/licenses/MIT) -[![CodeFactor](https://www.codefactor.io/repository/github/hardmandev/rs-clone/badge)](https://www.codefactor.io/repository/github/hardmandev/rs-clone) [![Linters checks](https://github.com/HardManDev/rs-clone/actions/workflows/linterChecks.yml/badge.svg)](https://github.com/HardManDev/rs-clone/actions/workflows/linterChecks.yml) [![Netlify Status](https://api.netlify.com/api/v1/badges/94ea65cd-5857-4022-a8f4-923b64062608/deploy-status?style=flat-square)](https://app.netlify.com/sites/hardmandev-rs-clone/deploys) From eb8865ba67e74b557d600c953ccd9ef135af31e9 Mon Sep 17 00:00:00 2001 From: HardManDev Date: Sun, 5 Mar 2023 18:37:28 +0300 Subject: [PATCH 196/196] hotfix: update README.md --- README.md | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/README.md b/README.md index f6a1026..69984ec 100644 --- a/README.md +++ b/README.md @@ -41,6 +41,30 @@ npm run start:dev ``` > NOTE: Default URL: http://localhost:8080 +## Development stack + - [TypeScript](https://github.com/microsoft/TypeScript) + - [ESLint](https://github.com/eslint/eslint) - for lint source code +#### Front-end + - CSS + - [SASS](https://github.com/sass/sass) + - [Webpack](https://github.com/webpack/webpack) - for build project + - [StyleLint](https://github.com/stylelint/stylelint) - for lint styles +#### Back-end + - [Prettier](https://github.com/prettier/prettier) + - ❤️[NestJS](https://github.com/nestjs/nest) - back-end framework + - [MongoDB](https://github.com/mongodb/mongo) - database for back-end + - [mongoose](https://github.com/nestjs/mongoose) - ORM for work with MongoDB + - [JWT](https://jwt.io/) - for simple authorization & authentication + - [bcrypt](https://github.com/pyca/bcrypt) - for encrypt passwords +#### Deploy + - [Netlify](https://netlify.app/) - for deploy front-end + - [Railway](https://railway.app/) - for deploy back-end +#### Team work + - Git Flow + - [GitHub Projects](https://github.com/users/HardManDev/projects/10) + - [GitHub Actions](https://github.com/HardManDev/rs-clone/actions) - for lint project on pull request + +> *Read more at [Dependency graph](https://github.com/HardManDev/rs-clone/network/dependencies)* ## License This software is licensed under the